Code

Suppress gradient direction line for 'solid' gradients.
[inkscape.git] / src / gradient-drag.cpp
index 246573e3f3fc0d05de413632b0f68b5c257404a6..8f0010925b513292a523bdd1079e6702cb5796a5 100644 (file)
@@ -1,14 +1,13 @@
-#define __GRADIENT_DRAG_C__
-
 /*
  * On-canvas gradient dragging
  *
  * Authors:
  *   bulia byak <buliabyak@users.sf.net>
  *   Johan Engelen <j.b.c.engelen@ewi.utwente.nl>
+ *   Jon A. Cruz <jon@joncruz.org>
  *
  * Copyright (C) 2007 Johan Engelen
- * Copyright (C) 2005 Authors
+ * Copyright (C) 2005,2010 Authors
  *
  * Released under GNU GPL, read the file 'COPYING' for more information
  */
@@ -332,12 +331,12 @@ GrDrag::addStopNearPoint (SPItem *item, Geom::Point mouse_p, double tolerance)
 
     if (addknot) {
         SPGradient *vector = sp_gradient_get_forked_vector_if_necessary (gradient, false);
-        SPStop* prev_stop = sp_first_stop(vector);
-        SPStop* next_stop = sp_next_stop(prev_stop);
+        SPStop* prev_stop = vector->getFirstStop();
+        SPStop* next_stop = prev_stop->getNextStop();
         guint i = 1;
         while ( (next_stop) && (next_stop->offset < offset) ) {
             prev_stop = next_stop;
-            next_stop = sp_next_stop(next_stop);
+            next_stop = next_stop->getNextStop();
             i++;
         }
         if (!next_stop) {
@@ -347,7 +346,7 @@ GrDrag::addStopNearPoint (SPItem *item, Geom::Point mouse_p, double tolerance)
 
 
         SPStop *newstop = sp_vector_add_stop (vector, prev_stop, next_stop, offset);
-        sp_gradient_ensure_vector (gradient);
+        gradient->ensureVector();
         updateDraggers();
 
         return newstop;
@@ -502,17 +501,18 @@ GrDraggable::~GrDraggable ()
 }
 
 
-SPObject *
-GrDraggable::getServer ()
+SPObject *GrDraggable::getServer()
 {
-    if (!item)
+    if (!item) {
         return NULL;
+    }
 
     SPObject *server = NULL;
-    if (fill_or_stroke)
-        server = SP_OBJECT_STYLE_FILL_SERVER (item);
-    else
-        server = SP_OBJECT_STYLE_STROKE_SERVER (item);
+    if (fill_or_stroke) {
+        server = item->style->getFillPaintServer();
+    }else {
+        server = item->style->getStrokePaintServer();
+    }
 
     return server;
 }
@@ -664,7 +664,7 @@ gr_knot_moved_handler(SPKnot *knot, Geom::Point const &ppointer, guint state, gp
                         s.setTransformation(s.getPoint() - p);
                         sc.points.push_back(s);
                     } else {
-                        Inkscape::SnappedPoint dummy(p + *snap_vector, Inkscape::SNAPSOURCE_OTHER_HANDLE, 0, Inkscape::SNAPTARGET_CONSTRAINED_ANGLE, Geom::L2(*snap_vector), 10000, true, false);
+                        Inkscape::SnappedPoint dummy(p + *snap_vector, Inkscape::SNAPSOURCE_OTHER_HANDLE, 0, Inkscape::SNAPTARGET_CONSTRAINED_ANGLE, Geom::L2(*snap_vector), 10000, true, true, false);
                         dummy.setTransformation(*snap_vector);
                         sc.points.push_back(dummy);
                     }
@@ -808,9 +808,10 @@ gr_knot_moved_midpoint_handler(SPKnot */*knot*/, Geom::Point const &ppointer, gu
     } else {
         p = snap_vector_midpoint (p, low_lim, high_lim, 0);
         if (!(state & GDK_SHIFT_MASK)) {
+            Inkscape::Snapper::ConstraintLine cl(low_lim, high_lim - low_lim);
             SPDesktop *desktop = dragger->parent->desktop;
             SnapManager &m = desktop->namedview->snap_manager;
-            Inkscape::Snapper::ConstraintLine cl(low_lim, high_lim - low_lim);
+            m.setup(desktop);
             m.constrainedSnapReturnByRef(p, Inkscape::SNAPSOURCE_OTHER_HANDLE, cl);
         }
     }
@@ -904,15 +905,15 @@ gr_knot_clicked_handler(SPKnot */*knot*/, guint state, gpointer data)
     if ( (state & GDK_CONTROL_MASK) && (state & GDK_MOD1_MASK ) ) {
     // delete this knot from vector
         SPGradient *gradient = sp_item_gradient (draggable->item, draggable->fill_or_stroke);
-        gradient = sp_gradient_get_vector (gradient, false);
+        gradient = gradient->getVector();
         if (gradient->vector.stops.size() > 2) { // 2 is the minimum
             SPStop *stop = NULL;
             switch (draggable->point_type) {  // if we delete first or last stop, move the next/previous to the edge
             case POINT_LG_BEGIN:
             case POINT_RG_CENTER:
-                stop = sp_first_stop(gradient);
+                stop = gradient->getFirstStop();
                 {
-                    SPStop *next = sp_next_stop (stop);
+                    SPStop *next = stop->getNextStop();
                     if (next) {
                         next->offset = 0;
                         sp_repr_set_css_double (SP_OBJECT_REPR (next), "offset", 0);
@@ -924,7 +925,7 @@ gr_knot_clicked_handler(SPKnot */*knot*/, guint state, gpointer data)
             case POINT_RG_R2:
                 stop = sp_last_stop(gradient);
                 {
-                    SPStop *prev = sp_prev_stop (stop, gradient);
+                    SPStop *prev = stop->getPrevStop();
                     if (prev) {
                         prev->offset = 1;
                         sp_repr_set_css_double (SP_OBJECT_REPR (prev), "offset", 1);
@@ -1622,41 +1623,43 @@ GrDrag::grabKnot (SPItem *item, gint point_type, gint point_i, bool fill_or_stro
 Regenerates the draggers list from the current selection; is called when selection is changed or
 modified, also when a radial dragger needs to update positions of other draggers in the gradient
 */
-void
-GrDrag::updateDraggers ()
+void GrDrag::updateDraggers ()
 {
     while (selected) {
         selected = g_list_remove(selected, selected->data);
     }
     // delete old draggers
     for (GList const* i = this->draggers; i != NULL; i = i->next) {
-        delete ((GrDragger *) i->data);
+        delete static_cast<GrDragger *>(i->data);
     }
-    g_list_free (this->draggers);
+    g_list_free(this->draggers);
     this->draggers = NULL;
 
-    g_return_if_fail (this->selection != NULL);
+    g_return_if_fail(this->selection != NULL);
 
     for (GSList const* i = this->selection->itemList(); i != NULL; i = i->next) {
-
         SPItem *item = SP_ITEM(i->data);
-        SPStyle *style = SP_OBJECT_STYLE (item);
+        SPStyle *style = item->style;
 
         if (style && (style->fill.isPaintserver())) {
-            SPObject *server = SP_OBJECT_STYLE_FILL_SERVER (item);
-            if (SP_IS_LINEARGRADIENT (server)) {
-                addDraggersLinear (SP_LINEARGRADIENT (server), item, true);
-            } else if (SP_IS_RADIALGRADIENT (server)) {
-                addDraggersRadial (SP_RADIALGRADIENT (server), item, true);
+            SPPaintServer *server = style->getFillPaintServer();
+            if ( server && server->isSolid() ) {
+                // Suppress "gradientness" of solid paint
+            } else if ( SP_IS_LINEARGRADIENT(server) ) {
+                addDraggersLinear( SP_LINEARGRADIENT(server), item, true );
+            } else if ( SP_IS_RADIALGRADIENT(server) ) {
+                addDraggersRadial( SP_RADIALGRADIENT(server), item, true );
             }
         }
 
         if (style && (style->stroke.isPaintserver())) {
-            SPObject *server = SP_OBJECT_STYLE_STROKE_SERVER (item);
-            if (SP_IS_LINEARGRADIENT (server)) {
-                addDraggersLinear (SP_LINEARGRADIENT (server), item, false);
-            } else if (SP_IS_RADIALGRADIENT (server)) {
-                addDraggersRadial (SP_RADIALGRADIENT (server), item, false);
+            SPPaintServer *server = style->getStrokePaintServer();
+            if ( server && server->isSolid() ) {
+                // Suppress "gradientness" of solid paint
+            } else if ( SP_IS_LINEARGRADIENT(server) ) {
+                addDraggersLinear( SP_LINEARGRADIENT(server), item, false );
+            } else if ( SP_IS_RADIALGRADIENT(server) ) {
+                addDraggersRadial( SP_RADIALGRADIENT(server), item, false );
             }
         }
     }
@@ -1701,10 +1704,12 @@ GrDrag::updateLines ()
         SPStyle *style = SP_OBJECT_STYLE (item);
 
         if (style && (style->fill.isPaintserver())) {
-            SPObject *server = SP_OBJECT_STYLE_FILL_SERVER (item);
-            if (SP_IS_LINEARGRADIENT (server)) {
+            SPPaintServer *server = item->style->getFillPaintServer();
+            if ( server && server->isSolid() ) {
+                // Suppress "gradientness" of solid paint
+            } else if ( SP_IS_LINEARGRADIENT(server) ) {
                 this->addLine (item, sp_item_gradient_get_coords (item, POINT_LG_BEGIN, 0, true), sp_item_gradient_get_coords (item, POINT_LG_END, 0, true), GR_LINE_COLOR_FILL);
-            } else if (SP_IS_RADIALGRADIENT (server)) {
+            } else if ( SP_IS_RADIALGRADIENT(server) ) {
                 Geom::Point center = sp_item_gradient_get_coords (item, POINT_RG_CENTER, 0, true);
                 this->addLine (item, center, sp_item_gradient_get_coords (item, POINT_RG_R1, 0, true), GR_LINE_COLOR_FILL);
                 this->addLine (item, center, sp_item_gradient_get_coords (item, POINT_RG_R2, 0, true), GR_LINE_COLOR_FILL);
@@ -1712,10 +1717,12 @@ GrDrag::updateLines ()
         }
 
         if (style && (style->stroke.isPaintserver())) {
-            SPObject *server = SP_OBJECT_STYLE_STROKE_SERVER (item);
-            if (SP_IS_LINEARGRADIENT (server)) {
+            SPPaintServer *server = item->style->getStrokePaintServer();
+            if ( server && server->isSolid() ) {
+                // Suppress "gradientness" of solid paint
+            } else if ( SP_IS_LINEARGRADIENT(server) ) {
                 this->addLine (item, sp_item_gradient_get_coords (item, POINT_LG_BEGIN, 0, false), sp_item_gradient_get_coords (item, POINT_LG_END, 0, false), GR_LINE_COLOR_STROKE);
-            } else if (SP_IS_RADIALGRADIENT (server)) {
+            } else if ( SP_IS_RADIALGRADIENT(server) ) {
                 Geom::Point center = sp_item_gradient_get_coords (item, POINT_RG_CENTER, 0, false);
                 this->addLine (item, center, sp_item_gradient_get_coords (item, POINT_RG_R1, 0, false), GR_LINE_COLOR_STROKE);
                 this->addLine (item, center, sp_item_gradient_get_coords (item, POINT_RG_R2, 0, false), GR_LINE_COLOR_STROKE);
@@ -1955,7 +1962,7 @@ GrDrag::deleteSelected (bool just_one)
                     {
                         SPStop *stop = NULL;
                         if ( (draggable->point_type == POINT_LG_BEGIN) || (draggable->point_type == POINT_RG_CENTER) ) {
-                            stop = sp_first_stop(vector);
+                            stop = vector->getFirstStop();
                         } else {
                             stop = sp_last_stop(vector);
                         }
@@ -2016,7 +2023,7 @@ GrDrag::deleteSelected (bool just_one)
                         SPLinearGradient *lg = SP_LINEARGRADIENT(stopinfo->gradient);
                         Geom::Point oldbegin = Geom::Point (lg->x1.computed, lg->y1.computed);
                         Geom::Point end = Geom::Point (lg->x2.computed, lg->y2.computed);
-                        SPStop *stop = sp_first_stop(stopinfo->vector);
+                        SPStop *stop = stopinfo->vector->getFirstStop();
                         gdouble offset = stop->offset;
                         Geom::Point newbegin = oldbegin + offset * (end - oldbegin);
                         lg->x1.computed = newbegin[Geom::X];
@@ -2030,11 +2037,11 @@ GrDrag::deleteSelected (bool just_one)
 
                         // iterate through midstops to set new offset values such that they won't move on canvas.
                         SPStop *laststop = sp_last_stop(stopinfo->vector);
-                        stop = sp_next_stop(stop);
+                        stop = stop->getNextStop();
                         while ( stop != laststop ) {
                             stop->offset = (stop->offset - offset)/(1 - offset);
                             sp_repr_set_css_double (SP_OBJECT_REPR (stop), "offset", stop->offset);
-                            stop = sp_next_stop(stop);
+                            stop = stop->getNextStop();
                         }
                     }
                     break;
@@ -2058,18 +2065,18 @@ GrDrag::deleteSelected (bool just_one)
                         sp_repr_set_css_double (SP_OBJECT_REPR (laststop), "offset", 1);
 
                         // iterate through midstops to set new offset values such that they won't move on canvas.
-                        SPStop *stop = sp_first_stop(stopinfo->vector);
-                        stop = sp_next_stop(stop);
+                        SPStop *stop = stopinfo->vector->getFirstStop();
+                        stop = stop->getNextStop();
                         while ( stop != laststop ) {
                             stop->offset = stop->offset / offset;
                             sp_repr_set_css_double (SP_OBJECT_REPR (stop), "offset", stop->offset);
-                            stop = sp_next_stop(stop);
+                            stop = stop->getNextStop();
                         }
                     }
                     break;
                 case POINT_RG_CENTER:
                     {
-                        SPStop *newfirst = sp_next_stop (stopinfo->spstop);
+                        SPStop *newfirst = stopinfo->spstop->getNextStop();
                         if (newfirst) {
                             newfirst->offset = 0;
                             sp_repr_set_css_double (SP_OBJECT_REPR (newfirst), "offset", 0);
@@ -2094,12 +2101,12 @@ GrDrag::deleteSelected (bool just_one)
                         sp_repr_set_css_double (SP_OBJECT_REPR (laststop), "offset", 1);
 
                         // iterate through midstops to set new offset values such that they won't move on canvas.
-                        SPStop *stop = sp_first_stop(stopinfo->vector);
-                        stop = sp_next_stop(stop);
+                        SPStop *stop = stopinfo->vector->getFirstStop();
+                        stop = stop->getNextStop();
                         while ( stop != laststop ) {
                             stop->offset = stop->offset / offset;
                             sp_repr_set_css_double (SP_OBJECT_REPR (stop), "offset", stop->offset);
-                            stop = sp_next_stop(stop);
+                            stop = stop->getNextStop();
                         }
                         break;
             }