Example #1
0
	static void HandleSizeChange(int newSizingType) {
		SavePosition();
		Core_NotifyWindowHidden(false);
		if (!g_Config.bPauseWhenMinimized) {
			NativeMessageReceived("window minimized", "false");
		}

		int width = 0, height = 0;
		RECT rc;
		GetClientRect(hwndMain, &rc);
		width = rc.right - rc.left;
		height = rc.bottom - rc.top;

		// Moves the internal display window to match the inner size of the main window.
		MoveWindow(hwndDisplay, 0, 0, width, height, TRUE);

		// Setting pixelWidth to be too small could have odd consequences.
		if (width >= 4 && height >= 4) {
			// The framebuffer manager reads these once per frame, hopefully safe enough.. should really use a mutex or some
			// much better mechanism.
			PSP_CoreParameter().pixelWidth = width;
			PSP_CoreParameter().pixelHeight = height;
		}

		DEBUG_LOG(SYSTEM, "Pixel width/height: %dx%d", PSP_CoreParameter().pixelWidth, PSP_CoreParameter().pixelHeight);

		if (UpdateScreenScale(width, height)) {
			NativeMessageReceived("gpu_resized", "");
		}

		// Don't save the window state if fullscreen.
		if (!g_Config.bFullScreen) {
			g_WindowState = newSizingType;
		}
	}
Example #2
0
	void _ViewFullScreen(HWND hWnd) {
		// Keep in mind normal window rectangle.
		::GetWindowRect(hWnd, &g_normalRC);

		// Remove caption and border styles.
		DWORD dwOldStyle = ::GetWindowLong(hWnd, GWL_STYLE);
		DWORD dwNewStyle = dwOldStyle & ~(WS_CAPTION | WS_THICKFRAME);
		::SetWindowLong(hWnd, GWL_STYLE, dwNewStyle);

		// Remove the menu bar.
		::SetMenu(hWnd, NULL);

		// Resize to full screen view.
		// NOTE: Use SWP_FRAMECHANGED to force redraw non-client.
		const int x = 0;
		const int y = 0;
		const int cx = ::GetSystemMetrics(SM_CXSCREEN);
		const int cy = ::GetSystemMetrics(SM_CYSCREEN);
		::SetWindowPos(hWnd, HWND_TOPMOST, x, y, cx, cy, SWP_FRAMECHANGED);

		// Set full screen indicator.
		g_bFullScreen = TRUE;
		CorrectCursor();
		ResizeDisplay();
		ShowOwnedPopups(hwndMain, FALSE);
		UpdateScreenScale();
	}
Example #3
0
void MainUI::resizeGL(int w, int h)
{
    bool smallWindow = g_Config.IsPortrait() ? (h < 480 + 80) : (w < 480 + 80);
    if (UpdateScreenScale(w, h, smallWindow)) {
        NativeMessageReceived("gpu resized", "");
    }
    xscale = w / this->width();
    yscale = h / this->height();

    PSP_CoreParameter().pixelWidth = pixel_xres;
    PSP_CoreParameter().pixelHeight = pixel_yres;
}
Example #4
0
static inline void UpdateRunLoop() {
	UpdateScreenScale();
	{
		{
#ifdef _WIN32
			lock_guard guard(input_state.lock);
			input_state.pad_buttons = 0;
			input_state.pad_lstick_x = 0;
			input_state.pad_lstick_y = 0;
			input_state.pad_rstick_x = 0;
			input_state.pad_rstick_y = 0;
			host->PollControllers(input_state);
			UpdateInputState(&input_state);
#endif
		}
		NativeUpdate(input_state);
		EndInputState(&input_state);
	}
	NativeRender();
}
Example #5
0
void Core_RunLoop()
{
	while (!coreState) {
		time_update();
		double startTime = time_now_d();
		UpdateScreenScale();
		{
			{
#ifdef _WIN32
				lock_guard guard(input_state.lock);
				input_state.pad_buttons = 0;
				input_state.pad_lstick_x = 0;
				input_state.pad_lstick_y = 0;
				input_state.pad_rstick_x = 0;
				input_state.pad_rstick_y = 0;
				// Temporary hack.
				if (GetAsyncKeyState(VK_ESCAPE)) {
					input_state.pad_buttons |= PAD_BUTTON_MENU;
				}
				host->PollControllers(input_state);
				UpdateInputState(&input_state);
#endif
			}
			NativeUpdate(input_state);
			EndInputState(&input_state);
		}
		NativeRender();
		time_update();
		// Simple throttling to not burn the GPU in the menu.
#ifdef _WIN32
		if (globalUIState != UISTATE_INGAME) {
			double sleepTime = 16.666 - (time_now_d() - startTime) * 1000.0;
			if (sleepTime > 0.0)
				Sleep((int)sleepTime);
			GL_SwapBuffers();
		} else if (!Core_IsStepping()) {
			GL_SwapBuffers();
		}
#endif
	}
}
Example #6
0
void Core_RunLoop()
{
	while (!coreState) {
		time_update();
		double startTime = time_now_d();
		UpdateScreenScale();
		{
			{
#ifdef _WIN32
				lock_guard guard(input_state.lock);
				input_state.pad_buttons = 0;
				input_state.pad_lstick_x = 0;
				input_state.pad_lstick_y = 0;
				input_state.pad_rstick_x = 0;
				input_state.pad_rstick_y = 0;
				host->PollControllers(input_state);
				UpdateInputState(&input_state);
#endif
			}
			NativeUpdate(input_state);
			EndInputState(&input_state);
		}
		NativeRender();
		time_update();
		// Simple throttling to not burn the GPU in the menu.
#ifdef _WIN32
		if (globalUIState != UISTATE_INGAME) {
			double diffTime = time_now_d() - startTime;
			int sleepTime = (int) (1000000.0 / 60.0) - (int) (diffTime * 1000000.0);
			if (sleepTime > 0)
				Sleep(sleepTime / 1000);
			GL_SwapBuffers();
		} else if (!Core_IsStepping()) {
			GL_SwapBuffers();
		}
#endif
	}
}
Example #7
0
unsigned int WINAPI TheThread(void *)
{
    _InterlockedExchange(&emuThreadReady, THREAD_INIT);

    setCurrentThreadName("EmuThread");

    // Native overwrites host. Can't allow that.

    Host *oldHost = host;
    UpdateScreenScale();

    NativeInit(__argc, (const char **)__argv, "1234", "1234", "1234");
    Host *nativeHost = host;
    host = oldHost;

    host->UpdateUI();

    //Check Colour depth
    HDC dc = GetDC(NULL);
    u32 colour_depth = GetDeviceCaps(dc, BITSPIXEL);
    ReleaseDC(NULL, dc);
    if (colour_depth != 32) {
        MessageBoxA(0, "Please switch your display to 32-bit colour mode", "OpenGL Error", MB_OK);
        ExitProcess(1);
    }

    std::string error_string;
    if (!host->InitGL(&error_string)) {
        Reporting::ReportMessage("OpenGL init error: %s", error_string.c_str());
        std::string full_error = StringFromFormat( "Failed initializing OpenGL. Try upgrading your graphics drivers.\n\nError message:\n\n%s", error_string.c_str());
        MessageBoxA(0, full_error.c_str(), "OpenGL Error", MB_OK | MB_ICONERROR);
        ERROR_LOG(BOOT, full_error.c_str());

        // No safe way out without OpenGL.
        ExitProcess(1);
    }

    NativeInitGraphics();

    INFO_LOG(BOOT, "Done.");
    _dbg_update_();

    if (coreState == CORE_POWERDOWN) {
        INFO_LOG(BOOT, "Exit before core loop.");
        goto shutdown;
    }

    _InterlockedExchange(&emuThreadReady, THREAD_CORE_LOOP);

    if (g_Config.bBrowse)
        PostMessage(MainWindow::GetHWND(), WM_COMMAND, ID_FILE_LOAD, 0);

    Core_EnableStepping(FALSE);

    while (globalUIState != UISTATE_EXIT)
    {
        // We're here again, so the game quit.  Restart Core_Run() which controls the UI.
        // This way they can load a new game.
        if (!Core_IsActive())
            UpdateUIState(UISTATE_MENU);

        Core_Run();
    }

shutdown:
    _InterlockedExchange(&emuThreadReady, THREAD_SHUTDOWN);

    NativeShutdownGraphics();

    host->ShutdownSound();
    host = nativeHost;
    NativeShutdown();
    host = oldHost;
    host->ShutdownGL();

    _InterlockedExchange(&emuThreadReady, THREAD_END);

    return 0;
}
Example #8
0
unsigned int WINAPI TheThread(void *)
{
    _InterlockedExchange(&emuThreadReady, THREAD_INIT);

    setCurrentThreadName("EmuThread");

    std::string memstick, flash0;
    GetSysDirectories(memstick, flash0);

    // Native overwrites host. Can't allow that.

    Host *oldHost = host;
    UpdateScreenScale();

    NativeInit(__argc, (const char **)__argv, memstick.c_str(), memstick.c_str(), "1234");
    Host *nativeHost = host;
    host = oldHost;

    host->UpdateUI();

    std::string error_string;
    if (!host->InitGL(&error_string)) {
        Reporting::ReportMessage("OpenGL init error: %s", error_string.c_str());
        std::string full_error = StringFromFormat( "Failed initializing OpenGL. Try upgrading your graphics drivers.\n\nError message:\n\n%s", error_string.c_str());
        MessageBoxA(0, full_error.c_str(), "OpenGL Error", MB_OK | MB_ICONERROR);
        ERROR_LOG(BOOT, full_error.c_str());
        goto shutdown;
    }

    NativeInitGraphics();

    INFO_LOG(BOOT, "Done.");
    _dbg_update_();

    if (coreState == CORE_POWERDOWN) {
        INFO_LOG(BOOT, "Exit before core loop.");
        goto shutdown;
    }

    _InterlockedExchange(&emuThreadReady, THREAD_CORE_LOOP);

    if (g_Config.bBrowse)
    {
        PostMessage(MainWindow::GetHWND(), WM_COMMAND, ID_FILE_LOAD, 0);
        //MainWindow::BrowseAndBoot("");
    }

    Core_EnableStepping(FALSE);

    while (globalUIState != UISTATE_EXIT)
    {
        Core_Run();

        // We're here again, so the game quit.  Restart Core_Run() which controls the UI.
        // This way they can load a new game.
        Core_UpdateState(CORE_RUNNING);
    }

shutdown:
    _InterlockedExchange(&emuThreadReady, THREAD_SHUTDOWN);

    NativeShutdownGraphics();
    host = nativeHost;
    NativeShutdown();
    host = oldHost;
    host->ShutdownGL();

    _InterlockedExchange(&emuThreadReady, THREAD_END);

    //The CPU should return when a game is stopped and cleanup should be done here,
    //so we can restart the plugins (or load new ones) for the next game
    return 0;
}
Example #9
0
	LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)	{
		switch (message) {
		case WM_CREATE:
			break;
			
		case WM_GETMINMAXINFO:
			{
				MINMAXINFO *minmax = reinterpret_cast<MINMAXINFO *>(lParam);
				RECT rc = { 0 };
				bool portrait = g_Config.IsPortrait();
				rc.right = portrait ? 272 : 480;
				rc.bottom = portrait ? 480 : 272;
				AdjustWindowRect(&rc, WS_OVERLAPPEDWINDOW, TRUE);
				minmax->ptMinTrackSize.x = rc.right - rc.left;
				minmax->ptMinTrackSize.y = rc.bottom - rc.top;
			}
			return 0;

		case WM_ACTIVATE:
			{
				bool pause = true;
				if (wParam == WA_ACTIVE || wParam == WA_CLICKACTIVE) {
					WindowsRawInput::GainFocus();
					InputDevice::GainFocus();
					g_activeWindow = WINDOW_MAINWINDOW;
					pause = false;
				}
				if (!noFocusPause && g_Config.bPauseOnLostFocus && GetUIState() == UISTATE_INGAME) {
					if (pause != Core_IsStepping()) {	// != is xor for bools
						if (disasmWindow[0])
							SendMessage(disasmWindow[0]->GetDlgHandle(), WM_COMMAND, IDC_STOPGO, 0);
						else
							Core_EnableStepping(pause);
					}
				}

				if (wParam == WA_ACTIVE) {
					NativeMessageReceived("got_focus", "");
				}
				if (wParam == WA_INACTIVE) {
					NativeMessageReceived("lost_focus", "");
					WindowsRawInput::LoseFocus();
					InputDevice::LoseFocus();
				}
			}
			break;

    case WM_ERASEBKGND:
      // This window is always covered by DisplayWindow. No reason to erase.
			return 1;

		case WM_MOVE:
			SavePosition();
			break;

		case WM_SIZE:
			switch (wParam) {
			case SIZE_RESTORED:
			case SIZE_MAXIMIZED:
				if (g_IgnoreWM_SIZE) {
					return DefWindowProc(hWnd, message, wParam, lParam);
				} else {
					SavePosition();
					Core_NotifyWindowHidden(false);
					if (!g_Config.bPauseWhenMinimized) {
						NativeMessageReceived("window minimized", "false");
					}

					int width = 0, height = 0;
					RECT rc;
					GetClientRect(hwndMain, &rc);
					width = rc.right - rc.left;
					height = rc.bottom - rc.top;

					// Moves the internal display window to match the inner size of the main window.
					MoveWindow(hwndDisplay, 0, 0, width, height, TRUE);

					// Setting pixelWidth to be too small could have odd consequences.
					if (width >= 4 && height >= 4) {
						// The framebuffer manager reads these once per frame, hopefully safe enough.. should really use a mutex or some
						// much better mechanism.
						PSP_CoreParameter().pixelWidth = width;
						PSP_CoreParameter().pixelHeight = height;
					}

					UpdateRenderResolution();

					if (UpdateScreenScale(width, height, IsWindowSmall())) {
						NativeMessageReceived("gpu resized", "");
					}

					// Don't save the window state if fullscreen.
					if (!g_Config.bFullScreen) {
						g_WindowState = wParam;
					}
				}
				break;

			case SIZE_MINIMIZED:
				Core_NotifyWindowHidden(true);
				if (!g_Config.bPauseWhenMinimized) {
					NativeMessageReceived("window minimized", "true");
				}
				break;
			default:
				break;
			}
			break;

    case WM_TIMER:
			// Hack: Take the opportunity to also show/hide the mouse cursor in fullscreen mode.
			switch (wParam) {
			case TIMER_CURSORUPDATE:
				CorrectCursor();
				return 0;

			case TIMER_CURSORMOVEUPDATE:
				hideCursor = true;
				KillTimer(hWnd, TIMER_CURSORMOVEUPDATE);
				return 0;
			}
			break;

		// For some reason, need to catch this here rather than in DisplayProc.
		case WM_MOUSEWHEEL:
			{
				int wheelDelta = (short)(wParam >> 16);
				KeyInput key;
				key.deviceId = DEVICE_ID_MOUSE;

				if (wheelDelta < 0) {
					key.keyCode = NKCODE_EXT_MOUSEWHEEL_DOWN;
					wheelDelta = -wheelDelta;
				} else {
					key.keyCode = NKCODE_EXT_MOUSEWHEEL_UP;
				}
				// There's no separate keyup event for mousewheel events, let's pass them both together.
				// This also means it really won't work great for key mapping :( Need to build a 1 frame delay or something.
				key.flags = KEY_DOWN | KEY_UP | KEY_HASWHEELDELTA | (wheelDelta << 16);
				NativeKey(key);
			}
			break;

		case WM_COMMAND:
			{
				if (!EmuThread_Ready())
					return DefWindowProc(hWnd, message, wParam, lParam);

				MainWindowMenu_Process(hWnd, wParam);
			}
			break;

		case WM_USER_TOGGLE_FULLSCREEN:
			ToggleFullscreen(hwndMain, !g_Config.bFullScreen);
			break;

		case WM_INPUT:
			return WindowsRawInput::Process(hWnd, wParam, lParam);

		// TODO: Could do something useful with WM_INPUT_DEVICE_CHANGE?

		// Not sure why we are actually getting WM_CHAR even though we use RawInput, but alright..
		case WM_CHAR:
			return WindowsRawInput::ProcessChar(hWnd, wParam, lParam);

		case WM_VERYSLEEPY_MSG:
			switch (wParam) {
			case VERYSLEEPY_WPARAM_SUPPORTED:
				return TRUE;

			case VERYSLEEPY_WPARAM_GETADDRINFO:
				{
					VerySleepy_AddrInfo *info = (VerySleepy_AddrInfo *)lParam;
					const u8 *ptr = (const u8 *)info->addr;
					std::string name;

					if (MIPSComp::jit && MIPSComp::jit->DescribeCodePtr(ptr, name)) {
						swprintf_s(info->name, L"Jit::%S", name.c_str());
						return TRUE;
					}
					if (gpu && gpu->DescribeCodePtr(ptr, name)) {
						swprintf_s(info->name, L"GPU::%S", name.c_str());
						return TRUE;
					}
				}
				return FALSE;

			default:
				return FALSE;
			}
			break;

		case WM_DROPFILES:
			{
				if (!EmuThread_Ready())
					return DefWindowProc(hWnd, message, wParam, lParam);

				HDROP hdrop = (HDROP)wParam;
				int count = DragQueryFile(hdrop,0xFFFFFFFF,0,0);
				if (count != 1) {
					MessageBox(hwndMain,L"You can only load one file at a time",L"Error",MB_ICONINFORMATION);
				}
				else
				{
					TCHAR filename[512];
					DragQueryFile(hdrop,0,filename,512);
					TCHAR *type = filename+_tcslen(filename)-3;
					
					NativeMessageReceived("boot", ConvertWStringToUTF8(filename).c_str());
					Core_EnableStepping(false);
				}
			}
			break;

		case WM_CLOSE:
			EmuThread_Stop();
			InputDevice::StopPolling();
			WindowsRawInput::Shutdown();

			return DefWindowProc(hWnd,message,wParam,lParam);

		case WM_DESTROY:
			KillTimer(hWnd, TIMER_CURSORUPDATE);
			KillTimer(hWnd, TIMER_CURSORMOVEUPDATE);
			PostQuitMessage(0);
			break;

		case WM_USER + 1:
			if (disasmWindow[0])
				disasmWindow[0]->NotifyMapLoaded();
			if (memoryWindow[0])
				memoryWindow[0]->NotifyMapLoaded();

			if (disasmWindow[0])
				disasmWindow[0]->UpdateDialog();

			SetForegroundWindow(hwndMain);
			break;

		case WM_USER_SAVESTATE_FINISH:
			SetCursor(LoadCursor(0, IDC_ARROW));
			break;

		case WM_USER_UPDATE_UI:
			TranslateMenus(hwndMain, menu);
			break;

		case WM_USER_UPDATE_SCREEN:
			ShowScreenResolution();
			break;

		case WM_USER_WINDOW_TITLE_CHANGED:
			UpdateWindowTitle();
			break;

		case WM_USER_BROWSE_BOOT_DONE:
			BrowseAndBootDone();
			break;

		case WM_MENUSELECT:
			// Unfortunately, accelerate keys (hotkeys) shares the same enabled/disabled states
			// with corresponding menu items.
			UpdateMenus();
			WindowsRawInput::NotifyMenu();
			break;

		// Turn off the screensaver.
		// Note that if there's a screensaver password, this simple method
		// doesn't work on Vista or higher.
		case WM_SYSCOMMAND:
			{
				switch (wParam) {
				case SC_SCREENSAVE:  
					return 0;
				case SC_MONITORPOWER:
					return 0;      
				}
				return DefWindowProc(hWnd, message, wParam, lParam);
			}

		default:
			return DefWindowProc(hWnd, message, wParam, lParam);
		}
		return 0;
	}