サブコントロールのマウスメッセージはどのように親コントロールに渡されますか?

2557 ワード

需要は、親widgetにサブwidgetを並べた後、clickサブwidgetの場合:サブwidgetの関連イベント処理関数には入らず、親widgetの対応するイベント処理関数に入る.たとえばmousePressEvent()イベントに入ります.通常、サブwidgetはメッセージを受信し、親widgetはメッセージを受信しません.結局、clickは親widgetを遮断し、親widgetがこのイベントを受信できない子widgetです.
QWidgetにQLabelを作ったというテストをしました.そして、親QWidgetのmousePressEvent()を実現し、私がclickというlabelをしたとき、親QWidgetのmousePressEvent()に入ることができたことについて発見します.しかし、子をQPShButtonに変更すると入れません!
 
他の人に聞いてみると、子widgetにacceptやignoreがなければ、その事件は父親に渡されるという答えが得られた.
 
事実も確かにそうです.
①QLabelについて:mouse処理関数を書き換えず、イベントフィルタを設定するなどの操作もしていなければ、mouseというイベントに対してずっと処理を行っていないということになりますが、それは処理を行っていないということで、上記のような場合に相当し、その時点でそのイベントがparentに渡されます.
2一方、QPShButtonでは、clickがそれを送信すると、clicked()信号が送信され、これはイベントに対するoperatorプロセスに相当する.したがって、ここではイベントをacceptし、対応処理を行います.したがって、親ウィンドウに渡すことはできません.
 
 
では、継承されたクラスについて、それぞれのイベント処理関数を実装した場合、対応するイベントは親widgetに渡されないに違いありません.書き換えたイベント処理関数の関数体が空であっても!
 
標準のコントロールオブジェクトの場合、各イベント処理関数は書き換えられていません.そのメッセージが親widgetに伝達されるかどうかは,途中でイベントフィルタなどを用いて信号を遮断したかどうかにかかっている.
 
ソリューション:
1. setAttribute(Qt::WA_TransparentForMouseEvents, true);
2.例:
赤のコントロールが緑のコントロールの下にあると仮定します.赤のコントロールを緑のコントロールの下でマウスドラッグすることもできます.緑のコントロールはマウスイベントをキャプチャした後、「迂回」して、後ろのコントロールにメッセージを送信します.
void     ::mouseMoveEvent( QMouseEvent *e )
{
    QWidget::mouseMoveEvent(e);
    MyMouseEvent(e);
}
 
void     ::mousePressEvent( QMouseEvent *e )
{
    QWidget::mousePressEvent(e);
    MyMouseEvent(e);
}
 
void     ::mouseReleaseEvent( QMouseEvent *e )
{
    QWidget::mouseReleaseEvent(e);
    MyMouseEvent(e);
}
 
void     ::mouseDoubleClickEvent( QMouseEvent *e )
{
    QWidget::mouseDoubleClickEvent(e);
    MyMouseEvent(e);
}
 
void     ::MyMouseEvent( QMouseEvent *e )
{
    if (this->parentWidget())
    {
        //                                。
        this->setAttribute(Qt::WA_TransparentForMouseEvents, true);
        QPoint pt = this->mapTo(this->parentWidget(), e->pos());
        QWidget *w = this->parentWidget()->childAt(pt);
        if (w)
        {
            pt = w->mapFrom(this->parentWidget(), pt);
            QMouseEvent *event = new QMouseEvent(e->type(), pt, e->button(), e->buttons(), e->modifiers());
            QApplication::postEvent(w, event);
        }
        //             ,    button   
        this->setAttribute(Qt::WA_TransparentForMouseEvents, false);
    }
}

参考記事:https://blog.csdn.net/qq_32250025/article/details/78257215
                    https://www.cnblogs.com/qq78292959/archive/2012/08/19/2646210.html