]> git.saurik.com Git - wxWidgets.git/blobdiff - utils/ogl/src/lines.cpp
Added test for sprintf and vsnprintf to fix string.cpp for non-GNU systems.
[wxWidgets.git] / utils / ogl / src / lines.cpp
index 18d726812039f8c39ac8eb8a0ae256c4b4512126..a44bb7d2c6322972b2e8f737ffffec87bdc12ec4 100644 (file)
@@ -11,6 +11,7 @@
 
 #ifdef __GNUG__
 #pragma implementation "lines.h"
+#pragma implementation "linesp.h"
 #endif
 
 // For compilers that support precompilation, includes "wx.h".
 #include <wx/wx.h>
 #endif
 
-#ifdef PROLOGIO
 #include <wx/wxexpr.h>
-#endif
 
-#if USE_IOSTREAMH
+#if wxUSE_IOSTREAMH
 #include <iostream.h>
 #else
 #include <iostream>
@@ -249,7 +248,7 @@ void wxLineShape::FormatText(wxDC& dc, const wxString& s, int i)
       EraseRegion(dc, region, xx, yy);
       if (m_labelObjects[i])
       {
-        m_labelObjects[i]->Select(FALSE);
+        m_labelObjects[i]->Select(FALSE, &dc);
         m_labelObjects[i]->Erase(dc);
         m_labelObjects[i]->SetSize(actualW, actualH);
       }
@@ -291,7 +290,7 @@ void wxLineShape::DrawRegion(wxDC& dc, wxShapeRegion *region, double x, double y
       // Now draw the text
       if (region->GetFont()) dc.SetFont(region->GetFont());
 
-      dc.DrawRectangle((double)(xp - w/2.0), (double)(yp - h/2.0), (double)w, (double)h);
+      dc.DrawRectangle((long)(xp - w/2.0), (long)(yp - h/2.0), (long)w, (long)h);
 
       if (m_pen) dc.SetPen(m_pen);
       dc.SetTextForeground(* region->GetActualColourObject());
@@ -324,7 +323,7 @@ void wxLineShape::EraseRegion(wxDC& dc, wxShapeRegion *region, double x, double
       dc.SetPen(g_oglWhiteBackgroundPen);
       dc.SetBrush(g_oglWhiteBackgroundBrush);
 
-      dc.DrawRectangle((double)(xp - w/2.0), (double)(yp - h/2.0), (double)w, (double)h);
+      dc.DrawRectangle((long)(xp - w/2.0), (long)(yp - h/2.0), (long)w, (long)h);
   }
 }
 
@@ -391,12 +390,13 @@ void GraphicsStraightenLine(wxRealPoint *point1, wxRealPoint *point2)
   else point2->y = point1->y;
 }
 
-void wxLineShape::Straighten(wxDCdc)
+void wxLineShape::Straighten(wxDC *dc)
 {
   if (!m_lineControlPoints || m_lineControlPoints->Number() < 3)
     return;
 
-  Erase(dc);
+  if (dc)
+    Erase(* dc);
 
   wxNode *first_point_node = m_lineControlPoints->First();
   wxNode *last_point_node = m_lineControlPoints->Last();
@@ -417,7 +417,8 @@ void wxLineShape::Straighten(wxDC& dc)
     node = node->Next();
   }
 
-  Draw(dc);
+  if (dc)
+    Draw(* dc);
 }
 
 
@@ -721,10 +722,10 @@ void wxLineShape::DrawArrow(wxDC& dc, wxArrowHead *arrow, double xOffset, bool p
                        &side1_x, &side1_y, &side2_x, &side2_y);
 
       wxPoint points[4];
-      points[0].x = tip_x; points[0].y = tip_y;
-      points[1].x = side1_x; points[1].y = side1_y;
-      points[2].x = side2_x; points[2].y = side2_y;
-      points[3].x = tip_x; points[3].y = tip_y;
+      points[0].x = (int) tip_x; points[0].y = (int) tip_y;
+      points[1].x = (int) side1_x; points[1].y = (int) side1_y;
+      points[2].x = (int) side2_x; points[2].y = (int) side2_y;
+      points[3].x = (int) tip_x; points[3].y = (int) tip_y;
 
       dc.SetPen(m_pen);
       dc.SetBrush(m_brush);
@@ -753,7 +754,7 @@ void wxLineShape::DrawArrow(wxDC& dc, wxArrowHead *arrow, double xOffset, bool p
       else
         dc.SetBrush(m_brush);
 
-      dc.DrawEllipse(x1, y1, diameter, diameter);
+      dc.DrawEllipse((long) x1, (long) y1, (long) diameter, (long) diameter);
       break;
     }
     case ARROW_SINGLE_OBLIQUE:
@@ -830,8 +831,8 @@ void wxLineShape::DrawArrow(wxDC& dc, wxArrowHead *arrow, double xOffset, bool p
           arrow->GetMetaFile()->GetBounds(&minX, &minY, &maxX, &maxY);
           // Make erasing rectangle slightly bigger or you get droppings.
           int extraPixels = 4;
-          dc.DrawRectangle((double)(deltaX + x + minX - (extraPixels/2.0)), (double)(deltaY + y + minY - (extraPixels/2.0)),
-                           (double)(maxX - minX + extraPixels), (double)(maxY - minY + extraPixels));
+          dc.DrawRectangle((long)(deltaX + x + minX - (extraPixels/2.0)), (long)(deltaY + y + minY - (extraPixels/2.0)),
+                           (long)(maxX - minX + extraPixels), (long)(maxY - minY + extraPixels));
         }
         else
           arrow->GetMetaFile()->Draw(dc, x+deltaX, y+deltaY);
@@ -876,8 +877,8 @@ void wxLineShape::OnErase(wxDC& dc)
     // of 1.
     if (old_pen && (old_pen->GetWidth() > 1))
     {
-      dc.DrawRectangle((double)(m_xpos - (bound_x/2.0) - 2.0), (double)(m_ypos - (bound_y/2.0) - 2.0),
-                        (double)(bound_x+4.0),  (double)(bound_y+4.0));
+      dc.DrawRectangle((long)(m_xpos - (bound_x/2.0) - 2.0), (long)(m_ypos - (bound_y/2.0) - 2.0),
+                        (long)(bound_x+4.0),  (long)(bound_y+4.0));
     }
     else
     {
@@ -1063,7 +1064,7 @@ void wxLineShape::OnMoveLink(wxDC& dc, bool moveControlPoints)
 
 //    if (moveControlPoints && m_lineControlPoints && !(x_offset == 0.0 && y_offset == 0.0))
     // Only move control points if it's a self link. And only works if attachment mode is ON.
-    if ((m_from == m_to) && m_from->GetAttachmentMode() && moveControlPoints && m_lineControlPoints && !(x_offset == 0.0 && y_offset == 0.0))
+    if ((m_from == m_to) && (m_from->GetAttachmentMode() != ATTACHMENT_MODE_NONE) && moveControlPoints && m_lineControlPoints && !(x_offset == 0.0 && y_offset == 0.0))
     {
       wxNode *node = m_lineControlPoints->First();
       while (node)
@@ -1108,7 +1109,7 @@ void wxLineShape::FindLineEndPoints(double *fromX, double *fromY, double *toX, d
 
   if (m_lineControlPoints->Number() > 2)
   {
-    if (m_from->GetAttachmentMode())
+    if (m_from->GetAttachmentMode() != ATTACHMENT_MODE_NONE)
     {
       int nth, no_arcs;
       FindNth(m_from, &nth, &no_arcs, FALSE); // Not incoming
@@ -1119,7 +1120,7 @@ void wxLineShape::FindLineEndPoints(double *fromX, double *fromY, double *toX, d
                                    (double)second_point->x, (double)second_point->y,
                                     &end_x, &end_y);
 
-    if (m_to->GetAttachmentMode())
+    if (m_to->GetAttachmentMode() != ATTACHMENT_MODE_NONE)
     {
       int nth, no_arcs;
       FindNth(m_to, &nth, &no_arcs, TRUE); // Incoming
@@ -1137,7 +1138,7 @@ void wxLineShape::FindLineEndPoints(double *fromX, double *fromY, double *toX, d
     double toX = m_to->GetX();
     double toY = m_to->GetY();
 
-    if (m_from->GetAttachmentMode())
+    if (m_from->GetAttachmentMode() != ATTACHMENT_MODE_NONE)
     {
       int nth, no_arcs;
       FindNth(m_from, &nth, &no_arcs, FALSE);
@@ -1146,7 +1147,7 @@ void wxLineShape::FindLineEndPoints(double *fromX, double *fromY, double *toX, d
       fromY = end_y;
     }
 
-    if (m_to->GetAttachmentMode())
+    if (m_to->GetAttachmentMode() != ATTACHMENT_MODE_NONE)
     {
       int nth, no_arcs;
       FindNth(m_to, &nth, &no_arcs, TRUE);
@@ -1155,12 +1156,12 @@ void wxLineShape::FindLineEndPoints(double *fromX, double *fromY, double *toX, d
       toY = other_end_y;
     }
 
-    if (!m_from->GetAttachmentMode())
+    if (m_from->GetAttachmentMode() == ATTACHMENT_MODE_NONE)
       (void) m_from->GetPerimeterPoint(m_from->GetX(), m_from->GetY(),
                                   toX, toY,
                                   &end_x, &end_y);
 
-    if (!m_to->GetAttachmentMode())
+    if (m_to->GetAttachmentMode() == ATTACHMENT_MODE_NONE)
       (void) m_to->GetPerimeterPoint(m_to->GetX(), m_to->GetY(),
                                 fromX, fromY,
                                 &other_end_x, &other_end_y);
@@ -1294,14 +1295,6 @@ void wxLineShape::OnDrawContents(wxDC& dc)
   }
 }
 
-
-#ifdef PROLOGIO
-char *wxLineShape::GetFunctor()
-{
-  return "arc_image";
-}
-#endif
-
 void wxLineShape::SetTo(wxShape *object)
 {
   m_to = object;
@@ -1375,9 +1368,9 @@ void wxLineShape::ResetControlPoints()
 }
 
 #ifdef PROLOGIO
-void wxLineShape::WritePrologAttributes(wxExpr *clause)
+void wxLineShape::WriteAttributes(wxExpr *clause)
 {
-  wxShape::WritePrologAttributes(clause);
+  wxShape::WriteAttributes(clause);
 
   if (m_from)
     clause->AddAttributeValue("from", m_from->GetId());
@@ -1399,12 +1392,12 @@ void wxLineShape::WritePrologAttributes(wxExpr *clause)
     clause->AddAttributeValue("keep_lines_straight", (long)m_maintainStraightLines);
 
   // Make a list of lists for the (sp)line controls
-  wxExpr *list = new wxExpr(PrologList);
+  wxExpr *list = new wxExpr(wxExprList);
   wxNode *node = m_lineControlPoints->First();
   while (node)
   {
     wxRealPoint *point = (wxRealPoint *)node->Data();
-    wxExpr *point_list = new wxExpr(PrologList);
+    wxExpr *point_list = new wxExpr(wxExprList);
     wxExpr *x_expr = new wxExpr((double) point->x);
     wxExpr *y_expr = new wxExpr((double) point->y);
     point_list->Append(x_expr);
@@ -1420,17 +1413,17 @@ void wxLineShape::WritePrologAttributes(wxExpr *clause)
   // (arrowType arrowEnd xOffset arrowSize)
   if (m_arcArrows.Number() > 0)
   {
-    wxExpr *arrow_list = new wxExpr(PrologList);
+    wxExpr *arrow_list = new wxExpr(wxExprList);
     node = m_arcArrows.First();
     while (node)
     {
       wxArrowHead *head = (wxArrowHead *)node->Data();
-      wxExpr *head_list = new wxExpr(PrologList);
+      wxExpr *head_list = new wxExpr(wxExprList);
       head_list->Append(new wxExpr((long)head->_GetType()));
       head_list->Append(new wxExpr((long)head->GetArrowEnd()));
       head_list->Append(new wxExpr(head->GetXOffset()));
       head_list->Append(new wxExpr(head->GetArrowSize()));
-      head_list->Append(new wxExpr(PrologString, (head->GetName() ? head->GetName() : "")));
+      head_list->Append(new wxExpr(wxExprString, head->GetName()));
       head_list->Append(new wxExpr(head->GetId()));
 
       // New members of wxArrowHead
@@ -1445,9 +1438,9 @@ void wxLineShape::WritePrologAttributes(wxExpr *clause)
   }
 }
 
-void wxLineShape::ReadPrologAttributes(wxExpr *clause)
+void wxLineShape::ReadAttributes(wxExpr *clause)
 {
-  wxShape::ReadPrologAttributes(clause);
+  wxShape::ReadAttributes(clause);
 
   int iVal = (int) m_isSpline;
   clause->AssignAttributeValue("is_spline", &iVal);
@@ -1496,7 +1489,7 @@ void wxLineShape::ReadPrologAttributes(wxExpr *clause)
   m_attachmentFrom = 0;
 
   clause->AssignAttributeValue("attachment_to", &m_attachmentTo);
-  clause->AssignAttributeValue("attachmen_from", &m_attachmentFrom);
+  clause->AssignAttributeValue("attachment_from", &m_attachmentFrom);
 
   wxExpr *line_list = NULL;
 
@@ -1666,12 +1659,12 @@ void wxLineShape::Select(bool select, wxDC* dc)
             m_labelObjects[i]->RemoveFromCanvas(m_canvas);
             delete m_labelObjects[i];
           }
-          m_labelObjects[i] = new wxLabelShape(this, region, w, h);
+          m_labelObjects[i] = OnCreateLabelShape(this, region, w, h);
           m_labelObjects[i]->AddToCanvas(m_canvas);
           m_labelObjects[i]->Show(TRUE);
           if (dc)
             m_labelObjects[i]->Move(*dc, (double)(x + xx), (double)(y + yy));
-          m_labelObjects[i]->Select(TRUE);
+          m_labelObjects[i]->Select(TRUE, dc);
         }
       }
     }
@@ -1683,6 +1676,7 @@ void wxLineShape::Select(bool select, wxDC* dc)
       if (m_labelObjects[i])
       {
         m_labelObjects[i]->Select(FALSE, dc);
+        m_labelObjects[i]->Erase(*dc);
         m_labelObjects[i]->RemoveFromCanvas(m_canvas);
         delete m_labelObjects[i];
         m_labelObjects[i] = NULL;
@@ -1704,6 +1698,7 @@ wxLineControlPoint::wxLineControlPoint(wxShapeCanvas *theCanvas, wxShape *object
   m_xpos = x;
   m_ypos = y;
   m_type = the_type;
+  m_point = NULL;
 }
 
 wxLineControlPoint::~wxLineControlPoint()
@@ -1770,7 +1765,7 @@ void wxLineShape::OnSizingDragLeft(wxControlPoint* pt, bool draw, double x, doub
 
   if (lpt->m_type == CONTROL_POINT_ENDPOINT_FROM || lpt->m_type == CONTROL_POINT_ENDPOINT_TO)
   {
-    lpt->SetX(x); lpt->SetY(y);
+//    lpt->SetX(x); lpt->SetY(y);
   }
 
 }
@@ -1785,6 +1780,7 @@ void wxLineShape::OnSizingBeginDragLeft(wxControlPoint* pt, double x, double y,
   wxLineShape *lineShape = (wxLineShape *)this;
   if (lpt->m_type == CONTROL_POINT_LINE)
   {
+    lpt->m_originalPos = * (lpt->m_point);
     m_canvas->Snap(&x, &y);
 
     this->Erase(dc);
@@ -1817,18 +1813,6 @@ void wxLineShape::OnSizingBeginDragLeft(wxControlPoint* pt, double x, double y,
 
   if (lpt->m_type == CONTROL_POINT_ENDPOINT_FROM || lpt->m_type == CONTROL_POINT_ENDPOINT_TO)
   {
-    lpt->Erase(dc);
-    lineShape->OnDraw(dc);
-    if (lpt->m_type == CONTROL_POINT_ENDPOINT_FROM)
-    {
-      lineShape->GetFrom()->OnDraw(dc);
-      lineShape->GetFrom()->OnDrawContents(dc);
-    }
-    else
-    {
-      lineShape->GetTo()->OnDraw(dc);
-      lineShape->GetTo()->OnDrawContents(dc);
-    }
     m_canvas->SetCursor(g_oglBullseyeCursor);
     lpt->m_oldCursor = wxSTANDARD_CURSOR;
   }
@@ -1848,19 +1832,26 @@ void wxLineShape::OnSizingEndDragLeft(wxControlPoint* pt, double x, double y, in
   {
     m_canvas->Snap(&x, &y);
 
-    dc.SetLogicalFunction(wxCOPY);
-    lpt->m_xpos = x; lpt->m_ypos = y;
-    lpt->m_point->x = x; lpt->m_point->y = y;
+    wxRealPoint pt = wxRealPoint(x, y);
 
-    lineShape->GetEventHandler()->OnMoveLink(dc);
+    // Move the control point back to where it was;
+    // MoveControlPoint will move it to the new position
+    // if it decides it wants. We only moved the position
+    // during user feedback so we could redraw the line
+    // as it changed shape.
+    lpt->m_xpos = lpt->m_originalPos.x; lpt->m_ypos = lpt->m_originalPos.y;
+    lpt->m_point->x = lpt->m_originalPos.x; lpt->m_point->y = lpt->m_originalPos.y;
+
+    OnMoveMiddleControlPoint(dc, lpt, pt);
   }
   if (lpt->m_type == CONTROL_POINT_ENDPOINT_FROM)
   {
     if (lpt->m_oldCursor)
       m_canvas->SetCursor(lpt->m_oldCursor);
-    this->Erase(dc);
 
-    lpt->m_xpos = x; lpt->m_ypos = y;
+//    this->Erase(dc);
+
+//    lpt->m_xpos = x; lpt->m_ypos = y;
 
     if (lineShape->GetFrom())
     {
@@ -1872,7 +1863,7 @@ void wxLineShape::OnSizingEndDragLeft(wxControlPoint* pt, double x, double y, in
     if (lpt->m_oldCursor)
       m_canvas->SetCursor(lpt->m_oldCursor);
 
-    lpt->m_xpos = x; lpt->m_ypos = y;
+//    lpt->m_xpos = x; lpt->m_ypos = y;
 
     if (lineShape->GetTo())
     {
@@ -1890,13 +1881,22 @@ void wxLineShape::OnSizingEndDragLeft(wxControlPoint* pt, double x, double y, in
   // N.B. in OnMoveControlPoint, an event handler in Hardy could have deselected
   // the line and therefore deleted 'this'. -> GPF, intermittently.
   // So assume at this point that we've been blown away.
-  wxLineShape *lineObj = lineShape;
-  wxShapeCanvas *objCanvas = m_canvas;
 
-  lineObj->OnMoveControlPoint(i+1, x, y);
+  lineShape->OnMoveControlPoint(i+1, x, y);
 #endif
 }
 
+// This is called only when a non-end control point is moved.
+bool wxLineShape::OnMoveMiddleControlPoint(wxDC& dc, wxLineControlPoint* lpt, const wxRealPoint& pt)
+{
+    lpt->m_xpos = pt.x; lpt->m_ypos = pt.y;
+    lpt->m_point->x = pt.x; lpt->m_point->y = pt.y;
+
+    GetEventHandler()->OnMoveLink(dc);
+
+    return TRUE;
+}
+
 // Implement movement of endpoint to a new attachment
 // OBSOLETE: done by dragging with the left button.
 
@@ -2394,6 +2394,12 @@ void wxArrowHead::SetSize(double size)
   }
 }
 
+// Can override this to create a different class of label shape
+wxLabelShape* wxLineShape::OnCreateLabelShape(wxLineShape *parent, wxShapeRegion *region, double w, double h)
+{
+    return new wxLabelShape(parent, region, w, h);
+}
+
 /*
  * Label object
  *
@@ -2456,14 +2462,19 @@ void wxLabelShape::OnEndDragLeft(double x, double y, int keys, int attachment)
 
 bool wxLabelShape::OnMovePre(wxDC& dc, double x, double y, double old_x, double old_y, bool display)
 {
-  m_shapeRegion->SetSize(m_width, m_height);
+    return m_lineShape->OnLabelMovePre(dc, this, x, y, old_x, old_y, display);
+}
+
+bool wxLineShape::OnLabelMovePre(wxDC& dc, wxLabelShape* labelShape, double x, double y, double old_x, double old_y, bool display)
+{
+  labelShape->m_shapeRegion->SetSize(labelShape->GetWidth(), labelShape->GetHeight());
 
   // Find position in line's region list
   int i = 0;
-  wxNode *node = m_lineShape->GetRegions().First();
+  wxNode *node = GetRegions().First();
   while (node)
   {
-    if (m_shapeRegion == (wxShapeRegion *)node->Data())
+    if (labelShape->m_shapeRegion == (wxShapeRegion *)node->Data())
       node = NULL;
     else
     {
@@ -2472,18 +2483,21 @@ bool wxLabelShape::OnMovePre(wxDC& dc, double x, double y, double old_x, double
     }
   }
   double xx, yy;
-  m_lineShape->GetLabelPosition(i, &xx, &yy);
+  GetLabelPosition(i, &xx, &yy);
   // Set the region's offset, relative to the default position for
   // each region.
-  m_shapeRegion->SetPosition((double)(x - xx), (double)(y - yy));
+  labelShape->m_shapeRegion->SetPosition((double)(x - xx), (double)(y - yy));
+
+  labelShape->SetX(x);
+  labelShape->SetY(y);
 
   // Need to reformat to fit region.
-  if (m_shapeRegion->GetText())
+  if (labelShape->m_shapeRegion->GetText())
   {
 
-    wxString s(m_shapeRegion->GetText());
-    m_lineShape->FormatText(dc, s, i);
-    m_lineShape->DrawRegion(dc, m_shapeRegion, xx, yy);
+    wxString s(labelShape->m_shapeRegion->GetText());
+    labelShape->FormatText(dc, s, i);
+    DrawRegion(dc, labelShape->m_shapeRegion, xx, yy);
   }
   return TRUE;
 }