Stipple the selected/hovered faces, instead of drawing them in
solid red or yellow. And add user interface to `hide' the faces (i.e., to make them unselectable), defaulting to hidden in everything except extrudes or imports. [git-p4: depot-paths = "//depot/solvespace/": change = 1768]
This commit is contained in:
parent
1f70494ce9
commit
a084b32064
64
glhelper.cpp
64
glhelper.cpp
|
@ -111,6 +111,53 @@ void glxColor4d(double r, double g, double b, double a)
|
|||
if(!ColorLocked) glColor4d(r, g, b, a);
|
||||
}
|
||||
|
||||
static void Stipple(BOOL forSel)
|
||||
{
|
||||
static BOOL Init;
|
||||
const int BYTES = (32*32)/8;
|
||||
static GLubyte HoverMask[BYTES];
|
||||
static GLubyte SelMask[BYTES];
|
||||
if(!Init) {
|
||||
int x, y;
|
||||
for(x = 0; x < 32; x++) {
|
||||
for(y = 0; y < 32; y++) {
|
||||
int i = y*4 + x/8, b = x % 8;
|
||||
int ym = y % 4, xm = x % 4;
|
||||
for(int k = 0; k < 2; k++) {
|
||||
if(xm >= 1 && xm <= 2 && ym >= 1 && ym <= 2) {
|
||||
(k == 0 ? SelMask : HoverMask)[i] |= (0x80 >> b);
|
||||
}
|
||||
ym = (ym + 2) % 4; xm = (xm + 2) % 4;
|
||||
}
|
||||
}
|
||||
}
|
||||
Init = TRUE;
|
||||
}
|
||||
|
||||
glEnable(GL_POLYGON_STIPPLE);
|
||||
if(forSel) {
|
||||
glPolygonStipple(SelMask);
|
||||
} else {
|
||||
glPolygonStipple(HoverMask);
|
||||
}
|
||||
}
|
||||
|
||||
static void StippleTriangle(STriangle *tr, BOOL s, double r, double g, double b)
|
||||
{
|
||||
glEnd();
|
||||
glDisable(GL_LIGHTING);
|
||||
glColor3d(r, g, b);
|
||||
Stipple(s);
|
||||
glBegin(GL_TRIANGLES);
|
||||
glxVertex3v(tr->a);
|
||||
glxVertex3v(tr->b);
|
||||
glxVertex3v(tr->c);
|
||||
glEnd();
|
||||
glEnable(GL_LIGHTING);
|
||||
glDisable(GL_POLYGON_STIPPLE);
|
||||
glBegin(GL_TRIANGLES);
|
||||
}
|
||||
|
||||
void glxFillMesh(int specColor, SMesh *m, DWORD h, DWORD s1, DWORD s2)
|
||||
{
|
||||
glEnable(GL_NORMALIZE);
|
||||
|
@ -122,13 +169,7 @@ void glxFillMesh(int specColor, SMesh *m, DWORD h, DWORD s1, DWORD s2)
|
|||
glNormal3d(n.x, n.y, n.z);
|
||||
|
||||
int color;
|
||||
if((s1 != 0 && tr->meta.face == s1) ||
|
||||
(s2 != 0 && tr->meta.face == s2))
|
||||
{
|
||||
color = RGB(200, 0, 0);
|
||||
} else if(h != 0 && tr->meta.face == h) {
|
||||
color = RGB(200, 200, 0);
|
||||
} else if(specColor < 0) {
|
||||
if(specColor < 0) {
|
||||
color = tr->meta.color;
|
||||
} else {
|
||||
color = specColor;
|
||||
|
@ -146,6 +187,15 @@ void glxFillMesh(int specColor, SMesh *m, DWORD h, DWORD s1, DWORD s2)
|
|||
glxVertex3v(tr->a);
|
||||
glxVertex3v(tr->b);
|
||||
glxVertex3v(tr->c);
|
||||
|
||||
if((s1 != 0 && tr->meta.face == s1) ||
|
||||
(s2 != 0 && tr->meta.face == s2))
|
||||
{
|
||||
StippleTriangle(tr, TRUE, 1, 0, 0);
|
||||
}
|
||||
if(h != 0 && tr->meta.face == h) {
|
||||
StippleTriangle(tr, FALSE, 1, 1, 0);
|
||||
}
|
||||
}
|
||||
glEnd();
|
||||
}
|
||||
|
|
|
@ -102,12 +102,14 @@ void GraphicsWindow::Init(void) {
|
|||
projRight.x = 1; projRight.y = projRight.z = 0;
|
||||
projUp.y = 1; projUp.z = projUp.x = 0;
|
||||
|
||||
// And with the latest visible group active
|
||||
// And with the latest visible group active, or failing that the first
|
||||
// group after the references
|
||||
int i;
|
||||
for(i = 0; i < SS.group.n; i++) {
|
||||
Group *g = &(SS.group.elem[i]);
|
||||
if(i == 0 || g->visible) activeGroup = g->h;
|
||||
if(i == 1 || g->visible) activeGroup = g->h;
|
||||
}
|
||||
SS.GetGroup(activeGroup)->Activate();
|
||||
|
||||
EnsureValidActives();
|
||||
|
||||
|
@ -248,6 +250,7 @@ void GraphicsWindow::EnsureValidActives(void) {
|
|||
}
|
||||
if(i >= SS.group.n) oops();
|
||||
activeGroup = SS.group.elem[i].h;
|
||||
SS.GetGroup(activeGroup)->Activate();
|
||||
change = true;
|
||||
}
|
||||
|
||||
|
@ -746,7 +749,7 @@ void GraphicsWindow::HitTestMakeSelection(Point2d mp) {
|
|||
}
|
||||
|
||||
// Faces, from the triangle mesh; these are lowest priority
|
||||
if(s.constraint.v == 0 && s.entity.v == 0 && (showMesh || showShaded)) {
|
||||
if(s.constraint.v == 0 && s.entity.v == 0 && showShaded && showFaces) {
|
||||
SMesh *m = &((SS.GetGroup(activeGroup))->mesh);
|
||||
DWORD v = m->FirstIntersectionWith(mp);
|
||||
if(v) {
|
||||
|
@ -1063,6 +1066,19 @@ void GraphicsWindow::MouseLeftDown(double mx, double my) {
|
|||
}
|
||||
if(i != MAX_SELECTED) break;
|
||||
|
||||
if(hover.entity.v != 0 && SS.GetEntity(hover.entity)->IsFace()) {
|
||||
// In the interest of speed for the triangle drawing code,
|
||||
// only two faces may be selected at a time.
|
||||
int c = 0;
|
||||
for(i = 0; i < MAX_SELECTED; i++) {
|
||||
hEntity he = selection[i].entity;
|
||||
if(he.v != 0 && SS.GetEntity(he)->IsFace()) {
|
||||
c++;
|
||||
if(c >= 2) selection[i].Clear();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for(i = 0; i < MAX_SELECTED; i++) {
|
||||
if(selection[i].IsEmpty()) {
|
||||
selection[i] = hover;
|
||||
|
@ -1147,6 +1163,10 @@ void GraphicsWindow::ToggleBool(int link, DWORD v) {
|
|||
bool *vb = (bool *)v;
|
||||
*vb = !*vb;
|
||||
|
||||
// The faces are shown as special stippling on the shaded triangle mesh,
|
||||
// so not meaningful to show them and hide the shaded.
|
||||
if(!SS.GW.showShaded) SS.GW.showFaces = false;
|
||||
|
||||
SS.GW.GeneratePerSolving();
|
||||
InvalidateGraphics();
|
||||
SS.TW.Show();
|
||||
|
|
10
sketch.cpp
10
sketch.cpp
|
@ -141,6 +141,7 @@ void Group::MenuGroup(int id) {
|
|||
if(g.type == DRAWING_WORKPLANE) {
|
||||
SS.GetGroup(g.h)->activeWorkplane = g.h.entity(0);
|
||||
}
|
||||
SS.GetGroup(g.h)->Activate();
|
||||
SS.GW.AnimateOntoWorkplane();
|
||||
TextWindow::ScreenSelectGroup(0, g.h.v);
|
||||
SS.TW.Show();
|
||||
|
@ -156,6 +157,15 @@ char *Group::DescriptionString(void) {
|
|||
return ret;
|
||||
}
|
||||
|
||||
void Group::Activate(void) {
|
||||
if(type == EXTRUDE || type == IMPORTED) {
|
||||
SS.GW.showFaces = true;
|
||||
} else {
|
||||
SS.GW.showFaces = false;
|
||||
}
|
||||
SS.TW.Show();
|
||||
}
|
||||
|
||||
void Group::Generate(IdList<Entity,hEntity> *entity,
|
||||
IdList<Param,hParam> *param)
|
||||
{
|
||||
|
|
1
sketch.h
1
sketch.h
|
@ -137,6 +137,7 @@ public:
|
|||
NameStr name;
|
||||
|
||||
|
||||
void Activate(void);
|
||||
char *DescriptionString(void);
|
||||
|
||||
static void AddParam(IdList<Param,hParam> *param, hParam hp, double v);
|
||||
|
|
15
textwin.cpp
15
textwin.cpp
|
@ -221,6 +221,10 @@ void TextWindow::Show(void) {
|
|||
InvalidateText();
|
||||
}
|
||||
|
||||
void TextWindow::ScreenUnselectAll(int link, DWORD v) {
|
||||
GraphicsWindow::MenuEdit(GraphicsWindow::MNU_UNSELECT_ALL);
|
||||
}
|
||||
|
||||
void TextWindow::DescribeSelection(void) {
|
||||
Entity *e;
|
||||
Vector p;
|
||||
|
@ -310,6 +314,12 @@ void TextWindow::DescribeSelection(void) {
|
|||
Printf(false, " radius = %Fi%s", SS.GW.ToString(r));
|
||||
break;
|
||||
}
|
||||
case Entity::FACE_NORMAL_PT:
|
||||
case Entity::FACE_XPROD:
|
||||
case Entity::FACE_N_ROT_TRANS:
|
||||
Printf(false, "%FtPLANE FACE%E");
|
||||
break;
|
||||
|
||||
default:
|
||||
Printf(true, "%Ft?? ENTITY%E");
|
||||
break;
|
||||
|
@ -335,6 +345,8 @@ void TextWindow::DescribeSelection(void) {
|
|||
} else {
|
||||
Printf(true, "%FtSELECTED:%E %d item%s", gs.n, gs.n == 1 ? "" : "s");
|
||||
}
|
||||
|
||||
Printf(true, "%Fl%f%Ll(unselect all)%E", &TextWindow::ScreenUnselectAll);
|
||||
}
|
||||
|
||||
void TextWindow::OneScreenForwardTo(int screen) {
|
||||
|
@ -397,9 +409,11 @@ hs(SS.GW.showConstraints), (DWORD)(&SS.GW.showConstraints), &(SS.GW.ToggleBool)
|
|||
);
|
||||
Printf(false, "%Bt%Ft "
|
||||
"%Fp%Ll%D%fshaded%E "
|
||||
"%Fp%Ll%D%ffaces%E "
|
||||
"%Fp%Ll%D%fmesh%E "
|
||||
"%Fp%Ll%D%fhidden-lines%E",
|
||||
hs(SS.GW.showShaded), (DWORD)(&SS.GW.showShaded), &(SS.GW.ToggleBool),
|
||||
hs(SS.GW.showFaces), (DWORD)(&SS.GW.showFaces), &(SS.GW.ToggleBool),
|
||||
hs(SS.GW.showMesh), (DWORD)(&SS.GW.showMesh), &(SS.GW.ToggleBool),
|
||||
hs(SS.GW.showHdnLines), (DWORD)(&SS.GW.showHdnLines), &(SS.GW.ToggleBool)
|
||||
);
|
||||
|
@ -437,6 +451,7 @@ void TextWindow::ScreenActivateGroup(int link, DWORD v) {
|
|||
Group *g = SS.GetGroup(hg);
|
||||
g->visible = true;
|
||||
SS.GW.activeGroup.v = v;
|
||||
SS.GetGroup(SS.GW.activeGroup)->Activate();
|
||||
SS.GW.ClearSuper();
|
||||
}
|
||||
void TextWindow::ReportHowGroupSolved(hGroup hg) {
|
||||
|
|
7
ui.h
7
ui.h
|
@ -99,12 +99,14 @@ public:
|
|||
static void ScreenChangeMeshCombine(int link, DWORD v);
|
||||
static void ScreenColor(int link, DWORD v);
|
||||
|
||||
static void ScreenUnselectAll(int link, DWORD v);
|
||||
|
||||
static void ScreenNavigation(int link, DWORD v);
|
||||
|
||||
// These ones do stuff with the edit control
|
||||
static void ScreenChangeExprA(int link, DWORD v);
|
||||
static void ScreenChangeGroupName(int link, DWORD v);
|
||||
|
||||
static void ScreenNavigation(int link, DWORD v);
|
||||
|
||||
void EditControlDone(char *s);
|
||||
};
|
||||
|
||||
|
@ -297,6 +299,7 @@ public:
|
|||
bool showConstraints;
|
||||
bool showTextWindow;
|
||||
bool showShaded;
|
||||
bool showFaces;
|
||||
bool showMesh;
|
||||
bool showHdnLines;
|
||||
static void ToggleBool(int link, DWORD v);
|
||||
|
|
Loading…
Reference in New Issue
Block a user