Make hidden line removal keep all the line styles, and don't apply

that to the constraints.

And fix two crashing bugs, embarrassing, both chasing null pointers.

[git-p4: depot-paths = "//depot/solvespace/": change = 2031]
This commit is contained in:
Jonathan Westhues 2009-09-21 22:47:11 -08:00
parent 9b8f32dad7
commit 274005c02c
4 changed files with 28 additions and 17 deletions

View File

@ -281,7 +281,7 @@ void GraphicsWindow::SpaceNavigatorMoved(double tx, double ty, double tz,
// but it's given with respect to screen projection frame
aa = aa.ScaleOutOfCsys(projRight, projUp, out);
double aam = aa.Magnitude();
aa = aa.WithMagnitude(1);
if(aam != 0.0) aa = aa.WithMagnitude(1);
// This can either transform our view, or transform an imported part.
GroupSelection();

View File

@ -120,7 +120,7 @@ void SolveSpace::ExportViewTo(char *filename) {
g->GenerateDisplayItems();
sm = &(g->displayMesh);
}
if(sm->IsEmpty()) {
if(sm && sm->IsEmpty()) {
sm = NULL;
}
@ -280,10 +280,17 @@ void SolveSpace::ExportLinesAndMesh(SEdgeList *sel, SBezierList *sbl, SMesh *sm,
SEdge *se;
for(se = sel->l.First(); se; se = sel->l.NextAfter(se)) {
if(se->auxA == Style::CONSTRAINT) {
// Constraints should not get hidden line removed; they're
// always on top.
hlrd.AddEdge(se->a, se->b, se->auxA);
continue;
}
SEdgeList out;
ZERO(&out);
// Split the original edge against the mesh
out.AddEdge(se->a, se->b);
out.AddEdge(se->a, se->b, se->auxA);
root->OcclusionTestLine(*se, &out, cnt);
// the occlusion test splits unnecessarily; so fix those
out.MergeCollinearSegments(se->a, se->b);
@ -291,7 +298,7 @@ void SolveSpace::ExportLinesAndMesh(SEdgeList *sel, SBezierList *sbl, SMesh *sm,
// And add the results to our output
SEdge *sen;
for(sen = out.l.First(); sen; sen = out.l.NextAfter(sen)) {
hlrd.AddEdge(sen->a, sen->b);
hlrd.AddEdge(sen->a, sen->b, sen->auxA);
}
out.Clear();
}

View File

@ -630,10 +630,11 @@ void SKdNode::SplitLinesAgainstTriangle(SEdgeList *sel, STriangle *tr) {
Vector tn = tr->Normal().WithMagnitude(1);
double td = tn.Dot(tr->a);
// Consider front-facing triangles only
// Consider front-facing triangles only.
if(tn.z > LENGTH_EPS) {
// If the edge crosses our triangle's plane, then split into above
// and below parts.
// and below parts. Note that we must preserve auxA, which contains
// the style associated with this line.
SEdge *se;
for(se = sel->l.First(); se; se = sel->l.NextAfter(se)) {
double da = (se->a).Dot(tn) - td,
@ -644,12 +645,12 @@ void SKdNode::SplitLinesAgainstTriangle(SEdgeList *sel, STriangle *tr) {
Vector m = Vector::AtIntersectionOfPlaneAndLine(
tn, td,
se->a, se->b, NULL);
seln.AddEdge(m, se->b);
seln.AddEdge(m, se->b, se->auxA);
se->b = m;
}
}
for(se = seln.l.First(); se; se = seln.l.NextAfter(se)) {
sel->AddEdge(se->a, se->b);
sel->AddEdge(se->a, se->b, se->auxA);
}
seln.Clear();
@ -659,10 +660,10 @@ void SKdNode::SplitLinesAgainstTriangle(SEdgeList *sel, STriangle *tr) {
if(pt.Dot(tn) - td > -LENGTH_EPS) {
// Edge is in front of or on our plane (remember, tn.z > 0)
// so it is exempt from further splitting
se->auxA = 1;
se->auxB = 1;
} else {
// Edge is behind our plane, needs further splitting
se->auxA = 0;
se->auxB = 0;
}
}
@ -684,7 +685,7 @@ void SKdNode::SplitLinesAgainstTriangle(SEdgeList *sel, STriangle *tr) {
int i;
for(i = 0; i < 3; i++) {
for(se = sel->l.First(); se; se = sel->l.NextAfter(se)) {
if(se->auxA) continue;
if(se->auxB) continue;
Point2d ap = (se->a).ProjectXy(),
bp = (se->b).ProjectXy();
@ -696,18 +697,20 @@ void SKdNode::SplitLinesAgainstTriangle(SEdgeList *sel, STriangle *tr) {
double dab = (db - da);
Vector spl = ((se->a).ScaledBy( db/dab)).Plus(
(se->b).ScaledBy(-da/dab));
seln.AddEdge(spl, se->b);
seln.AddEdge(spl, se->b, se->auxA);
se->b = spl;
}
}
for(se = seln.l.First(); se; se = seln.l.NextAfter(se)) {
sel->AddEdge(se->a, se->b, 0);
// The split pieces are all behind the triangle, since only
// edges behind the triangle got split. So their auxB is 0.
sel->AddEdge(se->a, se->b, se->auxA, 0);
}
seln.Clear();
}
for(se = sel->l.First(); se; se = sel->l.NextAfter(se)) {
if(se->auxA) {
if(se->auxB) {
// Lies above or on the triangle plane, so triangle doesn't
// occlude it.
se->tag = 0;
@ -929,7 +932,7 @@ void SKdNode::MakeCertainEdgesInto(SEdgeList *sel, int how,
// This triangle is back-facing (or on edge), and
// this edge has exactly one mate, and that mate is
// front-facing. So this is a turning edge.
sel->AddEdge(a, b);
sel->AddEdge(a, b, Style::SOLID_EDGE);
}
break;

View File

@ -79,9 +79,10 @@ bool GraphicsWindow::ToolbarMouseDown(int x, int y) {
x += ((int)width/2);
y += ((int)height/2);
int nh;
int nh = -1;
bool withinToolbar = ToolbarDrawOrHitTest(x, y, false, &nh);
if(withinToolbar) {
// They might have clicked within the toolbar, but not on a button.
if(withinToolbar && nh >= 0) {
for(int i = 0; SS.GW.menu[i].level >= 0; i++) {
if(nh == SS.GW.menu[i].id) {
(SS.GW.menu[i].fn)((GraphicsWindow::MenuId)SS.GW.menu[i].id);