2011-08-21 90 views
4

我用OpenCV捕獲攝像頭圖像。這工作正常。但是,如果我想在按下按鈕時關閉OpenCV,它不起作用(同時嘗試使用cvDestroyWindow("NameOfWindow")cvDestroyAllWindows())。窗口保持打開狀態,應用程序仍在運行。試圖關閉OpenCV窗口沒有效果

OpenCV是在與主GUI分開的線程上初始化的。

我在我的Mac上使用Juce框架和C++。但同樣的問題也發生在使用Qt和Windows窗體的Windows上,當OpenCV窗口有它自己的cvNamedWindow時。

這裏是VST插件編輯器類的基本代碼:

PluginEditor.cpp

#include <opencv2/opencv.hpp> 
#include <opencv2/highgui/highgui.hpp> 

#include "PluginProcessor.h" 
#include "PluginEditor.h" 

// 
TestAudioProcessorEditor::TestAudioProcessorEditor (TestAudioProcessor* ownerFilter) 
: AudioProcessorEditor (ownerFilter) 
{ 

    // This is where our plugin's editor size is set. 
    setSize (500, 500); 

    // open the tracker 
    openTracker(); 
} 

// code for opencv handling 
TestAudioProcessorEditor::openTracker() { 

    // KEY LINE: Start the window thread 
    cvStartWindowThread(); 

    // Create a window in which the captured images will be presented 
    cvNamedWindow("Webcam", CV_WINDOW_AUTOSIZE); 

    cvWaitKey(0); 

    cvDestroyWindow("Webcam"); 
    // window should disappear! 
} 


TestAudioProcessorEditor::~TestAudioProcessorEditor() 
{ 

} 

// paint stuff on the vst plugin surface 
void TestAudioProcessorEditor::paint (Graphics& g) { 
} 
+0

是否'cvDestroyAllWindows();'當它通過一個簡單的按鈕按下觸發? –

+1

你是否在產生窗口的同一個線程中調用'cvDestroy'(即叫做'cvNamedWindow')? – Jacob

+0

@Dan Cecile是的,我試過這個,但它不起作用。 – sn3ek

回答

5

你可能會丟失這件作品是對cvStartWindowThread函數的調用。

在Linux上,使用GTK HighGUI,這個例子再現了您的問題,直到我撥打cvStartWindowThread

#include "opencv2/highgui/highgui.hpp" 
#include "opencv2/imgproc/imgproc_c.h" 

#include <iostream> 
using namespace std; 

int main(int argc, char** argv) 
{ 
    // KEY LINE: Start the window thread 
    cvStartWindowThread(); 

    // Open a window 
    cvNamedWindow("original", 0); 

    // Wait until a key gets pressed inside the window 
    cvWaitKey(0); 

    // Close the window 
    cvDestroyWindow("original"); 

    // Verify that the window is closed 
    cout<<"The window should be closed now. (Press ENTER to continue.)"<<endl; 
    string line; 
    getline(cin, line); 
    cout<<"Exiting..."<<endl; 
} 

如果cvStartWindowThread沒有幫助,試試你的cvDestroy電話後做給cvWaitKey一個額外的電話。

要運行的例子中,使用GCC編譯:

g++ destroy_window.cpp -o destroy_window -lopencv_core -lopencv_highgui 
+0

我試過你的代碼作爲Xcode4中的控制檯應用程序,它工作正常。但是,如果我嘗試在我的Juce VST插件中執行相同的代碼,該窗口似乎認識到銷燬方法,但opencv窗口凍結並且什麼也沒有發生。我在destroy方法後拋出了一些日誌消息,但它們不會出現在我的日誌文件中,所以看起來,//驗證窗口關閉後的驗證代碼將不會被執行。 – sn3ek

+0

@ sn3ek我不得不說這聽起來像是多線程死鎖; 'cvDestroyWindow'開始執行,但在繼續之前它只是等待另一個線程。你可以在調用'cvDestroyWindow'之前使用調試器來暫停程序,並檢查其他線程正在運行嗎? –

+0

我需要糾正我的評論。代碼'cvDestroyWindow()'將被執行。我用幾條日誌消息試了一下。但窗口不會消失,但我的插件的其餘部分已關閉,我可以重新打開插件,並使用新的opencv窗口。有點奇怪! – sn3ek