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

raise external process window



  • Hello.

    Within a Qt GUI application, when I start 'xterm' with system() call or QProcess.execute(), the created xterm window does not get keyboard focus at all. Even when I click on the xterm window, the cursor is not activated in it. Is there a way to activate window of a started GUI application?

    Thanks.



  • @fatih.erol
    I do not know whether this would affect xterm's keyboard focus/cursor, but what have you done about, say, the state of its stdin when you invoke from QProcess::start()? Also, does your app need to wait for the xterm to exit? If not, is there any difference if you try startDetached() instead (probably not, but worth a look)?

    P.S.
    Using Python's os.system("xterm"), which really ought be the same as C's system(), from a PyQt GUI app gives me no problems, xterm opens and shows window/focus/cursor etc. Ubuntu 17.04, Unity desktop, FWIW.



  • How it works is:

    • Qt GUI application emits a signal. It is possible GUI thread receives other signals meanwhile, which may call activateWindow()

    • A QObject within a separate QThread has QueuedConnection for this signal, so calls the connected slot, which starts " xterm -e 'pcimset' ", where pcimset is a command line utility reading keyboard input from the user

    • I have tried with QProcess::execute()

    • I have tried with popen()

    • I have tried with popen() within a separate pthread

    I have read the following on QProcess class documentation, so tried giving -geometry parameter to xterm.

    The positioning and the screen Z-order of windows belonging to GUI applications started with QProcess are controlled by the underlying windowing system. For Qt 5 applications, the positioning can be specified using the -qwindowgeometry command line option; X11 applications generally accept a -geometry command line option.
    

    None of these worked unfortunately.

    I will try with system() and QProcess.startDetached as well.



  • @fatih.erol
    A couple of observations:

    • You state "the created xterm window does not get keyboard focus at all. Even when I click on the xterm window, the cursor is not activated in it."
    • In that case I don't believe geometry or Z order has any relevance to your problem.
    • Nor do I think your threads/queued connections etc. are relevant.
    • You start talking about popen(). What are you intending to do with pipes & redirection now?
    • Start by trying a command of plain xterm, without that -e pcimset. What is the behaviour now, wrt keyboard/focus etc. of the xterm window?


  • I tried the following options for only '/usr/bin/xterm' with no parameters:

    • popen() (Used just to capture command output)
    • popen() in separate pthread
    • system()
    • system() in separate pthread
    • QProcess::execute()
    • QProcess::startDetached()

    The xterm is created on top of the Qt GUI. But cursor is not highlighted, and does not have focus.
    Typing on the keyboard does not feed characters to xterm. It does not get handled by Qt GUI either.
    The mouse can be used to make selections on xterm. But clicking on xterm still does not activate the keyboard input. Also, after clicking on Qt GUI, it does not handle keyboard events either. Only after xterm is killed with kill command, Qt GUI handles keyboard keys.

    Is there a specific bash environment variable, or xterm setting that might trigger such behavior?



  • @fatih.erol
    As I said, for me (and I presume others) a plain, simple xterm spawned out of a Qt GUI app works just fine. Like (Python, but you get the gist):

        app = QtWidgets.QApplication(sys.argv)
    
        main = QtWidgets.QMainWindow()
        main.show()
    
        import os
        os.system("xterm")
    
        sys.exit(app.exec_())
    

    Perhaps you should at least start from that in C++ and see what your behaviour looks like?



  • I tested with a basic fullscreen GUI application, which runs system( "xterm" ) when 'x' is pressed, and activateWindow() when 'a' is pressed.

    void Widget::keyPressEvent( QKeyEvent *event )
    {
        switch ( event->key() )
        {
            case Qt::Key_Escape: close(); break;
            case Qt::Key_X: ::system( "/usr/bin/xterm" ); break;
            case Qt::Key_A: activateWindow(); break;
            default: QWidget::keyPressEvent( event ); break;
        }
    }
    

    If I press X first, xterm starts (not fullscreen) and I can type in it.
    Then, I click on Qt GUI, and press A to activateWindow. From this point on, xterm does not accept keyboard input.
    If I click on Qt GUI, and press Escape to close the GUI, I can click on xterm and continue typing again.

    If I press A to activateWindow first, then X to start xterm, xterm does not accept keyboard input. Pressing Escape will kill the GUI, and I can click and type on xterm again.

    I tried removing activateWindow() calls in the original Qt GUI application. But this did not fix it unfortunately. Though, there are many classes with 'setFocus' on different widgets, which might be creating a similar effect.

    I am guessing this issue is relevant to the explanation at the bottom of this old documentation: https://doc.qt.io/archives/2.3/commonproblems.html


Log in to reply