From 1a389c3759379f03f3099987c9934174884647f5 Mon Sep 17 00:00:00 2001 From: Kevin Trogant Date: Tue, 23 Jul 2024 19:18:47 +0200 Subject: [PATCH] feat(launcher): Add cvar for selecting an output monitor --- src/launcher/launcher.c | 52 +++++++++++++++++++++++++++++++++++++---- 1 file changed, 48 insertions(+), 4 deletions(-) diff --git a/src/launcher/launcher.c b/src/launcher/launcher.c index eab6530..83afd14 100644 --- a/src/launcher/launcher.c +++ b/src/launcher/launcher.c @@ -27,6 +27,7 @@ RT_CVAR_I(rt_WindowWidth, "The window width. (Default: 1024)", 1024); RT_CVAR_I(rt_WindowHeight, "The window height. (Default: 768)", 768); RT_CVAR_I(rt_WindowMode, "The window mode. Available options: 0 (=Windowed), 1 (=Borderless Fullscreen), 2 (=Exclusive Fullscreen) (Default: 0)", 0); RT_CVAR_I(rt_FullscreenRefreshRate, "Requested refresh rate for exclusive fullscreen. Set to 0 to use the monitors current setting. (Default: 0)", 0); +RT_CVAR_S(rt_Monitor, "Name of the monitor on which the window should be created. Leave empty to use the primary monitor. (Default: "")", ""); RT_CVAR_S(rt_GameLib, "Path to the game library. Only usable in internal builds. (Default: "")", ""); @@ -54,6 +55,7 @@ static void SetupConfig(void) { rtRegisterCVAR(&rt_WindowWidth); rtRegisterCVAR(&rt_WindowHeight); rtRegisterCVAR(&rt_WindowMode); + rtRegisterCVAR(&rt_Monitor); rtRegisterCVAR(&rt_GameLib); @@ -112,6 +114,35 @@ out: }; } +static void DisplayMonitors(void) { + int count = 0; + GLFWmonitor **monitors = glfwGetMonitors(&count); + rtLog("LAUNCHER", "Available monitors:"); + for (int i = 0; i < count; ++i) { + const char *name =glfwGetMonitorName(monitors[i]); + if (monitors[i] != glfwGetPrimaryMonitor()) + rtLog("LAUNCHER", " - %s", name); + else + rtLog("LAUNCHER", " - %s (Primary)", name); + } +} + +static GLFWmonitor *ChooseMonitor(void) { + GLFWmonitor *monitor = glfwGetPrimaryMonitor(); + int count = 0; + + if (strcmp(rt_Monitor.s, "") == 0) { + return monitor; + } + GLFWmonitor **monitors = glfwGetMonitors(&count); + for (int i = 0; i < count; ++i) { + const char *name = glfwGetMonitorName(monitors[i]); + if (strcmp(name, rt_Monitor.s) == 0) + return monitors[i]; + } + return monitor; +} + static void GlfwErrorCB(int err, const char *desc) { rtReportError("GLFW", "GLFW Error %d: %s", err, desc); } @@ -126,6 +157,7 @@ static int Entry(int argc, char **argv) { rtShutdownRuntime(); return -1; } + DisplayMonitors(); /* Load the renderer library. * We need it before window creation, to give it an opportunity to register its cvars */ @@ -152,6 +184,8 @@ static int Entry(int argc, char **argv) { LoadGameAndRendererConfig(); /* Create the window */ + GLFWmonitor *monitor = ChooseMonitor(); + GLFWwindow *window = NULL; glfwWindowHint(GLFW_CLIENT_API, GLFW_NO_API); glfwWindowHint(GLFW_FOCUSED, GLFW_TRUE); @@ -164,7 +198,7 @@ static int Entry(int argc, char **argv) { glfwWindowHint(GLFW_GREEN_BITS, mode->greenBits); glfwWindowHint(GLFW_BLUE_BITS, mode->blueBits); glfwWindowHint(GLFW_REFRESH_RATE, mode->refreshRate); - window = glfwCreateWindow(mode->width, mode->height, rt_WindowTitle.s, glfwGetPrimaryMonitor(), NULL); + window = glfwCreateWindow(mode->width, mode->height, rt_WindowTitle.s, monitor, NULL); } else if (rt_WindowMode.i == WINDOW_MODE_FULLSCREEN) { int refresh_rate = rt_FullscreenRefreshRate.i; @@ -190,7 +224,7 @@ static int Entry(int argc, char **argv) { } } glfwWindowHint(GLFW_REFRESH_RATE, refresh_rate); - window = glfwCreateWindow(rt_WindowWidth.i, rt_WindowHeight.i, rt_WindowTitle.s, glfwGetPrimaryMonitor(), NULL); + window = glfwCreateWindow(rt_WindowWidth.i, rt_WindowHeight.i, rt_WindowTitle.s, monitor, NULL); } else { window = glfwCreateWindow(rt_WindowWidth.i, rt_WindowHeight.i, rt_WindowTitle.s, NULL, NULL); @@ -217,11 +251,21 @@ static int Entry(int argc, char **argv) { renderer_init_info.is_fullscreen = rt_WindowMode.i != WINDOW_MODE_WINDOWED; glfwGetFramebufferSize(window, (int*)&renderer_init_info.width, (int*)&renderer_init_info.height); if (g_renderer.Init(&renderer_init_info) != RT_SUCCESS) { - + rtReportError("LAUNCHER", "Failed to initialize the renderer."); + if (_game_lib) + rtCloseLib(_game_lib); + glfwTerminate(); + rtShutdownRuntime(); + return -1; } if (game.Init() != RT_SUCCESS) { - + rtReportError("LAUNCHER", "Failed to initialize the renderer."); + if (_game_lib) + rtCloseLib(_game_lib); + glfwTerminate(); + rtShutdownRuntime(); + return -1; } while (!glfwWindowShouldClose(window)) {