📄 windowmanager.cpp
字号:
} // 状態を元に戻す state = STATE_NORMAL;}/** 指定したウィンドウを追加する. @param control 指定するウィンドウ */void WindowManager::add(Control *control){ // NULLチェック if (control == NULL) return; // ウィンドウ追加 _controlList->add(new LinkedItem(control)); // フォーカスアウトメッセージを投げる //postFocusedToWindows(false, _controlList->getLength()); // 再描画メッセージを投げる if (_controlList->endItem->prev != NULL) { Control *c = (Control *)_controlList->endItem->prev->data; postFocusedToWindow(false, c); postRepaintToWindow(c); } // フォーカスインメッセージを投げる //postFocusedToWindow(true, control); control->setFocused(true);}/** 指定したウィンドウを削除する @param control 指定するウィンドウ */void WindowManager::remove(Control *control){ // NULLチェック if (control == NULL) return; // 描画が必要かどうかチェックする領域 Rect *rect = control->getRect(); Rect srect; srect.x = rect->x; srect.y = rect->y; srect.width = rect->width; srect.height = rect->height; // 削除メッセージを投げる if (MonAPI::Message::send(control->getThreadID(), MSG_GUISERVER_REMOVE, 0, 0, 0, NULL)) { //printf("WindowManager->Window: MSG_GUISERVER_REMOVE failed %d\n", control->getThreadID()); } else { //printf("WindowManager->Window: MSG_GUISERVER_REMOVE sended %d\n", control->getThreadID()); } // 背景を塗りつぶす restoreBackGround(control); // ウィンドウ削除 _controlList->remove(getLinkedItem(control)); // NULLチェック if (_controlList->endItem == NULL) return; // フォーカスアウトメッセージを投げる postFocusedToWindows(false, _controlList->getLength()); // 再描画メッセージを投げる postRepaintToWindows(_controlList->getLength() - 1, &srect); // フォーカスインメッセージを投げる Control *c = (Control *)_controlList->endItem->data; postFocusedToWindow(true, c);}/** 指定したウィンドウを非活性/活性化する. <ul> <li>enabledがかわる <li>非活性/活性化メッセージをウィンドウに投げる </ul> @param activated true/false */void WindowManager::postEnabledToWindow(bool enabled, Control *control){ // NULLチェック if (control == NULL) return; control->setEnabled(enabled); if (enabled == true) { MessageInfo info; if (MonAPI::Message::sendReceive(&info, control->getThreadID(), MSG_GUISERVER_ENABLED, 0, 0, 0, NULL)) { //printf("WindowManager->Window: MSG_GUISERVER_ENABLED failed %d\n", control->getThreadID()); } else { //printf("WindowManager->Window: MSG_GUISERVER_ENABLED sended %d\n", control->getThreadID()); } } else { MessageInfo info; if (MonAPI::Message::sendReceive(&info, control->getThreadID(), MSG_GUISERVER_DISABLED, 0, 0, 0, NULL)) { //printf("WindowManager->Window: MSG_GUISERVER_DISABLED failed %d\n", control->getThreadID()); } else { //printf("WindowManager->Window: MSG_GUISERVER_DISABLED sended %d\n", control->getThreadID()); } }}/** 指定したウィンドウをフォーカスアウト/フォーカスインする. <ul> <li>focusedがかわる <li>フォーカスアウト/フォーカスインメッセージをウィンドウに投げる </ul> @param activated true/false */void WindowManager::postFocusedToWindow(bool focused, Control *control){ // NULLチェック if (control == NULL) return; control->setFocused(focused); if (focused == true) { MessageInfo info; if (MonAPI::Message::sendReceive(&info, control->getThreadID(), MSG_GUISERVER_FOCUSED, 0, 0, 0, NULL)) { //printf("WindowManager->Window: MSG_GUISERVER_FOCUSED failed %d\n", control->getThreadID()); } else { //printf("WindowManager->Window: MSG_GUISERVER_FOCUSED sended %d\n", control->getThreadID()); } } else { MessageInfo info; if (MonAPI::Message::sendReceive(&info, control->getThreadID(), MSG_GUISERVER_DEFOCUSED, 0, 0, 0, NULL)) { //printf("WindowManager->Window: MSG_GUISERVER_DEFOCUSED failed %d\n", control->getThreadID()); } else { //printf("WindowManager->Window: MSG_GUISERVER_DEFOCUSED sended %d\n", control->getThreadID()); } }}/** 指定したウィンドウをフォーカスアウト/フォーカスインする. <ul> <li>focusedがかわる <li>フォーカスアウト/フォーカスインメッセージをウィンドウに投げる </ul> @param activated true/false @param length 0番目からlength番目までのウィンドウを対象にする */void WindowManager::postFocusedToWindows(bool focused, int length){ for (int i = 0; i < length; i++) { Control *control = (Control *)_controlList->getItem(i)->data; postFocusedToWindow(focused, control); }}/** 指定したウィンドウを非アイコン/アイコン化する. <ul> <li>iconifiedがかわる <li>非アイコン/アイコン化メッセージをウィンドウに投げる </ul> @param activated true/false */void WindowManager::postIconifiedToWindow(bool iconified, Control *control){ // NULLチェック if (control == NULL) return; control->setIconified(iconified); if (iconified == true) { MessageInfo info; if (MonAPI::Message::sendReceive(&info, control->getThreadID(), MSG_GUISERVER_ICONIFIED, 0, 0, 0, NULL)) { //printf("WindowManager->Window: MSG_GUISERVER_ICONIFIED failed %d\n", control->getThreadID()); } else { //printf("WindowManager->Window: MSG_GUISERVER_ICONIFIED sended %d\n", control->getThreadID()); } } else { MessageInfo info; if (MonAPI::Message::sendReceive(&info, control->getThreadID(), MSG_GUISERVER_DEICONIFIED, 0, 0, 0, NULL)) { //printf("WindowManager->Window: MSG_GUISERVER_DEICONIFIED failed %d\n", control->getThreadID()); } else { //printf("WindowManager->Window: MSG_GUISERVER_DEICONIFIED sended %d\n", control->getThreadID()); } }}/** 指定したウィンドウを再描画する. <ul> <li>再描画メッセージをウィンドウに投げる </ul> */void WindowManager::postRepaintToWindow(Control *control){ // NULLチェック if (control == NULL) return; // 再描画メッセージを投げる MessageInfo info; if (MonAPI::Message::sendReceive(&info, control->getThreadID(), MSG_GUISERVER_REPAINT, 0, 0, 0, NULL)) { //printf("WindowManager->Window: MSG_GUISERVER_REPAINT failed %d\n", control->getThreadID()); } else { //printf("WindowManager->Window: MSG_GUISERVER_REPAINT sended %d\n", control->getThreadID()); }}/** 指定したウィンドウを再描画する. <ul> <li>再描画メッセージをウィンドウに投げる <li>drectに重なっていないウィンドウは描画対象外にする </ul> @param length 0番目からlength番目までのウィンドウを対象にする @param drect 描画が必要かチェックする領域 */void WindowManager::postRepaintToWindows(int length, Rect *drect){ // 再描画メッセージを投げる for (int i = 0; i < length; i++) { Control *control = (Control *)_controlList->getItem(i)->data; if (checkNeedsPaint(control->getRect(), drect) == true) { postRepaintToWindow(control); } }}/** 指定したウィンドウの背景を復元する @param control NULLのときは画面全体を更新する */void WindowManager::restoreBackGround(Control *control){ #if 1 if (control == NULL) { // 背景を塗りつぶす if (wallpaper->getData() != NULL) { _g->drawImage(wallpaper, 0, 0); } else { _g->setColor(128,128,255); _g->fillRect(0, 0, width, height); } } else { Rect *rect = control->getRect(); // 背景を塗りつぶす if (wallpaper->getData() != NULL) { _g->drawImage(wallpaper, rect->x, rect->y, rect->width + 1, rect->height + 1); } else { _g->setColor(128,128,255); _g->fillRect(rect->x, rect->y, rect->width + 1, rect->height + 1); } } #endif}/** 再描画 */void WindowManager::repaint(){ int i, j; if (isRunning == false) return; if (firstpaint == false) firstpaint = true; // 背景を塗りつぶす restoreBackGround(NULL); // メニューバー _g->setColor(200,200,200); _g->fillRect(0,0,width,20); _g->setColor(128,128,128); _g->drawLine(0,20,width-1,20); _g->setColor(0,0,0); _g->drawLine(0,21,width-1,21); // 左上 _g->drawLine(0,0,4,0); _g->drawLine(0,1,2,1); _g->drawLine(0,2,1,2); _g->drawLine(0,3,0,3); _g->drawLine(0,4,0,4); // 右上 _g->drawLine(width-5,0,width-1,0); _g->drawLine(width-3,1,width-1,1); _g->drawLine(width-2,2,width-1,2); _g->drawLine(width-1,3,width-1,3); _g->drawLine(width-1,4,width-1,4); // 左下 _g->drawLine(0,height-5,0,height-5); _g->drawLine(0,height-4,0,height-4); _g->drawLine(0,height-3,1,height-3); _g->drawLine(0,height-2,2,height-2); _g->drawLine(0,height-1,4,height-1); // 右下 _g->drawLine(width-5,height-1,width-1,height-1); _g->drawLine(width-3,height-2,width-1,height-2); _g->drawLine(width-2,height-3,width-1,height-3); _g->drawLine(width-1,height-4,width-1,height-4); _g->drawLine(width-1,height-5,width-1,height-5); // オレンジアイコン#if defined(PEKOE) for (i = 0; i < 15; i++) { for (j = 0; j < 15; j++) { _g->drawPixel(19 + j, 4 + i, orangeIcon[i][j]); } }#elif defined(MONA) for (i = 0; i < 15; i++) { for (j = 0; j < 16; j++) { _g->drawPixel(18 + j, 4 + i, monaIcon[i][j]); } }#endif // メニュー int fh = FontManager::getInstance()->getHeight(); _g->setColor(128,128,128); _g->drawText(WINDOWMANAGER_MENU_TITLE_JP, 45, 4 + (16 - fh) / 2);}/** スレッドスタート. <ul> <li>whileループに入るため、stop() が呼ばれる限り抜けることはない <li>イベントは各ウィンドウに通知される </ul>*/void WindowManager::service(){ MessageInfo info; bool isMouseClick = false; // すでに起動していたら実行しない if (isRunning == true) { return; } else { isRunning = true; } // スタートメッセージ monapi_call_mouse_set_cursor(0); syscall_clear_screen(); syscall_set_cursor(0, 0); printf(WINDOWMANAGER_STARUP_MESSAGE); // テストアプリ monapi_call_process_execute_file(LAUNCHER_NAME, MONAPI_FALSE); // 再描画 repaint(); // draw mouse_cursor monapi_call_mouse_set_cursor(1); while (isRunning == true) { if(!MonAPI::Message::receive(&info)){ //if(!MonAPI::Message::peek(&info, 0, PEEK_REMOVE)){ switch(info.header){ case MSG_KEY_VIRTUAL_CODE: if (info.arg2 & KEY_MODIFIER_DOWN) { // ESCで終了 if (info.arg1 == 27) { isRunning = false; break; } } // ウィンドウが一つもないときはイベントを送らない if (_controlList->endItem != NULL) { if (info.arg2 & KEY_MODIFIER_DOWN) { onKeyPress(info.arg1, info.arg2, info.arg3); } else if (info.arg2 & KEY_MODIFIER_UP) { onKeyRelease(info.arg1, info.arg2, info.arg3); } } break; case MSG_MOUSE_INFO: monapi_call_mouse_set_cursor(0); // ウィンドウが一つもないときはイベントを送らない if (_controlList->endItem != NULL) { if(info.arg3 != 0){ // press if(isMouseClick == false){ isMouseClick = true; onMousePress(info.arg1, info.arg2); // drag }else{ onMouseDrag(info.arg1, info.arg2); } }else{ // release if(isMouseClick == true){ isMouseClick = false; onMouseRelease(info.arg1, info.arg2); } } } monapi_call_mouse_set_cursor(1); break; case MSG_GUISERVER_ADD: { Control *control = new Control(); control->setThreadID(info.arg1); // ランチャーID登録 if (_controlList->endItem == NULL) { launcherID = info.arg1; } int x = info.arg2 >> 16; int y = info.arg2 & 0xFFFF; int w = info.arg3 >> 16; int h = info.arg3 & 0xFFFF; control->setRect(x, y, w, h); //printf("Window->WindowManager MSG_GUISERVER_ADD received %d, %d, %d, %d, %d\n", info.arg1, x, y, w, h); add(control); } //MonAPI::Message::reply(&info); break; case MSG_GUISERVER_REMOVE: //printf("Window->WindowManager MSG_GUISERVER_REMOVE received %d\n", info.arg1); if (_controlList->endItem != NULL) { remove((Control *)_controlList->endItem->data); } break; case MSG_GUISERVER_STOP: //printf("Window->WindowManager MSG_GUISERVER_STOP received %d\n", info.arg1); isRunning = false; break; case MSG_GUISERVER_GETFONT: //printf("FontManager->WindowManager MSG_GUISERVER_GETFONT received\n"); { monapi_cmemoryinfo *fpMemory = FontManager::getInstance()->fpMemory; MonAPI::Message::reply(&info, fpMemory->Handle, fpMemory->Size); } break; case MSG_GUISERVER_RESTORE: // KUKURIを移植するのに必要 //printf("Window->WindowManager MSG_GUISERVER_RESTORE received %d\n", info.arg1); if (_controlList->endItem != NULL) { restoreBackGround((Control *)_controlList->endItem->data); } MonAPI::Message::reply(&info); break; } } } // 画面クリア monapi_call_mouse_set_cursor(0); syscall_clear_screen(); monapi_call_mouse_set_cursor(1); syscall_set_cursor(0, 0); printf(WINDOWMANAGER_SHUTDOWN_MESSAGE);}/** メイン */int MonaMain(List<char*>* pekoe){ WindowManager *manager = WindowManager::getInstance(); manager->service(); delete(manager); return 0;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -