QT拖拽准星获取窗口信息

介绍

1.在Qt中如果获取其他窗口的信息,当然是使用WinApi,那么如何能实时获取鼠标位置的窗口信息呢?且如何能做出来类似于拖拽准星到窗口就能获取到信息呢?例如下图。在这里插入图片描述

效果

在这里插入图片描述

上代码

代码介绍

1.CrosshairLabelMove类是显示一张图片,可移动,背景透明设置了WA_TransparentForMouseEvents是穿过当前窗口的鼠标事件。
2.CrosshairLabelClick类是我用做点击弹出准星Label类,CrosshairLabelMove的移动是由CrosshairLabelClick类发送的坐标能保证点击后鼠标不松开可移动准星。
3.windowInfo是发送窗口信息。
4拖拽时会隐藏鼠标,且做了检测窗口属性防止鼠标一直被隐藏

//可移动准星Label
class CrosshairLabelMove : public QLabel
{
    Q_OBJECT

public:
    explicit CrosshairLabelMove() {
        this->setAttribute(Qt::WA_TransparentForMouseEvents);

        QPixmap pixmap(":/Crosshair.png"); // 替换为你的图片路径

        setPixmap(pixmap);
        setMask(pixmap.mask()); // 使图像的透明部分被视为透明
        setWindowFlags(Qt::FramelessWindowHint | Qt::WindowStaysOnTopHint); // 使窗口无边框并始终保持在顶部
        setAttribute(Qt::WA_TranslucentBackground); // 设置背景为透明


        m_Timer = new QTimer(this);
        connect(m_Timer, &QTimer::timeout, this, &CrosshairLabelMove::checkFocus);
        m_Timer->start(100); // 检查频率,可以根据实际需要进行调整
    }

    void setCurrentPos(const QPoint& pos) {
        m_QPoint = pos;
    }
protected:
    void showEvent(QShowEvent *event) override {

        int halfWidth = width() / 2;
        int halfHeight = height() / 2;
        move(m_QPoint.x() - halfWidth, m_QPoint.y() - halfHeight);
        QLabel::showEvent(event);
    }


public slots:
    void updatePosition(const QPoint& newPosition) {
        int halfWidth = width() / 2;
        int halfHeight = height() / 2;
        move(newPosition.x() - halfWidth, newPosition.y() - halfHeight);
    }
    void checkFocus() {
        //这段代码首先检查当前窗口是否是活动窗口,并且是否可见。如果窗口不是活动的,或者不可见,那么就恢复鼠标,取消鼠标事件的透明处理,并隐藏准星。
        if (QApplication::activeWindow() != this || !this->isVisible()) {
            if (QApplication::overrideCursor() != nullptr) {
                QApplication::restoreOverrideCursor(); // 恢复鼠标
                this->setAttribute(Qt::WA_TransparentForMouseEvents, false);
                if (this->isVisible()) {
                    this->hide();
                }
            }
        }
    }

private:
    QPoint m_QPoint;
    QTimer* m_Timer;
};


//弹出准星的可点击Label

class CrosshairLabelClick : public QLabel {
    Q_OBJECT

public:
    CrosshairLabelClick(QWidget* parent = nullptr) : QLabel(parent) {
        QPixmap pixmap(":/Crosshair.png"); // 替换为你的图片路径
        setPixmap(pixmap);

        m_CrosshairLabelMove = new CrosshairLabelMove();

        QObject::connect(this, &CrosshairLabelClick::mousePress, [&]() {
            m_CrosshairLabelMove->show();
        });

        QObject::connect(this, &CrosshairLabelClick::mouseMove, m_CrosshairLabelMove, &CrosshairLabelMove::updatePosition);
        QObject::connect(this, &CrosshairLabelClick::mouseRelease, [&]() {
            m_CrosshairLabelMove->hide();
        });
    }
    void setCurrentPos(const QPoint& pos) {
        m_CrosshairLabelMove->setCurrentPos(pos);
    }
signals:
    void windowInfo(const QString &title, const QString &className, HWND hwnd);
protected:
    void mousePressEvent(QMouseEvent* event) override {
        QLabel::mousePressEvent(event);
        if (event->button() == Qt::LeftButton) {
            emit mousePress(event->globalPos());
            QApplication::setOverrideCursor(QCursor(Qt::BlankCursor)); // 隐藏鼠标
        }
    }

    void mouseMoveEvent(QMouseEvent* event) override {
        QLabel::mouseMoveEvent(event);
        emit mouseMove(event->globalPos());
        HWND hwnd = ::WindowFromPoint(POINT{event->globalPos().x(), event->globalPos().y()});
        char title[256] = {0};
        ::GetWindowTextA(hwnd, title, sizeof(title));
        QString titleStr = QString::fromLocal8Bit(title);

        char className[256] = {0};
        ::GetClassNameA(hwnd, className, sizeof(className));
        QString classNameStr = QString::fromLocal8Bit(className);
        emit windowInfo(titleStr, classNameStr, hwnd);
    }

    void mouseReleaseEvent(QMouseEvent* event) override {
        QLabel::mouseReleaseEvent(event);
        emit mouseRelease();

        QApplication::restoreOverrideCursor(); // 恢复鼠标
        this->setAttribute(Qt::WA_TransparentForMouseEvents, false);
    }

    void hideEvent(QHideEvent* event) {
        QWidget::hideEvent(event);
        emit mouseRelease();

        QApplication::restoreOverrideCursor(); // 恢复鼠标
        this->setAttribute(Qt::WA_TransparentForMouseEvents, false);
    }

signals:
    void mousePress(QPoint startPosition);
    void mouseMove(QPoint currentPosition);
    void mouseRelease();

private:
    CrosshairLabelMove* m_CrosshairLabelMove;
};

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值