forked from bartvdbraak/blender
knife sort_by_frac_along was re-calculating the reference factor for every test, change to only calculate once and use line_point_factor_v3().
also add zero division check for line_point_factor_v3() since the 2d version already checked for this.
This commit is contained in:
parent
a5d6820b6d
commit
2a78a14369
@ -1654,9 +1654,16 @@ float closest_to_line_v2(float cp[2], const float p[2], const float l1[2], const
|
|||||||
float line_point_factor_v3(const float p[3], const float l1[3], const float l2[3])
|
float line_point_factor_v3(const float p[3], const float l1[3], const float l2[3])
|
||||||
{
|
{
|
||||||
float h[3], u[3];
|
float h[3], u[3];
|
||||||
|
float dot;
|
||||||
sub_v3_v3v3(u, l2, l1);
|
sub_v3_v3v3(u, l2, l1);
|
||||||
sub_v3_v3v3(h, p, l1);
|
sub_v3_v3v3(h, p, l1);
|
||||||
|
#if 0
|
||||||
return (dot_v3v3(u, h) / dot_v3v3(u, u));
|
return (dot_v3v3(u, h) / dot_v3v3(u, u));
|
||||||
|
#else
|
||||||
|
/* better check for zero */
|
||||||
|
dot = dot_v3v3(u, u);
|
||||||
|
return (dot != 0.0f) ? (dot_v3v3(u, h) / dot) : 0.0f;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
float line_point_factor_v2(const float p[2], const float l1[2], const float l2[2])
|
float line_point_factor_v2(const float p[2], const float l1[2], const float l2[2])
|
||||||
|
@ -2212,43 +2212,28 @@ static void knifenet_fill_faces(KnifeTool_OpData *kcd)
|
|||||||
|
|
||||||
#else /* use direct (non-scanfill) method for cuts */
|
#else /* use direct (non-scanfill) method for cuts */
|
||||||
|
|
||||||
/* assuming v is on line ab, what fraction of the way is v from a to b? */
|
|
||||||
static float frac_along(const float a[3], const float b[3], const float v[3])
|
|
||||||
{
|
|
||||||
float lab;
|
|
||||||
|
|
||||||
lab = len_v3v3(a, b);
|
|
||||||
if (lab == 0.0f) {
|
|
||||||
return 0.0f;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
return len_v3v3(a, v) / lab;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* sort list of kverts by fraction along edge e */
|
/* sort list of kverts by fraction along edge e */
|
||||||
static void sort_by_frac_along(ListBase *lst, BMEdge *e)
|
static void sort_by_frac_along(ListBase *lst, BMEdge *e)
|
||||||
{
|
{
|
||||||
KnifeVert *vcur, *vprev;
|
const float *v1co = e->v1->co;
|
||||||
float *v1co, *v2co;
|
const float *v2co = e->v2->co;
|
||||||
Ref *cur = NULL, *prev = NULL, *next = NULL;
|
Ref *cur = NULL, *prev = NULL, *next = NULL;
|
||||||
|
|
||||||
if (lst->first == lst->last)
|
if (lst->first == lst->last)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
v1co = e->v1->co;
|
|
||||||
v2co = e->v2->co;
|
|
||||||
|
|
||||||
for (cur = ((Ref *)lst->first)->next; cur; cur = next) {
|
for (cur = ((Ref *)lst->first)->next; cur; cur = next) {
|
||||||
|
KnifeVert *vcur = cur->ref;
|
||||||
|
const float vcur_fac = line_point_factor_v3(vcur->co, v1co, v2co);
|
||||||
|
|
||||||
next = cur->next;
|
next = cur->next;
|
||||||
prev = cur->prev;
|
prev = cur->prev;
|
||||||
|
|
||||||
BLI_remlink(lst, cur);
|
BLI_remlink(lst, cur);
|
||||||
|
|
||||||
vcur = cur->ref;
|
|
||||||
while (prev) {
|
while (prev) {
|
||||||
vprev = prev->ref;
|
KnifeVert *vprev = prev->ref;
|
||||||
if (frac_along(v1co, v2co, vprev->co) <= frac_along(v1co, v2co, vcur->co))
|
if (line_point_factor_v3(vprev->co, v1co, v2co) <= vcur_fac)
|
||||||
break;
|
break;
|
||||||
prev = prev->prev;
|
prev = prev->prev;
|
||||||
}
|
}
|
||||||
@ -2860,7 +2845,7 @@ static void knife_make_cuts(KnifeTool_OpData *kcd)
|
|||||||
sort_by_frac_along(lst, e);
|
sort_by_frac_along(lst, e);
|
||||||
for (ref = lst->first; ref; ref = ref->next) {
|
for (ref = lst->first; ref; ref = ref->next) {
|
||||||
kfv = ref->ref;
|
kfv = ref->ref;
|
||||||
pct = frac_along(e->v1->co, e->v2->co, kfv->co);
|
pct = line_point_factor_v3(kfv->co, e->v1->co, e->v2->co);
|
||||||
kfv->v = BM_edge_split(bm, e, e->v1, &enew, pct);
|
kfv->v = BM_edge_split(bm, e, e->v1, &enew, pct);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user