Newer
Older
PrismSoftware / ECTrainer2 / ECTrainerGUI.cpp
@Toshiya Nakaguchi Toshiya Nakaguchi on 16 Feb 2020 3 KB SceneCameraクラス実装

#include "ECTrainer.h"
#include "ECTrainerGUI.h"

#define CVUI_IMPLEMENTATION
#include "cvui.h"

#ifdef _DEBUG
#include <iostream>
#endif

// コンストラクタ
ECTrainerGUI::ECTrainerGUI(ECTrainer* pEct) 
	:_pEct(pEct)
{

}

// 初期化
bool ECTrainerGUI::Init() {
	// 実行環境の情報取得
	GetDisplayInfo();
	// GUIウインドウ
	cvui::init(WIN_MAIN);
	_MainFrame.create(cv::Size(640, 400), CV_8UC3);
	// 刺激提示ウインドウ
	cv::namedWindow(WIN_DISP, cv::WINDOW_NORMAL | cv::WINDOW_OPENGL);
	if (_Displays.size() > 1) {
		// マルチモニタの場合 サブ画面でフルスクリーン化
		cv::moveWindow(WIN_DISP, _Displays[1].left, _Displays[1].top);
		cv::setWindowProperty(WIN_DISP, cv::WND_PROP_FULLSCREEN, cv::WINDOW_FULLSCREEN);
		_DispFrame.create(cv::Size(_Displays[1].right - _Displays[1].left, 
			_Displays[1].bottom - _Displays[1].top), CV_8UC3);
	}
	else {
		// シングルモニタの場合
		cv::moveWindow(WIN_DISP, _Displays[0].left, _Displays[0].top);
		_DispFrame.create(cv::Size(640, 480), CV_8UC3);
	}
	_Logo = cv::imread("../images/ECTrainerLogo640x91.png");
	_DispBuffer = cv::imread("../images/calib.png");
	_SceneBuffer.create(SCENE_BUFFER_SIZE, CV_8UC3);
	_SceneBuffer = CV_RGB(0, 0, 0);

	return true;
}

// イベントループ
bool ECTrainerGUI::MainLoop() {
	while (_pEct->IsRunning() && cv::getWindowProperty(WIN_MAIN, 0) >= 0) {
		// 表示ウインドウフレーム生成
		_DispFrame = cv::Scalar(0, 0, 0);
		cv::Rect roiRect;
		if (_DispBuffer.rows * _DispFrame.cols / _DispFrame.rows > _DispBuffer.cols) {
			roiRect.width = _DispBuffer.cols * _DispFrame.rows / _DispBuffer.rows;
			roiRect.height = _DispFrame.rows;
		} else {
			roiRect.width = _DispFrame.cols;
			roiRect.height = _DispBuffer.rows * _DispFrame.cols / _DispBuffer.cols;
		}
		roiRect.x = (_DispFrame.cols - roiRect.width) / 2;
		roiRect.y = (_DispFrame.rows - roiRect.height) / 2;
		cv::Mat roi(_DispFrame, roiRect);
		cv::resize(_DispBuffer, roi, roi.size());


		// メインウインドウフレーム生成
		_MainFrame = cv::Scalar(49, 52, 49);
		cvui::image(_MainFrame, 0, 0, _Logo);
		cvui::beginRow(_MainFrame, 10, 100, -1, -1, 10);
		cvui::beginColumn(-1, -1, 10);
		if (cvui::button("Calibration")) ;
		if (cvui::button("Start"));
		if (cvui::button("Quit")) _pEct->Stop();
		cvui::endColumn();
		cvui::beginColumn();
		cvui::text("View camera");
		cvui::space();
		cvui::image(_SceneBuffer);
		cvui::endColumn();
		cvui::endRow();


		// 画面表示
		cvui::update();
		cv::imshow(WIN_MAIN, _MainFrame);
		cv::imshow(WIN_DISP, _DispFrame);
		int key = cv::waitKey(1);
		if (key == KEY_ESC) _pEct->Stop();
	}
	return true;
}

void ECTrainerGUI::SetSceneBuffer(cv::Mat& img) {
	cv::resize(img, _SceneBuffer, SCENE_BUFFER_SIZE);
}

// 全ディスプレイの情報を取得
void ECTrainerGUI::GetDisplayInfo() {
	EnumDisplayMonitors(NULL, NULL, 
		(MONITORENUMPROC)MonitorEnumProc, (LPARAM)&_Displays);
#ifdef _DEBUG
	for (int i = 0; i < _Displays.size(); i++) {
		std::cout << "Monitor" << i << " : "
			<< _Displays[i].left << ","	<< _Displays[i].top << ","
			<< _Displays[i].right << "," << _Displays[i].bottom << std::endl;
	}
#endif // _DEBUG
}

// 各ディスプレイの情報を取得
BOOL CALLBACK ECTrainerGUI::MonitorEnumProc(
	HMONITOR hMon, HDC hdcMon, LPRECT lpMon, LPARAM dwData) {
	std::vector<RECT>* displays = (std::vector<RECT>*)dwData;
	displays->push_back(*lpMon);
	return TRUE;
}