[qet] qet/qet: [5436] QETshapeItem rectangle can have rounded corner.

[ Thread Index | Date Index | More lists.tuxfamily.org/qet Archives ]


Revision: 5436
Author:   blacksun
Date:     2018-07-12 12:01:34 +0200 (Thu, 12 Jul 2018)
Log Message:
-----------
QETshapeItem rectangle can have rounded corner.

Modified Paths:
--------------
    trunk/sources/QetGraphicsItemModeler/qetgraphicshandlerutility.cpp
    trunk/sources/QetGraphicsItemModeler/qetgraphicshandlerutility.h
    trunk/sources/diagramevent/diagrameventaddshape.cpp
    trunk/sources/qetgraphicsitem/qetshapeitem.cpp
    trunk/sources/qetgraphicsitem/qetshapeitem.h

Modified: trunk/sources/QetGraphicsItemModeler/qetgraphicshandlerutility.cpp
===================================================================
--- trunk/sources/QetGraphicsItemModeler/qetgraphicshandlerutility.cpp	2018-07-11 09:28:38 UTC (rev 5435)
+++ trunk/sources/QetGraphicsItemModeler/qetgraphicshandlerutility.cpp	2018-07-12 10:01:34 UTC (rev 5436)
@@ -16,8 +16,6 @@
 	along with QElectroTech.  If not, see <http://www.gnu.org/licenses/>.
 */
 #include "qetgraphicshandlerutility.h"
-//#include <QVector>
-//#include <QPointF>
 #include <QPainterPath>
 
 
@@ -241,3 +239,80 @@
 	polygon.insert(index, pos);
 	return polygon;
 }
+
+/**
+ * @brief QetGraphicsHandlerUtility::pointForRadiusRect
+ * @param rect the rectangle.
+ * @param xRadius : x radius
+ * @param yRadius : y radius
+ * @param mode : absolute or relative size: NOTE this argument is not used, this function always compute with relative size.
+ * @return the points of x and y radius of a rounded rect.
+ * The points are always based on the top right corner of the rect.
+ * the first point of vector is X the second Y
+ */
+#include <QDebug>
+QVector<QPointF> QetGraphicsHandlerUtility::pointForRadiusRect(const QRectF &rect, qreal xRadius, qreal yRadius, Qt::SizeMode mode)
+{
+	Q_UNUSED(mode)
+	QVector<QPointF> v;
+	
+	qreal half_width = rect.width()/2;
+	qreal x_percent = std::min(xRadius, 100.00)/100;
+	QPointF X(rect.right() - half_width*x_percent,
+			  rect.top());
+	v << X;
+	
+	qreal half_height = rect.height()/2;
+	qreal y_percent = std::min(yRadius, 100.00)/100;
+	QPointF Y(rect.right(),
+			  rect.top()+ half_height*y_percent);
+	v << Y;
+	
+	return v;
+}
+
+/**
+ * @brief QetGraphicsHandlerUtility::radiusForPosAtIndex
+ * @param rect the rectangle
+ * @param pos : the pos of the new radius
+ * @param index : index of radius  0=X 1=Y
+ * @param mode
+ * @return 
+ */
+qreal QetGraphicsHandlerUtility::radiusForPosAtIndex(const QRectF &rect, const QPointF &pos, int index, Qt::SizeMode mode)
+{
+	Q_UNUSED(mode)
+	
+	if(index == 0) //X
+	{
+		if (pos.x() < rect.center().x()) {
+			return 100;
+		}
+		else if (pos.x() > rect.right()) {
+			return 0;
+		}
+		else {
+			return (100 - percentageInRange(rect.center().x(), rect.right(), pos.x()));
+		}
+	}
+	else if (index == 1) //Y
+	{
+		if (pos.y() < rect.top()) {
+			return 0;
+		}
+		else if (pos.y() > rect.center().y()) {
+			return 100;
+		}
+		else {
+			return percentageInRange(rect.top(), rect.center().y(), pos.y());
+		}
+	}
+	else {
+		return 0;
+	}
+}
+
+qreal QetGraphicsHandlerUtility::percentageInRange(qreal min, qreal max, qreal value) {
+	return ((value - min) * 100) / (max - min);
+}
+

Modified: trunk/sources/QetGraphicsItemModeler/qetgraphicshandlerutility.h
===================================================================
--- trunk/sources/QetGraphicsItemModeler/qetgraphicshandlerutility.h	2018-07-11 09:28:38 UTC (rev 5435)
+++ trunk/sources/QetGraphicsItemModeler/qetgraphicshandlerutility.h	2018-07-12 10:01:34 UTC (rev 5436)
@@ -41,6 +41,9 @@
 		static QRectF mirrorRectForPosAtIndex (const QRectF &old_rect, const QPointF &pos, int index);
 		static QLineF lineForPosAtIndex (const QLineF &old_line, const QPointF &pos, int index);
 		static QPolygonF polygonForInsertPoint(const QPolygonF &old_polygon, bool closed, const QPointF &pos);
+		static QVector <QPointF> pointForRadiusRect (const QRectF &rect, qreal xRadius, qreal yRadius, Qt::SizeMode mode = Qt::AbsoluteSize);
+		static qreal radiusForPosAtIndex (const QRectF &rect, const QPointF &pos, int index, Qt::SizeMode mode = Qt::AbsoluteSize);
+		static qreal percentageInRange(qreal min, qreal max, qreal value);
 };
 
 #endif // QETGRAPHICSHANDLERUTILITY_H

Modified: trunk/sources/diagramevent/diagrameventaddshape.cpp
===================================================================
--- trunk/sources/diagramevent/diagrameventaddshape.cpp	2018-07-11 09:28:38 UTC (rev 5435)
+++ trunk/sources/diagramevent/diagrameventaddshape.cpp	2018-07-12 10:01:34 UTC (rev 5436)
@@ -82,6 +82,9 @@
 		if (m_shape_type != QetShapeItem::Polygon)
 		{
 			m_shape_item->setP2 (pos);
+			if(m_shape_item->shapeType() == QetShapeItem::Rectangle || m_shape_item->shapeType() == QetShapeItem::Ellipse) {
+				m_shape_item->setRect(m_shape_item->rect().normalized());
+			}
 			m_diagram->undoStack().push (new AddItemCommand<QetShapeItem *> (m_shape_item, m_diagram));
 			m_shape_item = nullptr; //< set to nullptr for create new shape at next left clic
 		}

Modified: trunk/sources/qetgraphicsitem/qetshapeitem.cpp
===================================================================
--- trunk/sources/qetgraphicsitem/qetshapeitem.cpp	2018-07-11 09:28:38 UTC (rev 5435)
+++ trunk/sources/qetgraphicsitem/qetshapeitem.cpp	2018-07-12 10:01:34 UTC (rev 5436)
@@ -159,7 +159,9 @@
  */
 bool QetShapeItem::setPolygon(const QPolygonF &polygon)
 {
-	if (Q_UNLIKELY(m_shapeType != Polygon)) return false;
+	if (Q_UNLIKELY(m_shapeType != Polygon)) {
+		return false;
+	}
 	prepareGeometryChange();
 	m_polygon = polygon;
 	adjusteHandlerPos();
@@ -181,6 +183,22 @@
 	}
 }
 
+void QetShapeItem::setXRadius(qreal X)
+{
+	m_xRadius = X;
+	update();
+	adjusteHandlerPos();
+	emit XRadiusChanged();
+}
+
+void QetShapeItem::setYRadius(qreal Y)
+{
+	m_yRadius = Y;
+	update();
+	adjusteHandlerPos();
+	emit YRadiusChanged();
+}
+
 /**
  * @brief QetShapeItem::pointCount
  * @return the number of point in the polygon
@@ -246,7 +264,7 @@
 			path.lineTo(m_P2);                   
 			break;
 		case Rectangle: 
-			path.addRect(QRectF(m_P1, m_P2));
+			path.addRoundedRect(QRectF(m_P1, m_P2), m_xRadius, m_yRadius, Qt::RelativeSize);
 			break;
 		case Ellipse:
 			path.addEllipse(QRectF(m_P1, m_P2));
@@ -301,7 +319,7 @@
     switch (m_shapeType)
     {
         case Line:      painter->drawLine(QLineF(m_P1, m_P2)); break;
-        case Rectangle: painter->drawRect(QRectF(m_P1, m_P2)); break;
+        case Rectangle: painter->drawRoundedRect(QRectF(m_P1, m_P2), m_xRadius, m_yRadius, Qt::RelativeSize); break;
         case Ellipse:   painter->drawEllipse(QRectF(m_P1, m_P2)); break;
         case Polygon:   m_closed ? painter->drawPolygon(m_polygon) : painter->drawPolyline(m_polygon); break;
     }
@@ -331,17 +349,16 @@
 	QetGraphicsItem::hoverLeaveEvent(event);
 }
 
-/**
- * @brief QetShapeItem::mouseReleaseEvent
- * Handle mouse release event
- * @param event
- */
-void QetShapeItem::mouseReleaseEvent(QGraphicsSceneMouseEvent *event)
+void QetShapeItem::mousePressEvent(QGraphicsSceneMouseEvent *event)
 {
-	if (event->buttonDownPos(Qt::LeftButton) == event->pos())
+	event->ignore();
+	if (event->button() == Qt::LeftButton) {
 		switchResizeMode();
-
-    QetGraphicsItem::mouseReleaseEvent(event);
+		event->accept();
+	}
+	else {
+		QetGraphicsItem::mousePressEvent(event);
+	}
 }
 
 /**
@@ -364,10 +381,10 @@
                 qDeleteAll(m_handler_vector);
                 m_handler_vector.clear();
             }
+			m_resize_mode = 1;
         }
     }
-    else if (change == ItemPositionHasChanged)
-    {
+    else if (change == ItemPositionHasChanged) {
 		adjusteHandlerPos();
     }
 	else if (change == ItemSceneHasChanged)
@@ -485,19 +502,51 @@
  */
 void QetShapeItem::switchResizeMode()
 {
-	if (m_shapeType & (Rectangle | Ellipse))
+	if (m_shapeType == Ellipse)
 	{
 		if (m_resize_mode == 1)
 		{
 			m_resize_mode = 2;
-			for (QetGraphicsHandlerItem *qghi : m_handler_vector)
+			for (QetGraphicsHandlerItem *qghi : m_handler_vector) {
 				qghi->setColor(Qt::darkGreen);
+			}
 		}
 		else
 		{
 			m_resize_mode = 1;
+			for (QetGraphicsHandlerItem *qghi : m_handler_vector) {
+				qghi->setColor(Qt::blue);
+			}
+		}
+	}
+	else if (m_shapeType == Rectangle)
+	{
+		if (m_resize_mode == 1)
+		{
+			m_resize_mode = 2;
 			for (QetGraphicsHandlerItem *qghi : m_handler_vector)
+				qghi->setColor(Qt::darkGreen);
+		}
+		else if (m_resize_mode == 2)
+		{
+			m_resize_mode = 3;
+			qDeleteAll(m_handler_vector);
+			m_handler_vector.clear();
+			addHandler();
+			for (QetGraphicsHandlerItem *qghi : m_handler_vector) {
+				qghi->setColor(Qt::magenta);
+			}
+		}
+		else if (m_resize_mode == 3)
+		{
+			m_resize_mode = 1;
+			qDeleteAll(m_handler_vector);
+			m_handler_vector.clear();
+			addHandler();
+			for (QetGraphicsHandlerItem *qghi : m_handler_vector) {
 				qghi->setColor(Qt::blue);
+			}
+			
 		}
 	}
 }
@@ -509,10 +558,23 @@
 		QVector <QPointF> points_vector;
 		switch (m_shapeType)
 		{
-			case Line:      points_vector << m_P1 << m_P2; break;
-			case Rectangle: points_vector = QetGraphicsHandlerUtility::pointsForRect(QRectF(m_P1, m_P2)); break;
-			case Ellipse:   points_vector = QetGraphicsHandlerUtility::pointsForRect(QRectF(m_P1, m_P2)); break;
-			case Polygon:   points_vector = m_polygon; break;
+			case Line:
+				points_vector << m_P1 << m_P2;
+				break;
+			case Rectangle:
+				if (m_resize_mode == 3) {
+					points_vector = QetGraphicsHandlerUtility::pointForRadiusRect(QRectF(m_P1, m_P2), m_xRadius, m_yRadius);
+				}
+				else {
+					points_vector = QetGraphicsHandlerUtility::pointsForRect(QRectF(m_P1, m_P2));
+				}
+				break;
+			case Ellipse:
+				points_vector = QetGraphicsHandlerUtility::pointsForRect(QRectF(m_P1, m_P2));
+				break;
+			case Polygon:
+				points_vector = m_polygon;
+				break;
 		}
 		
 		if(!points_vector.isEmpty() && scene())
@@ -536,13 +598,34 @@
  */
 void QetShapeItem::adjusteHandlerPos()
 {
+	if (m_handler_vector.isEmpty()) {
+		return;
+	}
+	
 	QVector <QPointF> points_vector;
 	switch (m_shapeType)
 	{
-		case Line:      points_vector << m_P1 << m_P2; break;
-		case Rectangle: points_vector = QetGraphicsHandlerUtility::pointsForRect(QRectF(m_P1, m_P2)); break;
-		case Ellipse:   points_vector = QetGraphicsHandlerUtility::pointsForRect(QRectF(m_P1, m_P2)); break;
-		case Polygon:   points_vector = m_polygon; break;
+		case Line: {
+			points_vector << m_P1 << m_P2;
+			break;
+		}
+		case Rectangle: {
+			if (m_resize_mode != 3) {
+				points_vector = QetGraphicsHandlerUtility::pointsForRect(QRectF(m_P1, m_P2));
+			}
+			else {
+				points_vector = QetGraphicsHandlerUtility::pointForRadiusRect(QRectF(m_P1, m_P2), m_xRadius, m_yRadius);
+			}
+			break;
+		}
+		case Ellipse: {
+			points_vector = QetGraphicsHandlerUtility::pointsForRect(QRectF(m_P1, m_P2));
+			break;
+		}
+		case Polygon: {
+			points_vector = m_polygon;
+			break;
+		}
 	}
 	
 	if (m_handler_vector.size() == points_vector.size())
@@ -621,6 +704,11 @@
 	m_old_P1 = m_P1;
 	m_old_P2 = m_P2;
 	m_old_polygon = m_polygon;
+	m_old_xRadius = m_xRadius;
+	m_old_yRadius = m_yRadius;
+	if(m_xRadius == 0 && m_yRadius == 0) {
+		m_modifie_radius_equaly = true;
+	}
 }
 
 /**
@@ -650,10 +738,25 @@
 				setRect(QetGraphicsHandlerUtility::rectForPosAtIndex(QRectF(m_P1, m_P2), new_pos, m_vector_index));
 				break;
 			}
-			else {
+			else if (m_resize_mode == 2) {
 				setRect(QetGraphicsHandlerUtility::mirrorRectForPosAtIndex(QRectF(m_P1, m_P2), new_pos, m_vector_index));
 				break;
 			}
+			else {
+				qreal radius = QetGraphicsHandlerUtility::radiusForPosAtIndex(QRectF(m_P1, m_P2), new_pos, m_vector_index);
+				if(m_modifie_radius_equaly) {
+					setXRadius(radius);
+					setYRadius(radius);
+				}
+				else if(m_vector_index == 0) {
+					setXRadius(radius);
+				}
+				else {
+					setYRadius(radius);
+				}
+				adjusteHandlerPos();
+				break;
+			}
 		case Ellipse:
 			if (m_resize_mode == 1) {
 				setRect(QetGraphicsHandlerUtility::rectForPosAtIndex(QRectF(m_P1, m_P2), new_pos, m_vector_index));
@@ -682,19 +785,42 @@
 	Q_UNUSED(qghi);
 	Q_UNUSED(event);
 	
+	m_modifie_radius_equaly = false;
+	
 	if (diagram())
 	{
 		QPropertyUndoCommand *undo = nullptr;
-		if ((m_shapeType & (Line | Rectangle | Ellipse)) && (m_P1 != m_old_P1 || m_P2 != m_old_P2))
+		if ((m_shapeType & (Line | Rectangle | Ellipse)) && ((m_P1 != m_old_P1 || m_P2 != m_old_P2) ||
+															 (m_old_xRadius != XRadius() || m_old_yRadius != m_yRadius))
+			)
 		{
 			switch(m_shapeType)
 			{
-				case Line:      undo = new QPropertyUndoCommand(this, "line",QLineF(m_old_P1, m_old_P2), QLineF(m_P1, m_P2)); break;
-				case Rectangle: undo = new QPropertyUndoCommand(this, "rect",QRectF(m_old_P1, m_old_P2), QRectF(m_P1, m_P2)); break;
-				case Ellipse:   undo = new QPropertyUndoCommand(this, "rect",QRectF(m_old_P1, m_old_P2), QRectF(m_P1, m_P2)); break;
+				case Line: {
+					undo = new QPropertyUndoCommand(this, "line",QLineF(m_old_P1, m_old_P2), QLineF(m_P1, m_P2));
+					break;
+				}
+				case Rectangle: {
+					if (m_resize_mode == 1 || m_resize_mode == 2) {
+						undo = new QPropertyUndoCommand(this, "rect",QRectF(m_old_P1, m_old_P2), QRectF(m_P1, m_P2).normalized());
+					}
+					else if (m_resize_mode == 3)
+					{
+						undo = new QPropertyUndoCommand(this, "xRadius", m_old_xRadius, m_xRadius);
+						QPropertyUndoCommand *undo_ = new QPropertyUndoCommand(this, "yRadius", m_old_yRadius, m_yRadius, undo);
+						undo_->setAnimated();
+					}
+					break;
+				}
+				case Ellipse: {
+					undo = new QPropertyUndoCommand(this, "rect",QRectF(m_old_P1, m_old_P2), QRectF(m_P1, m_P2).normalized());
+					break;
+				}
 				case Polygon: break;
 			}
-			if (undo) undo->enableAnimation();
+			if (undo) {
+				undo->setAnimated(true, false);
+			}
 		}
 		else if (m_shapeType == Polygon && (m_polygon != m_old_polygon))
 			undo = new QPropertyUndoCommand(this, "polygon", m_old_polygon, m_polygon);

Modified: trunk/sources/qetgraphicsitem/qetshapeitem.h
===================================================================
--- trunk/sources/qetgraphicsitem/qetshapeitem.h	2018-07-11 09:28:38 UTC (rev 5435)
+++ trunk/sources/qetgraphicsitem/qetshapeitem.h	2018-07-12 10:01:34 UTC (rev 5436)
@@ -36,18 +36,23 @@
 {
 	Q_OBJECT
 
-		Q_PROPERTY(QPen pen READ pen WRITE setPen NOTIFY penChanged)
-		Q_PROPERTY(QBrush brush READ brush WRITE setBrush NOTIFY brushChanged)
-		Q_PROPERTY(QRectF rect READ rect WRITE setRect)
-		Q_PROPERTY(QLineF line READ line WRITE setLine)
-		Q_PROPERTY(QPolygonF polygon READ polygon WRITE setPolygon)
-		Q_PROPERTY(bool close READ isClosed WRITE setClosed NOTIFY closeChanged)
+	Q_PROPERTY(QPen pen READ pen WRITE setPen NOTIFY penChanged)
+	Q_PROPERTY(QBrush brush READ brush WRITE setBrush NOTIFY brushChanged)
+	Q_PROPERTY(QRectF rect READ rect WRITE setRect)
+	Q_PROPERTY(QLineF line READ line WRITE setLine)
+	Q_PROPERTY(QPolygonF polygon READ polygon WRITE setPolygon)
+	Q_PROPERTY(bool close READ isClosed WRITE setClosed NOTIFY closeChanged)
+	Q_PROPERTY(qreal xRadius READ XRadius WRITE setXRadius NOTIFY XRadiusChanged)
+	Q_PROPERTY(qreal yRadius READ YRadius WRITE setYRadius NOTIFY YRadiusChanged)
 
 	signals:
 		void penChanged();
 		void brushChanged();
 		void closeChanged();
-
+		void XRadiusChanged();
+		void YRadiusChanged();
+		
+		
 	public:
 		Q_ENUMS(ShapeType)
 		enum ShapeType {Line	  =1,
@@ -86,6 +91,10 @@
 		bool setPolygon (const QPolygonF &polygon);
 		bool isClosed() const {return m_closed;}
 		void setClosed (bool close);
+		qreal XRadius() const {return m_xRadius;}
+		void setXRadius(qreal X);
+		qreal YRadius() const {return m_yRadius;}
+		void setYRadius(qreal Y);
 
 			//Methods available for polygon shape
 		int  pointsCount  () const;
@@ -99,7 +108,7 @@
 		void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) override;
 		void hoverEnterEvent   (QGraphicsSceneHoverEvent *event) override;
 		void hoverLeaveEvent   (QGraphicsSceneHoverEvent *event) override;
-		void mouseReleaseEvent (QGraphicsSceneMouseEvent *event) override;
+		void mousePressEvent   (QGraphicsSceneMouseEvent *event) override;
         QVariant itemChange(GraphicsItemChange change, const QVariant &value) override;
         bool sceneEventFilter(QGraphicsItem *watched, QEvent *event) override;
 		void contextMenuEvent(QGraphicsSceneContextMenuEvent *event) override;
@@ -128,10 +137,15 @@
 		QPolygonF	 m_polygon, m_old_polygon;
 		bool		 m_hovered;
 		int			 m_vector_index;
-		bool m_closed = false;
+		bool m_closed = false,
+			 m_modifie_radius_equaly = false;
 		int m_resize_mode = 1;
         QVector<QetGraphicsHandlerItem *> m_handler_vector;
 		QAction *m_insert_point,
 				*m_remove_point;
+		qreal m_xRadius = 0,
+			  m_yRadius = 0,
+			  m_old_xRadius,
+			  m_old_yRadius;
 };
 #endif // QETSHAPEITEM_H


Mail converted by MHonArc 2.6.19+ http://listengine.tuxfamily.org/