Problem with graph drawing
-
Hello, Qt Community!
I am creating a graph/automata drawing tool with QGraphicsView framework. Lately I've been working around a geometrical problem that I just can't solve by myself. I need to draw oriented edges and arcs (edges are strigt lines, while arcs are curved splines). I use QGraphicsLineItem objects and QGraphicsPolygonItem to represent an edge and its arrow; for the arcs I use QGraphicsPathItem objects. What happens is that, since transitions (both, edges and arcs) are always oriented (that is, the arrow is always pointing) to the center of the node's items, I need to solve two problems.
First of all, the arrow position (and the edge's tip point too) should have an offset accordingly to the shape of the node. The arrow should be fixed to the outer point of the node's graphical object. The problem is that nodes may have arbitrary shapes and dimensions so I can't just define a fixed offset. I have to find a way to get an intersection point of the node's shape and the edge's line. It seems that the Qt documentation has no explicit technique to do that. So I'm asking your help...
The second problem rises from the first one. When a arc is added to a node, the end point is the node's center point. So the spline drawing is oriented to that point. If I change the fixing point to the outer point on the node's shape (that I describe in the first question) the rendering of the spline will also be affected (I use the path.quadTo(const QPointF & c, const QPointF & endPoint) method to draw the spline). So my question is: how can I keep the spline's orientation to the node's center point, but draw it only to the fixing point on the node's shape? And thus place the arrow to that fixing point.
Thanks in advance for your attention.
-
Hi,
Could you please share with me the code to create a Arrow Graphics Item? I believe it should be a subclass of QGraphicsLineItem. I'm a beginner in graphics concepts, hence need your help.
-
Hi!
I used PyQt4 in the project I describe above (http://guitar.odis.io), but the translation to Qt5/C++ should be really straightforward.
Here is the minimal version of a class that you can use to draw an arrow that can be updated given a tip point and an angle:
Hope it helps.
Cheers! -
Almost forgot!
If you want to have the arrow to be attached to a line, you should use QGraphicsItemGroup and add both, the arrow item and the line item to it.If something is not clear, let me know, I'll show you some sample code.
-
Hi,
bq. First of all, the arrow position (and the edge’s tip point too) should have an offset accordingly to the shape of the node. The arrow should be fixed to the outer point of the node’s graphical object. The problem is that nodes may have arbitrary shapes and dimensions so I can’t just define a fixed offset. I have to find a way to get an intersection point of the node’s shape and the edge’s line. It seems that the Qt documentation has no explicit technique to do that. So I’m asking your help…
just an idea: I think it can be used
@QPointF QPainterPath::pointAtPercent(qreal t)@to move through the path's points and for each one compute the angle between the lines returned point-node's center and the edge: if it is zero or close enough to zero then the edge's arrow head should be moved to that point ...
-
to Rlzo Isrof - Thank you for your response. I used the arrow creation code given in diagramview example of Qt. the arrow creation is similar to the one in your code.
Although i find it difficult to understand the arrow points calculation, the math is going over my head :-), the trignometry used to calculate the arrow points is above my understanding. Did you actually understand the calculations in below code?
@p1 = fp +
QPointF(math.sin(angle + math.pi + math.pi/3) * self.size,
math.cos(angle + math.pi + math.pi/3) * self.size)p2 = fp + \ QPointF(math.sin(angle - math.pi/3) * self.size, math.cos(angle - math.pi/3) * self.size)@