Qt中鼠标移动事件时调整/缩放矩形png图像的大小
我有一个QGraphicPixmapItem,它保存一个png图像,出现在场景中 图像本身是一个矩形图像。我的要求是,当我在鼠标移动事件中调整矩形图像的大小时,我应该能够调整/缩放图像。 我可以通过拖动矩形图像的任意一侧来调整矩形的大小 问题是,我可以通过拖动矩形图像的任何一侧来调整其大小,但原始图像被严重扭曲,无法识别。图像基本上 在连续调整大小(扩展/减小宽度或高度)时变成一团固体。 如何在Qt中实现图像的大小调整/缩放,而不会对原始图像造成太大损坏?我所经历的不是幻觉,而是更糟的幻觉 下面的代码是QGraphicsPixmapItem的mouseMoveEvent()的快照,用于通过拖动矩形图像的右/左侧来调整矩形的大小Qt中鼠标移动事件时调整/缩放矩形png图像的大小,qt,png,qgraphicsitem,Qt,Png,Qgraphicsitem,我有一个QGraphicPixmapItem,它保存一个png图像,出现在场景中 图像本身是一个矩形图像。我的要求是,当我在鼠标移动事件中调整矩形图像的大小时,我应该能够调整/缩放图像。 我可以通过拖动矩形图像的任意一侧来调整矩形的大小 问题是,我可以通过拖动矩形图像的任何一侧来调整其大小,但原始图像被严重扭曲,无法识别。图像基本上 在连续调整大小(扩展/减小宽度或高度)时变成一团固体。 如何在Qt中实现图像的大小调整/缩放,而不会对原始图像造成太大损坏?我所经历的不是幻觉,而是更糟的幻觉 下面
void PersonSizeGraphicsItem::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
{
const QPointF event_pos = event->pos();
const QPointF event_scene_pos = event->scenePos();
QPixmap current_pixmap = this->pixmap();
QImage current_image = current_pixmap.toImage();
QRect current_image_rect = current_image.rect();
QPoint current_top_left = current_image_rect.topLeft();
QPoint current_bottom_right = current_image_rect.bottomRight();
if((event->scenePos().x() > this->scene()->width()) || (event->scenePos().y() > this->scene()->height())
|| (event->scenePos().x() < 0) || (event->scenePos().y() < 0) )
{
return;
}
if( this->cursor().shape() == Qt::SizeHorCursor )
{
if(rect_right_condition)
{
new_rect = QRect( current_top_left, QPoint( event->pos().x(), current_bottom_right.y()) );
scaled_pixmap = QPixmap::fromImage(current_image.scaled(QSize(new_rect.width(),new_rect.height()),Qt::IgnoreAspectRatio,Qt::FastTransformation));
setPixmap(scaled_pixmap);
}
if(rect_left_condition)
{
new_rect = QRect( QPoint(event_pos.x(), 0), current_bottom_right );
scaled_pixmap = QPixmap::fromImage(current_image.scaled(QSize(new_rect.width(),new_rect.height()),Qt::IgnoreAspectRatio,Qt::FastTransformation));
setPixmap(scaled_pixmap);
QPoint new_top_left = new_rect.topLeft();
QPointF mapped_topLeft = mapToParent(QPointF(new_top_left.x(),new_top_left.y()));
this->setPos(mapped_topLeft);
rect_resize_occurred = true;
}
}
}
void PersonSizeGraphicsItem::mouseMoveEvent(QGraphicsSceneMouseEvent*事件)
{
const QPointF event_pos=事件->pos();
const QPointF event_scene_pos=事件->场景();
QPixmap current_pixmap=this->pixmap();
QImage current_image=current_pixmap.toImage();
QRect current_image_rect=current_image.rect();
QPoint current_top_left=当前_image_rect.toplight();
QPoint current_bottom_right=当前_image_rect.bottomRight();
如果((事件->场景().x()>此->场景()->宽度())| |(事件->场景().y()>此->场景()->高度())
||(event->scenePos().x()<0)| |(event->scenePos().y()<0))
{
返回;
}
if(this->cursor().shape()==Qt::SizeHorCursor)
{
if(右向右条件)
{
new_rect=QRect(当前左上角,QPoint(事件->位置().x(),当前右下角());
scaled_pixmap=QPixmap::fromImage(当前_image.scaled(QSize(new_rect.width(),new_rect.height()),Qt::IgnoreAspectRatio,Qt::FastTransformation));
setPixmap(缩放的pixmap);
}
if(矩形左矩形条件)
{
new_rect=QRect(QPoint(事件位置x(),0),当前右下角);
scaled_pixmap=QPixmap::fromImage(当前_image.scaled(QSize(new_rect.width(),new_rect.height()),Qt::IgnoreAspectRatio,Qt::FastTransformation));
setPixmap(缩放的pixmap);
QPoint new_top_left=new_rect.toplight();
QPointF mapped_topLeft=mapToParent(QPointF(new_top_left.x(),new_top_left.y());
此->设置位置(映射到左上角);
rect_resize_occurrent=true;
}
}
}
图像在不断调整大小(扩展/减小宽度或高度)时基本上会变成一个实心块
这是正常的。你需要做的是改变你想要的效果的方法。与其不断地更改同一个图像,不如从用户期望的最大大小的源图像开始。此图像将不会被更改
在mouseMove函数中,更新成员变量以存储所显示图像的大小
然后,在PersonSizeGraphicItem的paint函数中,使用drawImage指定源图像和目标矩形,以按照mouseMoveEvent中更新的大小绘制图像:-
void QPainter::drawImage(const QRectF & rectangle, const QImage & image);
因此,通过将源图像保持在其原始大小,您不会在每次连续调整大小时对其造成越来越大的扭曲
class PersonSizeGraphicsItem : public QGraphicsItem
{
public:
PersonSizeGraphicsItem(QGraphicsItem* parent);
protected:
void mouseMoveEvent(QGraphicsSceneMouseEvent *event);
void paint(QPainter * painter, const QStyleOptionGraphicsItem * option, QWidget * widget = 0)
private:
QRectF m_imageRect;
QImage m_image;
};
void PersonSizeGraphicsItem::mouseMoveEvent()
{
// Update the image rect here
}
void PersonSizeGraphicsItem::paint(QPainter * painter, const QStyleOptionGraphicsItem *, QWidget *)
{
painter->drawImage(m_imageRect, m_image);
}
基于Merlin069的答案重新实现的代码:
PersonSizeGraphicsItem::PersonSizeGraphicsItem(const QPixmap &pixmap, QGraphicsScene *scene)
:QGraphicsPixmapItem(pixmap, 0, scene)
{
this->setFlag(QGraphicsItem::ItemIsMovable, true);
this->setFlag(QGraphicsItem::ItemIsSelectable, true);
this->setFlag(QGraphicsItem::ItemSendsGeometryChanges, true);
this->setFlag(QGraphicsItem::ItemIsFocusable, true);
this->setFocus(Qt::MouseFocusReason);
this->setAcceptHoverEvents(true);
//this->setScale(0.5);
rect_left_condition = false;
rect_right_condition = false;
rect_top_condition = false;
rect_bottom_condition = false;
rect_resize_occurred = false;
image_rect = QRect();
image_rect = this->pixmap().toImage().rect();
}
void PersonSizeGraphicsItem::setSourceImage(const QImage& source_image)
{
this->source_image = source_image;
}
void PersonSizeGraphicsItem::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
{
const QPointF event_pos = event->pos();
const QPointF event_scene_pos = event->scenePos();
QPoint current_top_left = image_rect.topLeft();
QPoint current_bottom_right = image_rect.bottomRight();
if((event->scenePos().x() > this->scene()->width()) || (event->scenePos().y() > this->scene()->height())
|| (event->scenePos().x() < 0) || (event->scenePos().y() < 0) )
{
return;
}
if( this->cursor().shape() == Qt::SizeHorCursor )
{
if(rect_right_condition)
{
image_rect = QRect( current_top_left, QPoint( event->pos().x(), current_bottom_right.y()) );
}
if(rect_left_condition)
{
image_rect = QRect( QPoint(event_pos.x(), 0), current_bottom_right);
QPoint new_top_left = image_rect.topLeft();
QPointF mapped_topLeft = mapToParent(QPointF(new_top_left.x(),new_top_left.y()));
this->setPos(mapped_topLeft);
rect_resize_occurred = true;
//qDebug() << "new rectangle top left**:" << this->pixmap().rect().topLeft();
}
}
if( this->cursor().shape() == Qt::SizeVerCursor )
{
if(rect_bottom_condition)
{
image_rect = QRect(current_top_left, QPoint(current_bottom_right.x(), event->pos().y()));
}
if(rect_top_condition)
{
image_rect = QRect(QPoint(0, event_pos.y()), current_bottom_right);
QPoint new_top_left = image_rect.topLeft();
QPointF mapped_topLeft = mapToParent(QPointF(new_top_left.x(),new_top_left.y()));
this->setPos(mapped_topLeft);
}
}
this->update();
}
void PersonSizeGraphicsItem::paint (QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget)
{
painter->drawImage(image_rect, source_image);
}
PersonSizeGraphicsItem::PersonSizeGraphicsItem(const QPixmap&pixmap,QGraphicscene*场景)
:QGraphicsPixmapItem(pixmap,0,场景)
{
此->设置标志(QGraphicsItem::ItemIsMovable,true);
此->设置标志(QGraphicsItem::ItemIsSelectable,true);
此->设置标志(QGraphicsItem::itemssendsgeometrychanges,true);
此->设置标志(QGraphicsItem::ItemIsFocusable,true);
此->设置焦点(Qt::MouseFocusReason);
此->设置AcceptHoverEvents(true);
//此->设置刻度(0.5);
rect_left_条件=false;
rect_right_条件=false;
rect_top_条件=false;
rect_bottom_条件=false;
rect_resize_occurrent=false;
image_rect=QRect();
image_rect=this->pixmap().toImage().rect();
}
void PersonSizeGraphicsItem::setSourceImage(常量图像和源图像)
{
此->源图像=源图像;
}
void PersonSizeGraphicsItem::mouseMoveEvent(QGraphicsSceneMouseEvent*事件)
{
const QPointF event_pos=事件->pos();
const QPointF event_scene_pos=事件->场景();
QPoint current_top_left=image_rect.toplight();
QPoint current_bottom_right=image_rect.bottomRight();
如果((事件->场景().x()>此->场景()->宽度())| |(事件->场景().y()>此->场景()->高度())
||(event->scenePos().x()<0)| |(event->scenePos().y()<0))
{
返回;
}
if(this->cursor().shape()==Qt::SizeHorCursor)
{
if(右向右条件)
{
image_rect=QRect(当前左上角,QPoint(事件->位置().x(),当前右下角());
}
if(矩形左矩形条件)
{
image_rect=QRect(QPoint(事件位置x(),0),当前右下角);
QPoint new_top_left=图像_rect.toplight();
QPointF mapped_topLeft=mapToParent(QPointF(new_top_left.x(),new_top_left.y());
此->设置位置(映射到左上角);
rect_resize_occurrent=true;
//qDebug()游标().shape()==Qt::SizeVerCursor)
{
if(矩形底部条件)
{
image_rect=QRect(当前左上角,QPoint(当前右下角,x(),事件->位置().y());
}
if(矩形顶部条件)
{
image_rect=QRect(QPoint(0,事件位置y()),当前右下角);
QPoint new_top_left=图像_rect.toplight();