半透明的QWidget应该是可点击的跨操作系统 [英] Translucent QWidget should be clickable cross-os

查看:61
本文介绍了半透明的QWidget应该是可点击的跨操作系统的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试使用跨操作系统的Qt(C ++)应用程序来完成以下任务.运行该程序后,将弹出一个新窗口,即全屏QWidget.现在,我希望它是透明的/透明的,因此用户实际上不会看到它.用户可以在此层"上拖动鼠标以绘制(红色)矩形,以选择一个区域-当释放鼠标时,将其截屏.

I'm trying to accomplish the following with a Qt (C++) app, cross OS. Upon running the program a new window pops up, a fullscreen QWidget. Now I want this to be see-through/transparent, so the user won't actually see it. On this 'layer' a user can drag his/her mouse to draw a (red) rectangle to select an area which is - when the mouse is released - taken a screenshot of.

问题:
问题在于整个透明层,因为这似乎无法在整个OS上正常工作.因为当我单击该图层所在的位置时,要调用mousePressEvent(),我将其单击到它下面的窗口,好像它不在那里一样.但是,在Ubuntu上,我没有.我希望在Windows上具有相同的效果,但到目前为止我什么都没得到...
(使另一个GUI对象出现,例如按钮,只会使按钮成为图层中可点击的部分)

The problem:
The issue lays in the whole transparent layer thing since this doesn't appear to work well cross OS. Because when I click on where the layer is, to invoke the mousePressEvent(), I click through it on to the window below it as if it isn't even there. On Ubuntu, however, I do not. I want the same effect on Windows, but thus far I got nothing...
(Making another GUI object appear, such as button, would only make the button a clickable part of the layer)

已在32位Ubuntu 11.04和64位Windows 7 Home Premium上进行了测试.(尝试使用Mac,可以解决此问题.)

Tested on Ubuntu 11.04 32-bit and Windows 7 Home Premium 64-bit. (Trying to get around to a Mac one, would this issue be solved.)

那么有人知道这将如何工作吗?到目前为止,我已经包含了我的代码.(清除了我所有的100次其他尝试.)

So does anyone know how this would work? I've included my code thus far. (Clearing out all my 100 other attempts.)

main.cpp 在这里,我设置了translucentBackground,在这里我可能错过了设置,或者某些配置不正确.

main.cpp Here I set the translucentBackground, here I probably miss a setting or something is not configured right.

#include <QtGui/QApplication>
#include "widget.h"
int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    Widget w;
    //Fullscreen app
    w.showFullScreen();
    w.setAttribute(Qt::WA_NoSystemBackground);
    w.setAttribute(Qt::WA_TranslucentBackground);
    w.setMouseTracking(true);
    w.setWindowFlags(Qt::Window | Qt::CustomizeWindowHint | Qt::WindowStaysOnTopHint | Qt::FramelessWindowHint);
    //Show
    w.show();
    return a.exec();
}

widget.cpp

    #include "widget.h"
    #include "ui_widget.h"
    #include "QDebug"
    Widget::Widget(QWidget *parent) : QWidget(parent), ui(new Ui::Widget)
    {
        this->setWindowFlags(Qt::CustomizeWindowHint | Qt::WindowStaysOnTopHint | Qt::FramelessWindowHint);
        QPalette palette(Widget::palette());
        palette.setColor(backgroundRole(), Qt::white);
        setPalette(palette);
        this->clicked = false;
        ui->setupUi(this);
    }
    Widget::~Widget()
    {
        delete ui;
    }
    void Widget::mousePressEvent ( QMouseEvent * event )
    {
        //Record start
        if (event->button() == Qt::LeftButton){
                x = event->globalX();
                y = event->globalY();
                this->clicked = true;
                width = 0;
                height = 0;
        }
    }
    void Widget::mouseMoveEvent ( QMouseEvent * event )
    {
        if (this->clicked == true){
            int x2 = event->globalX();
            int y2 = event->globalY();
            if(x < x2){
                    width = x2 - x;
            }else{
                    width = x - x2;
                    //Resetting startpoint when dragging to the left side on your screen, copy from java so this doesn't actually works yet.
                    x = x - width-2;
            }
            if(y < y2){
                    height = y2 - y;
            }else{
                    height = y - y2;
                    //Resetting startpoint when dragging to the left side on your screen, copy from java so this doesn't actually works yet.
                    y = y - height-2;
            }
            //Redraw rectangle
            update();
            qDebug("wa");
        }
    }
    void Widget::mouseReleaseEvent ( QMouseEvent * event )
    {
        if (event->button() == Qt::LeftButton)
        {
            //Record end
            qDebug("-------");
            this->clicked = false;
        }
    }
    void Widget::paintEvent(QPaintEvent *)
    {
        QPainter painter(this);
        painter.setRenderHint(QPainter::Antialiasing);
        painter.setPen(Qt::red);
        painter.drawRect(x,y,width,height);
    }

widget.h

#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include <QtGui>
#include<QMouseEvent>
namespace Ui {
    class Widget;
}
class Widget : public QWidget
{
    Q_OBJECT
public:
    explicit Widget(QWidget *parent = 0);
    ~Widget();
private:
    Ui::Widget *ui;
    bool clicked;
    int x,y,width,height;
    void mousePressEvent ( QMouseEvent * event );
    void mouseMoveEvent ( QMouseEvent * event );
    void mouseReleaseEvent ( QMouseEvent * event );
protected:
    void paintEvent(QPaintEvent *);
};
#endif // WIDGET_H

此外,我认为我已经遍历了Google将在此主题上找到的所有结果,与Qt的API文档相同.我已经严重用尽了这个选项.(我用Java启动了这个项目,但是到目前为止,使用Qt的C ++似乎工作量少得多.)

Also, I think I've gone through every result Google will find on this subject, same as the API docs of Qt. I've seriously run out of options for this one. (I started this project in Java, but C++ with Qt seems to be, thus far, far less work.)

任何帮助将不胜感激!

推荐答案

这是一个完整而完整的技巧,但这是我所知道的唯一方法.截取屏幕截图,然后将其用作小部件的背景,确保在窗口中显示正确的屏幕,尤其是在调整大小或移动等方面.至少是跨平台的.

This is a complete and total hack but it's the only way that I know of to do it. Take a screenshot of the screen and then use that as your widget's background, making sure that the right piece of the screen shows in the window, especially on resizes or moves, etc. At least it's cross platform.

但是,这也是在ARGB视觉效果和X11中不存在的东西之前实现KDE 3的虚假透明度的方式.

However, it was also the way that KDE 3's fake transparency was implemented before such things like ARGB visuals and what not existed in X11.

这篇关于半透明的QWidget应该是可点击的跨操作系统的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆