Now I can display the edit control in the graphics window, and edit
the label associated with a constraint. And that even works, changes the length of the line. [git-p4: depot-paths = "//depot/solvespace/": change = 1678]solver
parent
2926fa95d9
commit
9b1b255e85
|
@ -25,7 +25,7 @@ void Constraint::LineDrawOrGetDistance(Vector a, Vector b) {
|
|||
}
|
||||
}
|
||||
|
||||
void Constraint::DrawOrGetDistance(void) {
|
||||
void Constraint::DrawOrGetDistance(Vector *labelPos) {
|
||||
if(!SS.GW.showConstraints) return;
|
||||
|
||||
// Unit vectors that describe our current view of the scene.
|
||||
|
@ -40,6 +40,7 @@ void Constraint::DrawOrGetDistance(void) {
|
|||
Vector bp = SS.GetEntity(ptB)->PointGetCoords();
|
||||
|
||||
Vector ref = ((ap.Plus(bp)).ScaledBy(0.5)).Plus(disp.offset);
|
||||
if(labelPos) *labelPos = ref;
|
||||
|
||||
Vector ab = ap.Minus(bp);
|
||||
Vector ar = ap.Minus(ref);
|
||||
|
@ -103,7 +104,7 @@ void Constraint::DrawOrGetDistance(void) {
|
|||
|
||||
void Constraint::Draw(void) {
|
||||
dogd.drawing = true;
|
||||
DrawOrGetDistance();
|
||||
DrawOrGetDistance(NULL);
|
||||
}
|
||||
|
||||
double Constraint::GetDistance(Point2d mp) {
|
||||
|
@ -111,8 +112,18 @@ double Constraint::GetDistance(Point2d mp) {
|
|||
dogd.mp = mp;
|
||||
dogd.dmin = 1e12;
|
||||
|
||||
DrawOrGetDistance();
|
||||
DrawOrGetDistance(NULL);
|
||||
|
||||
return dogd.dmin;
|
||||
}
|
||||
|
||||
Vector Constraint::GetLabelPos(void) {
|
||||
dogd.drawing = false;
|
||||
dogd.mp.x = 0; dogd.mp.y = 0;
|
||||
dogd.dmin = 1e12;
|
||||
|
||||
Vector p;
|
||||
DrawOrGetDistance(&p);
|
||||
return p;
|
||||
}
|
||||
|
||||
|
|
13
expr.cpp
13
expr.cpp
|
@ -49,6 +49,7 @@ int Expr::Children(void) {
|
|||
Expr *Expr::DeepCopy(void) {
|
||||
Expr *n = AllocExpr();
|
||||
*n = *this;
|
||||
n->marker = 0;
|
||||
int c = n->Children();
|
||||
if(c > 0) n->a = a->DeepCopy();
|
||||
if(c > 1) n->b = b->DeepCopy();
|
||||
|
@ -58,6 +59,7 @@ Expr *Expr::DeepCopy(void) {
|
|||
Expr *Expr::DeepCopyKeep(void) {
|
||||
Expr *n = (Expr *)MemAlloc(sizeof(Expr));
|
||||
*n = *this;
|
||||
n->marker = 0xbad2feed;
|
||||
n->a = n->b = NULL;
|
||||
int c = n->Children();
|
||||
if(c > 0) n->a = a->DeepCopyKeep();
|
||||
|
@ -65,6 +67,17 @@ Expr *Expr::DeepCopyKeep(void) {
|
|||
return n;
|
||||
}
|
||||
|
||||
void Expr::FreeKeep(Expr **e) {
|
||||
if(!(*e)) oops();
|
||||
|
||||
int c = (*e)->Children();
|
||||
if(c > 0) FreeKeep(&((*e)->a));
|
||||
if(c > 1) FreeKeep(&((*e)->b));
|
||||
if((*e)->marker != 0xbad2feed) oops();
|
||||
MemFree(*e);
|
||||
*e = NULL;
|
||||
}
|
||||
|
||||
Expr *Expr::DeepCopyWithParamsAsPointers(IdList<Param,hParam> *firstTry,
|
||||
IdList<Param,hParam> *thenTry)
|
||||
{
|
||||
|
|
5
expr.h
5
expr.h
|
@ -6,6 +6,8 @@ class Expr;
|
|||
|
||||
class Expr {
|
||||
public:
|
||||
DWORD marker;
|
||||
|
||||
// A parameter, by the hParam handle
|
||||
static const int PARAM = 0;
|
||||
// A parameter, by a pointer straight in to the param table (faster,
|
||||
|
@ -76,8 +78,9 @@ public:
|
|||
void PrintW(void); // worker
|
||||
|
||||
// Make a copy of an expression that won't get blown away when we
|
||||
// do a FreeAllExprs()
|
||||
// do a FreeAllExprs(), or free it later.
|
||||
Expr *DeepCopyKeep(void);
|
||||
static void FreeKeep(Expr **f);
|
||||
// or a copy that will
|
||||
Expr *DeepCopy(void);
|
||||
// number of child nodes: 0 (e.g. constant), 1 (sqrt), or 2 (+)
|
||||
|
|
|
@ -229,6 +229,7 @@ void GraphicsWindow::EnsureValidActives(void) {
|
|||
void GraphicsWindow::MenuEdit(int id) {
|
||||
switch(id) {
|
||||
case MNU_UNSELECT_ALL:
|
||||
HideGraphicsEditControl();
|
||||
SS.GW.ClearSelection();
|
||||
SS.GW.pendingOperation = 0;
|
||||
SS.GW.pendingDescription = NULL;
|
||||
|
@ -316,6 +317,8 @@ void GraphicsWindow::UpdateDraggedPoint(Vector *pos, double mx, double my) {
|
|||
void GraphicsWindow::MouseMoved(double x, double y, bool leftDown,
|
||||
bool middleDown, bool rightDown, bool shiftDown, bool ctrlDown)
|
||||
{
|
||||
if(GraphicsEditControlIsVisible()) return;
|
||||
|
||||
Point2d mp = { x, y };
|
||||
|
||||
if(middleDown) {
|
||||
|
@ -460,6 +463,8 @@ void GraphicsWindow::GroupSelection(void) {
|
|||
}
|
||||
|
||||
void GraphicsWindow::MouseMiddleDown(double x, double y) {
|
||||
if(GraphicsEditControlIsVisible()) return;
|
||||
|
||||
orig.offset = offset;
|
||||
orig.projUp = projUp;
|
||||
orig.projRight = projRight;
|
||||
|
@ -479,6 +484,8 @@ hRequest GraphicsWindow::AddRequest(int type) {
|
|||
}
|
||||
|
||||
void GraphicsWindow::MouseLeftDown(double mx, double my) {
|
||||
if(GraphicsEditControlIsVisible()) return;
|
||||
|
||||
// Make sure the hover is up to date.
|
||||
MouseMoved(mx, my, false, false, false, false, false);
|
||||
orig.mouse.x = mx;
|
||||
|
@ -542,6 +549,31 @@ void GraphicsWindow::MouseLeftDown(double mx, double my) {
|
|||
InvalidateGraphics();
|
||||
}
|
||||
|
||||
void GraphicsWindow::MouseLeftDoubleClick(double mx, double my) {
|
||||
if(GraphicsEditControlIsVisible()) return;
|
||||
|
||||
if(hover.constraint.v) {
|
||||
ClearSelection();
|
||||
Constraint *c = SS.GetConstraint(hover.constraint);
|
||||
Vector p3 = c->GetLabelPos();
|
||||
Point2d p2 = ProjectPoint(p3);
|
||||
ShowGraphicsEditControl((int)p2.x, (int)p2.y, c->exprA->Print());
|
||||
constraintBeingEdited = hover.constraint;
|
||||
}
|
||||
}
|
||||
|
||||
void GraphicsWindow::EditControlDone(char *s) {
|
||||
Expr *e = Expr::FromString(s);
|
||||
if(e) {
|
||||
Constraint *c = SS.GetConstraint(constraintBeingEdited);
|
||||
Expr::FreeKeep(&(c->exprA));
|
||||
c->exprA = e->DeepCopyKeep();
|
||||
HideGraphicsEditControl();
|
||||
} else {
|
||||
Error("Not a valid number or expression: '%s'", s);
|
||||
}
|
||||
}
|
||||
|
||||
void GraphicsWindow::MouseScroll(double x, double y, int delta) {
|
||||
double offsetRight = offset.Dot(projRight);
|
||||
double offsetUp = offset.Dot(projUp);
|
||||
|
|
4
sketch.h
4
sketch.h
|
@ -246,9 +246,11 @@ public:
|
|||
double dmin;
|
||||
} dogd; // state for drawing or getting distance (for hit testing)
|
||||
void LineDrawOrGetDistance(Vector a, Vector b);
|
||||
void DrawOrGetDistance(Vector *labelPos);
|
||||
|
||||
double GetDistance(Point2d mp);
|
||||
Vector GetLabelPos(void);
|
||||
void Draw(void);
|
||||
void DrawOrGetDistance(void);
|
||||
|
||||
bool HasLabel(void);
|
||||
|
||||
|
|
|
@ -35,6 +35,10 @@ BOOL GetOpenFile(char *file, char *defExtension, char *selPattern);
|
|||
void CheckMenuById(int id, BOOL checked);
|
||||
void EnableMenuById(int id, BOOL checked);
|
||||
|
||||
void ShowGraphicsEditControl(int x, int y, char *s);
|
||||
void HideGraphicsEditControl(void);
|
||||
BOOL GraphicsEditControlIsVisible(void);
|
||||
|
||||
void InvalidateGraphics(void);
|
||||
void InvalidateText(void);
|
||||
SDWORD GetMilliseconds(void);
|
||||
|
|
3
ui.h
3
ui.h
|
@ -144,6 +144,8 @@ public:
|
|||
char *pendingDescription;
|
||||
hRequest AddRequest(int type);
|
||||
|
||||
// The constraint that is being edited with the on-screen textbox.
|
||||
hConstraint constraintBeingEdited;
|
||||
|
||||
// The current selection.
|
||||
class Selection {
|
||||
|
@ -194,6 +196,7 @@ public:
|
|||
void MouseLeftDoubleClick(double x, double y);
|
||||
void MouseMiddleDown(double x, double y);
|
||||
void MouseScroll(double x, double y, int delta);
|
||||
void EditControlDone(char *s);
|
||||
};
|
||||
|
||||
|
||||
|
|
|
@ -24,6 +24,7 @@ int TextWndScrollPos;
|
|||
int TextWndRows;
|
||||
|
||||
HWND GraphicsWnd;
|
||||
HWND GraphicsEditControl;
|
||||
HMENU SubMenus[100];
|
||||
struct {
|
||||
int x, y;
|
||||
|
@ -291,6 +292,18 @@ LRESULT CALLBACK TextWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
|
|||
|
||||
static BOOL ProcessKeyDown(WPARAM wParam)
|
||||
{
|
||||
if(GraphicsEditControlIsVisible() && wParam != VK_ESCAPE) {
|
||||
if(wParam == VK_RETURN) {
|
||||
char s[1024];
|
||||
memset(s, 0, sizeof(s));
|
||||
SendMessage(GraphicsEditControl, WM_GETTEXT, 900, (LPARAM)s);
|
||||
SS.GW.EditControlDone(s);
|
||||
return TRUE;
|
||||
} else {
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
int c;
|
||||
switch(wParam) {
|
||||
case VK_OEM_PLUS: c = '+'; break;
|
||||
|
@ -383,6 +396,32 @@ void InvalidateText(void)
|
|||
InvalidateRect(TextWnd, NULL, FALSE);
|
||||
}
|
||||
|
||||
void ShowGraphicsEditControl(int x, int y, char *s)
|
||||
{
|
||||
RECT r;
|
||||
GetClientRect(GraphicsWnd, &r);
|
||||
x = x + (r.right - r.left)/2;
|
||||
y = (r.bottom - r.top)/2 - y;
|
||||
|
||||
// (x, y) are the bottom left, but the edit control is placed by its
|
||||
// top left corner
|
||||
y -= 21;
|
||||
|
||||
MoveWindow(GraphicsEditControl, x, y, 120, 21, TRUE);
|
||||
ShowWindow(GraphicsEditControl, SW_SHOW);
|
||||
SendMessage(GraphicsEditControl, WM_SETTEXT, 0, (LPARAM)s);
|
||||
SendMessage(GraphicsEditControl, EM_SETSEL, 0, strlen(s));
|
||||
SetFocus(GraphicsEditControl);
|
||||
}
|
||||
void HideGraphicsEditControl(void)
|
||||
{
|
||||
ShowWindow(GraphicsEditControl, SW_HIDE);
|
||||
}
|
||||
BOOL GraphicsEditControlIsVisible(void)
|
||||
{
|
||||
return IsWindowVisible(GraphicsEditControl);
|
||||
}
|
||||
|
||||
LRESULT CALLBACK GraphicsWndProc(HWND hwnd, UINT msg, WPARAM wParam,
|
||||
LPARAM lParam)
|
||||
{
|
||||
|
@ -407,6 +446,7 @@ LRESULT CALLBACK GraphicsWndProc(HWND hwnd, UINT msg, WPARAM wParam,
|
|||
|
||||
case WM_MOUSEMOVE:
|
||||
case WM_LBUTTONDOWN:
|
||||
case WM_LBUTTONDBLCLK:
|
||||
case WM_MBUTTONDOWN: {
|
||||
int x = LOWORD(lParam);
|
||||
int y = HIWORD(lParam);
|
||||
|
@ -421,6 +461,8 @@ LRESULT CALLBACK GraphicsWndProc(HWND hwnd, UINT msg, WPARAM wParam,
|
|||
|
||||
if(msg == WM_LBUTTONDOWN) {
|
||||
SS.GW.MouseLeftDown(x, y);
|
||||
} else if(msg == WM_LBUTTONDBLCLK) {
|
||||
SS.GW.MouseLeftDoubleClick(x, y);
|
||||
} else if(msg == WM_MBUTTONDOWN) {
|
||||
SS.GW.MouseMiddleDown(x, y);
|
||||
} else if(msg == WM_MOUSEMOVE) {
|
||||
|
@ -441,11 +483,13 @@ LRESULT CALLBACK GraphicsWndProc(HWND hwnd, UINT msg, WPARAM wParam,
|
|||
break;
|
||||
}
|
||||
case WM_COMMAND: {
|
||||
int id = LOWORD(wParam);
|
||||
for(int i = 0; SS.GW.menu[i].level >= 0; i++) {
|
||||
if(id == SS.GW.menu[i].id) {
|
||||
(SS.GW.menu[i].fn)((GraphicsWindow::MenuId)id);
|
||||
break;
|
||||
if(HIWORD(wParam) == 0) {
|
||||
int id = LOWORD(wParam);
|
||||
for(int i = 0; SS.GW.menu[i].level >= 0; i++) {
|
||||
if(id == SS.GW.menu[i].id) {
|
||||
(SS.GW.menu[i].fn)((GraphicsWindow::MenuId)id);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
@ -604,6 +648,11 @@ static void CreateMainWindows(void)
|
|||
600, 300, 200, 200, NULL, top, Instance, NULL);
|
||||
if(!GraphicsWnd) oops();
|
||||
|
||||
GraphicsEditControl = CreateWindowEx(WS_EX_CLIENTEDGE, WC_EDIT, "",
|
||||
WS_CHILD | ES_AUTOHSCROLL | WS_TABSTOP | WS_CLIPSIBLINGS,
|
||||
50, 50, 100, 21, GraphicsWnd, NULL, Instance, NULL);
|
||||
SendMessage(GraphicsEditControl, WM_SETFONT, (WPARAM)FixedFont, TRUE);
|
||||
|
||||
|
||||
// The text window, with a comand line and some textual information
|
||||
// about the sketch.
|
||||
|
@ -643,12 +692,7 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
|
|||
{
|
||||
Instance = hInstance;
|
||||
|
||||
// Create the root windows: one for control, with text, and one for
|
||||
// the graphics
|
||||
CreateMainWindows();
|
||||
|
||||
ThawWindowPos(TextWnd);
|
||||
ThawWindowPos(GraphicsWnd);
|
||||
InitCommonControls();
|
||||
|
||||
// A monospaced font
|
||||
FixedFont = CreateFont(TEXT_HEIGHT-2, TEXT_WIDTH, 0, 0, FW_REGULAR, FALSE,
|
||||
|
@ -662,6 +706,13 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
|
|||
if(!LinkFont)
|
||||
LinkFont = (HFONT)GetStockObject(SYSTEM_FONT);
|
||||
|
||||
// Create the root windows: one for control, with text, and one for
|
||||
// the graphics
|
||||
CreateMainWindows();
|
||||
|
||||
ThawWindowPos(TextWnd);
|
||||
ThawWindowPos(GraphicsWnd);
|
||||
|
||||
// Create the heap that we use to store Exprs.
|
||||
FreeAllExprs();
|
||||
|
||||
|
|
Loading…
Reference in New Issue