Important: Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

How to use and event filter in a QTest instance (video player application)



  • Hello everyone

    I encounter kind of an issue when I try to write different GUI test for my application.
    I'm currently developing a video player under Qt using the QtAV framework and I try to test the different features I have included.
    To use some of the features, I have written an Event Filter class to parse different keyboard/mouse shortcuts. One of which is the well known spacebar shortcut which allows to play and pause the video at will. But when I try to test it like I test my play/pause button, it systematically fails.

    Here my eventFilter function declaration in my Event Filter class:

    bool EventFilter::eventFilter(QObject *watched, QEvent *event)
    {
        Q_UNUSED(watched);
        AVPlayer *player = static_cast<AVPlayer*>(parent());
        if(!player || !player->renderer() || !player->renderer()->widget())
                return false;
        if (qobject_cast<QWidget*>(watched) != player->renderer()->widget()) {
               return false;
           }
        QEvent::Type type = event->type();
        switch(type){
        case QEvent::KeyPress:{
            QKeyEvent *key_event = static_cast<QKeyEvent*>(event);
            int key = key_event->key();
            Qt::KeyboardModifiers modifiers = key_event->modifiers();
            switch(key){
                case Qt::Key_F11:
                case Qt::Key_F:
                {
                    QWidget *w = qApp->activeWindow();
                    if (!w)
                        return false;
                    w->setWindowState(w->windowState() ^ Qt::WindowFullScreen);
                }
                    break;
    
                case Qt::Key_Escape:
                case Qt::Key_Q:
                {
                    if(modifiers == Qt::ControlModifier)
                    {
                        qApp->quit();
                    }
                }
                    break;
    
                case Qt::Key_Left:
                    qDebug("<-");
                    player->stepBackward();
                    break;
    
                case Qt::Key_Right:
                    qDebug("->");
                    player->stepForward();
                    break;
    
                case Qt::Key_Space:
                    if(!player->isPlaying())
                    {
                        player->play();
                    }
                    player->pause(!player->isPaused());
                    break;
    
                case Qt::Key_O: 
                         openLocalFile();
                         break;
                case Qt::Key_F1:
                        help();
                        break;
                default:
                    return false;
                }
                break;
            }
    
    
            default:
                return false;
                break;
    
    
        }
    
        return true;
    
    
    
    }
    

    and here is my test declaration for the spacebar shortcut

    void EagleEye_GUI_Tests::test_casePlayer_space()
    {
        MainWindow *windowTest = new MainWindow;
    
        QtAV_Player *playerTest = new QtAV_Player(windowTest);
    
        EventFilter *ef = new EventFilter(playerTest->m_player);
        windowTest -> installEventFilter(ef);
    
        windowTest->show();
    
        if(QTest::qWaitForWindowExposed(windowTest)){
    
            QString file = "/home/pasquerk/Documents/calcio_3_10s_1280x720_2400.mp4";
            playerTest->m_player->setFile(file);
            playerTest->m_player->setAsyncLoad(false);
            playerTest->m_player->play();
    
    
            QTest::keyClick(windowTest,Qt::Key_Space);
            QCOMPARE(playerTest->m_player->state(),playerTest->m_player->PausedState);
            QTest::keyClick(windowTest,Qt::Key_Space);
            QCOMPARE(playerTest->m_player->state(),playerTest->m_player->PlayingState);
    
        }
    }
    

    I don't know what I am missing here. And I've already tested without windowTest just by using playerTest as the one to show etc. It constantly fails at the first QCOMPARE line.

    Thanks for your help !



  • @Brioche

    Does no keyboard shortcut work? Does the event filter respond at all?

    playerTest->m_player->state()

    Is your m_player a public member of QtAV_Player?



  • @Pl45m4

    It works when I run the application but not when I run the test

    m_player is actually a private member of my QtAV_Player but my test class is set as friend with my QtAV_Player class
    Do you think that since m_player is private, Event Filter doesn't reach it ?

    I already have instancied Event Filter into my QtAV_Player class but I thought I had to do it again in my test function in order to install the Event filter to the right window/widget

    QtAV_Player::QtAV_Player(QWidget *parent): QWidget(parent)
    {
    
       //...
    
        m_player = new AVPlayer(this);
        m_vo = new VideoOutput(this);
    
        EventFilter *ef = new EventFilter(m_player);
            qApp->installEventFilter(ef);
    
       //...
    }
    


  • @Brioche said in How to use and event filter in a QTest instance (video player application):

    I already have instancied Event Filter into my QtAV_Player class but I thought I had to do it again in my test function in order to install the Event filter to the right window/widget

    No.
    This might cause the issue. There is one ef installed on windowTest and one "global" (on your QApplication). Both seem to watch the same object.
    Debug to see what exactly happens and where your KeyEvent went.

    Installing a global event filter can also lead to performance issues.

    AVPlayer player = static_cast<AVPlayer>(parent());

    Try not to be reliant on parent, especially when using qApp.
    Also, better use qobject_cast or dynamic_cast here.


Log in to reply