Я использовал этот код для реализации изменения размера в моих QGraphicsRectItem и QGraphicsEllipseItem, так как Rect и Ellipse реализовали функцию SetRect (qreal x, qreal y, qreal width, qreal height), это не было проблемой, но с QGraphicsPolygonItem ближайшим Функция setPolygon (), но она принимает только QPolygonf & Polygon в качестве параметра, который не работает с моим кодом sizeGripItem
mainwindow. cpp
class RectResizer : public SizeGripItem::Resizer // resize class for rectagle
{
public:
virtual void operator()(QGraphicsItem* item, const QRectF& rect)
{
QGraphicsRectItem* rectItem =
dynamic_cast<QGraphicsRectItem*>(item);
if (rectItem)
{
rectItem->setRect(rect);
}
}
};
class EllipseResizer : public SizeGripItem::Resizer //resize class for ellipse
{
public:
virtual void operator()(QGraphicsItem* item, const QRectF& rect)
{
QGraphicsEllipseItem* ellipseItem =
dynamic_cast<QGraphicsEllipseItem*>(item);
if (ellipseItem)
{
ellipseItem->setRect(rect);
}
}
};
class PolygonResizer : public SizeGripItem::Resizer // resize class for polygon
{
public:
virtual void operator()(QGraphicsItem* item, const QRectF& rect)
{
QGraphicsPolygonItem* polygonItem =
dynamic_cast<QGraphicsPolygonItem*>(item);
if (polygonItem)
{
polygonItem->setPolygon(rect);
} //^ doesn't work when i attempt to resize shape, it changes to rectangle
}
};
sizegripitem. cpp
#include "sizegripitem.h"
#include <QBrush>
SizeGripItem::HandleItem::HandleItem(int positionFlags, SizeGripItem* parent)
: QGraphicsRectItem(-4, -4, 8, 8, parent),
positionFlags_(positionFlags),
parent_(parent)
{
setBrush(QBrush(Qt::lightGray));
setFlag(ItemIsMovable);
setFlag(ItemSendsGeometryChanges);
}
int SizeGripItem::HandleItem::positionFlags() const
{
return positionFlags_;
}
QVariant SizeGripItem::HandleItem::itemChange(GraphicsItemChange change,
const QVariant &value)
{
QVariant retVal = value;
if (change == ItemPositionChange)
{
retVal = restrictPosition(value.toPointF());
}
else if (change == ItemPositionHasChanged)
{
QPointF pos = value.toPointF();
switch (positionFlags_)
{
case TopLeft:
parent_->setTopLeft(pos);
break;
case Top:
parent_->setTop(pos.y());
break;
case TopRight:
parent_->setTopRight(pos);
break;
case Right:
parent_->setRight(pos.x());
break;
case BottomRight:
parent_->setBottomRight(pos);
break;
case Bottom:
parent_->setBottom(pos.y());
break;
case BottomLeft:
parent_->setBottomLeft(pos);
break;
case Left:
parent_->setLeft(pos.x());
break;
}
}
return retVal;
}
QPointF SizeGripItem::HandleItem::restrictPosition(const QPointF& newPos)
{
QPointF retVal = pos();
if (positionFlags_ & Top || positionFlags_ & Bottom)
retVal.setY(newPos.y());
if (positionFlags_ & Left || positionFlags_ & Right)
retVal.setX(newPos.x());
if (positionFlags_ & Top && retVal.y() > parent_->rect_.bottom())
retVal.setY(parent_->rect_.bottom());
else if (positionFlags_ & Bottom && retVal.y() < parent_->rect_.top())
retVal.setY(parent_->rect_.top());
if (positionFlags_ & Left && retVal.x() > parent_->rect_.right())
retVal.setX(parent_->rect_.right());
else if (positionFlags_ & Right && retVal.x() < parent_->rect_.left())
retVal.setX(parent_->rect_.left());
return retVal;
}
SizeGripItem::SizeGripItem(Resizer* resizer, QGraphicsItem* parent)
: QGraphicsItem(parent),
resizer_(resizer)
{
if (parentItem())
rect_ = parentItem()->boundingRect();
handleItems_.append(new HandleItem(TopLeft, this));
handleItems_.append(new HandleItem(Top, this));
handleItems_.append(new HandleItem(TopRight, this));
handleItems_.append(new HandleItem(Right, this));
handleItems_.append(new HandleItem(BottomRight, this));
handleItems_.append(new HandleItem(Bottom, this));
handleItems_.append(new HandleItem(BottomLeft, this));
handleItems_.append(new HandleItem(Left, this));
updateHandleItemPositions();
}
SizeGripItem::~SizeGripItem()
{
if (resizer_)
delete resizer_;
}
QRectF SizeGripItem::boundingRect() const
{
return rect_;
}
void SizeGripItem::paint(QPainter* painter,
const QStyleOptionGraphicsItem* option,
QWidget* widget)
{
}
#define IMPL_SET_FN(TYPE, POS) \
void SizeGripItem::set ## POS (TYPE v) \
{ \
rect_.set ## POS (v); \
doResize(); \
}
IMPL_SET_FN(qreal, Top)
IMPL_SET_FN(qreal, Right)
IMPL_SET_FN(qreal, Bottom)
IMPL_SET_FN(qreal, Left)
IMPL_SET_FN(const QPointF&, TopLeft)
IMPL_SET_FN(const QPointF&, TopRight)
IMPL_SET_FN(const QPointF&, BottomRight)
IMPL_SET_FN(const QPointF&, BottomLeft)
void SizeGripItem::doResize()
{
if (resizer_)
{
(*resizer_)(parentItem(), rect_);
updateHandleItemPositions();
}
}
void SizeGripItem::updateHandleItemPositions()
{
foreach (HandleItem* item, handleItems_)
{
item->setFlag(ItemSendsGeometryChanges, false);
switch (item->positionFlags())
{
case TopLeft:
item->setPos(rect_.topLeft());
break;
case Top:
item->setPos(rect_.left() + rect_.width() / 2 - 1,
rect_.top());
break;
case TopRight:
item->setPos(rect_.topRight());
break;
case Right:
item->setPos(rect_.right(),
rect_.top() + rect_.height() / 2 - 1);
break;
case BottomRight:
item->setPos(rect_.bottomRight());
break;
case Bottom:
item->setPos(rect_.left() + rect_.width() / 2 - 1,
rect_.bottom());
break;
case BottomLeft:
item->setPos(rect_.bottomLeft());
break;
case Left:
item->setPos(rect_.left(),
rect_.top() + rect_.height() / 2 - 1);
break;
}
item->setFlag(ItemSendsGeometryChanges, true);
}
}
sizegripitem.h
#ifndef SIZEGRIPITEM_H
#define SIZEGRIPITEM_H
#include <QGraphicsItem>
#include <QGraphicsRectItem>
class SizeGripItem : public QGraphicsItem
{
private:
enum
{
Top = 0x1,
Bottom = 0x2,
Left = 0x4,
TopLeft = Top | Left,
BottomLeft = Bottom | Left,
Right = 0x8,
TopRight = Top | Right,
BottomRight = Bottom | Right
};
class HandleItem : public QGraphicsRectItem
{
public:
HandleItem(int positionFlags, SizeGripItem* parent);
int positionFlags() const;
protected:
virtual QVariant itemChange(GraphicsItemChange change,
const QVariant &value);
private:
QPointF restrictPosition(const QPointF& newPos);
int positionFlags_;
SizeGripItem* parent_;
};
public:
class Resizer
{
public:
virtual void operator()(QGraphicsItem* item,
const QRectF& rect) = 0;
};
SizeGripItem(Resizer* resizer = 0, QGraphicsItem* parent = 0);
virtual ~SizeGripItem();
virtual QRectF boundingRect() const;
virtual void paint(QPainter* painter,
const QStyleOptionGraphicsItem* option,
QWidget* widget = 0);
void setTopLeft(const QPointF& pos);
void setTop(qreal y);
void setTopRight(const QPointF& pos);
void setRight(qreal x);
void setBottomRight(const QPointF& pos);
void setBottom(qreal y);
void setBottomLeft(const QPointF& pos);
void setLeft(qreal x);
private:
void doResize();
void updateHandleItemPositions();
QList<HandleItem*> handleItems_;
QRectF rect_;
Resizer* resizer_;
};
#endif // SIZEGRIPITEM_H
Я не могу придумать, как изменить размер многоугольника, поскольку библиотека пропускает множество функций, реализованных в Rect и Ellipse. Спасибо за любую помощь