Results 1 to 6 of 6

Thread: move/drag points on qwt plot

  1. #1
    Join Date
    Nov 2009
    Posts
    94
    Thanks
    14
    Thanked 1 Time in 1 Post
    Qt products
    Qt4
    Platforms
    Unix/X11

    Question move/drag points on qwt plot

    Hello,

    I'm wondering whether it is possible to move/drag the items resp. points which I would like to put on the qwt plot.
    My background is as follows: I want to use Qt and Qwt to build up a GUI Framework for Evolutionary Algorithms. For instance, I want to optimize something by finding a global maximum within the surface ( f(x1,x2) ). To do so, there will be a lot of inidviduals (sample points) genarated and placed randomly on the x1, x2 grid and then every sample point will be evaluated to the benchmark function ( f(x1,x2) ) and so on. My task is, to visualize the contours (elevation lines) of the benchmark function and to visualize the sample points on the grid. As far as I have read about Qwt, it is no problem to do that, but I would like to know, whether I can move/drag these sample points by mouse in order to change their positions.

    Thank you

    best regards,

    Vitali Anselm

  2. #2
    Join Date
    Feb 2006
    Location
    Munich, Germany
    Posts
    3,312
    Thanked 879 Times in 827 Posts
    Qt products
    Qt3 Qt4 Qt/Embedded
    Platforms
    MacOS X Unix/X11 Windows

    Default Re: move/drag points on qwt plot

    The event filter example shows an implementation of drag&drop of curve points. But this type of implementation might be too slow for plots with many points, because it does a replot for every mouse movement.

    A better implementation is to use an overlay widget, like it is done in QwtPlotPicker. Maybe the easiest way is to derive from QwtPlotPicker. Then in YourPicker::drawRubberBand() you have to paint a symbol ( or whatever you want display while moving ). Then you have to replot only at the beginning and the end of the drag operation.

    HTH,
    Uwe

  3. #3
    Join Date
    Nov 2009
    Posts
    94
    Thanks
    14
    Thanked 1 Time in 1 Post
    Qt products
    Qt4
    Platforms
    Unix/X11

    Default Re: move/drag points on qwt plot

    Quote Originally Posted by Uwe View Post
    A better implementation is to use an overlay widget, like it is done in QwtPlotPicker. Maybe the easiest way is to derive from QwtPlotPicker. Then in YourPicker::drawRubberBand() you have to paint a symbol ( or whatever you want display while moving ). Then you have to replot only at the beginning and the end of the drag operation
    Thank you for reply, Uwe.
    I don't think, that it is necessary to repaint the contour plot, because probably it is possible to plot the contour on the lowest layer and the points above it, on the higher layer, so that if I move the points only the higher layer should be updated. Is it possible to paint in 2 layers? The points must not be connected to the contour plot directly, they should only inform the user, that these points sample the surface on the corresponding x,y coordinates.

    Thank you

  4. #4
    Join Date
    Nov 2009
    Posts
    94
    Thanks
    14
    Thanked 1 Time in 1 Post
    Qt products
    Qt4
    Platforms
    Unix/X11

    Question Re: move/drag points on qwt plot

    Hello,

    in my previous example I have worked with the GraphicsView and Scene and GraphicsItem, where I have defined an own class of Graphicsitem and implemented the function where moving the item caused some changings of other parameters.

    Now I'm using QwtPlot and want to have the same functionality according to moving items. In fact, there is a QwtPlotItem which sound similar to GraphicsItem and seems to be the right thing and it has got the function "ItemChange()", too. Can I rewrite my old code (see below) to let the QwtPlotItem do the same?

    Vertex.h :
    Qt Code:
    1. #ifndef VERTEX_H
    2. #define VERTEX_H
    3.  
    4. #include <QGraphicsItem>
    5. #include <QObject>
    6. #include <QGraphicsSceneMouseEvent>
    7. #include "mainframe.h"
    8.  
    9. class Vertex : public QObject , public QGraphicsItem
    10. {
    11. Q_OBJECT
    12.  
    13. public:
    14. Vertex(mainFrame *mf, unsigned idx);
    15. QRectF boundingRect() const;
    16. QPainterPath shape() const;
    17. void paint(QPainter *painter, const QStyleOptionGraphicsItem *option,
    18. QWidget *widget);
    19. protected:
    20. void mouseReleaseEvent(QGraphicsSceneMouseEvent *event);
    21. QVariant itemChange(GraphicsItemChange change, const QVariant &value);
    22.  
    23. private:
    24. unsigned index;
    25. QColor color;
    26. QPointF dragStartPosition;
    27. mainFrame *_mf;
    28. };
    29.  
    30. #endif
    To copy to clipboard, switch view to plain text mode 

    Vertex.cpp :
    Qt Code:
    1. #include "Vertex.h"
    2.  
    3. /*
    4.  #include <QGraphicsScene>
    5.  #include <QPainter>
    6.  #include <QStyleOption>
    7.  #include <QApplication>
    8.  #include <QDrag>
    9.  #include <QMimeData>
    10.  #include <QBitmap>
    11. */
    12. #include <iostream>
    13. #include <QtGui>
    14.  
    15. using namespace std;
    16.  
    17. Vertex::Vertex(mainFrame *mf, unsigned idx)
    18. : color(Qt::white)
    19. {
    20. _mf = mf;
    21. index = idx;
    22. setZValue(1);
    23. //setAcceptHoverEvents(true);
    24. }
    25.  
    26. QRectF Vertex::boundingRect() const
    27. {
    28. qreal adjust = 0.5;
    29. return QRectF(-20 - adjust, -22 - adjust,
    30. 40 + adjust, 83 + adjust);
    31. }
    32.  
    33. QPainterPath Vertex::shape() const
    34. {
    35. path.addRect(-8, -8, 8, 8);
    36. return path;
    37. }
    38.  
    39. void Vertex::paint(QPainter *painter, const QStyleOptionGraphicsItem *, QWidget *)
    40. {
    41. // Vertex point
    42. painter->setBrush(color);
    43. painter->drawEllipse(-8, -8, 8, 8);
    44.  
    45.  
    46. }
    47.  
    48. void Vertex::mouseReleaseEvent(QGraphicsSceneMouseEvent *event){
    49. setCursor(Qt::OpenHandCursor);
    50. //update();
    51. QVector<QGraphicsScene *> scenesPhen = _mf->getScenes();
    52. QVector<QGraphicsScene *>::iterator it2 = scenesPhen.begin();
    53. unsigned j=0;
    54. unsigned idxIndiv = 0;
    55. while (it2 != scenesPhen.end()) {
    56. //cout << "(*it2): " << (*it2) << "\t\t scene(): "<< this->scene()<< endl;
    57. if((*it2) == scene()){
    58. qDebug() << "index of scene: " << j;
    59. idxIndiv = j;
    60. }
    61. ++it2;
    62. ++j;
    63. }
    64. QGraphicsItem::mouseReleaseEvent(event);
    65. _mf->updateScene(idxIndiv);
    66.  
    67. }
    68.  
    69. QVariant Vertex::itemChange(GraphicsItemChange change, const QVariant &value){
    70.  
    71. if (change == ItemPositionChange && scene()) {
    72. // value is the new position.
    73. QPointF newPos = value.toPointF();
    74. QRectF rect = scene()->sceneRect();
    75. // find out which element of chromosome it is (-> index of Vertex)
    76. qDebug() << "index of Vertex: " << this->index;
    77. unsigned idxChrom = this->index;
    78. // find out which individual it is
    79.  
    80. QVector<QGraphicsScene *> scenesPhen = _mf->getScenes();
    81. QVector<QGraphicsScene *>::iterator it2 = scenesPhen.begin();
    82. unsigned j=0;
    83. unsigned idxIndiv = 0;
    84. while (it2 != scenesPhen.end()) {
    85. //cout << "(*it2): " << (*it2) << "\t\t scene(): "<< this->scene()<< endl;
    86. if((*it2) == scene()){
    87. qDebug() << "index of scene: " << j;
    88. idxIndiv = j;
    89. }
    90. ++it2;
    91. ++j;
    92. }
    93. // if the point will be moved out of scene, its position will be set to the max size of scene
    94. if (!rect.contains(newPos)) {
    95. // Keep the item inside the scene rect.
    96. newPos.setX(qMin(rect.right(), qMax(newPos.x(), rect.left())));
    97. newPos.setY(qMin(rect.bottom(), qMax(newPos.y(), rect.top())));
    98. return newPos;
    99. }
    100.  
    101. // update the corresponding chromosome
    102. qDebug() << "newPos = " << newPos;
    103. _mf->updateChromosome(newPos, idxChrom, idxIndiv);
    104.  
    105. }
    106. return QGraphicsItem::itemChange(change, value);
    107. }
    To copy to clipboard, switch view to plain text mode 

  5. #5
    Join Date
    Nov 2009
    Posts
    94
    Thanks
    14
    Thanked 1 Time in 1 Post
    Qt products
    Qt4
    Platforms
    Unix/X11

    Question Re: move/drag points on qwt plot

    Hello,

    I'm still trying to get the by me generated QwtPlotMarkers dragged on the plot (to change their x, y coordinates and replot it). I'm using the Spectrogram example and try to use the canvaspicker files from event_filter example, but then there is a conflict of mouse events between zoomer (spectrogram) and selection (even_filter), so that if I use the canvas picker, I cannot use the zoom function anymore. This is the first problem...

    The second problem is the fact, that wthin the function "select" of canvaspicker, my QwtPlotMarker is detected correctly and I also can set the new coordinates to it, but the plot shows the same picture and the item is not moved however. Why? Please help me by providing some code snippets, which could be helpful in my case.

    Thank you.

    canvaspicker.cpp
    Qt Code:
    1. #include <qapplication.h>
    2. #include <qevent.h>
    3. #include <qwhatsthis.h>
    4. #include <qpainter.h>
    5. #include <qwt_plot.h>
    6. #include <qwt_symbol.h>
    7. #include <qwt_scale_map.h>
    8. #include <qwt_plot_canvas.h>
    9. #include <qwt_plot_curve.h>
    10. #include <qwt_plot_marker.h>
    11. #include "canvaspicker.h"
    12. #include <iostream>
    13. #include "point.h"
    14.  
    15. CanvasPicker::CanvasPicker(QwtPlot *plot):
    16. QObject(plot),
    17. d_selectedMarker(NULL),
    18. d_selectedPoint(-1)
    19. {
    20. QwtPlotCanvas *canvas = plot->canvas();
    21.  
    22. canvas->installEventFilter(this);
    23.  
    24. // We want the focus, but no focus rect. The
    25. // selected point will be highlighted instead.
    26.  
    27. #if QT_VERSION >= 0x040000
    28. canvas->setFocusPolicy(Qt::StrongFocus);
    29. #ifndef QT_NO_CURSOR
    30. canvas->setCursor(Qt::PointingHandCursor);
    31. #endif
    32. #else
    33. canvas->setFocusPolicy(QWidget::StrongFocus);
    34. #ifndef QT_NO_CURSOR
    35. canvas->setCursor(Qt::pointingHandCursor);
    36. #endif
    37. #endif
    38. canvas->setFocusIndicator(QwtPlotCanvas::ItemFocusIndicator);
    39. canvas->setFocus();
    40.  
    41. shiftCurveCursor(true);
    42. }
    43.  
    44. bool CanvasPicker::event(QEvent *e)
    45. {
    46. if ( e->type() == QEvent::User )
    47. {
    48. showCursor(true);
    49. return true;
    50. }
    51. return QObject::event(e);
    52. }
    53.  
    54. bool CanvasPicker::eventFilter(QObject *object, QEvent *e)
    55. {
    56. std::cout << "in CanvasPicker::eventFilter \n" ;
    57. if ( object != (QObject *)plot()->canvas() )
    58. return false;
    59.  
    60. switch(e->type())
    61. {
    62. case QEvent::FocusIn:
    63. showCursor(true);
    64. case QEvent::FocusOut:
    65. showCursor(false);
    66.  
    67. case QEvent::Paint:
    68. {
    69. QApplication::postEvent(this, new QEvent(QEvent::User));
    70. break;
    71. }
    72. case QEvent::MouseButtonPress:
    73. {
    74. select(((QMouseEvent *)e)->pos());
    75. return true;
    76. }
    77. case QEvent::MouseMove:
    78. {
    79. move(((QMouseEvent *)e)->pos());
    80. return true;
    81. }
    82. default:
    83. break;
    84. }
    85. return QObject::eventFilter(object, e);
    86. }
    87.  
    88. // Select the point at a position. If there is no point
    89. // deselect the selected point
    90.  
    91. void CanvasPicker::select(const QPoint &pos)
    92. {
    93. std::cout << "in CanvasPicker::select \n" ;
    94. QwtPlotMarker *marker = NULL;
    95. double dist = 1;
    96. int index = -1;
    97.  
    98. const QwtPlotItemList& itmList = plot()->itemList();
    99. for ( QwtPlotItemIterator it = itmList.begin();
    100. it != itmList.end(); ++it )
    101. {
    102. std::cout << "(*it) "<< (*it) << std::endl;
    103. if ( (*it)->rtti() == QwtPlotItem::Rtti_PlotMarker )
    104. {
    105. QwtPlotMarker *mark = ((QwtPlotMarker*)(*it));
    106. showCursor(true);
    107. double x_t = plot()->invTransform(mark->xAxis(), pos.x());
    108. double y_t = plot()->invTransform(mark->yAxis(), pos.y());
    109. std::cout << "x_t: " <<x_t<< "y_t: "<< y_t << std::endl;
    110. double d = pow(x_t-mark->xValue(),2) + pow(y_t-mark->yValue(),2);
    111. //int idx = mark->closestPoint(pos, &d);
    112. if ( d < dist )
    113. {
    114. marker = mark;
    115. // index = idx;
    116. dist = d;
    117. }
    118. }
    119. }
    120.  
    121. showCursor(false);
    122. d_selectedMarker = NULL;
    123. d_selectedPoint = -1;
    124.  
    125. if ( marker && dist < 0.1 ) // 10 pixels tolerance
    126. {
    127. d_selectedMarker = marker;
    128. std::cout << "d_selectedMarker: " << d_selectedMarker << std::endl;
    129. // d_selectedPoint = index;
    130. showCursor(true);
    131. }
    132. }
    133.  
    134. // Move the selected point
    135. void CanvasPicker::moveBy(int dx, int dy)
    136. {
    137. std::cout << "in CanvasPicker::moveBy \n" ;
    138. if ( dx == 0 && dy == 0 )
    139. return;
    140.  
    141. if ( !d_selectedMarker )
    142. return;
    143. const double x = d_selectedMarker->xValue() + dx;
    144. const double y = d_selectedMarker->yValue() + dy;
    145.  
    146. move(QPoint(x, y));
    147. }
    148.  
    149. // Move the selected point
    150. void CanvasPicker::move(const QPoint &pos)
    151. {
    152. std::cout << "in CanvasPicker::move \n" ;
    153. if ( !d_selectedMarker )
    154. return;
    155.  
    156. double xData = plot()->invTransform(d_selectedMarker->xAxis(), pos.x());;
    157. double yData = plot()->invTransform(d_selectedMarker->yAxis(), pos.y());;
    158.  
    159. std::cout << "xData: " << xData <<"yData: " << yData<< std::endl;
    160. d_selectedMarker->setXValue(xData);
    161. d_selectedMarker->setYValue(yData);
    162.  
    163. std::cout << "d_selectedMarker->xValue(): " << d_selectedMarker->xValue() <<"d_selectedMarker->yValue(): " << d_selectedMarker->yValue()<< std::endl;
    164.  
    165. PointItem *item = new PointItem(QwtDoubleRect(0.5, 0.5 , 0.0001, 0.0001));
    166. item->attach(plot());
    167.  
    168. plot()->replot();
    169. showCursor(true);
    170. }
    171.  
    172. // Hightlight the selected point
    173. void CanvasPicker::showCursor(bool showIt)
    174. {
    175. std::cout << "in CanvasPicker::showCursor \n" ;
    176. if ( !d_selectedMarker )
    177. return;
    178.  
    179. const QwtSymbol symbol = d_selectedMarker->symbol();
    180.  
    181. QwtSymbol newSymbol = symbol;
    182. if ( showIt )
    183. newSymbol.setBrush(symbol.brush().color().dark(150));
    184.  
    185. const bool doReplot = plot()->autoReplot();
    186.  
    187. plot()->setAutoReplot(false);
    188. d_selectedMarker->setSymbol(newSymbol);
    189.  
    190. //d_selectedMarker->draw(painter,const xMap,const yMap,const canvasRect) );
    191.  
    192. d_selectedMarker->setSymbol(symbol);
    193. plot()->setAutoReplot(doReplot);
    194. }
    195.  
    196. // Select the next/previous curve
    197. void CanvasPicker::shiftCurveCursor(bool up)
    198. {
    199. std::cout << "in CanvasPicker::shiftPointCursor \n" ;
    200. QwtPlotItemIterator it;
    201.  
    202. const QwtPlotItemList &itemList = plot()->itemList();
    203.  
    204. QwtPlotItemList markerList;
    205. for ( it = itemList.begin(); it != itemList.end(); ++it )
    206. {
    207. if ( (*it)->rtti() == QwtPlotItem::Rtti_PlotMarker )
    208. markerList += *it;
    209. }
    210. if ( markerList.isEmpty() )
    211. return;
    212.  
    213. it = markerList.begin();
    214.  
    215. if ( d_selectedMarker )
    216. {
    217. for ( it = markerList.begin(); it != markerList.end(); ++it )
    218. {
    219. if ( d_selectedMarker == *it )
    220. break;
    221. }
    222. if ( it == markerList.end() ) // not found
    223. it = markerList.begin();
    224.  
    225. if ( up )
    226. {
    227. ++it;
    228. if ( it == markerList.end() )
    229. it = markerList.begin();
    230. }
    231. else
    232. {
    233. if ( it == markerList.begin() )
    234. it = markerList.end();
    235. --it;
    236. }
    237. }
    238.  
    239. showCursor(false);
    240. d_selectedPoint = 0;
    241. d_selectedMarker = (QwtPlotMarker *)*it;
    242. showCursor(true);
    243. }
    244.  
    245. // Select the next/previous neighbour of the selected point
    246. void CanvasPicker::shiftPointCursor(bool up)
    247. {
    248. if ( !d_selectedMarker )
    249. return;
    250. std::cout << "in CanvasPicker::shiftPointCursor \n" ;
    251. }
    To copy to clipboard, switch view to plain text mode 

    the point, I want to move:

    point.h
    Qt Code:
    1. #include <qpainter.h>
    2. #include <qwt_plot_grid.h>
    3. #include <qwt_plot_canvas.h>
    4. #include <qwt_plot_layout.h>
    5. #include <qwt_double_interval.h>
    6. #include <qwt_painter.h>
    7. #include <qwt_plot_item.h>
    8. #include <qwt_plot_marker.h>
    9. #include <stdlib.h>
    10.  
    11. class PointItem: public QObject, public QwtPlotMarker
    12. {
    13. Q_OBJECT
    14.  
    15. public:
    16.  
    17. PointItem(QwtDoubleRect rect);
    18.  
    19.  
    20. QwtDoubleRect boundingRect() const;
    21.  
    22. void draw(QPainter *painter,
    23. const QwtScaleMap &xMap, const QwtScaleMap &yMap, const QRect &) const;
    24. protected:
    25. virtual void itemChanged();
    26.  
    27. private:
    28. QwtDoubleRect d_rect;
    29. };
    To copy to clipboard, switch view to plain text mode 

    point.cpp
    Qt Code:
    1. #include "point.h"
    2. #include <iostream>
    3.  
    4. PointItem::PointItem(QwtDoubleRect rect):d_rect(rect){
    5. //setZ(20);
    6. }
    7.  
    8. QwtDoubleRect PointItem::boundingRect() const{
    9. return d_rect;
    10. }
    11.  
    12. void PointItem::itemChanged(){
    13. std::cout << "in ItemChanged() \n";
    14. }
    15.  
    16. void PointItem::draw(QPainter *painter,
    17. const QwtScaleMap &xMap, const QwtScaleMap &yMap, const QRect &) const
    18. {
    19. if ( d_rect.isValid() )
    20. {
    21. const QRect rect = transform(xMap, yMap, d_rect);
    22. painter->setPen(QColor(Qt::black));
    23. painter->setBrush(QBrush(QColor(Qt::white)));
    24. QwtPainter::drawEllipse(painter, rect);
    25. }
    26. }
    To copy to clipboard, switch view to plain text mode 

  6. #6
    Join Date
    Nov 2009
    Posts
    94
    Thanks
    14
    Thanked 1 Time in 1 Post
    Qt products
    Qt4
    Platforms
    Unix/X11

    Default Re: move/drag points on qwt plot

    Hello,

    the problem is still there. Could someone help me please? Thank you.

    regards

Similar Threads

  1. Help understanding QWT Contour Plot
    By jwieland in forum Qwt
    Replies: 11
    Last Post: 7th December 2009, 06:47
  2. Labeling scatter plot points
    By hamid ghous in forum Qwt
    Replies: 1
    Last Post: 29th October 2009, 06:35
  3. Plotting specific points with qwt
    By byb810 in forum Qwt
    Replies: 0
    Last Post: 30th July 2009, 15:42
  4. legend inside qwt plot
    By kaustav98255 in forum Qwt
    Replies: 5
    Last Post: 11th February 2009, 20:39
  5. Replies: 1
    Last Post: 2nd October 2008, 07:29

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  
Digia, Qt and their respective logos are trademarks of Digia Plc in Finland and/or other countries worldwide.