diff --git a/src/nodepath.h b/src/nodepath.h
index fbcfe69dabbda01cfe56cc0684a7c446552fd57b..1dcb4527c64ca0ef0cd57bf010e0f75f8583c407 100644 (file)
--- a/src/nodepath.h
+++ b/src/nodepath.h
-#ifndef __SP_NODEPATH_H__
-#define __SP_NODEPATH_H__
-
-/** \file
- * Path handler in node edit mode
+/** @file
+ * @brief Path handler in node edit mode
*/
-
-/*
- * Authors:
+/* Authors:
* Lauris Kaplinski <lauris@kaplinski.com>
*
* This code is in public domain
*/
-//#include "knot.h"
-//#include "sp-path.h"
-//#include "desktop-handles.h"
+#ifndef SEEN_SP_NODEPATH_H
+#define SEEN_SP_NODEPATH_H
+
#include "libnr/nr-path-code.h"
-#include "livarot/Path.h"
#include <glibmm/ustring.h>
#include <gdk/gdkevents.h>
#include <list>
+#include <2geom/point.h>
+#include <2geom/matrix.h>
+#include <boost/optional.hpp>
+
+struct SPCanvasItem;
+class SPCurve;
+struct SPItem;
class SPObject;
class SPDesktop;
class SPPath;
class LivePathEffectObject;
namespace Inkscape {
-namespace XML {
-class Node;
-}
+ namespace XML {
+ class Node;
+ }
+
+ namespace LivePathEffect {
+ class Effect;
+ }
}
+typedef std::map<Inkscape::LivePathEffect::Effect *, std::vector<SPCanvasItem *> > HelperPathList;
/**
* Radial objects are represented by an angle and a distance from
class Radial{
public:
/** Radius */
- double r;
+ double r;
/** Amplitude */
- double a;
- Radial() {}
- // Radial(NR::Point const &p); // Convert a point to radial coordinates
- Radial(Radial &p) : r(p.r),a(p.a) {}
- // operator NR::Point() const;
+ double a;
+ Radial() {}
+ // Radial(Geom::Point const &p); // Convert a point to radial coordinates
+ Radial(Radial &p) : r(p.r),a(p.a) {}
+ // operator Geom::Point() const;
/**
- * Construct Radial from NR::Point.
+ * Construct Radial from Geom::Point.
*/
-Radial(NR::Point const &p)
+Radial(Geom::Point const &p)
{
- r = NR::L2(p);
- if (r > 0) {
- a = NR::atan2 (p);
- } else {
- a = HUGE_VAL; //undefined
- }
+ r = Geom::L2(p);
+ if (r > 0) {
+ a = Geom::atan2 (p);
+ } else {
+ a = HUGE_VAL; //undefined
+ }
}
/**
- * Cast Radial to cartesian NR::Point.
+ * Cast Radial to cartesian Geom::Point.
*/
-operator NR::Point() const
+operator Geom::Point() const
{
- if (a == HUGE_VAL) {
- return NR::Point(0,0);
- } else {
- return r*NR::Point(cos(a), sin(a));
- }
+ if (a == HUGE_VAL) {
+ return Geom::Point(0,0);
+ } else {
+ return r*Geom::Point(cos(a), sin(a));
+ }
}
};
namespace NodePath {
/**
- * This is a node on a subpath
+ * The entire nodepath, containing multiple subpaths
*/
class Path;
/**
- * This is a subdivision of a NodePath
+ * A subpath is a continuous chain of linked nodes
*/
class SubPath;
+/**
+ * One side of a node, i.e. prev or next
+ */
class NodeSide;
/**
- * This is a node (point) along a subpath
+ * A node on a subpath
*/
class Node;
class SubPath {
public:
/** The parent of this subpath */
- Path * nodepath;
+ Path * nodepath;
/** Is this path closed (no endpoints) or not?*/
- gboolean closed;
+ gboolean closed;
/** The nodes in this subpath. */
- GList * nodes;
+ GList * nodes;
/** The first node of the subpath (does not imply open/closed)*/
- Node * first;
+ Node * first;
/** The last node of the subpath */
- Node * last;
+ Node * last;
};
*/
typedef enum {
/** A normal node */
- NODE_NONE,
+ NODE_NONE,
/** This node non-continuously joins two segments.*/
- NODE_CUSP,
+ NODE_CUSP,
/** This node continuously joins two segments. */
- NODE_SMOOTH,
+ NODE_SMOOTH,
+/** This node has automatic handles. */
+ NODE_AUTO,
/** This node is symmetric. */
- NODE_SYMM
+ NODE_SYMM
} NodeType;
class NodeSide{
public:
/** Pointer to the next node, */
- Node * other;
+ Node * other;
/** Position */
- NR::Point pos;
+ Geom::Point pos;
/** Origin (while dragging) in radial notation */
- Radial origin_radial;
+ Radial origin_radial;
/** Origin (while dragging) in x/y notation */
- NR::Point origin;
+ Geom::Point origin;
/** Knots are Inkscape's way of providing draggable points. This
* Knot is the point on the curve representing the control point in a
* bezier curve.*/
- SPKnot * knot;
+ SPKnot * knot;
/** What kind of rendering? */
- SPCanvasItem * line;
+ SPCanvasItem * line;
};
/**
class Node {
public:
/** The parent subpath of this node */
- SubPath * subpath;
+ SubPath * subpath;
/** Type is selected from NodeType.*/
- guint type : 4;
+ guint type : 4;
/** Code refers to which ArtCode is used to represent the segment
* (which segment?).*/
- guint code : 4;
+ guint code : 4;
/** Boolean. Am I currently selected or not? */
- guint selected : 1;
+ guint selected : 1;
/** */
- NR::Point pos;
+ Geom::Point pos;
/** */
- NR::Point origin;
+ Geom::Point origin;
/** Knots are Inkscape's way of providing draggable points. This
* Knot is the point on the curve representing the endpoint.*/
- SPKnot * knot;
+ SPKnot * knot;
/** The NodeSide in the 'next' direction */
- NodeSide n;
+ NodeSide n;
/** The NodeSide in the 'previous' direction */
- NodeSide p;
+ NodeSide p;
- /** The pointer to the nodeside which we are dragging out with Shift */
- NodeSide *dragging_out;
+ /** The pointer to the nodeside which we are dragging out with Shift */
+ NodeSide *dragging_out;
/** Boolean. Am I being dragged? */
guint is_dragging : 1;
*/
class Path {
public:
+ /** Constructor should private, people should create new nodepaths using sp_nodepath_new
+ * But for some reason I cannot make sp_nodepath_new a friend :-(
+ */
+ Path() {};
+ /** Destructor */
+ ~Path();
+
/** Pointer to the current desktop, for reporting purposes */
- SPDesktop * desktop;
+ SPDesktop * desktop;
/** The parent path of this nodepath */
- SPObject * object;
+ SPObject * object;
/** The parent livepatheffect of this nodepath, if applicable */
SPItem * item;
/** The context which created this nodepath. Important if this nodepath is deleted */
- ShapeEditor *shape_editor;
+ ShapeEditor *shape_editor;
/** The subpaths which comprise this NodePath */
- GList * subpaths;
+ GList * subpaths;
/** A list of nodes which are currently selected */
- GList * selected;
+ GList * selected;
/** Transforms (userspace <---> virtual space? someone please describe )
- njh: I'd be guessing that these are item <-> desktop transforms.*/
- NR::Matrix i2d, d2i;
+ njh: I'd be guessing that these are item <-> desktop transforms.*/
+ Geom::Matrix i2d, d2i;
/** The DOM node which describes this NodePath */
Inkscape::XML::Node *repr;
gchar *repr_key;
gchar *repr_nodetypes_key;
- //STL compliant method to get the selected nodes
- void selection(std::list<Node *> &l);
+ //STL compliant method to get the selected nodes
+ void selection(std::list<Node *> &l);
- guint numSelected() {return (selected? g_list_length(selected) : 0);}
- NR::Point& singleSelectedCoords() {return (((Node *) selected->data)->pos);}
+ guint numSelected() {return (selected? g_list_length(selected) : 0);}
+ Geom::Point& singleSelectedCoords() {return (((Node *) selected->data)->pos);}
- /// livarot library is used for "point on path" and "nearest position on path", so we need to maintain its path representation as well
- ::Path *livarot_path;
-
/// draw a "sketch" of the path by using these variables
SPCanvasItem *helper_path;
SPCurve *curve;
guint32 helperpath_rgba;
gdouble helperpath_width;
+ // the helperpaths provided by all LPEs (and their paramaters) of the current item
+ HelperPathList helper_path_vec;
+
/// true if we changed repr, to tell this change from an external one such as from undo, simplify, or another desktop
- unsigned int local_change;
+ unsigned int local_change;
- /// true if we're showing selected nodes' handles
- bool show_handles;
+ /// true if we're showing selected nodes' handles
+ bool show_handles;
/// true if the path cannot contain curves, just straight lines
bool straight_path;
- /// active_node points to the node that is currently mouseovered (= NULL if
- /// there isn't any); we also consider the node mouseovered if it is covered
- /// by one of its handles and the latter is mouseovered
- static Node *active_node;
+ /// active_node points to the node that is currently mouseovered (= NULL if
+ /// there isn't any); we also consider the node mouseovered if it is covered
+ /// by one of its handles and the latter is mouseovered
+ static Node *active_node;
+
+ /// Location of mouse pointer when we started dragging, needed for snapping
+ Geom::Point drag_origin_mouse;
+
};
} // namespace NodePath
// Do function documentation in nodepath.cpp
Inkscape::NodePath::Path * sp_nodepath_new (SPDesktop * desktop, SPObject *object, bool show_handles, const char * repr_key = NULL, SPItem *item = NULL);
-void sp_nodepath_destroy (Inkscape::NodePath::Path * nodepath);
-void sp_nodepath_ensure_livarot_path(Inkscape::NodePath::Path *np);
void sp_nodepath_deselect (Inkscape::NodePath::Path *nodepath);
void sp_nodepath_select_all (Inkscape::NodePath::Path *nodepath, bool invert);
void sp_nodepath_select_all_from_subpath(Inkscape::NodePath::Path *nodepath, bool invert);
void sp_nodepath_select_next (Inkscape::NodePath::Path *nodepath);
void sp_nodepath_select_prev (Inkscape::NodePath::Path *nodepath);
-void sp_nodepath_select_rect (Inkscape::NodePath::Path * nodepath, NR::Rect const &b, gboolean incremental);
+void sp_nodepath_select_rect (Inkscape::NodePath::Path * nodepath, Geom::Rect const &b, gboolean incremental);
GList *save_nodepath_selection (Inkscape::NodePath::Path *nodepath);
void restore_nodepath_selection (Inkscape::NodePath::Path *nodepath, GList *r);
gboolean nodepath_repr_d_changed (Inkscape::NodePath::Path * np, const char *newd);
@@ -282,12 +302,14 @@ gboolean nodepath_repr_typestr_changed (Inkscape::NodePath::Path * np, const cha
gboolean node_key (GdkEvent * event);
void sp_nodepath_update_repr(Inkscape::NodePath::Path *np, const gchar *annotation);
void sp_nodepath_update_statusbar (Inkscape::NodePath::Path *nodepath);
-void sp_nodepath_selected_align(Inkscape::NodePath::Path *nodepath, NR::Dim2 axis);
-void sp_nodepath_selected_distribute(Inkscape::NodePath::Path *nodepath, NR::Dim2 axis);
-void sp_nodepath_select_segment_near_point(Inkscape::NodePath::Path *nodepath, NR::Point p, bool toggle);
-void sp_nodepath_add_node_near_point(Inkscape::NodePath::Path *nodepath, NR::Point p);
-void sp_nodepath_curve_drag(int node, double t, NR::Point delta);
-Inkscape::NodePath::Node * sp_nodepath_get_node_by_index(int index);
+void sp_nodepath_selected_align(Inkscape::NodePath::Path *nodepath, Geom::Dim2 axis);
+void sp_nodepath_selected_distribute(Inkscape::NodePath::Path *nodepath, Geom::Dim2 axis);
+void sp_nodepath_select_segment_near_point(Inkscape::NodePath::Path *nodepath, Geom::Point p, bool toggle);
+void sp_nodepath_add_node_near_point(Inkscape::NodePath::Path *nodepath, Geom::Point p);
+void sp_nodepath_curve_drag(Inkscape::NodePath::Path *nodepath, int node, double t, Geom::Point delta);
+Inkscape::NodePath::Node * sp_nodepath_get_node_by_index(Inkscape::NodePath::Path *np, int index);
+bool sp_node_side_is_line (Inkscape::NodePath::Node *node, Inkscape::NodePath::NodeSide *side);
+
/* possibly private functions */
void sp_node_selected_add_node (Inkscape::NodePath::Path *nodepath);
void sp_node_selected_set_type (Inkscape::NodePath::Path *nodepath, Inkscape::NodePath::NodeType type);
void sp_node_selected_set_line_type (Inkscape::NodePath::Path *nodepath, NRPathcode code);
void sp_node_selected_move (Inkscape::NodePath::Path *nodepath, gdouble dx, gdouble dy);
-void sp_node_selected_move_screen (Inkscape::NodePath::Path *nodepath, gdouble dx, gdouble dy);
-void sp_node_selected_move_absolute (Inkscape::NodePath::Path *nodepath, NR::Coord val, NR::Dim2 axis);
-NR::Rect sp_node_selected_bbox (Inkscape::NodePath::Path *nodepath);
-NR::Maybe<NR::Coord> sp_node_selected_common_coord (Inkscape::NodePath::Path *nodepath, NR::Dim2 axis);
+void sp_node_selected_move_screen (SPDesktop *desktop, Inkscape::NodePath::Path *nodepath, gdouble dx, gdouble dy);
+void sp_node_selected_move_absolute (Inkscape::NodePath::Path *nodepath, Geom::Coord val, Geom::Dim2 axis);
+Geom::Rect sp_node_selected_bbox (Inkscape::NodePath::Path *nodepath);
+boost::optional<Geom::Coord> sp_node_selected_common_coord (Inkscape::NodePath::Path *nodepath, Geom::Dim2 axis);
void sp_nodepath_show_handles(Inkscape::NodePath::Path *nodepath, bool show);
-SPCanvasItem *sp_nodepath_generate_helperpath(SPDesktop *desktop, SPCurve *curve, const SPItem *item, guint32 color);
-SPCanvasItem *sp_nodepath_generate_helperpath(SPDesktop *desktop, SPPath *path);
+SPCanvasItem *sp_nodepath_generate_helperpath(SPDesktop *desktop, SPCurve *curve, const Geom::Matrix & i2d, guint32 color);
+SPCanvasItem *sp_nodepath_generate_helperpath(SPDesktop *desktop, SPItem *item);
void sp_nodepath_show_helperpath(Inkscape::NodePath::Path *nodepath, bool show);
+void sp_nodepath_update_helperpaths(Inkscape::NodePath::Path *np);
void sp_nodepath_make_straight_path(Inkscape::NodePath::Path *np);
void sp_nodepath_selected_nodes_rotate (Inkscape::NodePath::Path * nodepath, gdouble angle, int which, bool screen);
@@ -317,6 +340,6 @@ void sp_nodepath_selected_nodes_rotate (Inkscape::NodePath::Path * nodepath, gdo
void sp_nodepath_selected_nodes_scale (Inkscape::NodePath::Path * nodepath, gdouble grow, int which);
void sp_nodepath_selected_nodes_scale_screen (Inkscape::NodePath::Path * nodepath, gdouble grow, int which);
-void sp_nodepath_flip (Inkscape::NodePath::Path *nodepath, NR::Dim2 axis, NR::Maybe<NR::Point> center);
+void sp_nodepath_flip (Inkscape::NodePath::Path *nodepath, Geom::Dim2 axis, boost::optional<Geom::Point> center);
#endif