]> Shamusworld >> Repos - ttedit/commitdiff
Fixed a handful of bugs related to clicking and dragging
authorShamus Hammons <jlhamm@acm.org>
Fri, 4 Jan 2013 00:39:06 +0000 (18:39 -0600)
committerShamus Hammons <jlhamm@acm.org>
Fri, 4 Jan 2013 00:39:06 +0000 (18:39 -0600)
Mostly these were related to clicking and dragging with the selection
arrow and the add point tool on an empty canvas. Also fixed bug that
caused crashing when trying to add a poly after using the 'New' menu
command.

.gitignore
Makefile
src/editwindow.cpp
src/editwindow.h
src/glyphpoints.cpp
src/graphicprimitives.cpp
src/graphicprimitives.h
src/mainwindow.cpp

index 384123627196e4df382696115a1688018d28ecac..fdd715511b61d3ffe7aad4b06f472d586b7c4030 100644 (file)
@@ -1 +1,6 @@
+Makefile
 src/*~
+ttedit
+debug.log
+obj/*
+saves/*
index a8af53525c769321bfff41aaca875883a5bfc43d..81a051d024c26debcb7002251f5cf97cc823f5d4 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -1,6 +1,6 @@
 #############################################################################
 # Makefile for building: ttedit
-# Generated by qmake (2.01a) (Qt 4.8.3) on: Tue Nov 20 15:23:38 2012
+# Generated by qmake (2.01a) (Qt 4.8.4) on: Mon Dec 31 13:07:16 2012
 # Project:  ttedit.pro
 # Template: app
 # Command: /usr/bin/qmake -o Makefile ttedit.pro
index 192c9d2ee30b5bb5736588544af24895a504718c..ef3d585b2ddd4fd333c2c74759c3a43e3ccf9376 100755 (executable)
@@ -117,17 +117,9 @@ void EditWindow::paintEvent(QPaintEvent * /*event*/)
        QPainter p(this);
 //hm, causes lockup (or does it???)
        p.setRenderHint(QPainter::Antialiasing);
-//Doesn't do crap!
-//dc.SetBackground(*wxWHITE_BRUSH);
 
-// Due to the screwiness of wxWidgets coord system, the origin is ALWAYS
-// the upper left corner--regardless of axis orientation, etc...
-//     int width, height;
-//     dc.GetSize(&width, &height);
        QSize winSize = size();
 
-//     dc.SetDeviceOrigin(-offsetX, height - (-offsetY));
-//     dc.SetAxisOrientation(true, true);
        p.translate(QPoint(-offsetX, winSize.height() - (-offsetY)));
        p.scale(1.0, -1.0);
 
@@ -138,13 +130,10 @@ void EditWindow::paintEvent(QPaintEvent * /*event*/)
 // Instead, we have to scale EVERYTHING by hand. Crap!
 // It's not *that* bad, but not as convenient either...
 
-//     dc.SetPen(*(wxThePenList->FindOrCreatePen(wxColour(0x00, 0x00, 0xFF), 1, wxDOT)));
-////   dc.DrawLine(0, 0, 10, 10);
        p.setPen(QPen(Qt::blue, 1.0, Qt::DotLine));
 
        // Draw coordinate axes
 
-//     dc.CrossHair(0, 0);
        p.drawLine(0, -16384, 0, 16384);
        p.drawLine(-16384, 0, 16384, 0);
 
@@ -237,46 +226,89 @@ void EditWindow::DrawGlyph(QPainter & p, GlyphPoints & glyph)
 {
        for(int poly=0; poly<glyph.GetNumPolys(); poly++)
        {
-               if (glyph.GetNumPoints(poly) > 2)
-               {
-                       // Initial move...
-                       // If it's not on curve, then move to it, otherwise move to last point...
+               if (glyph.GetNumPoints(poly) < 3)
+                       continue;
 
-                       int x, y;
+               // Initial move: If our start point is on curve, then go to it. Otherwise,
+               // check previous point. If it's on curve, go to it otherwise go the
+               // midpoint between start point and previous (since it's between two curve
+               // control points).
+               IPoint pt = (glyph.GetOnCurve(poly, 0)
+                       ? glyph.GetPoint(poly, 0) : (glyph.GetPrevOnCurve(poly, 0)
+                               ? glyph.GetPrevPoint(poly, 0) : glyph.GetMidpointToPrev(poly, 0)));
 
-                       if (glyph.GetOnCurve(poly, glyph.GetNumPoints(poly) - 1))
-                               x = (int)glyph.GetX(poly, glyph.GetNumPoints(poly) - 1), y = (int)glyph.GetY(poly, glyph.GetNumPoints(poly) - 1);
-                       else
-                               x = (int)glyph.GetX(poly, 0), y = (int)glyph.GetY(poly, 0);
+// Need to add separate color handling here for polys that are being manipulated...
 
-                       for(int i=0; i<glyph.GetNumPoints(poly); i++)
+               for(int i=0; i<glyph.GetNumPoints(poly); i++)
+               {
+                       // If this point and then next are both on curve, we have a line...
+                       if (glyph.GetOnCurve(poly, i) && glyph.GetNextOnCurve(poly, i))
+                       {
+                               IPoint pt2 = glyph.GetNextPoint(poly, i);
+                               p.drawLine(pt.x, pt.y, pt2.x, pt2.y);
+                               pt = pt2;
+                       }
+                       else
                        {
+                               // Skip point if it's on curve (start of curve--it's already
+                               // been plotted so we don't need to handle it...)
                                if (glyph.GetOnCurve(poly, i))
-                               {
-                                       p.drawLine(x, y, glyph.GetX(poly, i), glyph.GetY(poly, i));
-                                       x = (int)glyph.GetX(poly, i), y = (int)glyph.GetY(poly, i);
-                               }
-                               else
-                               {
-                                       uint32 prev = glyph.GetPrev(poly, i), next = glyph.GetNext(poly, i);
-                                       float px = glyph.GetX(poly, prev), py = glyph.GetY(poly, prev),
-                                               nx = glyph.GetX(poly, next), ny = glyph.GetY(poly, next);
+                                       continue;
 
-                                       if (!glyph.GetOnCurve(poly, prev))
-                                               px = (px + glyph.GetX(poly, i)) / 2.0f,
-                                               py = (py + glyph.GetY(poly, i)) / 2.0f;
+                               // We are now guaranteed that we are sitting on a curve control point
+                               // (off curve). Figure the extent of the curve: If the following is a
+                               // curve control point, then use the midpoint to it otherwise go to
+                               // the next point since it's on curve.
+                               IPoint pt2 = (glyph.GetNextOnCurve(poly, i)
+                                       ? glyph.GetNextPoint(poly, i) : glyph.GetMidpointToNext(poly, i));
 
-                                       if (!glyph.GetOnCurve(poly, next))
-                                               nx = (nx + glyph.GetX(poly, i)) / 2.0f,
-                                               ny = (ny + glyph.GetY(poly, i)) / 2.0f;
+                               Bezier(p, pt, glyph.GetPoint(poly, i), pt2);
+                               pt = pt2;
+                       }
+               }
+       }
+}
 
-                                       Bezier(p, point(px, py), point(glyph.GetX(poly, i), glyph.GetY(poly, i)), point(nx, ny));
-                                       x = (int)nx, y = (int)ny;
 
-                                       if (glyph.GetOnCurve(poly, next))
-                                               i++;                                    // Following point is on curve, so move past it
-                               }
-                       }
+void EditWindow::DrawGlyphPoly(QPainter & p, GlyphPoints & glyph, uint16 poly)
+{
+       // Sanity check
+       if (glyph.GetNumPoints(poly) < 3)
+               return;
+
+       // Initial move: If our start point is on curve, then go to it. Otherwise,
+       // check previous point. If it's on curve, go to it otherwise go the
+       // midpoint between start point and previous (since it's between two curve
+       // control points).
+       IPoint pt = (glyph.GetOnCurve(poly, 0)
+               ? glyph.GetPoint(poly, 0) : (glyph.GetPrevOnCurve(poly, 0)
+                       ? glyph.GetPrevPoint(poly, 0) : glyph.GetMidpointToPrev(poly, 0)));
+
+       for(int i=0; i<glyph.GetNumPoints(poly); i++)
+       {
+               // If this point and then next are both on curve, we have a line...
+               if (glyph.GetOnCurve(poly, i) && glyph.GetNextOnCurve(poly, i))
+               {
+                       IPoint pt2 = glyph.GetNextPoint(poly, i);
+                       p.drawLine(pt.x, pt.y, pt2.x, pt2.y);
+                       pt = pt2;
+               }
+               else
+               {
+                       // Skip point if it's on curve (start of curve--it's already
+                       // been plotted so we don't need to handle it...)
+                       if (glyph.GetOnCurve(poly, i))
+                               continue;
+
+                       // We are now guaranteed that we are sitting on a curve control point
+                       // (off curve). Figure the extent of the curve: If the following is a
+                       // curve control point, then use the midpoint to it otherwise go to
+                       // the next point since it's on curve.
+                       IPoint pt2 = (glyph.GetNextOnCurve(poly, i)
+                               ? glyph.GetNextPoint(poly, i) : glyph.GetMidpointToNext(poly, i));
+
+                       Bezier(p, pt, glyph.GetPoint(poly, i), pt2);
+                       pt = pt2;
                }
        }
 }
@@ -301,13 +333,25 @@ void EditWindow::mousePressEvent(QMouseEvent * event)
 ;//meh                 CaptureMouse();                                         // Make sure we capture the mouse when in scroll/zoom mode
                else if (tool == TOOLAddPt)             // "Add Point" tool
                {
-                       if (pts.GetNumPoints() > 0)
+                       QPoint pt = GetAdjustedMousePosition(event);
+                       IPoint pointToAdd(pt.x(), pt.y(), ((event->modifiers() == Qt::ShiftModifier || event->modifiers() == Qt::ControlModifier) ? false : true));
+
+                       if (pts.GetNumPoints() < 2)
                        {
-                               QPoint pt = GetAdjustedMousePosition(event);
-                               pts.InsertPoint(pts.GetNext(ptHighlight), pt.x(), pt.y(), ((event->modifiers() == Qt::ShiftModifier || event->modifiers() == Qt::ControlModifier) ? false : true));
+//                             pts += IPoint(pt.x(), pt.y(), ((event->modifiers() == Qt::ShiftModifier || event->modifiers() == Qt::ControlModifier) ? false : true));
+                               pts += pointToAdd;
+                               ptHighlight = pts.GetNumPoints() - 1;
+                       }
+                       else
+                       {
+//                             QPoint pt = GetAdjustedMousePosition(event);
+//                             pts.InsertPoint(pts.GetNext(ptHighlight), pt.x(), pt.y(), ((event->modifiers() == Qt::ShiftModifier || event->modifiers() == Qt::ControlModifier) ? false : true));
+                               pts.InsertPoint(pts.GetNext(ptHighlight), pointToAdd);
                                ptHighlight = ptNextHighlight;
-                               update();
+//                             update();
                        }
+
+                       update();
                }
                else if (tool == TOOLAddPoly)   // "Add Poly" tool
                {
@@ -384,18 +428,10 @@ WriteLogMsg(" --> [# polys: %u, # points: %u]\n", pts.GetNumPolys(), pts.GetNumP
                }
                else if (tool == TOOLFlipWinding)
                {
-//                     IPoint centroid = pts.GetPolyCentroid(pts.GetPolyForPointNumber(ptHighlight));
-//                     rotationCenter = QPoint(centroid.x, centroid.y);
-//                     showRotationCenter = true;
                        pts.InvertPolyDrawSequence(pts.GetPolyForPointNumber(ptHighlight));
                        pt = GetAdjustedClientPosition(pts.GetX(ptHighlight), pts.GetY(ptHighlight));
                        QCursor::setPos(mapToGlobal(pt));
-//                     rotationZeroPoint = QPoint(pts.GetX(ptHighlight), pts.GetY(ptHighlight));
-//                     haveZeroPoint = true;
-//                     rotationAngle = 0;
                        update();
-//                     ((TTEdit *)qApp)->charWnd->MakePathFromPoints(&pts);
-//                     ((TTEdit *)qApp)->charWnd->update();
                }
        }
 
@@ -432,15 +468,13 @@ void EditWindow::mouseMoveEvent(QMouseEvent * event)
        {
                if (tool == TOOLAddPt || tool == TOOLAddPoly || tool == TOOLSelect)
                {
-                       if (tool != TOOLAddPt || pts.GetNumPoints() > 0)//yecch.
-                       {
-//temporary, for testing. BTW, Select drag bug is here...!
-#if 1
-                               QPoint pt2 = GetAdjustedMousePosition(event);
-                               pts.SetXY(ptHighlight, pt2.x(), pt2.y());
-                               update();
-#endif
-                       }
+                       // Bail out if we have the select tool and no points yet...
+                       if (tool == TOOLSelect && pts.GetNumPoints() == 0)
+                               return;
+
+                       QPoint pt2 = GetAdjustedMousePosition(event);
+                       pts.SetXY(ptHighlight, pt2.x(), pt2.y());
+                       update();
                }
                else if (tool == TOOLPolySelect)
                {
@@ -449,6 +483,8 @@ void EditWindow::mouseMoveEvent(QMouseEvent * event)
                                QPoint pt2 = GetAdjustedMousePosition(event);
                                // Should also set onCurve here as well, depending on keystate
 //Or should we?
+//Would be nice, but we'd need to trap the keyPressEvent() as well, otherwise pressing/releasing
+//the hotkey would show no change until the user moved their mouse.
                                pts.OffsetPoly(pts.GetPoly(ptHighlight), pt2.x() - pts.GetX(ptHighlight), pt2.y() - pts.GetY(ptHighlight));
                                update();
                        }
index c60317fbcb5344d52be6bf292c24c39695ea9afa..98691a46e755eee681dd23a4aad6311ca7c8be8e 100755 (executable)
@@ -33,6 +33,7 @@ class EditWindow: public QWidget
                QPoint GetAdjustedMousePosition(QMouseEvent * event);
                QPoint GetAdjustedClientPosition(int x, int y);
                void DrawGlyph(QPainter & p, GlyphPoints & glyph);
+               void DrawGlyphPoly(QPainter & p, GlyphPoints & glyph, uint16 poly);
 
        public:
                QImage image;
index a11b09ca3c5b82ba0221a832ab3052eefefda0cd..2e80e387e4987871dbf6c261ea608ea18b91046d 100755 (executable)
@@ -238,6 +238,10 @@ void GlyphPoints::Clear(void)
        onCurve = NULL;
        polyEnd = NULL;
        numPoints = numPolys = pointsAllocated = polysAllocated = 0;
+
+       numPolys = 1;
+       polyEnd = new uint16[numPolys];
+       polyEnd[0] = numPoints - 1;
 }
 
 
index 82e15ab323db6b2bf70e569808fa5707c94ced22..dd9b480e54650eca6ce7553d3326276da7de3511 100755 (executable)
@@ -23,6 +23,7 @@ double abs(double n)                                                  // Helper function
        return (n < 0 ? -n : n);
 }
 
+
 //
 // This function takes three points and draws a curve using a second order
 // Bezier function.
@@ -49,6 +50,16 @@ void Bezier(QPainter &p, point p1, point p2, point p3)
        p.drawLine(prevX, prevY, (int)p3.x, (int)p3.y);
 }
 
+
+//
+// This is a convenience funtion, using IPoints :-)
+//
+void Bezier(QPainter &p, IPoint p1, IPoint p2, IPoint p3)
+{
+       Bezier(p, point(p1.x, p1.y), point(p2.x, p2.y), point(p3.x, p3.y));
+}
+
+
 //
 // Draw a round dot (5x5, centered on [x, y])
 //
@@ -68,6 +79,7 @@ void DrawRoundDot(QPainter &p, int32 x, int32 y)
        p.drawPolygon(pt, 8);
 }
 
+
 //
 // Draw a sqaure dot (5x5, centered on [x, y])
 //
@@ -83,6 +95,7 @@ void DrawSquareDot(QPainter &p, int32 x, int32 y)
        p.drawPolygon(pt, 4);
 }
 
+
 //
 // Draw a sqaure dot (nxn, centered on [x, y])
 //
@@ -99,6 +112,7 @@ void DrawSquareDotN(QPainter &p, int32 x, int32 y, uint32 n)
        p.drawPolygon(pt, 4);
 }
 
+
 //
 // Draw a round dot (nxn, centered on [x, y])
 //
index 1513ebbe4ba23c4617f31e5891fca79e2008e8c5..9b2de448b8deac80c20e3645993c99e03793c015 100755 (executable)
@@ -10,6 +10,7 @@
 
 #include <QtGui>                                                               // For QPainter
 #include "types.h"                                                             // For int32
+#include "glyphpoints.h"                                               // For IPoint
 
 struct point
 {
@@ -19,6 +20,7 @@ struct point
 };
 
 void Bezier(QPainter &, point, point, point);
+void Bezier(QPainter &, IPoint, IPoint, IPoint);
 void DrawRoundDot(QPainter &, int32, int32);
 void DrawSquareDot(QPainter &, int32, int32);
 void DrawRoundDotN(QPainter &, int32, int32, uint32);
index 378c2ee9b2198c6772c0d1c511e5e61683ba5ced..076769589de113e7c8ee42200b1c64b8fd078fe8 100644 (file)
@@ -191,6 +191,7 @@ void MainWindow::NewGlyph(void)
        editWnd->pts.Clear();
        ((TTEdit *)qApp)->charWnd->MakePathFromPoints(&(editWnd->pts));
        ((TTEdit *)qApp)->charWnd->update();
+//     editWnd->polyFirstPoint = true;
        editWnd->update();
 }