]> Shamusworld >> Repos - architektonas/blobdiff - src/line.cpp
Misc. fixes & additions
[architektonas] / src / line.cpp
index 956b9bdd3c7174c16041885ed43100e758f2ff67..060868562a8299c3d335bb849f3657d4a0d7417c 100644 (file)
@@ -123,6 +123,11 @@ Line::~Line()
 
 /*virtual*/ bool Line::Collided(Vector point)
 {
+/*
+what we can do here is set ignoreClicks to true to keep other objects that are
+selected from deselecting themselves. Will that fuck up something else? Not sure
+yet... :-/
+*/
        // Someone told us to fuck off, so we'll fuck off. :-)
        if (ignoreClicks)
                return false;
@@ -167,6 +172,13 @@ key to make it draw/show on the other side...
 
 TODO: Make Dimension preview with modifier keys for showing on other side
 */
+/*
+
+N.B.: This no longer works, as the DrawDimension object takes precedence over this code.
+      THIS DOES NOTHING ANYMORE!!!
+
+*/
+#if 0
        // Is the dimension tool active? Let's use it:
        if (dimensionActive)
        {
@@ -218,6 +230,7 @@ a dimension only) Draw() function... :-/
                        return true;
                }
        }
+#endif
 
        if (state == OSInactive)
        {
@@ -330,6 +343,18 @@ a dimension only) Draw() function... :-/
                needUpdate = true;
 
 //doesn't work         QMainWindow::statusBar()->setText("You are manipulating a line");
+
+               // Tell connected objects to move themselves...
+               if (draggingLine)
+               {
+                       std::vector<Connection>::iterator i;
+
+                       for(i=connected.begin(); i!=connected.end(); i++)
+                       {
+                               if ((*i).object->type == OTLine)
+                                       ((Line *)((*i).object))->MovePointAtParameter((*i).t, delta);
+                       }
+               }
        }
 
 /*
@@ -444,23 +469,13 @@ the horizontal line or vertical line that intersects from the current mouse posi
 
 /*virtual*/ bool Line::HitTest(Point point)
 {
-//     SaveHitState();
-
        hitPoint1 = hitPoint2 = hitLine = false;
        Vector lineSegment = endpoint - position;
        Vector v1 = point - position;
        Vector v2 = point - endpoint;
-//     double t = Vector::Parameter(position, endpoint, point);
        double t = Geometry::ParameterOfLineAndPoint(position, endpoint, point);
        double distance;
 
-       // Geometric interpretation:
-       // The parameter "t" on the vector lineSegment is where the normal of
-       // lineSegment coincides with point. If t < 0, the normal lies beyond the
-       // 1st endpoint. If t > 1, then the normal lies beyond the 2nd endpoint. We
-       // only calculate the length of the normal between the point and the
-       // lineSegment when the parameter is between 0 and 1.
-
        // Geometric interpretation of "distance = ?Det?(ls, v1) / |ls|":
        // If the segment endpoints are s and e, and the point is p, then the test
        // for the perpendicular intercepting the segment is equivalent to insisting
@@ -496,7 +511,6 @@ the horizontal line or vertical line that intersects from the current mouse posi
                hitLine = true;
 
        return (hitPoint1 || hitPoint2 || hitLine ? true : false);
-//     return HitStateChanged();
 }
 
 
@@ -537,23 +551,29 @@ same reference number.
 
 /*virtual*/ Vector Line::GetPointAtParameter(double parameter)
 {
+// Is there any real reason to clamp this to the endpoints?
+// (hey, whaddya know? this was masking a bug!)
+#if 0
        if (parameter <= 0)
                return position;
        else if (parameter >= 1.0)
                return endpoint;
+#endif
 
-       // Our parameter lies between zero and one, so calculate it!
-       Vector v(endpoint, position);
-       double length = v.Magnitude();
-       // We scale the magnitude of v so that it lies between 0 and 1...
-       // By multiplying the parameter by the magnitude, we obtain the point we
-       // want. No scaling necessary as it's inherent in the approach!
-       double spotOnLength = length * parameter;
-
-       // To get our point, we use the initial point of the line and add in our
-       // scaled point.
-       Vector result = position + (v * spotOnLength);
-       return result;
+       // The parameter is a percentage of the length of the vector, so all we
+       // have to do is scale the vector by it to find the point.
+       return position + (Vector(position, endpoint) * parameter);
+}
+
+
+/*virtual*/ void Line::MovePointAtParameter(double parameter, Vector v)
+{
+       if (parameter == 0)
+               position += v;
+       else if (parameter == 1.0)
+               endpoint += v;
+       else
+               {} // Not sure how to handle this case :-P
 }
 
 
@@ -571,71 +591,44 @@ same reference number.
 }
 
 
-/*virtual*/ void Line::Rotate(Vector point, double angle)
+/*virtual*/ void Line::Rotate(Point point, double angle)
 {
+       Point l1 = Geometry::RotatePointAroundPoint(position, point, angle);
+       Point l2 = Geometry::RotatePointAroundPoint(endpoint, point, angle);
+       position = l1;
+       endpoint = l2;
 }
 
 
-/*virtual*/ void Line::Scale(Vector point, double amount)
+/*virtual*/ void Line::Scale(Point point, double amount)
 {
 }
 
 
-/*virtual*/ Object * Line::Mirror(Vector p1, Vector p2)
+/*virtual*/ void Line::Mirror(Point p1, Point p2)
 {
-#if 1
        Point l1 = Geometry::MirrorPointAroundLine(position, p1, p2);
        Point l2 = Geometry::MirrorPointAroundLine(endpoint, p1, p2);
-       return new Line(l1, l2);
-#else
-       Vector normal = Vector::Normal(p1, p2);
-       Vector p4 = position + normal;
-
-       // Find the intersection of the line and position + normal to the line
-       double px = (((p1.x * p2.y) - (p1.y * p2.x)) * (position.x - p4.x))
-               - ((p1.x - p2.x) * ((position.x * p4.y) - (position.y * p4.x)));
-       double py = (((p1.x * p2.y) - (p1.y * p2.x)) * (position.y - p4.y))
-               - ((p1.y - p2.y) * ((position.x * p4.y) - (position.y * p4.x)));
-       double d = ((p1.x - p2.x) * (position.y - p4.y))
-               - ((p1.y - p2.y) * (position.x - p4.x));
-
-       // px = (x1y2 - y1x2)(x3 - x4) - (x1 - x2)(x3y4 - y3x4)
-       // py = (x1y2 - y1x2)(y3 - y4) - (y1 - y2)(x3y4 - y3x4)
-       // d = (x1 - x2)(y3 - y4) - (y1 - y2)(x3 - x4) = 0 if lines are parallel
-       // Intersection is (px / d, py / d)
-
-       Vector v1(px / d, py / d);
-
-//     Vector normal = Vector::Normal(p1, p2);
-       p4 = endpoint + normal;
+       position = l1;
+       endpoint = l2;
+}
 
-       // Find the intersection of the line and endpoint + normal to the line
-       px = (((p1.x * p2.y) - (p1.y * p2.x)) * (endpoint.x - p4.x))
-               - ((p1.x - p2.x) * ((endpoint.x * p4.y) - (endpoint.y * p4.x)));
-       py = (((p1.x * p2.y) - (p1.y * p2.x)) * (endpoint.y - p4.y))
-               - ((p1.y - p2.y) * ((endpoint.x * p4.y) - (endpoint.y * p4.x)));
-       d = ((p1.x - p2.x) * (endpoint.y - p4.y))
-               - ((p1.y - p2.y) * (endpoint.x - p4.x));
 
-       Vector v2(px / d, py / d);
+/*virtual*/ void Line::Save(void)
+{
+       Object::Save();
+       oldEndpoint = endpoint;
+}
 
-#if 0
-       Vector v3 = position - v1;
-       Vector v4 = endpoint - v2;
 
-       Vector v5 = v1 + -v3;
-       Vector v6 = v2 + -v4;
-#else
-       Vector v5 = v1 + v1 - position;
-       Vector v6 = v2 + v2 - endpoint;
-#endif
-
-       return new Line(v5, v6);
-#endif
+/*virtual*/ void Line::Restore(void)
+{
+       Object::Restore();
+       endpoint = oldEndpoint;
 }
 
 
-void Line::SetDimensionOnLine(Dimension * dimension/*=NULL*/)
+void Line::SetDimensionOnLine(Dimension * dimension/*= NULL*/)
 {
        // If they don't pass one in, create it for the caller.
        if (dimension == NULL)