Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Embedding One Qt Application into another on Windows [SOLVED]
Forum Updated to NodeBB v4.3 + New Features

Embedding One Qt Application into another on Windows [SOLVED]

Scheduled Pinned Locked Moved General and Desktop
4 Posts 2 Posters 2.1k Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • I Offline
    I Offline
    ion_knight
    wrote on last edited by
    #1

    Hi there currently trying to create program than launches two instances of calculator and places it inside a QWidget.

    @#include "mplayer.h"
    #include "mplayer_wrapper.h"
    #include <QState>
    #include <QDebug>
    #include <Windows.h>
    #include <QWindow>

    mplayer::mplayer(QString rtsp_path, QWidget *parent) :
    QWidget(parent)
    {
    QPalette p(palette());
    p.setColor(QPalette::Background, Qt::black);
    this->setAutoFillBackground(true);
    this->setPalette(p);
    this->setMinimumSize(720,576);

    qDebug("\nCreating Process = Mplayer");
    WId winid = this->winId();
    arguments << "";
    
    qDebug() << arguments;
    
    this->m_process = new QProcess();
    this->m_process->setProgram(program);
    this->m_process->setArguments(arguments);
    this->m_process->start();
    
    if(this->m_process->waitForStarted())
    {
        qDebug("\nSuccess in starting Process = Mplayer");
    }
    else
    {
        qDebug("\nFailed To start Process = Mplayer");
    }/**/
    
    WId ide = (WId)FindWindowW(L"CalcFrame", NULL);
    if (ide)
        qDebug() << ide << "is the ID of mplayer";
        //return -1;
    
    QWindow *container = QWindow::fromWinId(ide);
    QWidget *program_start  = QWidget::createWindowContainer(container);
    
    //QMessageBox test;
    //test.setText(QString::number(id));
    //test.exec&#40;&#41;;
    
    //setCentralWidget(program_start&#41;;
    program_start->setParent(this&#41;;
    program_start->setMinimumSize(400,400&#41;;
    program_start->setSizePolicy(QSizePolicy::Expanding,QSizePolicy::Expanding);
    QVBoxLayout *layout = new QVBoxLayout;
    layout->addWidget(program_start);
    program_start->setLayout(layout);
    

    }

    mplayer::~mplayer()
    {
    qDebug("\nDeleting Process = Mplayer");
    this->m_process->close();
    }

    @

    However if I create a window fromwinid, the program crashes, once I have again removed this and the container the programs will start but just obviously doesn't launch inside the QWidget. If anyone has any idea how I should do this or if there is a better/easier way of doing this please let me know. Currently using FindWindow does output the correct ID for the device (checked via winspector) just have no idea why it isn't creating the QWindow and why this isn't being placed inside the created window container QWidget.

    @MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
    {
    ui->setupUi(this);
    //mplayer_wrapper *cameras = new mplayer_wrapper("rtsp://169.254.133.191/output","rtsp://169.254.133.193/output",this);
    QPalette p(palette());
    p.setColor(QPalette::Background, Qt::lightGray);
    this->setAutoFillBackground(true);
    this->setPalette(p);
    this->setWindowTitle(QApplication::translate("toplevel", "CCTV"));
    //centralWidget()->layout()->addWidget(cameras);

    connect(ui->Start_Stream, &QPushButton::clicked,ui->widget,&mplayer_wrapper::start_mplayer);
    //connect(ui->Stop_Stream, &QPushButton::clicked,cameras,&mplayer_wrapper::stop_mplayer);
    //connect(ui->Start_Stream, &QPushButton::clicked,cameras,&mplayer_wrapper::start_mplayer);
    connect(Timer,&QTimer::timeout,this,&MainWindow::show_time);
    
    cmd_text = ui->cmd_edit->text();
    
    Timer->start();
    

    Timer = new QTimer(this);
    connect(ui->Stop_Stream, &QPushButton::clicked,ui->widget,&mplayer_wrapper::stop_mplayer);
    } @

    1 Reply Last reply
    0
    • I Offline
      I Offline
      ion_knight
      wrote on last edited by
      #2

      Figured out the problem had a silly mistake (forgot to include request activate on the main Qwindow).

      @#include "mainwindow.h"
      #include "ui_mainwindow.h"

      MainWindow::MainWindow(QWidget *parent) :
      QMainWindow(parent),
      ui(new Ui::MainWindow)
      {
      ui->setupUi(this);

      QVBoxLayout *mainLayout = new QVBoxLayout;
      QTimer t;
      t.start(2500);
      QProcess *m_process = new QProcess(this);
      QStringList arguments;
      arguments << "";
      //m_process->setProgram("C:\\Windows\\SysWOW64\\calc.exe");
      //m_process->setArguments(arguments);
      m_process->start("C:\\Windows\\SysWOW64\\calc.exe");
      
      if(m_process->waitForStarted())
      {
          qDebug("\nSuccess in starting Process = Mplayer");
      }
      else
      {
          qDebug("\nFailed To start Process = Mplayer");
      }
      
      WId id = (WId)FindWindow(NULL,L"Calculator");
      if (id)
          qDebug() << id;
      
      QWindow* window = QWindow::fromWinId(id);
      window->show();
      window->requestActivate();
      QWidget* widget = QWidget::createWindowContainer(window);
      widget->show();
      widget->setFixedWidth(1000);
      //setCentralWidget(widget);
      

      }

      MainWindow::~MainWindow()
      {
      delete ui;
      }@

      Made a mini program that embeds the Calculator into the QWidget however it's has to contain requestactivate otherwise the program will crash.

      However when testing this I have found an error that I cannot figure out how to resolve. If I launch the program without any calculator program already in the background the program will just start an instance of the calculator (which isn't inside the QWidget, then only if I run the program again will the system actually place the calculator program inside a QWindow, however this means that every time the program needs to be launch the internal program (in this case the calculator, has to be launched twice (once for external and then the second for internal of the QWindow). If anyone has an idea why this is happening or if i'm missing anything please let me know.

      Here is the only error below that I am receivin.
      ASSERT: "result.hwnd" in file qwindowswindow.cpp, line 555
      Invalid parameter passed to C runtime function.
      Invalid parameter passed to C runtime function.

      Thanks
      Nick

      1 Reply Last reply
      0
      • I Offline
        I Offline
        ion_knight
        wrote on last edited by
        #3

        Found the problem was related to QProcess not starting the process properly before it began searching for the HWID of the Process so once I had place waitforfinished before starting the program it would work (after quite a wait).

        To resolve this I place a timeout on waitforfinished of 200 msecs so that the process had time to start but wasn't waiting for ages till wait for finished had cleared.

        1 Reply Last reply
        0
        • SGaistS Offline
          SGaistS Offline
          SGaist
          Lifetime Qt Champion
          wrote on last edited by
          #4

          Hi,

          waitForFinished doesn't mean that the application started by QProcess has in fact started, it's for when it should finish.

          You should rather use waitForStarted

          Interested in AI ? www.idiap.ch
          Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

          1 Reply Last reply
          0

          • Login

          • Login or register to search.
          • First post
            Last post
          0
          • Categories
          • Recent
          • Tags
          • Popular
          • Users
          • Groups
          • Search
          • Get Qt Extensions
          • Unsolved