- 📢博客主页:https://blog.csdn.net/weixin_43197380
- 📢欢迎点赞 👍 收藏 ⭐留言 📝 如有错误敬请指正!
- 📢本文由 Loewen丶原创,首发于 CSDN,转载注明出处🙉
- 📢现在的付出,都会是一种沉淀,只为让你成为更好的人✨
👀 前言
十字标辅助线是3D
雷达点云标注和2D
分类中常用的辅助标注工具。这个效果在经典的CAD
软件中很常用,还有一些股票软件,也有这种十字线定位线,有时候需要在十字交叉地方获取对应点的数据来显示等。如下,是海康相机客户端MVS
中的十字标辅助线效果,本文仿照其效果使用Qt
来进行实现。
💨 方式一:重构drawForeground()函数
这种方法主要是在继承基类QGraphicsView
的子类MF_GraphicsView
中完成,通过重写drawForeground()
函数功能,运行时系统会自动调用该函数,最终实现QWidget窗体中绘制红色十字前景函数的自动触发。
核心代码:
//.h——头文件
class MF_GraphicsView :public QGraphicsView
{
public:
MF_GraphicsView(QWidget* _parent = nullptr);
~MF_GraphicsView();
protected:
//QGraphicsView重构函数
virtual void drawForeground(QPainter *painter, const QRectF &rect);
}
//.cpp——源文件
void MF_GraphicsView::drawForeground(QPainter *painter, const QRectF &rect)
{
QRectF rt = scene()->sceneRect(); //获取场景大小的绘制面积
QPen _pen;
_pen.setColor(QColor(255,0,0));
_pen.setWidth(2);
painter->setPen(_pen);
//绘制两条红色十字交叉线
painter->drawLine(QLine(QPoint(rt.center().x(), 0), QPoint(rt.center().x(), rt.height())));
painter->drawLine(QLine(QPoint(0, rt.center().y()), QPoint(rt.width(), rt.center().y())));
}
强调:该函数drawForeground()
所在的类需要继承基类QGraphicsView。其声明函数前写不写virtual
都可以,因为基类中的drawForeground()
函数是虚函数,所以子类同名函数默认是虚函数。
💨 方式一:效果展示
参考帖子中的问答:https://bbs.csdn.net/topics/392435787
问题:重写QGraphicsView类,在类中重写paintEvent调用Qpainter的drawRect方法绘制矩形,单步调试,确定执行了drawRect, 但是发现绘制无效,哪位可以解答这是为什么?
解答:
1、别使用它的paintEvent(),要绘制图形需要重写GGraphicsItem中的paint()纯虚函数。或者也可以覆盖写QGraphicsView的drawBackground()或drawForeground()函数。
2、为什么要在view中重写paintEvent…一般是在scene上加item,然后重写item的paint 。
💦 方式二:手动添加辅助线——addLine
方式一是系统运行时,自动执行drawForeground
函数来添加辅助线的,后面我想的是通过右键菜单的方式来手动添加和取消,所以我又换了一种方式
核心代码:
//.h
public:
void dispCrossLine();
private:
QGraphicsLineItem *m_HLineItem = nullptr;
QGraphicsLineItem *m_VLineItem = nullptr;
//.cpp
void MF_GraphicsView::dispCrossLine()
{
if (m_HLineItem == nullptr && m_VLineItem == nullptr) {
m_HLineItem = new QGraphicsLineItem;
m_VLineItem = new QGraphicsLineItem;
m_HLineItem = m_scene->addLine(-m_view->viewport()->width(), 0, m_view->viewport()->width(), 0, QPen(Qt::red, 1)); //左右线
m_VLineItem = m_scene->addLine(0, -(m_view->viewport()->height()), 0, m_view->viewport()->height(), QPen(Qt::red, 1)); //上下线
}
else {
m_scene->removeItem((QGraphicsItem*)m_HLineItem);
m_scene->removeItem((QGraphicsItem*)m_VLineItem);
delete m_HLineItem;
m_HLineItem = nullptr;
delete m_VLineItem;
m_VLineItem = nullptr;
}
}
强调:该函数也是在自定义的QGraphicsView的子类中完成的。这样,通过在菜单相应槽函数中直接调动实现函数dispCrossLine可实现手动添加/取消十字标辅助线。
💦 方式二:效果展示
戳戳小手帮忙点个免费的赞和关注吧,嘿嘿。 |