0

多くのボタンがあるウィンドウがあります。それぞれがサブプログラム (Opencv API を使用して作成) をトリガーします。各サブプログラムは、ウィンドウに画像などを表示します。

問題は、これらのウィンドウを (小さな赤い十字で) 閉じると、すべてのボタンがクリックできなくなることです。そのため、別のプログラムを起動したい場合は、メイン ウィンドウを終了して再度実行する必要があります。

つまり、毎回最初からやり直すことなく、すべてのサブプログラムを実行できるようにしたいのです。

GUIのコードは次のとおりです。

.cpp

#include "fenprincipale.h"
#include "ui_fenprincipale.h"
#include<highgui.h>
 #include<cv.h>
 #include <moyenetmedian.h>
#include<morpho.h>
#include<tracking.h>
#include<contour.h>
#include<QApplication>

FenPrincipale::FenPrincipale(QWidget *parent) :
QWidget(parent),
ui(new Ui::FenPrincipale)

{
ui->setupUi(this);
MoyenEtMedian *moyenEtMedian = new MoyenEtMedian;
morpho * mor = new morpho;
tracking * tra= new tracking;
contour * cont= new contour;

QObject::connect(ui->bMoyMed, SIGNAL( clicked() ), moyenEtMedian, SLOT( exec() ),    Qt::AutoConnection );
QObject::connect(ui->bMorph, SIGNAL( clicked() ), mor, SLOT( exec() ), Qt::AutoConnection );
QObject::connect(ui->bTrack, SIGNAL( clicked() ), tra, SLOT( exec() ), Qt::AutoConnection );
QObject::connect(ui->bCont, SIGNAL( clicked() ), cont, SLOT( exec() ), Qt::AutoConnection );

}



 FenPrincipale::~FenPrincipale()
{
 delete ui;
}

.h :

 #ifndef FENPRINCIPALE_H
  #define FENPRINCIPALE_H

    #include <QWidget>
    #include <QApplication>

    namespace Ui {
    class FenPrincipale;
     }

    class FenPrincipale : public QWidget
   {
     Q_OBJECT

  public:
     explicit FenPrincipale(QWidget *parent = 0);
      void switch_callback(int);
      void execMoyMed (void);


  ~FenPrincipale();

 private:
   Ui::FenPrincipale *ui;
   };

    #endif // FENPRINCIPALE_H

メインクラス:

  #include <QCoreApplication>
  #include <QApplication>
  #include <QtGui>
   #include <QWidget>
   #include "fenprincipale.h"

    int main(int argc, char *argv[])
   {
        QApplication a(argc, argv);
        FenPrincipale fenetre;
        fenetre.show();
        return a.exec();

     }

「 moyenetmedian 」のスロット実装:

 void MoyenEtMedian::exec(void)
{
    const char* name = "Filtres";
    IplImage* img = cvLoadImage( "C:/Users/XELTINFO/ProjetVision/image.png" );
    IplImage* out = cvCreateImage( cvGetSize(img), IPL_DEPTH_8U, 3 );
    cvNamedWindow( name, 1 );
    cvShowImage(name, out);

    // Create trackbar
    cvCreateTrackbar2( "Filtre", name, &g_switch_value, 1,  &MoyenEtMedian::switch_callback, this );

    while( 1 ) {
        switch( filterInt ){
            case 0:
                cvSmooth( img, out, CV_BLUR, 7, 7 );
                break;
            case 1:
                cvSmooth( img, out, CV_MEDIAN, 7, 7 );
                break;
                    }
        if(filterInt != lastfilterInt){
            cvShowImage(name, out);
            lastfilterInt = filterInt;
        }
        if( cvWaitKey( 15 ) == 27 )
            break;
    }

    cvReleaseImage( &img );
    cvReleaseImage( &out );
    cvDestroyWindow( name );

  }

クラス宣言:

  #ifndef MOYENETMEDIAN_H
   #define MOYENETMEDIAN_H
   #include "ui_fenprincipale.h"
    #include<QObject>

     class MoyenEtMedian : public QObject
    {
   Q_OBJECT
public:
      MoyenEtMedian();
      static void switch_callback(int position, void*);

     public slots :
         void exec(void);

      };

   #endif // MOYENETMEDIAN_H

クラスの宣言とスロットの実装は、すべてのクラスで非常に似ています。これで足りない場合は追加します。

4

2 に答える 2

1

exec()スロットのイベントループはすぐには戻らないため、ブロックしています。代わりに、QWidgetをサブクラス化し、keyPressEvent()をオーバーライドして、現在のビジーループを実行する代わりに、Qtのイベントループからキーボード入力を取得する必要があります。

于 2012-12-14T17:54:22.560 に答える
1

したがって、OpenCV で Qt を使用する場合、while ループの代わりに Qt のタイマーを使用してポーリングをセットアップします。

QTimers を使用して OpenCV オブジェクトとやり取りするための非常に優れたチュートリアルがここにあります。

http://www.youtube.com/watch?v=0ONxIy8itRA

35 分または 38 分にジャンプして、彼がクラスをどのように書いているかを確認してください。

基本的に、タイミングを行う待機呼び出しを含む while ループを使用する代わりに、Qt に待機とタイミングを行わせます。

また、可能であれば、Qt にウィンドウを作成させ、OpenCV ウィンドウを Qt のウィンドウにネストして、Qt がウィンドウのイベントを管理できるようにします。

それが役立つことを願っています。

于 2012-12-14T20:19:03.443 に答える