graph_displayer_canvas.h
author hegyi
Mon, 18 Sep 2006 16:02:20 +0000
changeset 148 5adf29662354
parent 147 10ef59f6633c
child 149 930e838ad5b6
permissions -rw-r--r--
When moving nodes with midbutton little red arrows keep their position.
     1 // -*- C++ -*- //
     2 
     3 #ifndef GRAPH_DISPLAYER_CANVAS_H
     4 #define GRAPH_DISPLAYER_CANVAS_H
     5 
     6 class GraphDisplayerCanvas;
     7 
     8 #include "all_include.h"
     9 #include "nbtab.h"
    10 #include <libgnomecanvasmm.h>
    11 #include <libgnomecanvasmm/polygon.h>
    12 #include <lemon/xy.h>
    13 
    14 ///This class is the canvas, on which the graph can be drawn.
    15 class GraphDisplayerCanvas : public Gnome::Canvas::CanvasAA
    16 {
    17   friend class BrokenEdge;
    18   friend class LoopEdge;
    19 
    20   class EdgeBase : public Gnome::Canvas::Group
    21   {
    22     protected:
    23       ///Reference to the canvas, on which the graph is drawn.
    24 
    25       ///It is needed, because some datas needed from
    26       ///graph can be accessed by this or should be sent
    27       ///as parameter, but it would be complicated
    28       GraphDisplayerCanvas& canvas;
    29 
    30       ///The edge that the class displays.
    31 
    32       ///It is needed, because some datas needed from
    33       ///graph can be accessed by this or should be sent
    34       ///as parameter, but it would be complicated
    35       Edge edge;
    36 
    37       Gnome::Canvas::Polygon arrow;
    38 
    39       void drawArrow(XY);
    40     public:
    41       EdgeBase(Gnome::Canvas::Group&, Edge, GraphDisplayerCanvas&);
    42       virtual ~EdgeBase();
    43       virtual void draw() = 0;
    44       virtual void setLineWidth(int) = 0;
    45       virtual void setFillColor(Gdk::Color) = 0;
    46   };
    47 
    48   ///Edge displayer class
    49 
    50   ///This class is responsible for displaying edges in graph.
    51   ///The displayed edge is broken in the middle. The
    52   ///aim of this is to be able to indicate direction of edges
    53   ///and to be able to display more then one edges between the
    54   ///same source and target
    55   class BrokenEdge : public EdgeBase
    56   {
    57     private:
    58       Gnome::Canvas::Line line;
    59 
    60       ///Indicates whether the button of mouse is pressed or not at the moment.
    61       bool isbutton;
    62 
    63       ///At this location was the mousebutton pressed. Horizontal component.
    64 
    65       ///It helps to calculate the
    66       ///distance of dragging.
    67       double clicked_x;
    68 
    69       ///At this location was the mousebutton pressed. Vertical component.
    70 
    71       ///It helps to calculate the
    72       ///distance of dragging.
    73       double clicked_y;
    74 
    75       ///event handler for forming broken edges
    76 
    77       ///\param event the
    78       ///event to handle
    79       bool edgeFormerEventHandler(GdkEvent* event);
    80 
    81     public:
    82       ///Constructor of broken edge class.
    83 
    84       ///\param g the group to which the edge belongs
    85       ///\param _edge the represented edge
    86       ///\param gc the canvas
    87       BrokenEdge(Gnome::Canvas::Group&, Edge, GraphDisplayerCanvas&);
    88 
    89       ///Destructor of broken edge class
    90 
    91       ///Frees up
    92       ///reserved memory
    93       ~BrokenEdge();
    94 
    95       ///The function that draws the edge based on collected data
    96       void draw();
    97 
    98       void setLineWidth(int);
    99       void setFillColor(Gdk::Color);
   100   };
   101 
   102   class LoopEdge : public EdgeBase
   103   {
   104     private:
   105       Gnome::Canvas::Ellipse line;
   106     public:
   107       LoopEdge(Gnome::Canvas::Group&, Edge, GraphDisplayerCanvas&);
   108       ~LoopEdge();
   109       void draw();
   110       void setLineWidth(int);
   111       void setFillColor(Gdk::Color);
   112   };
   113 
   114   ///Type of canvas, on which the graph is drawn
   115   typedef Gnome::Canvas::CanvasAA Parent;
   116 
   117 public:
   118   ///Constructor
   119 
   120   ///\param nbt the tab of the window, in which the graph is displayed
   121   GraphDisplayerCanvas(NoteBookTab & nbt);
   122 
   123   ///destructor of the class
   124   virtual ~GraphDisplayerCanvas();
   125 
   126   ///Changes the width of edge(s) according to the given map.
   127 
   128   ///\param mapname is the name of the map which contains the values to be set
   129   ///\param edge if it is given, only the width of the given edge will be set, instead of all of them.
   130   int changeEdgeWidth (std::string mapname, Edge edge=INVALID);
   131 
   132   ///Resets width of edge(s) to the default value
   133 
   134   ///\param edge if it is given, only the width of the
   135   ///given edge will be reset, instead of all of them.
   136   int resetEdgeWidth (Edge edge=INVALID);
   137 
   138   ///Changes the color of edge(s) according to the given map.
   139 
   140   ///\param mapname is the name of the map which contains the new values
   141   ///\param edge if it is given, only the color of the given edge will be set, instead of all of them.
   142   int changeEdgeColor (std::string mapname, Edge edge=INVALID);
   143 
   144   ///Resets color of edge(s) to the default value
   145 
   146   ///\param edge if it is given, only the color of the
   147   ///given edge will be reset, instead of all of them.
   148   int resetEdgeColor (Edge edge=INVALID);
   149 
   150   ///Changes the label of edge(s) according to the given map.
   151 
   152   ///\param mapname is the name of the map which contains the new values
   153   ///\param edge if it is given, only the label of the given edge will be set, instead of all of them.
   154   int changeEdgeText (std::string mapname, Edge edge=INVALID);
   155 
   156   ///Resets label of edge(s) to the default value
   157 
   158   ///\param edge if it is given, only the color of the
   159   ///given edge will be reset, instead of all of them.
   160   int resetEdgeText (Edge edge=INVALID);
   161 
   162   ///Changes the radius of node(s) according to the given map.
   163 
   164   ///\param mapname is the name of the map which contains the new values
   165   ///\param node if it is given, only the radius of the given node will be set, instead of all of them.
   166   int changeNodeRadius (std::string mapname, Node node=INVALID);
   167 
   168   ///Resets radius of node(s) to the default value
   169 
   170   ///\param node if it is given, only the radius of the
   171   ///given node will be reset, instead of all of them.
   172   int resetNodeRadius (Node node=INVALID);
   173 
   174   ///Changes the color of node(s) according to the given map.
   175 
   176   ///\param mapname is the name of the map which contains the new values
   177   ///\param node if it is given, only the color of the given node will be set, instead of all of them.
   178   int changeNodeColor (std::string mapname, Node node=INVALID);
   179 
   180   ///Resets color of node(s) to the default value
   181 
   182   ///\param node if it is given, only the color of the
   183   ///given node will be reset, instead of all of them.
   184   int resetNodeColor (Node node=INVALID);
   185 
   186   ///Changes the label of node(s) according to the given map.
   187 
   188   ///\param mapname is the name of the map which contains the new values
   189   ///\param node if it is given, only the label of the given node will be set, instead of all of them.
   190   int changeNodeText (std::string mapname, Node node=INVALID);
   191 
   192   ///Resets label of node(s) to the default value
   193 
   194   ///\param node if it is given, only the label of the
   195   ///given node will be reset, instead of all of them.
   196   int resetNodeText (Node node=INVALID);
   197 
   198   ///This function is called, when any of the displayed attributes have to be updated, or changed
   199 
   200   ///\param itisedge if true, edge property has to be changed, else node property
   201   ///\param prop the id of property that has to changed or updated
   202   void propertyChange(bool itisedge, int prop);
   203 
   204   ///updates the given property
   205 
   206   ///\param edge if it is not INVALID, only the property of the given edge will be updated, instead of all of them
   207   ///\param prop the property to update
   208   void propertyUpdate(Edge edge, int prop);
   209 
   210   ///updates the given property
   211 
   212   ///\param node if it is not INVALID, only the property of the given node will be updated, instead of all of them
   213   ///\param prop the property to update
   214   void propertyUpdate(Node node, int prop);
   215 
   216   ///updates all the property for the given edge
   217   void propertyUpdate(Edge);
   218 
   219   ///updates all the property for the given node
   220   void propertyUpdate(Node);
   221 
   222   ///Callback for 'ViewZoomIn' action.
   223   virtual void zoomIn();
   224   ///Callback for 'ViewZoomOut' action.
   225   virtual void zoomOut();
   226   ///Callback for 'ViewZoomFit' action.
   227   virtual void zoomFit();
   228   ///Callback for 'ViewZoom100' action.
   229   virtual void zoom100();
   230   ///Sets the scroll region of the convas to the bounding box of the graph.
   231   void updateScrollRegion();
   232 
   233   ///This function changes the tool in the graph-editor's hand
   234   void changeEditorialTool(int);
   235 
   236 protected:
   237 
   238   //maximizing, minimizing, restoring window, etc.
   239   virtual bool on_expose_event(GdkEventExpose *);
   240 
   241 private:
   242 
   243   ///This function is responsible for the correct
   244   ///reaction of any action happened in the territory
   245   ///of the canvas
   246   ///DEPRECATED!!!!
   247   bool eventHandler(GdkEvent* e, Node n);
   248 
   249   ///actual event handler
   250   ///
   251   ///Actual event handler should be stored, to be able to disconnect it and later reconnect it.
   252   sigc::connection actual_handler;
   253 
   254   ///event handler for the case when move-tool is active
   255   bool moveEventHandler(GdkEvent*);
   256   ///event handler for the case when create_node-tool is active
   257   bool createNodeEventHandler(GdkEvent*);
   258   ///event handler for the case when create_edge-tool is active
   259   bool createEdgeEventHandler(GdkEvent*);
   260   ///event handler for the case when eraser-tool is active
   261   bool eraserEventHandler(GdkEvent*);
   262   ///event handler for the case when edge map editor tool is active
   263   bool edgeMapEditEventHandler(GdkEvent*);
   264   ///event handler for the case when node map editor tool is active
   265   bool nodeMapEditEventHandler(GdkEvent*);
   266 
   267 public:
   268   ///Moves the text to new place
   269   void textReposition(xy<double>);
   270 
   271   ///Activates an edge belonging to an EdgeBase
   272 
   273   ///After we have activated an edge this way,
   274   ///the GDC object will know, which edge is under forming
   275   ///therefore it can redraw the necessary elements on the canvas,
   276   ///for example the text belonging to the \ref EdgeBase can be
   277   ///redrawn (\ref textReposition).
   278   void toggleEdgeActivity(EdgeBase*, bool);
   279 
   280 public:
   281 
   282   ///Returns the actual tool in hand
   283   int getActualTool();
   284 
   285   ///draws the graph
   286 
   287   ///Called when opening a file.
   288   void drawGraph();
   289 
   290   ///Clears the canvas
   291 
   292   ///It achieves this by deleting all data
   293   ///structure used to help handle the displayed graph.
   294   void clear();
   295 
   296   ///creates a new Nodemap
   297 
   298   ///\param init initial value of the map
   299   ///\param mapname name of new map
   300   int addNewNodeMap(double init,std::string mapname);
   301   ///creates a new Edgemap
   302 
   303   ///\param init initial value of the map
   304   ///\param mapname name of new map
   305   int addNewEdgeMap(double init,std::string mapname);
   306 
   307 private:
   308   ///Deletes the given element.
   309   void deleteItem(Node);
   310   ///Deletes the given element.
   311   void deleteItem(Edge);
   312 
   313 private:
   314 
   315   ///Map of nodes of graph
   316   Graph::NodeMap<Gnome::Canvas::Ellipse *> nodesmap;
   317 
   318   ///Map of edges of graph
   319   Graph::EdgeMap<EdgeBase*> edgesmap;
   320 
   321   ///Map of texts to write on edges
   322   Graph::EdgeMap<Gnome::Canvas::Text *> edgetextmap;
   323 
   324   ///Map of texts to write on nodes
   325   Graph::NodeMap<Gnome::Canvas::Text *> nodetextmap;
   326 
   327   ///Group of graphical elements of displayed_graph
   328   Gnome::Canvas::Group displayed_graph;
   329 
   330 private:
   331   ///Indicates whether the button of mouse is pressed or not
   332   int isbutton;
   333 
   334   ///Stores the actual tool in hand
   335   int actual_tool;
   336 
   337   ///At this location was the mousebutton pressed.
   338   ///It helps to calculate the distance of dragging.
   339   double clicked_x, clicked_y;
   340 
   341   ///Remembers which Gnome::Canvas::Item was pressed.
   342 
   343   ///this variable is needed, to work on it after selection
   344   Gnome::Canvas::Item * active_item;
   345 
   346   ///Remembers which Gnome::Canvas::Item was pressed.
   347 
   348   ///this variable is used at edge creation, it will
   349   ///be the secondly selected node. No local variable
   350   ///can be used for this purpose inside the function,
   351   ///because the node selected by button press, and
   352   ///the edge is created by button release. Both of
   353   ///them is different function call.
   354   Gnome::Canvas::Item * target_item;
   355 
   356   ///selected node (for any editing)
   357   Node active_node;
   358 
   359   ///selected edge (for any editing)
   360   Edge active_edge;
   361 
   362   ///the edge that is selected by clicking on the red arrow in the middle of it
   363 
   364   ///This edge is stored only for the purpose of reshape it.
   365   ///That is why it is selected in a different manner.
   366   Edge forming_edge;
   367 
   368   ///Map displayed by label can be edited.
   369   std::string nodemap_to_edit;
   370 
   371   ///Map displayed by label can be edited.
   372   std::string edgemap_to_edit;
   373 
   374   static const int zoom_step = 5;
   375 
   376 private:
   377 
   378   ///reference to the container, in which the canvas is
   379   NoteBookTab & mytab;
   380 
   381   XY calcArrowPos(XY, XY, XY, XY, int);
   382 };
   383 
   384 #endif //GRAPH_DISPLAYER_CANVAS_H