1b877906bSopenharmony_ci//======================================================================== 2b877906bSopenharmony_ci// GLFW 3.5 X11 - www.glfw.org 3b877906bSopenharmony_ci//------------------------------------------------------------------------ 4b877906bSopenharmony_ci// Copyright (c) 2002-2006 Marcus Geelnard 5b877906bSopenharmony_ci// Copyright (c) 2006-2019 Camilla Löwy <elmindreda@glfw.org> 6b877906bSopenharmony_ci// 7b877906bSopenharmony_ci// This software is provided 'as-is', without any express or implied 8b877906bSopenharmony_ci// warranty. In no event will the authors be held liable for any damages 9b877906bSopenharmony_ci// arising from the use of this software. 10b877906bSopenharmony_ci// 11b877906bSopenharmony_ci// Permission is granted to anyone to use this software for any purpose, 12b877906bSopenharmony_ci// including commercial applications, and to alter it and redistribute it 13b877906bSopenharmony_ci// freely, subject to the following restrictions: 14b877906bSopenharmony_ci// 15b877906bSopenharmony_ci// 1. The origin of this software must not be misrepresented; you must not 16b877906bSopenharmony_ci// claim that you wrote the original software. If you use this software 17b877906bSopenharmony_ci// in a product, an acknowledgment in the product documentation would 18b877906bSopenharmony_ci// be appreciated but is not required. 19b877906bSopenharmony_ci// 20b877906bSopenharmony_ci// 2. Altered source versions must be plainly marked as such, and must not 21b877906bSopenharmony_ci// be misrepresented as being the original software. 22b877906bSopenharmony_ci// 23b877906bSopenharmony_ci// 3. This notice may not be removed or altered from any source 24b877906bSopenharmony_ci// distribution. 25b877906bSopenharmony_ci// 26b877906bSopenharmony_ci//======================================================================== 27b877906bSopenharmony_ci 28b877906bSopenharmony_ci#include "internal.h" 29b877906bSopenharmony_ci 30b877906bSopenharmony_ci#if defined(_GLFW_X11) 31b877906bSopenharmony_ci 32b877906bSopenharmony_ci#include <stdlib.h> 33b877906bSopenharmony_ci#include <string.h> 34b877906bSopenharmony_ci#include <limits.h> 35b877906bSopenharmony_ci#include <stdio.h> 36b877906bSopenharmony_ci#include <locale.h> 37b877906bSopenharmony_ci#include <unistd.h> 38b877906bSopenharmony_ci#include <fcntl.h> 39b877906bSopenharmony_ci#include <errno.h> 40b877906bSopenharmony_ci#include <assert.h> 41b877906bSopenharmony_ci 42b877906bSopenharmony_ci 43b877906bSopenharmony_ci// Translate the X11 KeySyms for a key to a GLFW key code 44b877906bSopenharmony_ci// NOTE: This is only used as a fallback, in case the XKB method fails 45b877906bSopenharmony_ci// It is layout-dependent and will fail partially on most non-US layouts 46b877906bSopenharmony_ci// 47b877906bSopenharmony_cistatic int translateKeySyms(const KeySym* keysyms, int width) 48b877906bSopenharmony_ci{ 49b877906bSopenharmony_ci if (width > 1) 50b877906bSopenharmony_ci { 51b877906bSopenharmony_ci switch (keysyms[1]) 52b877906bSopenharmony_ci { 53b877906bSopenharmony_ci case XK_KP_0: return GLFW_KEY_KP_0; 54b877906bSopenharmony_ci case XK_KP_1: return GLFW_KEY_KP_1; 55b877906bSopenharmony_ci case XK_KP_2: return GLFW_KEY_KP_2; 56b877906bSopenharmony_ci case XK_KP_3: return GLFW_KEY_KP_3; 57b877906bSopenharmony_ci case XK_KP_4: return GLFW_KEY_KP_4; 58b877906bSopenharmony_ci case XK_KP_5: return GLFW_KEY_KP_5; 59b877906bSopenharmony_ci case XK_KP_6: return GLFW_KEY_KP_6; 60b877906bSopenharmony_ci case XK_KP_7: return GLFW_KEY_KP_7; 61b877906bSopenharmony_ci case XK_KP_8: return GLFW_KEY_KP_8; 62b877906bSopenharmony_ci case XK_KP_9: return GLFW_KEY_KP_9; 63b877906bSopenharmony_ci case XK_KP_Separator: 64b877906bSopenharmony_ci case XK_KP_Decimal: return GLFW_KEY_KP_DECIMAL; 65b877906bSopenharmony_ci case XK_KP_Equal: return GLFW_KEY_KP_EQUAL; 66b877906bSopenharmony_ci case XK_KP_Enter: return GLFW_KEY_KP_ENTER; 67b877906bSopenharmony_ci default: break; 68b877906bSopenharmony_ci } 69b877906bSopenharmony_ci } 70b877906bSopenharmony_ci 71b877906bSopenharmony_ci switch (keysyms[0]) 72b877906bSopenharmony_ci { 73b877906bSopenharmony_ci case XK_Escape: return GLFW_KEY_ESCAPE; 74b877906bSopenharmony_ci case XK_Tab: return GLFW_KEY_TAB; 75b877906bSopenharmony_ci case XK_Shift_L: return GLFW_KEY_LEFT_SHIFT; 76b877906bSopenharmony_ci case XK_Shift_R: return GLFW_KEY_RIGHT_SHIFT; 77b877906bSopenharmony_ci case XK_Control_L: return GLFW_KEY_LEFT_CONTROL; 78b877906bSopenharmony_ci case XK_Control_R: return GLFW_KEY_RIGHT_CONTROL; 79b877906bSopenharmony_ci case XK_Meta_L: 80b877906bSopenharmony_ci case XK_Alt_L: return GLFW_KEY_LEFT_ALT; 81b877906bSopenharmony_ci case XK_Mode_switch: // Mapped to Alt_R on many keyboards 82b877906bSopenharmony_ci case XK_ISO_Level3_Shift: // AltGr on at least some machines 83b877906bSopenharmony_ci case XK_Meta_R: 84b877906bSopenharmony_ci case XK_Alt_R: return GLFW_KEY_RIGHT_ALT; 85b877906bSopenharmony_ci case XK_Super_L: return GLFW_KEY_LEFT_SUPER; 86b877906bSopenharmony_ci case XK_Super_R: return GLFW_KEY_RIGHT_SUPER; 87b877906bSopenharmony_ci case XK_Menu: return GLFW_KEY_MENU; 88b877906bSopenharmony_ci case XK_Num_Lock: return GLFW_KEY_NUM_LOCK; 89b877906bSopenharmony_ci case XK_Caps_Lock: return GLFW_KEY_CAPS_LOCK; 90b877906bSopenharmony_ci case XK_Print: return GLFW_KEY_PRINT_SCREEN; 91b877906bSopenharmony_ci case XK_Scroll_Lock: return GLFW_KEY_SCROLL_LOCK; 92b877906bSopenharmony_ci case XK_Pause: return GLFW_KEY_PAUSE; 93b877906bSopenharmony_ci case XK_Delete: return GLFW_KEY_DELETE; 94b877906bSopenharmony_ci case XK_BackSpace: return GLFW_KEY_BACKSPACE; 95b877906bSopenharmony_ci case XK_Return: return GLFW_KEY_ENTER; 96b877906bSopenharmony_ci case XK_Home: return GLFW_KEY_HOME; 97b877906bSopenharmony_ci case XK_End: return GLFW_KEY_END; 98b877906bSopenharmony_ci case XK_Page_Up: return GLFW_KEY_PAGE_UP; 99b877906bSopenharmony_ci case XK_Page_Down: return GLFW_KEY_PAGE_DOWN; 100b877906bSopenharmony_ci case XK_Insert: return GLFW_KEY_INSERT; 101b877906bSopenharmony_ci case XK_Left: return GLFW_KEY_LEFT; 102b877906bSopenharmony_ci case XK_Right: return GLFW_KEY_RIGHT; 103b877906bSopenharmony_ci case XK_Down: return GLFW_KEY_DOWN; 104b877906bSopenharmony_ci case XK_Up: return GLFW_KEY_UP; 105b877906bSopenharmony_ci case XK_F1: return GLFW_KEY_F1; 106b877906bSopenharmony_ci case XK_F2: return GLFW_KEY_F2; 107b877906bSopenharmony_ci case XK_F3: return GLFW_KEY_F3; 108b877906bSopenharmony_ci case XK_F4: return GLFW_KEY_F4; 109b877906bSopenharmony_ci case XK_F5: return GLFW_KEY_F5; 110b877906bSopenharmony_ci case XK_F6: return GLFW_KEY_F6; 111b877906bSopenharmony_ci case XK_F7: return GLFW_KEY_F7; 112b877906bSopenharmony_ci case XK_F8: return GLFW_KEY_F8; 113b877906bSopenharmony_ci case XK_F9: return GLFW_KEY_F9; 114b877906bSopenharmony_ci case XK_F10: return GLFW_KEY_F10; 115b877906bSopenharmony_ci case XK_F11: return GLFW_KEY_F11; 116b877906bSopenharmony_ci case XK_F12: return GLFW_KEY_F12; 117b877906bSopenharmony_ci case XK_F13: return GLFW_KEY_F13; 118b877906bSopenharmony_ci case XK_F14: return GLFW_KEY_F14; 119b877906bSopenharmony_ci case XK_F15: return GLFW_KEY_F15; 120b877906bSopenharmony_ci case XK_F16: return GLFW_KEY_F16; 121b877906bSopenharmony_ci case XK_F17: return GLFW_KEY_F17; 122b877906bSopenharmony_ci case XK_F18: return GLFW_KEY_F18; 123b877906bSopenharmony_ci case XK_F19: return GLFW_KEY_F19; 124b877906bSopenharmony_ci case XK_F20: return GLFW_KEY_F20; 125b877906bSopenharmony_ci case XK_F21: return GLFW_KEY_F21; 126b877906bSopenharmony_ci case XK_F22: return GLFW_KEY_F22; 127b877906bSopenharmony_ci case XK_F23: return GLFW_KEY_F23; 128b877906bSopenharmony_ci case XK_F24: return GLFW_KEY_F24; 129b877906bSopenharmony_ci case XK_F25: return GLFW_KEY_F25; 130b877906bSopenharmony_ci 131b877906bSopenharmony_ci // Numeric keypad 132b877906bSopenharmony_ci case XK_KP_Divide: return GLFW_KEY_KP_DIVIDE; 133b877906bSopenharmony_ci case XK_KP_Multiply: return GLFW_KEY_KP_MULTIPLY; 134b877906bSopenharmony_ci case XK_KP_Subtract: return GLFW_KEY_KP_SUBTRACT; 135b877906bSopenharmony_ci case XK_KP_Add: return GLFW_KEY_KP_ADD; 136b877906bSopenharmony_ci 137b877906bSopenharmony_ci // These should have been detected in secondary keysym test above! 138b877906bSopenharmony_ci case XK_KP_Insert: return GLFW_KEY_KP_0; 139b877906bSopenharmony_ci case XK_KP_End: return GLFW_KEY_KP_1; 140b877906bSopenharmony_ci case XK_KP_Down: return GLFW_KEY_KP_2; 141b877906bSopenharmony_ci case XK_KP_Page_Down: return GLFW_KEY_KP_3; 142b877906bSopenharmony_ci case XK_KP_Left: return GLFW_KEY_KP_4; 143b877906bSopenharmony_ci case XK_KP_Right: return GLFW_KEY_KP_6; 144b877906bSopenharmony_ci case XK_KP_Home: return GLFW_KEY_KP_7; 145b877906bSopenharmony_ci case XK_KP_Up: return GLFW_KEY_KP_8; 146b877906bSopenharmony_ci case XK_KP_Page_Up: return GLFW_KEY_KP_9; 147b877906bSopenharmony_ci case XK_KP_Delete: return GLFW_KEY_KP_DECIMAL; 148b877906bSopenharmony_ci case XK_KP_Equal: return GLFW_KEY_KP_EQUAL; 149b877906bSopenharmony_ci case XK_KP_Enter: return GLFW_KEY_KP_ENTER; 150b877906bSopenharmony_ci 151b877906bSopenharmony_ci // Last resort: Check for printable keys (should not happen if the XKB 152b877906bSopenharmony_ci // extension is available). This will give a layout dependent mapping 153b877906bSopenharmony_ci // (which is wrong, and we may miss some keys, especially on non-US 154b877906bSopenharmony_ci // keyboards), but it's better than nothing... 155b877906bSopenharmony_ci case XK_a: return GLFW_KEY_A; 156b877906bSopenharmony_ci case XK_b: return GLFW_KEY_B; 157b877906bSopenharmony_ci case XK_c: return GLFW_KEY_C; 158b877906bSopenharmony_ci case XK_d: return GLFW_KEY_D; 159b877906bSopenharmony_ci case XK_e: return GLFW_KEY_E; 160b877906bSopenharmony_ci case XK_f: return GLFW_KEY_F; 161b877906bSopenharmony_ci case XK_g: return GLFW_KEY_G; 162b877906bSopenharmony_ci case XK_h: return GLFW_KEY_H; 163b877906bSopenharmony_ci case XK_i: return GLFW_KEY_I; 164b877906bSopenharmony_ci case XK_j: return GLFW_KEY_J; 165b877906bSopenharmony_ci case XK_k: return GLFW_KEY_K; 166b877906bSopenharmony_ci case XK_l: return GLFW_KEY_L; 167b877906bSopenharmony_ci case XK_m: return GLFW_KEY_M; 168b877906bSopenharmony_ci case XK_n: return GLFW_KEY_N; 169b877906bSopenharmony_ci case XK_o: return GLFW_KEY_O; 170b877906bSopenharmony_ci case XK_p: return GLFW_KEY_P; 171b877906bSopenharmony_ci case XK_q: return GLFW_KEY_Q; 172b877906bSopenharmony_ci case XK_r: return GLFW_KEY_R; 173b877906bSopenharmony_ci case XK_s: return GLFW_KEY_S; 174b877906bSopenharmony_ci case XK_t: return GLFW_KEY_T; 175b877906bSopenharmony_ci case XK_u: return GLFW_KEY_U; 176b877906bSopenharmony_ci case XK_v: return GLFW_KEY_V; 177b877906bSopenharmony_ci case XK_w: return GLFW_KEY_W; 178b877906bSopenharmony_ci case XK_x: return GLFW_KEY_X; 179b877906bSopenharmony_ci case XK_y: return GLFW_KEY_Y; 180b877906bSopenharmony_ci case XK_z: return GLFW_KEY_Z; 181b877906bSopenharmony_ci case XK_1: return GLFW_KEY_1; 182b877906bSopenharmony_ci case XK_2: return GLFW_KEY_2; 183b877906bSopenharmony_ci case XK_3: return GLFW_KEY_3; 184b877906bSopenharmony_ci case XK_4: return GLFW_KEY_4; 185b877906bSopenharmony_ci case XK_5: return GLFW_KEY_5; 186b877906bSopenharmony_ci case XK_6: return GLFW_KEY_6; 187b877906bSopenharmony_ci case XK_7: return GLFW_KEY_7; 188b877906bSopenharmony_ci case XK_8: return GLFW_KEY_8; 189b877906bSopenharmony_ci case XK_9: return GLFW_KEY_9; 190b877906bSopenharmony_ci case XK_0: return GLFW_KEY_0; 191b877906bSopenharmony_ci case XK_space: return GLFW_KEY_SPACE; 192b877906bSopenharmony_ci case XK_minus: return GLFW_KEY_MINUS; 193b877906bSopenharmony_ci case XK_equal: return GLFW_KEY_EQUAL; 194b877906bSopenharmony_ci case XK_bracketleft: return GLFW_KEY_LEFT_BRACKET; 195b877906bSopenharmony_ci case XK_bracketright: return GLFW_KEY_RIGHT_BRACKET; 196b877906bSopenharmony_ci case XK_backslash: return GLFW_KEY_BACKSLASH; 197b877906bSopenharmony_ci case XK_semicolon: return GLFW_KEY_SEMICOLON; 198b877906bSopenharmony_ci case XK_apostrophe: return GLFW_KEY_APOSTROPHE; 199b877906bSopenharmony_ci case XK_grave: return GLFW_KEY_GRAVE_ACCENT; 200b877906bSopenharmony_ci case XK_comma: return GLFW_KEY_COMMA; 201b877906bSopenharmony_ci case XK_period: return GLFW_KEY_PERIOD; 202b877906bSopenharmony_ci case XK_slash: return GLFW_KEY_SLASH; 203b877906bSopenharmony_ci case XK_less: return GLFW_KEY_WORLD_1; // At least in some layouts... 204b877906bSopenharmony_ci default: break; 205b877906bSopenharmony_ci } 206b877906bSopenharmony_ci 207b877906bSopenharmony_ci // No matching translation was found 208b877906bSopenharmony_ci return GLFW_KEY_UNKNOWN; 209b877906bSopenharmony_ci} 210b877906bSopenharmony_ci 211b877906bSopenharmony_ci// Create key code translation tables 212b877906bSopenharmony_ci// 213b877906bSopenharmony_cistatic void createKeyTables(void) 214b877906bSopenharmony_ci{ 215b877906bSopenharmony_ci int scancodeMin, scancodeMax; 216b877906bSopenharmony_ci 217b877906bSopenharmony_ci memset(_glfw.x11.keycodes, -1, sizeof(_glfw.x11.keycodes)); 218b877906bSopenharmony_ci memset(_glfw.x11.scancodes, -1, sizeof(_glfw.x11.scancodes)); 219b877906bSopenharmony_ci 220b877906bSopenharmony_ci if (_glfw.x11.xkb.available) 221b877906bSopenharmony_ci { 222b877906bSopenharmony_ci // Use XKB to determine physical key locations independently of the 223b877906bSopenharmony_ci // current keyboard layout 224b877906bSopenharmony_ci 225b877906bSopenharmony_ci XkbDescPtr desc = XkbGetMap(_glfw.x11.display, 0, XkbUseCoreKbd); 226b877906bSopenharmony_ci XkbGetNames(_glfw.x11.display, XkbKeyNamesMask | XkbKeyAliasesMask, desc); 227b877906bSopenharmony_ci 228b877906bSopenharmony_ci scancodeMin = desc->min_key_code; 229b877906bSopenharmony_ci scancodeMax = desc->max_key_code; 230b877906bSopenharmony_ci 231b877906bSopenharmony_ci const struct 232b877906bSopenharmony_ci { 233b877906bSopenharmony_ci int key; 234b877906bSopenharmony_ci char* name; 235b877906bSopenharmony_ci } keymap[] = 236b877906bSopenharmony_ci { 237b877906bSopenharmony_ci { GLFW_KEY_GRAVE_ACCENT, "TLDE" }, 238b877906bSopenharmony_ci { GLFW_KEY_1, "AE01" }, 239b877906bSopenharmony_ci { GLFW_KEY_2, "AE02" }, 240b877906bSopenharmony_ci { GLFW_KEY_3, "AE03" }, 241b877906bSopenharmony_ci { GLFW_KEY_4, "AE04" }, 242b877906bSopenharmony_ci { GLFW_KEY_5, "AE05" }, 243b877906bSopenharmony_ci { GLFW_KEY_6, "AE06" }, 244b877906bSopenharmony_ci { GLFW_KEY_7, "AE07" }, 245b877906bSopenharmony_ci { GLFW_KEY_8, "AE08" }, 246b877906bSopenharmony_ci { GLFW_KEY_9, "AE09" }, 247b877906bSopenharmony_ci { GLFW_KEY_0, "AE10" }, 248b877906bSopenharmony_ci { GLFW_KEY_MINUS, "AE11" }, 249b877906bSopenharmony_ci { GLFW_KEY_EQUAL, "AE12" }, 250b877906bSopenharmony_ci { GLFW_KEY_Q, "AD01" }, 251b877906bSopenharmony_ci { GLFW_KEY_W, "AD02" }, 252b877906bSopenharmony_ci { GLFW_KEY_E, "AD03" }, 253b877906bSopenharmony_ci { GLFW_KEY_R, "AD04" }, 254b877906bSopenharmony_ci { GLFW_KEY_T, "AD05" }, 255b877906bSopenharmony_ci { GLFW_KEY_Y, "AD06" }, 256b877906bSopenharmony_ci { GLFW_KEY_U, "AD07" }, 257b877906bSopenharmony_ci { GLFW_KEY_I, "AD08" }, 258b877906bSopenharmony_ci { GLFW_KEY_O, "AD09" }, 259b877906bSopenharmony_ci { GLFW_KEY_P, "AD10" }, 260b877906bSopenharmony_ci { GLFW_KEY_LEFT_BRACKET, "AD11" }, 261b877906bSopenharmony_ci { GLFW_KEY_RIGHT_BRACKET, "AD12" }, 262b877906bSopenharmony_ci { GLFW_KEY_A, "AC01" }, 263b877906bSopenharmony_ci { GLFW_KEY_S, "AC02" }, 264b877906bSopenharmony_ci { GLFW_KEY_D, "AC03" }, 265b877906bSopenharmony_ci { GLFW_KEY_F, "AC04" }, 266b877906bSopenharmony_ci { GLFW_KEY_G, "AC05" }, 267b877906bSopenharmony_ci { GLFW_KEY_H, "AC06" }, 268b877906bSopenharmony_ci { GLFW_KEY_J, "AC07" }, 269b877906bSopenharmony_ci { GLFW_KEY_K, "AC08" }, 270b877906bSopenharmony_ci { GLFW_KEY_L, "AC09" }, 271b877906bSopenharmony_ci { GLFW_KEY_SEMICOLON, "AC10" }, 272b877906bSopenharmony_ci { GLFW_KEY_APOSTROPHE, "AC11" }, 273b877906bSopenharmony_ci { GLFW_KEY_Z, "AB01" }, 274b877906bSopenharmony_ci { GLFW_KEY_X, "AB02" }, 275b877906bSopenharmony_ci { GLFW_KEY_C, "AB03" }, 276b877906bSopenharmony_ci { GLFW_KEY_V, "AB04" }, 277b877906bSopenharmony_ci { GLFW_KEY_B, "AB05" }, 278b877906bSopenharmony_ci { GLFW_KEY_N, "AB06" }, 279b877906bSopenharmony_ci { GLFW_KEY_M, "AB07" }, 280b877906bSopenharmony_ci { GLFW_KEY_COMMA, "AB08" }, 281b877906bSopenharmony_ci { GLFW_KEY_PERIOD, "AB09" }, 282b877906bSopenharmony_ci { GLFW_KEY_SLASH, "AB10" }, 283b877906bSopenharmony_ci { GLFW_KEY_BACKSLASH, "BKSL" }, 284b877906bSopenharmony_ci { GLFW_KEY_WORLD_1, "LSGT" }, 285b877906bSopenharmony_ci { GLFW_KEY_SPACE, "SPCE" }, 286b877906bSopenharmony_ci { GLFW_KEY_ESCAPE, "ESC" }, 287b877906bSopenharmony_ci { GLFW_KEY_ENTER, "RTRN" }, 288b877906bSopenharmony_ci { GLFW_KEY_TAB, "TAB" }, 289b877906bSopenharmony_ci { GLFW_KEY_BACKSPACE, "BKSP" }, 290b877906bSopenharmony_ci { GLFW_KEY_INSERT, "INS" }, 291b877906bSopenharmony_ci { GLFW_KEY_DELETE, "DELE" }, 292b877906bSopenharmony_ci { GLFW_KEY_RIGHT, "RGHT" }, 293b877906bSopenharmony_ci { GLFW_KEY_LEFT, "LEFT" }, 294b877906bSopenharmony_ci { GLFW_KEY_DOWN, "DOWN" }, 295b877906bSopenharmony_ci { GLFW_KEY_UP, "UP" }, 296b877906bSopenharmony_ci { GLFW_KEY_PAGE_UP, "PGUP" }, 297b877906bSopenharmony_ci { GLFW_KEY_PAGE_DOWN, "PGDN" }, 298b877906bSopenharmony_ci { GLFW_KEY_HOME, "HOME" }, 299b877906bSopenharmony_ci { GLFW_KEY_END, "END" }, 300b877906bSopenharmony_ci { GLFW_KEY_CAPS_LOCK, "CAPS" }, 301b877906bSopenharmony_ci { GLFW_KEY_SCROLL_LOCK, "SCLK" }, 302b877906bSopenharmony_ci { GLFW_KEY_NUM_LOCK, "NMLK" }, 303b877906bSopenharmony_ci { GLFW_KEY_PRINT_SCREEN, "PRSC" }, 304b877906bSopenharmony_ci { GLFW_KEY_PAUSE, "PAUS" }, 305b877906bSopenharmony_ci { GLFW_KEY_F1, "FK01" }, 306b877906bSopenharmony_ci { GLFW_KEY_F2, "FK02" }, 307b877906bSopenharmony_ci { GLFW_KEY_F3, "FK03" }, 308b877906bSopenharmony_ci { GLFW_KEY_F4, "FK04" }, 309b877906bSopenharmony_ci { GLFW_KEY_F5, "FK05" }, 310b877906bSopenharmony_ci { GLFW_KEY_F6, "FK06" }, 311b877906bSopenharmony_ci { GLFW_KEY_F7, "FK07" }, 312b877906bSopenharmony_ci { GLFW_KEY_F8, "FK08" }, 313b877906bSopenharmony_ci { GLFW_KEY_F9, "FK09" }, 314b877906bSopenharmony_ci { GLFW_KEY_F10, "FK10" }, 315b877906bSopenharmony_ci { GLFW_KEY_F11, "FK11" }, 316b877906bSopenharmony_ci { GLFW_KEY_F12, "FK12" }, 317b877906bSopenharmony_ci { GLFW_KEY_F13, "FK13" }, 318b877906bSopenharmony_ci { GLFW_KEY_F14, "FK14" }, 319b877906bSopenharmony_ci { GLFW_KEY_F15, "FK15" }, 320b877906bSopenharmony_ci { GLFW_KEY_F16, "FK16" }, 321b877906bSopenharmony_ci { GLFW_KEY_F17, "FK17" }, 322b877906bSopenharmony_ci { GLFW_KEY_F18, "FK18" }, 323b877906bSopenharmony_ci { GLFW_KEY_F19, "FK19" }, 324b877906bSopenharmony_ci { GLFW_KEY_F20, "FK20" }, 325b877906bSopenharmony_ci { GLFW_KEY_F21, "FK21" }, 326b877906bSopenharmony_ci { GLFW_KEY_F22, "FK22" }, 327b877906bSopenharmony_ci { GLFW_KEY_F23, "FK23" }, 328b877906bSopenharmony_ci { GLFW_KEY_F24, "FK24" }, 329b877906bSopenharmony_ci { GLFW_KEY_F25, "FK25" }, 330b877906bSopenharmony_ci { GLFW_KEY_KP_0, "KP0" }, 331b877906bSopenharmony_ci { GLFW_KEY_KP_1, "KP1" }, 332b877906bSopenharmony_ci { GLFW_KEY_KP_2, "KP2" }, 333b877906bSopenharmony_ci { GLFW_KEY_KP_3, "KP3" }, 334b877906bSopenharmony_ci { GLFW_KEY_KP_4, "KP4" }, 335b877906bSopenharmony_ci { GLFW_KEY_KP_5, "KP5" }, 336b877906bSopenharmony_ci { GLFW_KEY_KP_6, "KP6" }, 337b877906bSopenharmony_ci { GLFW_KEY_KP_7, "KP7" }, 338b877906bSopenharmony_ci { GLFW_KEY_KP_8, "KP8" }, 339b877906bSopenharmony_ci { GLFW_KEY_KP_9, "KP9" }, 340b877906bSopenharmony_ci { GLFW_KEY_KP_DECIMAL, "KPDL" }, 341b877906bSopenharmony_ci { GLFW_KEY_KP_DIVIDE, "KPDV" }, 342b877906bSopenharmony_ci { GLFW_KEY_KP_MULTIPLY, "KPMU" }, 343b877906bSopenharmony_ci { GLFW_KEY_KP_SUBTRACT, "KPSU" }, 344b877906bSopenharmony_ci { GLFW_KEY_KP_ADD, "KPAD" }, 345b877906bSopenharmony_ci { GLFW_KEY_KP_ENTER, "KPEN" }, 346b877906bSopenharmony_ci { GLFW_KEY_KP_EQUAL, "KPEQ" }, 347b877906bSopenharmony_ci { GLFW_KEY_LEFT_SHIFT, "LFSH" }, 348b877906bSopenharmony_ci { GLFW_KEY_LEFT_CONTROL, "LCTL" }, 349b877906bSopenharmony_ci { GLFW_KEY_LEFT_ALT, "LALT" }, 350b877906bSopenharmony_ci { GLFW_KEY_LEFT_SUPER, "LWIN" }, 351b877906bSopenharmony_ci { GLFW_KEY_RIGHT_SHIFT, "RTSH" }, 352b877906bSopenharmony_ci { GLFW_KEY_RIGHT_CONTROL, "RCTL" }, 353b877906bSopenharmony_ci { GLFW_KEY_RIGHT_ALT, "RALT" }, 354b877906bSopenharmony_ci { GLFW_KEY_RIGHT_ALT, "LVL3" }, 355b877906bSopenharmony_ci { GLFW_KEY_RIGHT_ALT, "MDSW" }, 356b877906bSopenharmony_ci { GLFW_KEY_RIGHT_SUPER, "RWIN" }, 357b877906bSopenharmony_ci { GLFW_KEY_MENU, "MENU" } 358b877906bSopenharmony_ci }; 359b877906bSopenharmony_ci 360b877906bSopenharmony_ci // Find the X11 key code -> GLFW key code mapping 361b877906bSopenharmony_ci for (int scancode = scancodeMin; scancode <= scancodeMax; scancode++) 362b877906bSopenharmony_ci { 363b877906bSopenharmony_ci int key = GLFW_KEY_UNKNOWN; 364b877906bSopenharmony_ci 365b877906bSopenharmony_ci // Map the key name to a GLFW key code. Note: We use the US 366b877906bSopenharmony_ci // keyboard layout. Because function keys aren't mapped correctly 367b877906bSopenharmony_ci // when using traditional KeySym translations, they are mapped 368b877906bSopenharmony_ci // here instead. 369b877906bSopenharmony_ci for (int i = 0; i < sizeof(keymap) / sizeof(keymap[0]); i++) 370b877906bSopenharmony_ci { 371b877906bSopenharmony_ci if (strncmp(desc->names->keys[scancode].name, 372b877906bSopenharmony_ci keymap[i].name, 373b877906bSopenharmony_ci XkbKeyNameLength) == 0) 374b877906bSopenharmony_ci { 375b877906bSopenharmony_ci key = keymap[i].key; 376b877906bSopenharmony_ci break; 377b877906bSopenharmony_ci } 378b877906bSopenharmony_ci } 379b877906bSopenharmony_ci 380b877906bSopenharmony_ci // Fall back to key aliases in case the key name did not match 381b877906bSopenharmony_ci for (int i = 0; i < desc->names->num_key_aliases; i++) 382b877906bSopenharmony_ci { 383b877906bSopenharmony_ci if (key != GLFW_KEY_UNKNOWN) 384b877906bSopenharmony_ci break; 385b877906bSopenharmony_ci 386b877906bSopenharmony_ci if (strncmp(desc->names->key_aliases[i].real, 387b877906bSopenharmony_ci desc->names->keys[scancode].name, 388b877906bSopenharmony_ci XkbKeyNameLength) != 0) 389b877906bSopenharmony_ci { 390b877906bSopenharmony_ci continue; 391b877906bSopenharmony_ci } 392b877906bSopenharmony_ci 393b877906bSopenharmony_ci for (int j = 0; j < sizeof(keymap) / sizeof(keymap[0]); j++) 394b877906bSopenharmony_ci { 395b877906bSopenharmony_ci if (strncmp(desc->names->key_aliases[i].alias, 396b877906bSopenharmony_ci keymap[j].name, 397b877906bSopenharmony_ci XkbKeyNameLength) == 0) 398b877906bSopenharmony_ci { 399b877906bSopenharmony_ci key = keymap[j].key; 400b877906bSopenharmony_ci break; 401b877906bSopenharmony_ci } 402b877906bSopenharmony_ci } 403b877906bSopenharmony_ci } 404b877906bSopenharmony_ci 405b877906bSopenharmony_ci _glfw.x11.keycodes[scancode] = key; 406b877906bSopenharmony_ci } 407b877906bSopenharmony_ci 408b877906bSopenharmony_ci XkbFreeNames(desc, XkbKeyNamesMask, True); 409b877906bSopenharmony_ci XkbFreeKeyboard(desc, 0, True); 410b877906bSopenharmony_ci } 411b877906bSopenharmony_ci else 412b877906bSopenharmony_ci XDisplayKeycodes(_glfw.x11.display, &scancodeMin, &scancodeMax); 413b877906bSopenharmony_ci 414b877906bSopenharmony_ci int width; 415b877906bSopenharmony_ci KeySym* keysyms = XGetKeyboardMapping(_glfw.x11.display, 416b877906bSopenharmony_ci scancodeMin, 417b877906bSopenharmony_ci scancodeMax - scancodeMin + 1, 418b877906bSopenharmony_ci &width); 419b877906bSopenharmony_ci 420b877906bSopenharmony_ci for (int scancode = scancodeMin; scancode <= scancodeMax; scancode++) 421b877906bSopenharmony_ci { 422b877906bSopenharmony_ci // Translate the un-translated key codes using traditional X11 KeySym 423b877906bSopenharmony_ci // lookups 424b877906bSopenharmony_ci if (_glfw.x11.keycodes[scancode] < 0) 425b877906bSopenharmony_ci { 426b877906bSopenharmony_ci const size_t base = (scancode - scancodeMin) * width; 427b877906bSopenharmony_ci _glfw.x11.keycodes[scancode] = translateKeySyms(&keysyms[base], width); 428b877906bSopenharmony_ci } 429b877906bSopenharmony_ci 430b877906bSopenharmony_ci // Store the reverse translation for faster key name lookup 431b877906bSopenharmony_ci if (_glfw.x11.keycodes[scancode] > 0) 432b877906bSopenharmony_ci _glfw.x11.scancodes[_glfw.x11.keycodes[scancode]] = scancode; 433b877906bSopenharmony_ci } 434b877906bSopenharmony_ci 435b877906bSopenharmony_ci XFree(keysyms); 436b877906bSopenharmony_ci} 437b877906bSopenharmony_ci 438b877906bSopenharmony_ci// Check whether the IM has a usable style 439b877906bSopenharmony_ci// 440b877906bSopenharmony_cistatic GLFWbool hasUsableInputMethodStyle(void) 441b877906bSopenharmony_ci{ 442b877906bSopenharmony_ci GLFWbool found = GLFW_FALSE; 443b877906bSopenharmony_ci XIMStyles* styles = NULL; 444b877906bSopenharmony_ci 445b877906bSopenharmony_ci if (XGetIMValues(_glfw.x11.im, XNQueryInputStyle, &styles, NULL) != NULL) 446b877906bSopenharmony_ci return GLFW_FALSE; 447b877906bSopenharmony_ci 448b877906bSopenharmony_ci for (unsigned int i = 0; i < styles->count_styles; i++) 449b877906bSopenharmony_ci { 450b877906bSopenharmony_ci if (styles->supported_styles[i] == (XIMPreeditNothing | XIMStatusNothing)) 451b877906bSopenharmony_ci { 452b877906bSopenharmony_ci found = GLFW_TRUE; 453b877906bSopenharmony_ci break; 454b877906bSopenharmony_ci } 455b877906bSopenharmony_ci } 456b877906bSopenharmony_ci 457b877906bSopenharmony_ci XFree(styles); 458b877906bSopenharmony_ci return found; 459b877906bSopenharmony_ci} 460b877906bSopenharmony_ci 461b877906bSopenharmony_cistatic void inputMethodDestroyCallback(XIM im, XPointer clientData, XPointer callData) 462b877906bSopenharmony_ci{ 463b877906bSopenharmony_ci _glfw.x11.im = NULL; 464b877906bSopenharmony_ci} 465b877906bSopenharmony_ci 466b877906bSopenharmony_cistatic void inputMethodInstantiateCallback(Display* display, 467b877906bSopenharmony_ci XPointer clientData, 468b877906bSopenharmony_ci XPointer callData) 469b877906bSopenharmony_ci{ 470b877906bSopenharmony_ci if (_glfw.x11.im) 471b877906bSopenharmony_ci return; 472b877906bSopenharmony_ci 473b877906bSopenharmony_ci _glfw.x11.im = XOpenIM(_glfw.x11.display, 0, NULL, NULL); 474b877906bSopenharmony_ci if (_glfw.x11.im) 475b877906bSopenharmony_ci { 476b877906bSopenharmony_ci if (!hasUsableInputMethodStyle()) 477b877906bSopenharmony_ci { 478b877906bSopenharmony_ci XCloseIM(_glfw.x11.im); 479b877906bSopenharmony_ci _glfw.x11.im = NULL; 480b877906bSopenharmony_ci } 481b877906bSopenharmony_ci } 482b877906bSopenharmony_ci 483b877906bSopenharmony_ci if (_glfw.x11.im) 484b877906bSopenharmony_ci { 485b877906bSopenharmony_ci XIMCallback callback; 486b877906bSopenharmony_ci callback.callback = (XIMProc) inputMethodDestroyCallback; 487b877906bSopenharmony_ci callback.client_data = NULL; 488b877906bSopenharmony_ci XSetIMValues(_glfw.x11.im, XNDestroyCallback, &callback, NULL); 489b877906bSopenharmony_ci 490b877906bSopenharmony_ci for (_GLFWwindow* window = _glfw.windowListHead; window; window = window->next) 491b877906bSopenharmony_ci _glfwCreateInputContextX11(window); 492b877906bSopenharmony_ci } 493b877906bSopenharmony_ci} 494b877906bSopenharmony_ci 495b877906bSopenharmony_ci// Return the atom ID only if it is listed in the specified array 496b877906bSopenharmony_ci// 497b877906bSopenharmony_cistatic Atom getAtomIfSupported(Atom* supportedAtoms, 498b877906bSopenharmony_ci unsigned long atomCount, 499b877906bSopenharmony_ci const char* atomName) 500b877906bSopenharmony_ci{ 501b877906bSopenharmony_ci const Atom atom = XInternAtom(_glfw.x11.display, atomName, False); 502b877906bSopenharmony_ci 503b877906bSopenharmony_ci for (unsigned long i = 0; i < atomCount; i++) 504b877906bSopenharmony_ci { 505b877906bSopenharmony_ci if (supportedAtoms[i] == atom) 506b877906bSopenharmony_ci return atom; 507b877906bSopenharmony_ci } 508b877906bSopenharmony_ci 509b877906bSopenharmony_ci return None; 510b877906bSopenharmony_ci} 511b877906bSopenharmony_ci 512b877906bSopenharmony_ci// Check whether the running window manager is EWMH-compliant 513b877906bSopenharmony_ci// 514b877906bSopenharmony_cistatic void detectEWMH(void) 515b877906bSopenharmony_ci{ 516b877906bSopenharmony_ci // First we read the _NET_SUPPORTING_WM_CHECK property on the root window 517b877906bSopenharmony_ci 518b877906bSopenharmony_ci Window* windowFromRoot = NULL; 519b877906bSopenharmony_ci if (!_glfwGetWindowPropertyX11(_glfw.x11.root, 520b877906bSopenharmony_ci _glfw.x11.NET_SUPPORTING_WM_CHECK, 521b877906bSopenharmony_ci XA_WINDOW, 522b877906bSopenharmony_ci (unsigned char**) &windowFromRoot)) 523b877906bSopenharmony_ci { 524b877906bSopenharmony_ci return; 525b877906bSopenharmony_ci } 526b877906bSopenharmony_ci 527b877906bSopenharmony_ci _glfwGrabErrorHandlerX11(); 528b877906bSopenharmony_ci 529b877906bSopenharmony_ci // If it exists, it should be the XID of a top-level window 530b877906bSopenharmony_ci // Then we look for the same property on that window 531b877906bSopenharmony_ci 532b877906bSopenharmony_ci Window* windowFromChild = NULL; 533b877906bSopenharmony_ci if (!_glfwGetWindowPropertyX11(*windowFromRoot, 534b877906bSopenharmony_ci _glfw.x11.NET_SUPPORTING_WM_CHECK, 535b877906bSopenharmony_ci XA_WINDOW, 536b877906bSopenharmony_ci (unsigned char**) &windowFromChild)) 537b877906bSopenharmony_ci { 538b877906bSopenharmony_ci XFree(windowFromRoot); 539b877906bSopenharmony_ci return; 540b877906bSopenharmony_ci } 541b877906bSopenharmony_ci 542b877906bSopenharmony_ci _glfwReleaseErrorHandlerX11(); 543b877906bSopenharmony_ci 544b877906bSopenharmony_ci // If the property exists, it should contain the XID of the window 545b877906bSopenharmony_ci 546b877906bSopenharmony_ci if (*windowFromRoot != *windowFromChild) 547b877906bSopenharmony_ci { 548b877906bSopenharmony_ci XFree(windowFromRoot); 549b877906bSopenharmony_ci XFree(windowFromChild); 550b877906bSopenharmony_ci return; 551b877906bSopenharmony_ci } 552b877906bSopenharmony_ci 553b877906bSopenharmony_ci XFree(windowFromRoot); 554b877906bSopenharmony_ci XFree(windowFromChild); 555b877906bSopenharmony_ci 556b877906bSopenharmony_ci // We are now fairly sure that an EWMH-compliant WM is currently running 557b877906bSopenharmony_ci // We can now start querying the WM about what features it supports by 558b877906bSopenharmony_ci // looking in the _NET_SUPPORTED property on the root window 559b877906bSopenharmony_ci // It should contain a list of supported EWMH protocol and state atoms 560b877906bSopenharmony_ci 561b877906bSopenharmony_ci Atom* supportedAtoms = NULL; 562b877906bSopenharmony_ci const unsigned long atomCount = 563b877906bSopenharmony_ci _glfwGetWindowPropertyX11(_glfw.x11.root, 564b877906bSopenharmony_ci _glfw.x11.NET_SUPPORTED, 565b877906bSopenharmony_ci XA_ATOM, 566b877906bSopenharmony_ci (unsigned char**) &supportedAtoms); 567b877906bSopenharmony_ci 568b877906bSopenharmony_ci // See which of the atoms we support that are supported by the WM 569b877906bSopenharmony_ci 570b877906bSopenharmony_ci _glfw.x11.NET_WM_STATE = 571b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_WM_STATE"); 572b877906bSopenharmony_ci _glfw.x11.NET_WM_STATE_ABOVE = 573b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_WM_STATE_ABOVE"); 574b877906bSopenharmony_ci _glfw.x11.NET_WM_STATE_FULLSCREEN = 575b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_WM_STATE_FULLSCREEN"); 576b877906bSopenharmony_ci _glfw.x11.NET_WM_STATE_MAXIMIZED_VERT = 577b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_WM_STATE_MAXIMIZED_VERT"); 578b877906bSopenharmony_ci _glfw.x11.NET_WM_STATE_MAXIMIZED_HORZ = 579b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_WM_STATE_MAXIMIZED_HORZ"); 580b877906bSopenharmony_ci _glfw.x11.NET_WM_STATE_DEMANDS_ATTENTION = 581b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_WM_STATE_DEMANDS_ATTENTION"); 582b877906bSopenharmony_ci _glfw.x11.NET_WM_FULLSCREEN_MONITORS = 583b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_WM_FULLSCREEN_MONITORS"); 584b877906bSopenharmony_ci _glfw.x11.NET_WM_WINDOW_TYPE = 585b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_WM_WINDOW_TYPE"); 586b877906bSopenharmony_ci _glfw.x11.NET_WM_WINDOW_TYPE_NORMAL = 587b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_WM_WINDOW_TYPE_NORMAL"); 588b877906bSopenharmony_ci _glfw.x11.NET_WORKAREA = 589b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_WORKAREA"); 590b877906bSopenharmony_ci _glfw.x11.NET_CURRENT_DESKTOP = 591b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_CURRENT_DESKTOP"); 592b877906bSopenharmony_ci _glfw.x11.NET_ACTIVE_WINDOW = 593b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_ACTIVE_WINDOW"); 594b877906bSopenharmony_ci _glfw.x11.NET_FRAME_EXTENTS = 595b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_FRAME_EXTENTS"); 596b877906bSopenharmony_ci _glfw.x11.NET_REQUEST_FRAME_EXTENTS = 597b877906bSopenharmony_ci getAtomIfSupported(supportedAtoms, atomCount, "_NET_REQUEST_FRAME_EXTENTS"); 598b877906bSopenharmony_ci 599b877906bSopenharmony_ci if (supportedAtoms) 600b877906bSopenharmony_ci XFree(supportedAtoms); 601b877906bSopenharmony_ci} 602b877906bSopenharmony_ci 603b877906bSopenharmony_ci// Look for and initialize supported X11 extensions 604b877906bSopenharmony_ci// 605b877906bSopenharmony_cistatic GLFWbool initExtensions(void) 606b877906bSopenharmony_ci{ 607b877906bSopenharmony_ci#if defined(__OpenBSD__) || defined(__NetBSD__) 608b877906bSopenharmony_ci _glfw.x11.vidmode.handle = _glfwPlatformLoadModule("libXxf86vm.so"); 609b877906bSopenharmony_ci#else 610b877906bSopenharmony_ci _glfw.x11.vidmode.handle = _glfwPlatformLoadModule("libXxf86vm.so.1"); 611b877906bSopenharmony_ci#endif 612b877906bSopenharmony_ci if (_glfw.x11.vidmode.handle) 613b877906bSopenharmony_ci { 614b877906bSopenharmony_ci _glfw.x11.vidmode.QueryExtension = (PFN_XF86VidModeQueryExtension) 615b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.vidmode.handle, "XF86VidModeQueryExtension"); 616b877906bSopenharmony_ci _glfw.x11.vidmode.GetGammaRamp = (PFN_XF86VidModeGetGammaRamp) 617b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.vidmode.handle, "XF86VidModeGetGammaRamp"); 618b877906bSopenharmony_ci _glfw.x11.vidmode.SetGammaRamp = (PFN_XF86VidModeSetGammaRamp) 619b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.vidmode.handle, "XF86VidModeSetGammaRamp"); 620b877906bSopenharmony_ci _glfw.x11.vidmode.GetGammaRampSize = (PFN_XF86VidModeGetGammaRampSize) 621b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.vidmode.handle, "XF86VidModeGetGammaRampSize"); 622b877906bSopenharmony_ci 623b877906bSopenharmony_ci _glfw.x11.vidmode.available = 624b877906bSopenharmony_ci XF86VidModeQueryExtension(_glfw.x11.display, 625b877906bSopenharmony_ci &_glfw.x11.vidmode.eventBase, 626b877906bSopenharmony_ci &_glfw.x11.vidmode.errorBase); 627b877906bSopenharmony_ci } 628b877906bSopenharmony_ci 629b877906bSopenharmony_ci#if defined(__CYGWIN__) 630b877906bSopenharmony_ci _glfw.x11.xi.handle = _glfwPlatformLoadModule("libXi-6.so"); 631b877906bSopenharmony_ci#elif defined(__OpenBSD__) || defined(__NetBSD__) 632b877906bSopenharmony_ci _glfw.x11.xi.handle = _glfwPlatformLoadModule("libXi.so"); 633b877906bSopenharmony_ci#else 634b877906bSopenharmony_ci _glfw.x11.xi.handle = _glfwPlatformLoadModule("libXi.so.6"); 635b877906bSopenharmony_ci#endif 636b877906bSopenharmony_ci if (_glfw.x11.xi.handle) 637b877906bSopenharmony_ci { 638b877906bSopenharmony_ci _glfw.x11.xi.QueryVersion = (PFN_XIQueryVersion) 639b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xi.handle, "XIQueryVersion"); 640b877906bSopenharmony_ci _glfw.x11.xi.SelectEvents = (PFN_XISelectEvents) 641b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xi.handle, "XISelectEvents"); 642b877906bSopenharmony_ci 643b877906bSopenharmony_ci if (XQueryExtension(_glfw.x11.display, 644b877906bSopenharmony_ci "XInputExtension", 645b877906bSopenharmony_ci &_glfw.x11.xi.majorOpcode, 646b877906bSopenharmony_ci &_glfw.x11.xi.eventBase, 647b877906bSopenharmony_ci &_glfw.x11.xi.errorBase)) 648b877906bSopenharmony_ci { 649b877906bSopenharmony_ci _glfw.x11.xi.major = 2; 650b877906bSopenharmony_ci _glfw.x11.xi.minor = 0; 651b877906bSopenharmony_ci 652b877906bSopenharmony_ci if (XIQueryVersion(_glfw.x11.display, 653b877906bSopenharmony_ci &_glfw.x11.xi.major, 654b877906bSopenharmony_ci &_glfw.x11.xi.minor) == Success) 655b877906bSopenharmony_ci { 656b877906bSopenharmony_ci _glfw.x11.xi.available = GLFW_TRUE; 657b877906bSopenharmony_ci } 658b877906bSopenharmony_ci } 659b877906bSopenharmony_ci } 660b877906bSopenharmony_ci 661b877906bSopenharmony_ci#if defined(__CYGWIN__) 662b877906bSopenharmony_ci _glfw.x11.randr.handle = _glfwPlatformLoadModule("libXrandr-2.so"); 663b877906bSopenharmony_ci#elif defined(__OpenBSD__) || defined(__NetBSD__) 664b877906bSopenharmony_ci _glfw.x11.randr.handle = _glfwPlatformLoadModule("libXrandr.so"); 665b877906bSopenharmony_ci#else 666b877906bSopenharmony_ci _glfw.x11.randr.handle = _glfwPlatformLoadModule("libXrandr.so.2"); 667b877906bSopenharmony_ci#endif 668b877906bSopenharmony_ci if (_glfw.x11.randr.handle) 669b877906bSopenharmony_ci { 670b877906bSopenharmony_ci _glfw.x11.randr.AllocGamma = (PFN_XRRAllocGamma) 671b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRAllocGamma"); 672b877906bSopenharmony_ci _glfw.x11.randr.FreeGamma = (PFN_XRRFreeGamma) 673b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRFreeGamma"); 674b877906bSopenharmony_ci _glfw.x11.randr.FreeCrtcInfo = (PFN_XRRFreeCrtcInfo) 675b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRFreeCrtcInfo"); 676b877906bSopenharmony_ci _glfw.x11.randr.FreeGamma = (PFN_XRRFreeGamma) 677b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRFreeGamma"); 678b877906bSopenharmony_ci _glfw.x11.randr.FreeOutputInfo = (PFN_XRRFreeOutputInfo) 679b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRFreeOutputInfo"); 680b877906bSopenharmony_ci _glfw.x11.randr.FreeScreenResources = (PFN_XRRFreeScreenResources) 681b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRFreeScreenResources"); 682b877906bSopenharmony_ci _glfw.x11.randr.GetCrtcGamma = (PFN_XRRGetCrtcGamma) 683b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRGetCrtcGamma"); 684b877906bSopenharmony_ci _glfw.x11.randr.GetCrtcGammaSize = (PFN_XRRGetCrtcGammaSize) 685b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRGetCrtcGammaSize"); 686b877906bSopenharmony_ci _glfw.x11.randr.GetCrtcInfo = (PFN_XRRGetCrtcInfo) 687b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRGetCrtcInfo"); 688b877906bSopenharmony_ci _glfw.x11.randr.GetOutputInfo = (PFN_XRRGetOutputInfo) 689b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRGetOutputInfo"); 690b877906bSopenharmony_ci _glfw.x11.randr.GetOutputPrimary = (PFN_XRRGetOutputPrimary) 691b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRGetOutputPrimary"); 692b877906bSopenharmony_ci _glfw.x11.randr.GetScreenResourcesCurrent = (PFN_XRRGetScreenResourcesCurrent) 693b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRGetScreenResourcesCurrent"); 694b877906bSopenharmony_ci _glfw.x11.randr.QueryExtension = (PFN_XRRQueryExtension) 695b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRQueryExtension"); 696b877906bSopenharmony_ci _glfw.x11.randr.QueryVersion = (PFN_XRRQueryVersion) 697b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRQueryVersion"); 698b877906bSopenharmony_ci _glfw.x11.randr.SelectInput = (PFN_XRRSelectInput) 699b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRSelectInput"); 700b877906bSopenharmony_ci _glfw.x11.randr.SetCrtcConfig = (PFN_XRRSetCrtcConfig) 701b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRSetCrtcConfig"); 702b877906bSopenharmony_ci _glfw.x11.randr.SetCrtcGamma = (PFN_XRRSetCrtcGamma) 703b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRSetCrtcGamma"); 704b877906bSopenharmony_ci _glfw.x11.randr.UpdateConfiguration = (PFN_XRRUpdateConfiguration) 705b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.randr.handle, "XRRUpdateConfiguration"); 706b877906bSopenharmony_ci 707b877906bSopenharmony_ci if (XRRQueryExtension(_glfw.x11.display, 708b877906bSopenharmony_ci &_glfw.x11.randr.eventBase, 709b877906bSopenharmony_ci &_glfw.x11.randr.errorBase)) 710b877906bSopenharmony_ci { 711b877906bSopenharmony_ci if (XRRQueryVersion(_glfw.x11.display, 712b877906bSopenharmony_ci &_glfw.x11.randr.major, 713b877906bSopenharmony_ci &_glfw.x11.randr.minor)) 714b877906bSopenharmony_ci { 715b877906bSopenharmony_ci // The GLFW RandR path requires at least version 1.3 716b877906bSopenharmony_ci if (_glfw.x11.randr.major > 1 || _glfw.x11.randr.minor >= 3) 717b877906bSopenharmony_ci _glfw.x11.randr.available = GLFW_TRUE; 718b877906bSopenharmony_ci } 719b877906bSopenharmony_ci else 720b877906bSopenharmony_ci { 721b877906bSopenharmony_ci _glfwInputError(GLFW_PLATFORM_ERROR, 722b877906bSopenharmony_ci "X11: Failed to query RandR version"); 723b877906bSopenharmony_ci } 724b877906bSopenharmony_ci } 725b877906bSopenharmony_ci } 726b877906bSopenharmony_ci 727b877906bSopenharmony_ci if (_glfw.x11.randr.available) 728b877906bSopenharmony_ci { 729b877906bSopenharmony_ci XRRScreenResources* sr = XRRGetScreenResourcesCurrent(_glfw.x11.display, 730b877906bSopenharmony_ci _glfw.x11.root); 731b877906bSopenharmony_ci 732b877906bSopenharmony_ci if (!sr->ncrtc || !XRRGetCrtcGammaSize(_glfw.x11.display, sr->crtcs[0])) 733b877906bSopenharmony_ci { 734b877906bSopenharmony_ci // This is likely an older Nvidia driver with broken gamma support 735b877906bSopenharmony_ci // Flag it as useless and fall back to xf86vm gamma, if available 736b877906bSopenharmony_ci _glfw.x11.randr.gammaBroken = GLFW_TRUE; 737b877906bSopenharmony_ci } 738b877906bSopenharmony_ci 739b877906bSopenharmony_ci if (!sr->ncrtc) 740b877906bSopenharmony_ci { 741b877906bSopenharmony_ci // A system without CRTCs is likely a system with broken RandR 742b877906bSopenharmony_ci // Disable the RandR monitor path and fall back to core functions 743b877906bSopenharmony_ci _glfw.x11.randr.monitorBroken = GLFW_TRUE; 744b877906bSopenharmony_ci } 745b877906bSopenharmony_ci 746b877906bSopenharmony_ci XRRFreeScreenResources(sr); 747b877906bSopenharmony_ci } 748b877906bSopenharmony_ci 749b877906bSopenharmony_ci if (_glfw.x11.randr.available && !_glfw.x11.randr.monitorBroken) 750b877906bSopenharmony_ci { 751b877906bSopenharmony_ci XRRSelectInput(_glfw.x11.display, _glfw.x11.root, 752b877906bSopenharmony_ci RROutputChangeNotifyMask); 753b877906bSopenharmony_ci } 754b877906bSopenharmony_ci 755b877906bSopenharmony_ci#if defined(__CYGWIN__) 756b877906bSopenharmony_ci _glfw.x11.xcursor.handle = _glfwPlatformLoadModule("libXcursor-1.so"); 757b877906bSopenharmony_ci#elif defined(__OpenBSD__) || defined(__NetBSD__) 758b877906bSopenharmony_ci _glfw.x11.xcursor.handle = _glfwPlatformLoadModule("libXcursor.so"); 759b877906bSopenharmony_ci#else 760b877906bSopenharmony_ci _glfw.x11.xcursor.handle = _glfwPlatformLoadModule("libXcursor.so.1"); 761b877906bSopenharmony_ci#endif 762b877906bSopenharmony_ci if (_glfw.x11.xcursor.handle) 763b877906bSopenharmony_ci { 764b877906bSopenharmony_ci _glfw.x11.xcursor.ImageCreate = (PFN_XcursorImageCreate) 765b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xcursor.handle, "XcursorImageCreate"); 766b877906bSopenharmony_ci _glfw.x11.xcursor.ImageDestroy = (PFN_XcursorImageDestroy) 767b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xcursor.handle, "XcursorImageDestroy"); 768b877906bSopenharmony_ci _glfw.x11.xcursor.ImageLoadCursor = (PFN_XcursorImageLoadCursor) 769b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xcursor.handle, "XcursorImageLoadCursor"); 770b877906bSopenharmony_ci _glfw.x11.xcursor.GetTheme = (PFN_XcursorGetTheme) 771b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xcursor.handle, "XcursorGetTheme"); 772b877906bSopenharmony_ci _glfw.x11.xcursor.GetDefaultSize = (PFN_XcursorGetDefaultSize) 773b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xcursor.handle, "XcursorGetDefaultSize"); 774b877906bSopenharmony_ci _glfw.x11.xcursor.LibraryLoadImage = (PFN_XcursorLibraryLoadImage) 775b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xcursor.handle, "XcursorLibraryLoadImage"); 776b877906bSopenharmony_ci } 777b877906bSopenharmony_ci 778b877906bSopenharmony_ci#if defined(__CYGWIN__) 779b877906bSopenharmony_ci _glfw.x11.xinerama.handle = _glfwPlatformLoadModule("libXinerama-1.so"); 780b877906bSopenharmony_ci#elif defined(__OpenBSD__) || defined(__NetBSD__) 781b877906bSopenharmony_ci _glfw.x11.xinerama.handle = _glfwPlatformLoadModule("libXinerama.so"); 782b877906bSopenharmony_ci#else 783b877906bSopenharmony_ci _glfw.x11.xinerama.handle = _glfwPlatformLoadModule("libXinerama.so.1"); 784b877906bSopenharmony_ci#endif 785b877906bSopenharmony_ci if (_glfw.x11.xinerama.handle) 786b877906bSopenharmony_ci { 787b877906bSopenharmony_ci _glfw.x11.xinerama.IsActive = (PFN_XineramaIsActive) 788b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xinerama.handle, "XineramaIsActive"); 789b877906bSopenharmony_ci _glfw.x11.xinerama.QueryExtension = (PFN_XineramaQueryExtension) 790b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xinerama.handle, "XineramaQueryExtension"); 791b877906bSopenharmony_ci _glfw.x11.xinerama.QueryScreens = (PFN_XineramaQueryScreens) 792b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xinerama.handle, "XineramaQueryScreens"); 793b877906bSopenharmony_ci 794b877906bSopenharmony_ci if (XineramaQueryExtension(_glfw.x11.display, 795b877906bSopenharmony_ci &_glfw.x11.xinerama.major, 796b877906bSopenharmony_ci &_glfw.x11.xinerama.minor)) 797b877906bSopenharmony_ci { 798b877906bSopenharmony_ci if (XineramaIsActive(_glfw.x11.display)) 799b877906bSopenharmony_ci _glfw.x11.xinerama.available = GLFW_TRUE; 800b877906bSopenharmony_ci } 801b877906bSopenharmony_ci } 802b877906bSopenharmony_ci 803b877906bSopenharmony_ci _glfw.x11.xkb.major = 1; 804b877906bSopenharmony_ci _glfw.x11.xkb.minor = 0; 805b877906bSopenharmony_ci _glfw.x11.xkb.available = 806b877906bSopenharmony_ci XkbQueryExtension(_glfw.x11.display, 807b877906bSopenharmony_ci &_glfw.x11.xkb.majorOpcode, 808b877906bSopenharmony_ci &_glfw.x11.xkb.eventBase, 809b877906bSopenharmony_ci &_glfw.x11.xkb.errorBase, 810b877906bSopenharmony_ci &_glfw.x11.xkb.major, 811b877906bSopenharmony_ci &_glfw.x11.xkb.minor); 812b877906bSopenharmony_ci 813b877906bSopenharmony_ci if (_glfw.x11.xkb.available) 814b877906bSopenharmony_ci { 815b877906bSopenharmony_ci Bool supported; 816b877906bSopenharmony_ci 817b877906bSopenharmony_ci if (XkbSetDetectableAutoRepeat(_glfw.x11.display, True, &supported)) 818b877906bSopenharmony_ci { 819b877906bSopenharmony_ci if (supported) 820b877906bSopenharmony_ci _glfw.x11.xkb.detectable = GLFW_TRUE; 821b877906bSopenharmony_ci } 822b877906bSopenharmony_ci 823b877906bSopenharmony_ci XkbStateRec state; 824b877906bSopenharmony_ci if (XkbGetState(_glfw.x11.display, XkbUseCoreKbd, &state) == Success) 825b877906bSopenharmony_ci _glfw.x11.xkb.group = (unsigned int)state.group; 826b877906bSopenharmony_ci 827b877906bSopenharmony_ci XkbSelectEventDetails(_glfw.x11.display, XkbUseCoreKbd, XkbStateNotify, 828b877906bSopenharmony_ci XkbGroupStateMask, XkbGroupStateMask); 829b877906bSopenharmony_ci } 830b877906bSopenharmony_ci 831b877906bSopenharmony_ci if (_glfw.hints.init.x11.xcbVulkanSurface) 832b877906bSopenharmony_ci { 833b877906bSopenharmony_ci#if defined(__CYGWIN__) 834b877906bSopenharmony_ci _glfw.x11.x11xcb.handle = _glfwPlatformLoadModule("libX11-xcb-1.so"); 835b877906bSopenharmony_ci#elif defined(__OpenBSD__) || defined(__NetBSD__) 836b877906bSopenharmony_ci _glfw.x11.x11xcb.handle = _glfwPlatformLoadModule("libX11-xcb.so"); 837b877906bSopenharmony_ci#else 838b877906bSopenharmony_ci _glfw.x11.x11xcb.handle = _glfwPlatformLoadModule("libX11-xcb.so.1"); 839b877906bSopenharmony_ci#endif 840b877906bSopenharmony_ci } 841b877906bSopenharmony_ci 842b877906bSopenharmony_ci if (_glfw.x11.x11xcb.handle) 843b877906bSopenharmony_ci { 844b877906bSopenharmony_ci _glfw.x11.x11xcb.GetXCBConnection = (PFN_XGetXCBConnection) 845b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.x11xcb.handle, "XGetXCBConnection"); 846b877906bSopenharmony_ci } 847b877906bSopenharmony_ci 848b877906bSopenharmony_ci#if defined(__CYGWIN__) 849b877906bSopenharmony_ci _glfw.x11.xrender.handle = _glfwPlatformLoadModule("libXrender-1.so"); 850b877906bSopenharmony_ci#elif defined(__OpenBSD__) || defined(__NetBSD__) 851b877906bSopenharmony_ci _glfw.x11.xrender.handle = _glfwPlatformLoadModule("libXrender.so"); 852b877906bSopenharmony_ci#else 853b877906bSopenharmony_ci _glfw.x11.xrender.handle = _glfwPlatformLoadModule("libXrender.so.1"); 854b877906bSopenharmony_ci#endif 855b877906bSopenharmony_ci if (_glfw.x11.xrender.handle) 856b877906bSopenharmony_ci { 857b877906bSopenharmony_ci _glfw.x11.xrender.QueryExtension = (PFN_XRenderQueryExtension) 858b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xrender.handle, "XRenderQueryExtension"); 859b877906bSopenharmony_ci _glfw.x11.xrender.QueryVersion = (PFN_XRenderQueryVersion) 860b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xrender.handle, "XRenderQueryVersion"); 861b877906bSopenharmony_ci _glfw.x11.xrender.FindVisualFormat = (PFN_XRenderFindVisualFormat) 862b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xrender.handle, "XRenderFindVisualFormat"); 863b877906bSopenharmony_ci 864b877906bSopenharmony_ci if (XRenderQueryExtension(_glfw.x11.display, 865b877906bSopenharmony_ci &_glfw.x11.xrender.errorBase, 866b877906bSopenharmony_ci &_glfw.x11.xrender.eventBase)) 867b877906bSopenharmony_ci { 868b877906bSopenharmony_ci if (XRenderQueryVersion(_glfw.x11.display, 869b877906bSopenharmony_ci &_glfw.x11.xrender.major, 870b877906bSopenharmony_ci &_glfw.x11.xrender.minor)) 871b877906bSopenharmony_ci { 872b877906bSopenharmony_ci _glfw.x11.xrender.available = GLFW_TRUE; 873b877906bSopenharmony_ci } 874b877906bSopenharmony_ci } 875b877906bSopenharmony_ci } 876b877906bSopenharmony_ci 877b877906bSopenharmony_ci#if defined(__CYGWIN__) 878b877906bSopenharmony_ci _glfw.x11.xshape.handle = _glfwPlatformLoadModule("libXext-6.so"); 879b877906bSopenharmony_ci#elif defined(__OpenBSD__) || defined(__NetBSD__) 880b877906bSopenharmony_ci _glfw.x11.xshape.handle = _glfwPlatformLoadModule("libXext.so"); 881b877906bSopenharmony_ci#else 882b877906bSopenharmony_ci _glfw.x11.xshape.handle = _glfwPlatformLoadModule("libXext.so.6"); 883b877906bSopenharmony_ci#endif 884b877906bSopenharmony_ci if (_glfw.x11.xshape.handle) 885b877906bSopenharmony_ci { 886b877906bSopenharmony_ci _glfw.x11.xshape.QueryExtension = (PFN_XShapeQueryExtension) 887b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xshape.handle, "XShapeQueryExtension"); 888b877906bSopenharmony_ci _glfw.x11.xshape.ShapeCombineRegion = (PFN_XShapeCombineRegion) 889b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xshape.handle, "XShapeCombineRegion"); 890b877906bSopenharmony_ci _glfw.x11.xshape.QueryVersion = (PFN_XShapeQueryVersion) 891b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xshape.handle, "XShapeQueryVersion"); 892b877906bSopenharmony_ci _glfw.x11.xshape.ShapeCombineMask = (PFN_XShapeCombineMask) 893b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xshape.handle, "XShapeCombineMask"); 894b877906bSopenharmony_ci 895b877906bSopenharmony_ci if (XShapeQueryExtension(_glfw.x11.display, 896b877906bSopenharmony_ci &_glfw.x11.xshape.errorBase, 897b877906bSopenharmony_ci &_glfw.x11.xshape.eventBase)) 898b877906bSopenharmony_ci { 899b877906bSopenharmony_ci if (XShapeQueryVersion(_glfw.x11.display, 900b877906bSopenharmony_ci &_glfw.x11.xshape.major, 901b877906bSopenharmony_ci &_glfw.x11.xshape.minor)) 902b877906bSopenharmony_ci { 903b877906bSopenharmony_ci _glfw.x11.xshape.available = GLFW_TRUE; 904b877906bSopenharmony_ci } 905b877906bSopenharmony_ci } 906b877906bSopenharmony_ci } 907b877906bSopenharmony_ci 908b877906bSopenharmony_ci // Update the key code LUT 909b877906bSopenharmony_ci // FIXME: We should listen to XkbMapNotify events to track changes to 910b877906bSopenharmony_ci // the keyboard mapping. 911b877906bSopenharmony_ci createKeyTables(); 912b877906bSopenharmony_ci 913b877906bSopenharmony_ci // String format atoms 914b877906bSopenharmony_ci _glfw.x11.NULL_ = XInternAtom(_glfw.x11.display, "NULL", False); 915b877906bSopenharmony_ci _glfw.x11.UTF8_STRING = XInternAtom(_glfw.x11.display, "UTF8_STRING", False); 916b877906bSopenharmony_ci _glfw.x11.ATOM_PAIR = XInternAtom(_glfw.x11.display, "ATOM_PAIR", False); 917b877906bSopenharmony_ci 918b877906bSopenharmony_ci // Custom selection property atom 919b877906bSopenharmony_ci _glfw.x11.GLFW_SELECTION = 920b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "GLFW_SELECTION", False); 921b877906bSopenharmony_ci 922b877906bSopenharmony_ci // ICCCM standard clipboard atoms 923b877906bSopenharmony_ci _glfw.x11.TARGETS = XInternAtom(_glfw.x11.display, "TARGETS", False); 924b877906bSopenharmony_ci _glfw.x11.MULTIPLE = XInternAtom(_glfw.x11.display, "MULTIPLE", False); 925b877906bSopenharmony_ci _glfw.x11.PRIMARY = XInternAtom(_glfw.x11.display, "PRIMARY", False); 926b877906bSopenharmony_ci _glfw.x11.INCR = XInternAtom(_glfw.x11.display, "INCR", False); 927b877906bSopenharmony_ci _glfw.x11.CLIPBOARD = XInternAtom(_glfw.x11.display, "CLIPBOARD", False); 928b877906bSopenharmony_ci 929b877906bSopenharmony_ci // Clipboard manager atoms 930b877906bSopenharmony_ci _glfw.x11.CLIPBOARD_MANAGER = 931b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "CLIPBOARD_MANAGER", False); 932b877906bSopenharmony_ci _glfw.x11.SAVE_TARGETS = 933b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "SAVE_TARGETS", False); 934b877906bSopenharmony_ci 935b877906bSopenharmony_ci // Xdnd (drag and drop) atoms 936b877906bSopenharmony_ci _glfw.x11.XdndAware = XInternAtom(_glfw.x11.display, "XdndAware", False); 937b877906bSopenharmony_ci _glfw.x11.XdndEnter = XInternAtom(_glfw.x11.display, "XdndEnter", False); 938b877906bSopenharmony_ci _glfw.x11.XdndPosition = XInternAtom(_glfw.x11.display, "XdndPosition", False); 939b877906bSopenharmony_ci _glfw.x11.XdndStatus = XInternAtom(_glfw.x11.display, "XdndStatus", False); 940b877906bSopenharmony_ci _glfw.x11.XdndActionCopy = XInternAtom(_glfw.x11.display, "XdndActionCopy", False); 941b877906bSopenharmony_ci _glfw.x11.XdndDrop = XInternAtom(_glfw.x11.display, "XdndDrop", False); 942b877906bSopenharmony_ci _glfw.x11.XdndFinished = XInternAtom(_glfw.x11.display, "XdndFinished", False); 943b877906bSopenharmony_ci _glfw.x11.XdndSelection = XInternAtom(_glfw.x11.display, "XdndSelection", False); 944b877906bSopenharmony_ci _glfw.x11.XdndTypeList = XInternAtom(_glfw.x11.display, "XdndTypeList", False); 945b877906bSopenharmony_ci _glfw.x11.text_uri_list = XInternAtom(_glfw.x11.display, "text/uri-list", False); 946b877906bSopenharmony_ci 947b877906bSopenharmony_ci // ICCCM, EWMH and Motif window property atoms 948b877906bSopenharmony_ci // These can be set safely even without WM support 949b877906bSopenharmony_ci // The EWMH atoms that require WM support are handled in detectEWMH 950b877906bSopenharmony_ci _glfw.x11.WM_PROTOCOLS = 951b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "WM_PROTOCOLS", False); 952b877906bSopenharmony_ci _glfw.x11.WM_STATE = 953b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "WM_STATE", False); 954b877906bSopenharmony_ci _glfw.x11.WM_DELETE_WINDOW = 955b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "WM_DELETE_WINDOW", False); 956b877906bSopenharmony_ci _glfw.x11.NET_SUPPORTED = 957b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "_NET_SUPPORTED", False); 958b877906bSopenharmony_ci _glfw.x11.NET_SUPPORTING_WM_CHECK = 959b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "_NET_SUPPORTING_WM_CHECK", False); 960b877906bSopenharmony_ci _glfw.x11.NET_WM_ICON = 961b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "_NET_WM_ICON", False); 962b877906bSopenharmony_ci _glfw.x11.NET_WM_PING = 963b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "_NET_WM_PING", False); 964b877906bSopenharmony_ci _glfw.x11.NET_WM_PID = 965b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "_NET_WM_PID", False); 966b877906bSopenharmony_ci _glfw.x11.NET_WM_NAME = 967b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "_NET_WM_NAME", False); 968b877906bSopenharmony_ci _glfw.x11.NET_WM_ICON_NAME = 969b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "_NET_WM_ICON_NAME", False); 970b877906bSopenharmony_ci _glfw.x11.NET_WM_BYPASS_COMPOSITOR = 971b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "_NET_WM_BYPASS_COMPOSITOR", False); 972b877906bSopenharmony_ci _glfw.x11.NET_WM_WINDOW_OPACITY = 973b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "_NET_WM_WINDOW_OPACITY", False); 974b877906bSopenharmony_ci _glfw.x11.MOTIF_WM_HINTS = 975b877906bSopenharmony_ci XInternAtom(_glfw.x11.display, "_MOTIF_WM_HINTS", False); 976b877906bSopenharmony_ci 977b877906bSopenharmony_ci // The compositing manager selection name contains the screen number 978b877906bSopenharmony_ci { 979b877906bSopenharmony_ci char name[32]; 980b877906bSopenharmony_ci snprintf(name, sizeof(name), "_NET_WM_CM_S%u", _glfw.x11.screen); 981b877906bSopenharmony_ci _glfw.x11.NET_WM_CM_Sx = XInternAtom(_glfw.x11.display, name, False); 982b877906bSopenharmony_ci } 983b877906bSopenharmony_ci 984b877906bSopenharmony_ci // Detect whether an EWMH-conformant window manager is running 985b877906bSopenharmony_ci detectEWMH(); 986b877906bSopenharmony_ci 987b877906bSopenharmony_ci return GLFW_TRUE; 988b877906bSopenharmony_ci} 989b877906bSopenharmony_ci 990b877906bSopenharmony_ci// Retrieve system content scale via folklore heuristics 991b877906bSopenharmony_ci// 992b877906bSopenharmony_cistatic void getSystemContentScale(float* xscale, float* yscale) 993b877906bSopenharmony_ci{ 994b877906bSopenharmony_ci // Start by assuming the default X11 DPI 995b877906bSopenharmony_ci // NOTE: Some desktop environments (KDE) may remove the Xft.dpi field when it 996b877906bSopenharmony_ci // would be set to 96, so assume that is the case if we cannot find it 997b877906bSopenharmony_ci float xdpi = 96.f, ydpi = 96.f; 998b877906bSopenharmony_ci 999b877906bSopenharmony_ci // NOTE: Basing the scale on Xft.dpi where available should provide the most 1000b877906bSopenharmony_ci // consistent user experience (matches Qt, Gtk, etc), although not 1001b877906bSopenharmony_ci // always the most accurate one 1002b877906bSopenharmony_ci char* rms = XResourceManagerString(_glfw.x11.display); 1003b877906bSopenharmony_ci if (rms) 1004b877906bSopenharmony_ci { 1005b877906bSopenharmony_ci XrmDatabase db = XrmGetStringDatabase(rms); 1006b877906bSopenharmony_ci if (db) 1007b877906bSopenharmony_ci { 1008b877906bSopenharmony_ci XrmValue value; 1009b877906bSopenharmony_ci char* type = NULL; 1010b877906bSopenharmony_ci 1011b877906bSopenharmony_ci if (XrmGetResource(db, "Xft.dpi", "Xft.Dpi", &type, &value)) 1012b877906bSopenharmony_ci { 1013b877906bSopenharmony_ci if (type && strcmp(type, "String") == 0) 1014b877906bSopenharmony_ci xdpi = ydpi = atof(value.addr); 1015b877906bSopenharmony_ci } 1016b877906bSopenharmony_ci 1017b877906bSopenharmony_ci XrmDestroyDatabase(db); 1018b877906bSopenharmony_ci } 1019b877906bSopenharmony_ci } 1020b877906bSopenharmony_ci 1021b877906bSopenharmony_ci *xscale = xdpi / 96.f; 1022b877906bSopenharmony_ci *yscale = ydpi / 96.f; 1023b877906bSopenharmony_ci} 1024b877906bSopenharmony_ci 1025b877906bSopenharmony_ci// Create a blank cursor for hidden and disabled cursor modes 1026b877906bSopenharmony_ci// 1027b877906bSopenharmony_cistatic Cursor createHiddenCursor(void) 1028b877906bSopenharmony_ci{ 1029b877906bSopenharmony_ci unsigned char pixels[16 * 16 * 4] = { 0 }; 1030b877906bSopenharmony_ci GLFWimage image = { 16, 16, pixels }; 1031b877906bSopenharmony_ci return _glfwCreateNativeCursorX11(&image, 0, 0); 1032b877906bSopenharmony_ci} 1033b877906bSopenharmony_ci 1034b877906bSopenharmony_ci// Create a helper window for IPC 1035b877906bSopenharmony_ci// 1036b877906bSopenharmony_cistatic Window createHelperWindow(void) 1037b877906bSopenharmony_ci{ 1038b877906bSopenharmony_ci XSetWindowAttributes wa; 1039b877906bSopenharmony_ci wa.event_mask = PropertyChangeMask; 1040b877906bSopenharmony_ci 1041b877906bSopenharmony_ci return XCreateWindow(_glfw.x11.display, _glfw.x11.root, 1042b877906bSopenharmony_ci 0, 0, 1, 1, 0, 0, 1043b877906bSopenharmony_ci InputOnly, 1044b877906bSopenharmony_ci DefaultVisual(_glfw.x11.display, _glfw.x11.screen), 1045b877906bSopenharmony_ci CWEventMask, &wa); 1046b877906bSopenharmony_ci} 1047b877906bSopenharmony_ci 1048b877906bSopenharmony_ci// Create the pipe for empty events without assumuing the OS has pipe2(2) 1049b877906bSopenharmony_ci// 1050b877906bSopenharmony_cistatic GLFWbool createEmptyEventPipe(void) 1051b877906bSopenharmony_ci{ 1052b877906bSopenharmony_ci if (pipe(_glfw.x11.emptyEventPipe) != 0) 1053b877906bSopenharmony_ci { 1054b877906bSopenharmony_ci _glfwInputError(GLFW_PLATFORM_ERROR, 1055b877906bSopenharmony_ci "X11: Failed to create empty event pipe: %s", 1056b877906bSopenharmony_ci strerror(errno)); 1057b877906bSopenharmony_ci return GLFW_FALSE; 1058b877906bSopenharmony_ci } 1059b877906bSopenharmony_ci 1060b877906bSopenharmony_ci for (int i = 0; i < 2; i++) 1061b877906bSopenharmony_ci { 1062b877906bSopenharmony_ci const int sf = fcntl(_glfw.x11.emptyEventPipe[i], F_GETFL, 0); 1063b877906bSopenharmony_ci const int df = fcntl(_glfw.x11.emptyEventPipe[i], F_GETFD, 0); 1064b877906bSopenharmony_ci 1065b877906bSopenharmony_ci if (sf == -1 || df == -1 || 1066b877906bSopenharmony_ci fcntl(_glfw.x11.emptyEventPipe[i], F_SETFL, sf | O_NONBLOCK) == -1 || 1067b877906bSopenharmony_ci fcntl(_glfw.x11.emptyEventPipe[i], F_SETFD, df | FD_CLOEXEC) == -1) 1068b877906bSopenharmony_ci { 1069b877906bSopenharmony_ci _glfwInputError(GLFW_PLATFORM_ERROR, 1070b877906bSopenharmony_ci "X11: Failed to set flags for empty event pipe: %s", 1071b877906bSopenharmony_ci strerror(errno)); 1072b877906bSopenharmony_ci return GLFW_FALSE; 1073b877906bSopenharmony_ci } 1074b877906bSopenharmony_ci } 1075b877906bSopenharmony_ci 1076b877906bSopenharmony_ci return GLFW_TRUE; 1077b877906bSopenharmony_ci} 1078b877906bSopenharmony_ci 1079b877906bSopenharmony_ci// X error handler 1080b877906bSopenharmony_ci// 1081b877906bSopenharmony_cistatic int errorHandler(Display *display, XErrorEvent* event) 1082b877906bSopenharmony_ci{ 1083b877906bSopenharmony_ci if (_glfw.x11.display != display) 1084b877906bSopenharmony_ci return 0; 1085b877906bSopenharmony_ci 1086b877906bSopenharmony_ci _glfw.x11.errorCode = event->error_code; 1087b877906bSopenharmony_ci return 0; 1088b877906bSopenharmony_ci} 1089b877906bSopenharmony_ci 1090b877906bSopenharmony_ci 1091b877906bSopenharmony_ci////////////////////////////////////////////////////////////////////////// 1092b877906bSopenharmony_ci////// GLFW internal API ////// 1093b877906bSopenharmony_ci////////////////////////////////////////////////////////////////////////// 1094b877906bSopenharmony_ci 1095b877906bSopenharmony_ci// Sets the X error handler callback 1096b877906bSopenharmony_ci// 1097b877906bSopenharmony_civoid _glfwGrabErrorHandlerX11(void) 1098b877906bSopenharmony_ci{ 1099b877906bSopenharmony_ci assert(_glfw.x11.errorHandler == NULL); 1100b877906bSopenharmony_ci _glfw.x11.errorCode = Success; 1101b877906bSopenharmony_ci _glfw.x11.errorHandler = XSetErrorHandler(errorHandler); 1102b877906bSopenharmony_ci} 1103b877906bSopenharmony_ci 1104b877906bSopenharmony_ci// Clears the X error handler callback 1105b877906bSopenharmony_ci// 1106b877906bSopenharmony_civoid _glfwReleaseErrorHandlerX11(void) 1107b877906bSopenharmony_ci{ 1108b877906bSopenharmony_ci // Synchronize to make sure all commands are processed 1109b877906bSopenharmony_ci XSync(_glfw.x11.display, False); 1110b877906bSopenharmony_ci XSetErrorHandler(_glfw.x11.errorHandler); 1111b877906bSopenharmony_ci _glfw.x11.errorHandler = NULL; 1112b877906bSopenharmony_ci} 1113b877906bSopenharmony_ci 1114b877906bSopenharmony_ci// Reports the specified error, appending information about the last X error 1115b877906bSopenharmony_ci// 1116b877906bSopenharmony_civoid _glfwInputErrorX11(int error, const char* message) 1117b877906bSopenharmony_ci{ 1118b877906bSopenharmony_ci char buffer[_GLFW_MESSAGE_SIZE]; 1119b877906bSopenharmony_ci XGetErrorText(_glfw.x11.display, _glfw.x11.errorCode, 1120b877906bSopenharmony_ci buffer, sizeof(buffer)); 1121b877906bSopenharmony_ci 1122b877906bSopenharmony_ci _glfwInputError(error, "%s: %s", message, buffer); 1123b877906bSopenharmony_ci} 1124b877906bSopenharmony_ci 1125b877906bSopenharmony_ci// Creates a native cursor object from the specified image and hotspot 1126b877906bSopenharmony_ci// 1127b877906bSopenharmony_ciCursor _glfwCreateNativeCursorX11(const GLFWimage* image, int xhot, int yhot) 1128b877906bSopenharmony_ci{ 1129b877906bSopenharmony_ci Cursor cursor; 1130b877906bSopenharmony_ci 1131b877906bSopenharmony_ci if (!_glfw.x11.xcursor.handle) 1132b877906bSopenharmony_ci return None; 1133b877906bSopenharmony_ci 1134b877906bSopenharmony_ci XcursorImage* native = XcursorImageCreate(image->width, image->height); 1135b877906bSopenharmony_ci if (native == NULL) 1136b877906bSopenharmony_ci return None; 1137b877906bSopenharmony_ci 1138b877906bSopenharmony_ci native->xhot = xhot; 1139b877906bSopenharmony_ci native->yhot = yhot; 1140b877906bSopenharmony_ci 1141b877906bSopenharmony_ci unsigned char* source = (unsigned char*) image->pixels; 1142b877906bSopenharmony_ci XcursorPixel* target = native->pixels; 1143b877906bSopenharmony_ci 1144b877906bSopenharmony_ci for (int i = 0; i < image->width * image->height; i++, target++, source += 4) 1145b877906bSopenharmony_ci { 1146b877906bSopenharmony_ci unsigned int alpha = source[3]; 1147b877906bSopenharmony_ci 1148b877906bSopenharmony_ci *target = (alpha << 24) | 1149b877906bSopenharmony_ci ((unsigned char) ((source[0] * alpha) / 255) << 16) | 1150b877906bSopenharmony_ci ((unsigned char) ((source[1] * alpha) / 255) << 8) | 1151b877906bSopenharmony_ci ((unsigned char) ((source[2] * alpha) / 255) << 0); 1152b877906bSopenharmony_ci } 1153b877906bSopenharmony_ci 1154b877906bSopenharmony_ci cursor = XcursorImageLoadCursor(_glfw.x11.display, native); 1155b877906bSopenharmony_ci XcursorImageDestroy(native); 1156b877906bSopenharmony_ci 1157b877906bSopenharmony_ci return cursor; 1158b877906bSopenharmony_ci} 1159b877906bSopenharmony_ci 1160b877906bSopenharmony_ci 1161b877906bSopenharmony_ci////////////////////////////////////////////////////////////////////////// 1162b877906bSopenharmony_ci////// GLFW platform API ////// 1163b877906bSopenharmony_ci////////////////////////////////////////////////////////////////////////// 1164b877906bSopenharmony_ci 1165b877906bSopenharmony_ciGLFWbool _glfwConnectX11(int platformID, _GLFWplatform* platform) 1166b877906bSopenharmony_ci{ 1167b877906bSopenharmony_ci const _GLFWplatform x11 = 1168b877906bSopenharmony_ci { 1169b877906bSopenharmony_ci .platformID = GLFW_PLATFORM_X11, 1170b877906bSopenharmony_ci .init = _glfwInitX11, 1171b877906bSopenharmony_ci .terminate = _glfwTerminateX11, 1172b877906bSopenharmony_ci .getCursorPos = _glfwGetCursorPosX11, 1173b877906bSopenharmony_ci .setCursorPos = _glfwSetCursorPosX11, 1174b877906bSopenharmony_ci .setCursorMode = _glfwSetCursorModeX11, 1175b877906bSopenharmony_ci .setRawMouseMotion = _glfwSetRawMouseMotionX11, 1176b877906bSopenharmony_ci .rawMouseMotionSupported = _glfwRawMouseMotionSupportedX11, 1177b877906bSopenharmony_ci .createCursor = _glfwCreateCursorX11, 1178b877906bSopenharmony_ci .createStandardCursor = _glfwCreateStandardCursorX11, 1179b877906bSopenharmony_ci .destroyCursor = _glfwDestroyCursorX11, 1180b877906bSopenharmony_ci .setCursor = _glfwSetCursorX11, 1181b877906bSopenharmony_ci .getScancodeName = _glfwGetScancodeNameX11, 1182b877906bSopenharmony_ci .getKeyScancode = _glfwGetKeyScancodeX11, 1183b877906bSopenharmony_ci .setClipboardString = _glfwSetClipboardStringX11, 1184b877906bSopenharmony_ci .getClipboardString = _glfwGetClipboardStringX11, 1185b877906bSopenharmony_ci#if defined(GLFW_BUILD_LINUX_JOYSTICK) 1186b877906bSopenharmony_ci .initJoysticks = _glfwInitJoysticksLinux, 1187b877906bSopenharmony_ci .terminateJoysticks = _glfwTerminateJoysticksLinux, 1188b877906bSopenharmony_ci .pollJoystick = _glfwPollJoystickLinux, 1189b877906bSopenharmony_ci .getMappingName = _glfwGetMappingNameLinux, 1190b877906bSopenharmony_ci .updateGamepadGUID = _glfwUpdateGamepadGUIDLinux, 1191b877906bSopenharmony_ci#else 1192b877906bSopenharmony_ci .initJoysticks = _glfwInitJoysticksNull, 1193b877906bSopenharmony_ci .terminateJoysticks = _glfwTerminateJoysticksNull, 1194b877906bSopenharmony_ci .pollJoystick = _glfwPollJoystickNull, 1195b877906bSopenharmony_ci .getMappingName = _glfwGetMappingNameNull, 1196b877906bSopenharmony_ci .updateGamepadGUID = _glfwUpdateGamepadGUIDNull, 1197b877906bSopenharmony_ci#endif 1198b877906bSopenharmony_ci .freeMonitor = _glfwFreeMonitorX11, 1199b877906bSopenharmony_ci .getMonitorPos = _glfwGetMonitorPosX11, 1200b877906bSopenharmony_ci .getMonitorContentScale = _glfwGetMonitorContentScaleX11, 1201b877906bSopenharmony_ci .getMonitorWorkarea = _glfwGetMonitorWorkareaX11, 1202b877906bSopenharmony_ci .getVideoModes = _glfwGetVideoModesX11, 1203b877906bSopenharmony_ci .getVideoMode = _glfwGetVideoModeX11, 1204b877906bSopenharmony_ci .getGammaRamp = _glfwGetGammaRampX11, 1205b877906bSopenharmony_ci .setGammaRamp = _glfwSetGammaRampX11, 1206b877906bSopenharmony_ci .createWindow = _glfwCreateWindowX11, 1207b877906bSopenharmony_ci .destroyWindow = _glfwDestroyWindowX11, 1208b877906bSopenharmony_ci .setWindowTitle = _glfwSetWindowTitleX11, 1209b877906bSopenharmony_ci .setWindowIcon = _glfwSetWindowIconX11, 1210b877906bSopenharmony_ci .getWindowPos = _glfwGetWindowPosX11, 1211b877906bSopenharmony_ci .setWindowPos = _glfwSetWindowPosX11, 1212b877906bSopenharmony_ci .getWindowSize = _glfwGetWindowSizeX11, 1213b877906bSopenharmony_ci .setWindowSize = _glfwSetWindowSizeX11, 1214b877906bSopenharmony_ci .setWindowSizeLimits = _glfwSetWindowSizeLimitsX11, 1215b877906bSopenharmony_ci .setWindowAspectRatio = _glfwSetWindowAspectRatioX11, 1216b877906bSopenharmony_ci .getFramebufferSize = _glfwGetFramebufferSizeX11, 1217b877906bSopenharmony_ci .getWindowFrameSize = _glfwGetWindowFrameSizeX11, 1218b877906bSopenharmony_ci .getWindowContentScale = _glfwGetWindowContentScaleX11, 1219b877906bSopenharmony_ci .iconifyWindow = _glfwIconifyWindowX11, 1220b877906bSopenharmony_ci .restoreWindow = _glfwRestoreWindowX11, 1221b877906bSopenharmony_ci .maximizeWindow = _glfwMaximizeWindowX11, 1222b877906bSopenharmony_ci .showWindow = _glfwShowWindowX11, 1223b877906bSopenharmony_ci .hideWindow = _glfwHideWindowX11, 1224b877906bSopenharmony_ci .requestWindowAttention = _glfwRequestWindowAttentionX11, 1225b877906bSopenharmony_ci .focusWindow = _glfwFocusWindowX11, 1226b877906bSopenharmony_ci .setWindowMonitor = _glfwSetWindowMonitorX11, 1227b877906bSopenharmony_ci .windowFocused = _glfwWindowFocusedX11, 1228b877906bSopenharmony_ci .windowIconified = _glfwWindowIconifiedX11, 1229b877906bSopenharmony_ci .windowVisible = _glfwWindowVisibleX11, 1230b877906bSopenharmony_ci .windowMaximized = _glfwWindowMaximizedX11, 1231b877906bSopenharmony_ci .windowHovered = _glfwWindowHoveredX11, 1232b877906bSopenharmony_ci .framebufferTransparent = _glfwFramebufferTransparentX11, 1233b877906bSopenharmony_ci .getWindowOpacity = _glfwGetWindowOpacityX11, 1234b877906bSopenharmony_ci .setWindowResizable = _glfwSetWindowResizableX11, 1235b877906bSopenharmony_ci .setWindowDecorated = _glfwSetWindowDecoratedX11, 1236b877906bSopenharmony_ci .setWindowFloating = _glfwSetWindowFloatingX11, 1237b877906bSopenharmony_ci .setWindowOpacity = _glfwSetWindowOpacityX11, 1238b877906bSopenharmony_ci .setWindowMousePassthrough = _glfwSetWindowMousePassthroughX11, 1239b877906bSopenharmony_ci .pollEvents = _glfwPollEventsX11, 1240b877906bSopenharmony_ci .waitEvents = _glfwWaitEventsX11, 1241b877906bSopenharmony_ci .waitEventsTimeout = _glfwWaitEventsTimeoutX11, 1242b877906bSopenharmony_ci .postEmptyEvent = _glfwPostEmptyEventX11, 1243b877906bSopenharmony_ci .getEGLPlatform = _glfwGetEGLPlatformX11, 1244b877906bSopenharmony_ci .getEGLNativeDisplay = _glfwGetEGLNativeDisplayX11, 1245b877906bSopenharmony_ci .getEGLNativeWindow = _glfwGetEGLNativeWindowX11, 1246b877906bSopenharmony_ci .getRequiredInstanceExtensions = _glfwGetRequiredInstanceExtensionsX11, 1247b877906bSopenharmony_ci .getPhysicalDevicePresentationSupport = _glfwGetPhysicalDevicePresentationSupportX11, 1248b877906bSopenharmony_ci .createWindowSurface = _glfwCreateWindowSurfaceX11 1249b877906bSopenharmony_ci }; 1250b877906bSopenharmony_ci 1251b877906bSopenharmony_ci // HACK: If the application has left the locale as "C" then both wide 1252b877906bSopenharmony_ci // character text input and explicit UTF-8 input via XIM will break 1253b877906bSopenharmony_ci // This sets the CTYPE part of the current locale from the environment 1254b877906bSopenharmony_ci // in the hope that it is set to something more sane than "C" 1255b877906bSopenharmony_ci if (strcmp(setlocale(LC_CTYPE, NULL), "C") == 0) 1256b877906bSopenharmony_ci setlocale(LC_CTYPE, ""); 1257b877906bSopenharmony_ci 1258b877906bSopenharmony_ci#if defined(__CYGWIN__) 1259b877906bSopenharmony_ci void* module = _glfwPlatformLoadModule("libX11-6.so"); 1260b877906bSopenharmony_ci#elif defined(__OpenBSD__) || defined(__NetBSD__) 1261b877906bSopenharmony_ci void* module = _glfwPlatformLoadModule("libX11.so"); 1262b877906bSopenharmony_ci#else 1263b877906bSopenharmony_ci void* module = _glfwPlatformLoadModule("libX11.so.6"); 1264b877906bSopenharmony_ci#endif 1265b877906bSopenharmony_ci if (!module) 1266b877906bSopenharmony_ci { 1267b877906bSopenharmony_ci if (platformID == GLFW_PLATFORM_X11) 1268b877906bSopenharmony_ci _glfwInputError(GLFW_PLATFORM_ERROR, "X11: Failed to load Xlib"); 1269b877906bSopenharmony_ci 1270b877906bSopenharmony_ci return GLFW_FALSE; 1271b877906bSopenharmony_ci } 1272b877906bSopenharmony_ci 1273b877906bSopenharmony_ci PFN_XInitThreads XInitThreads = (PFN_XInitThreads) 1274b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(module, "XInitThreads"); 1275b877906bSopenharmony_ci PFN_XrmInitialize XrmInitialize = (PFN_XrmInitialize) 1276b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(module, "XrmInitialize"); 1277b877906bSopenharmony_ci PFN_XOpenDisplay XOpenDisplay = (PFN_XOpenDisplay) 1278b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(module, "XOpenDisplay"); 1279b877906bSopenharmony_ci if (!XInitThreads || !XrmInitialize || !XOpenDisplay) 1280b877906bSopenharmony_ci { 1281b877906bSopenharmony_ci if (platformID == GLFW_PLATFORM_X11) 1282b877906bSopenharmony_ci _glfwInputError(GLFW_PLATFORM_ERROR, "X11: Failed to load Xlib entry point"); 1283b877906bSopenharmony_ci 1284b877906bSopenharmony_ci _glfwPlatformFreeModule(module); 1285b877906bSopenharmony_ci return GLFW_FALSE; 1286b877906bSopenharmony_ci } 1287b877906bSopenharmony_ci 1288b877906bSopenharmony_ci XInitThreads(); 1289b877906bSopenharmony_ci XrmInitialize(); 1290b877906bSopenharmony_ci 1291b877906bSopenharmony_ci Display* display = XOpenDisplay(NULL); 1292b877906bSopenharmony_ci if (!display) 1293b877906bSopenharmony_ci { 1294b877906bSopenharmony_ci if (platformID == GLFW_PLATFORM_X11) 1295b877906bSopenharmony_ci { 1296b877906bSopenharmony_ci const char* name = getenv("DISPLAY"); 1297b877906bSopenharmony_ci if (name) 1298b877906bSopenharmony_ci { 1299b877906bSopenharmony_ci _glfwInputError(GLFW_PLATFORM_UNAVAILABLE, 1300b877906bSopenharmony_ci "X11: Failed to open display %s", name); 1301b877906bSopenharmony_ci } 1302b877906bSopenharmony_ci else 1303b877906bSopenharmony_ci { 1304b877906bSopenharmony_ci _glfwInputError(GLFW_PLATFORM_UNAVAILABLE, 1305b877906bSopenharmony_ci "X11: The DISPLAY environment variable is missing"); 1306b877906bSopenharmony_ci } 1307b877906bSopenharmony_ci } 1308b877906bSopenharmony_ci 1309b877906bSopenharmony_ci _glfwPlatformFreeModule(module); 1310b877906bSopenharmony_ci return GLFW_FALSE; 1311b877906bSopenharmony_ci } 1312b877906bSopenharmony_ci 1313b877906bSopenharmony_ci _glfw.x11.display = display; 1314b877906bSopenharmony_ci _glfw.x11.xlib.handle = module; 1315b877906bSopenharmony_ci 1316b877906bSopenharmony_ci *platform = x11; 1317b877906bSopenharmony_ci return GLFW_TRUE; 1318b877906bSopenharmony_ci} 1319b877906bSopenharmony_ci 1320b877906bSopenharmony_ciint _glfwInitX11(void) 1321b877906bSopenharmony_ci{ 1322b877906bSopenharmony_ci _glfw.x11.xlib.AllocClassHint = (PFN_XAllocClassHint) 1323b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XAllocClassHint"); 1324b877906bSopenharmony_ci _glfw.x11.xlib.AllocSizeHints = (PFN_XAllocSizeHints) 1325b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XAllocSizeHints"); 1326b877906bSopenharmony_ci _glfw.x11.xlib.AllocWMHints = (PFN_XAllocWMHints) 1327b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XAllocWMHints"); 1328b877906bSopenharmony_ci _glfw.x11.xlib.ChangeProperty = (PFN_XChangeProperty) 1329b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XChangeProperty"); 1330b877906bSopenharmony_ci _glfw.x11.xlib.ChangeWindowAttributes = (PFN_XChangeWindowAttributes) 1331b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XChangeWindowAttributes"); 1332b877906bSopenharmony_ci _glfw.x11.xlib.CheckIfEvent = (PFN_XCheckIfEvent) 1333b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XCheckIfEvent"); 1334b877906bSopenharmony_ci _glfw.x11.xlib.CheckTypedWindowEvent = (PFN_XCheckTypedWindowEvent) 1335b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XCheckTypedWindowEvent"); 1336b877906bSopenharmony_ci _glfw.x11.xlib.CloseDisplay = (PFN_XCloseDisplay) 1337b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XCloseDisplay"); 1338b877906bSopenharmony_ci _glfw.x11.xlib.CloseIM = (PFN_XCloseIM) 1339b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XCloseIM"); 1340b877906bSopenharmony_ci _glfw.x11.xlib.ConvertSelection = (PFN_XConvertSelection) 1341b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XConvertSelection"); 1342b877906bSopenharmony_ci _glfw.x11.xlib.CreateColormap = (PFN_XCreateColormap) 1343b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XCreateColormap"); 1344b877906bSopenharmony_ci _glfw.x11.xlib.CreateFontCursor = (PFN_XCreateFontCursor) 1345b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XCreateFontCursor"); 1346b877906bSopenharmony_ci _glfw.x11.xlib.CreateIC = (PFN_XCreateIC) 1347b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XCreateIC"); 1348b877906bSopenharmony_ci _glfw.x11.xlib.CreateRegion = (PFN_XCreateRegion) 1349b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XCreateRegion"); 1350b877906bSopenharmony_ci _glfw.x11.xlib.CreateWindow = (PFN_XCreateWindow) 1351b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XCreateWindow"); 1352b877906bSopenharmony_ci _glfw.x11.xlib.DefineCursor = (PFN_XDefineCursor) 1353b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XDefineCursor"); 1354b877906bSopenharmony_ci _glfw.x11.xlib.DeleteContext = (PFN_XDeleteContext) 1355b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XDeleteContext"); 1356b877906bSopenharmony_ci _glfw.x11.xlib.DeleteProperty = (PFN_XDeleteProperty) 1357b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XDeleteProperty"); 1358b877906bSopenharmony_ci _glfw.x11.xlib.DestroyIC = (PFN_XDestroyIC) 1359b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XDestroyIC"); 1360b877906bSopenharmony_ci _glfw.x11.xlib.DestroyRegion = (PFN_XDestroyRegion) 1361b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XDestroyRegion"); 1362b877906bSopenharmony_ci _glfw.x11.xlib.DestroyWindow = (PFN_XDestroyWindow) 1363b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XDestroyWindow"); 1364b877906bSopenharmony_ci _glfw.x11.xlib.DisplayKeycodes = (PFN_XDisplayKeycodes) 1365b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XDisplayKeycodes"); 1366b877906bSopenharmony_ci _glfw.x11.xlib.EventsQueued = (PFN_XEventsQueued) 1367b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XEventsQueued"); 1368b877906bSopenharmony_ci _glfw.x11.xlib.FilterEvent = (PFN_XFilterEvent) 1369b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XFilterEvent"); 1370b877906bSopenharmony_ci _glfw.x11.xlib.FindContext = (PFN_XFindContext) 1371b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XFindContext"); 1372b877906bSopenharmony_ci _glfw.x11.xlib.Flush = (PFN_XFlush) 1373b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XFlush"); 1374b877906bSopenharmony_ci _glfw.x11.xlib.Free = (PFN_XFree) 1375b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XFree"); 1376b877906bSopenharmony_ci _glfw.x11.xlib.FreeColormap = (PFN_XFreeColormap) 1377b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XFreeColormap"); 1378b877906bSopenharmony_ci _glfw.x11.xlib.FreeCursor = (PFN_XFreeCursor) 1379b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XFreeCursor"); 1380b877906bSopenharmony_ci _glfw.x11.xlib.FreeEventData = (PFN_XFreeEventData) 1381b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XFreeEventData"); 1382b877906bSopenharmony_ci _glfw.x11.xlib.GetErrorText = (PFN_XGetErrorText) 1383b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetErrorText"); 1384b877906bSopenharmony_ci _glfw.x11.xlib.GetEventData = (PFN_XGetEventData) 1385b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetEventData"); 1386b877906bSopenharmony_ci _glfw.x11.xlib.GetICValues = (PFN_XGetICValues) 1387b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetICValues"); 1388b877906bSopenharmony_ci _glfw.x11.xlib.GetIMValues = (PFN_XGetIMValues) 1389b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetIMValues"); 1390b877906bSopenharmony_ci _glfw.x11.xlib.GetInputFocus = (PFN_XGetInputFocus) 1391b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetInputFocus"); 1392b877906bSopenharmony_ci _glfw.x11.xlib.GetKeyboardMapping = (PFN_XGetKeyboardMapping) 1393b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetKeyboardMapping"); 1394b877906bSopenharmony_ci _glfw.x11.xlib.GetScreenSaver = (PFN_XGetScreenSaver) 1395b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetScreenSaver"); 1396b877906bSopenharmony_ci _glfw.x11.xlib.GetSelectionOwner = (PFN_XGetSelectionOwner) 1397b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetSelectionOwner"); 1398b877906bSopenharmony_ci _glfw.x11.xlib.GetVisualInfo = (PFN_XGetVisualInfo) 1399b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetVisualInfo"); 1400b877906bSopenharmony_ci _glfw.x11.xlib.GetWMNormalHints = (PFN_XGetWMNormalHints) 1401b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetWMNormalHints"); 1402b877906bSopenharmony_ci _glfw.x11.xlib.GetWindowAttributes = (PFN_XGetWindowAttributes) 1403b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetWindowAttributes"); 1404b877906bSopenharmony_ci _glfw.x11.xlib.GetWindowProperty = (PFN_XGetWindowProperty) 1405b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGetWindowProperty"); 1406b877906bSopenharmony_ci _glfw.x11.xlib.GrabPointer = (PFN_XGrabPointer) 1407b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XGrabPointer"); 1408b877906bSopenharmony_ci _glfw.x11.xlib.IconifyWindow = (PFN_XIconifyWindow) 1409b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XIconifyWindow"); 1410b877906bSopenharmony_ci _glfw.x11.xlib.InternAtom = (PFN_XInternAtom) 1411b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XInternAtom"); 1412b877906bSopenharmony_ci _glfw.x11.xlib.LookupString = (PFN_XLookupString) 1413b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XLookupString"); 1414b877906bSopenharmony_ci _glfw.x11.xlib.MapRaised = (PFN_XMapRaised) 1415b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XMapRaised"); 1416b877906bSopenharmony_ci _glfw.x11.xlib.MapWindow = (PFN_XMapWindow) 1417b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XMapWindow"); 1418b877906bSopenharmony_ci _glfw.x11.xlib.MoveResizeWindow = (PFN_XMoveResizeWindow) 1419b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XMoveResizeWindow"); 1420b877906bSopenharmony_ci _glfw.x11.xlib.MoveWindow = (PFN_XMoveWindow) 1421b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XMoveWindow"); 1422b877906bSopenharmony_ci _glfw.x11.xlib.NextEvent = (PFN_XNextEvent) 1423b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XNextEvent"); 1424b877906bSopenharmony_ci _glfw.x11.xlib.OpenIM = (PFN_XOpenIM) 1425b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XOpenIM"); 1426b877906bSopenharmony_ci _glfw.x11.xlib.PeekEvent = (PFN_XPeekEvent) 1427b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XPeekEvent"); 1428b877906bSopenharmony_ci _glfw.x11.xlib.Pending = (PFN_XPending) 1429b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XPending"); 1430b877906bSopenharmony_ci _glfw.x11.xlib.QueryExtension = (PFN_XQueryExtension) 1431b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XQueryExtension"); 1432b877906bSopenharmony_ci _glfw.x11.xlib.QueryPointer = (PFN_XQueryPointer) 1433b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XQueryPointer"); 1434b877906bSopenharmony_ci _glfw.x11.xlib.RaiseWindow = (PFN_XRaiseWindow) 1435b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XRaiseWindow"); 1436b877906bSopenharmony_ci _glfw.x11.xlib.RegisterIMInstantiateCallback = (PFN_XRegisterIMInstantiateCallback) 1437b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XRegisterIMInstantiateCallback"); 1438b877906bSopenharmony_ci _glfw.x11.xlib.ResizeWindow = (PFN_XResizeWindow) 1439b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XResizeWindow"); 1440b877906bSopenharmony_ci _glfw.x11.xlib.ResourceManagerString = (PFN_XResourceManagerString) 1441b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XResourceManagerString"); 1442b877906bSopenharmony_ci _glfw.x11.xlib.SaveContext = (PFN_XSaveContext) 1443b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSaveContext"); 1444b877906bSopenharmony_ci _glfw.x11.xlib.SelectInput = (PFN_XSelectInput) 1445b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSelectInput"); 1446b877906bSopenharmony_ci _glfw.x11.xlib.SendEvent = (PFN_XSendEvent) 1447b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSendEvent"); 1448b877906bSopenharmony_ci _glfw.x11.xlib.SetClassHint = (PFN_XSetClassHint) 1449b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetClassHint"); 1450b877906bSopenharmony_ci _glfw.x11.xlib.SetErrorHandler = (PFN_XSetErrorHandler) 1451b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetErrorHandler"); 1452b877906bSopenharmony_ci _glfw.x11.xlib.SetICFocus = (PFN_XSetICFocus) 1453b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetICFocus"); 1454b877906bSopenharmony_ci _glfw.x11.xlib.SetIMValues = (PFN_XSetIMValues) 1455b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetIMValues"); 1456b877906bSopenharmony_ci _glfw.x11.xlib.SetInputFocus = (PFN_XSetInputFocus) 1457b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetInputFocus"); 1458b877906bSopenharmony_ci _glfw.x11.xlib.SetLocaleModifiers = (PFN_XSetLocaleModifiers) 1459b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetLocaleModifiers"); 1460b877906bSopenharmony_ci _glfw.x11.xlib.SetScreenSaver = (PFN_XSetScreenSaver) 1461b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetScreenSaver"); 1462b877906bSopenharmony_ci _glfw.x11.xlib.SetSelectionOwner = (PFN_XSetSelectionOwner) 1463b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetSelectionOwner"); 1464b877906bSopenharmony_ci _glfw.x11.xlib.SetWMHints = (PFN_XSetWMHints) 1465b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetWMHints"); 1466b877906bSopenharmony_ci _glfw.x11.xlib.SetWMNormalHints = (PFN_XSetWMNormalHints) 1467b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetWMNormalHints"); 1468b877906bSopenharmony_ci _glfw.x11.xlib.SetWMProtocols = (PFN_XSetWMProtocols) 1469b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSetWMProtocols"); 1470b877906bSopenharmony_ci _glfw.x11.xlib.SupportsLocale = (PFN_XSupportsLocale) 1471b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSupportsLocale"); 1472b877906bSopenharmony_ci _glfw.x11.xlib.Sync = (PFN_XSync) 1473b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XSync"); 1474b877906bSopenharmony_ci _glfw.x11.xlib.TranslateCoordinates = (PFN_XTranslateCoordinates) 1475b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XTranslateCoordinates"); 1476b877906bSopenharmony_ci _glfw.x11.xlib.UndefineCursor = (PFN_XUndefineCursor) 1477b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XUndefineCursor"); 1478b877906bSopenharmony_ci _glfw.x11.xlib.UngrabPointer = (PFN_XUngrabPointer) 1479b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XUngrabPointer"); 1480b877906bSopenharmony_ci _glfw.x11.xlib.UnmapWindow = (PFN_XUnmapWindow) 1481b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XUnmapWindow"); 1482b877906bSopenharmony_ci _glfw.x11.xlib.UnsetICFocus = (PFN_XUnsetICFocus) 1483b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XUnsetICFocus"); 1484b877906bSopenharmony_ci _glfw.x11.xlib.VisualIDFromVisual = (PFN_XVisualIDFromVisual) 1485b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XVisualIDFromVisual"); 1486b877906bSopenharmony_ci _glfw.x11.xlib.WarpPointer = (PFN_XWarpPointer) 1487b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XWarpPointer"); 1488b877906bSopenharmony_ci _glfw.x11.xkb.FreeKeyboard = (PFN_XkbFreeKeyboard) 1489b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XkbFreeKeyboard"); 1490b877906bSopenharmony_ci _glfw.x11.xkb.FreeNames = (PFN_XkbFreeNames) 1491b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XkbFreeNames"); 1492b877906bSopenharmony_ci _glfw.x11.xkb.GetMap = (PFN_XkbGetMap) 1493b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XkbGetMap"); 1494b877906bSopenharmony_ci _glfw.x11.xkb.GetNames = (PFN_XkbGetNames) 1495b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XkbGetNames"); 1496b877906bSopenharmony_ci _glfw.x11.xkb.GetState = (PFN_XkbGetState) 1497b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XkbGetState"); 1498b877906bSopenharmony_ci _glfw.x11.xkb.KeycodeToKeysym = (PFN_XkbKeycodeToKeysym) 1499b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XkbKeycodeToKeysym"); 1500b877906bSopenharmony_ci _glfw.x11.xkb.QueryExtension = (PFN_XkbQueryExtension) 1501b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XkbQueryExtension"); 1502b877906bSopenharmony_ci _glfw.x11.xkb.SelectEventDetails = (PFN_XkbSelectEventDetails) 1503b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XkbSelectEventDetails"); 1504b877906bSopenharmony_ci _glfw.x11.xkb.SetDetectableAutoRepeat = (PFN_XkbSetDetectableAutoRepeat) 1505b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XkbSetDetectableAutoRepeat"); 1506b877906bSopenharmony_ci _glfw.x11.xrm.DestroyDatabase = (PFN_XrmDestroyDatabase) 1507b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XrmDestroyDatabase"); 1508b877906bSopenharmony_ci _glfw.x11.xrm.GetResource = (PFN_XrmGetResource) 1509b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XrmGetResource"); 1510b877906bSopenharmony_ci _glfw.x11.xrm.GetStringDatabase = (PFN_XrmGetStringDatabase) 1511b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XrmGetStringDatabase"); 1512b877906bSopenharmony_ci _glfw.x11.xrm.UniqueQuark = (PFN_XrmUniqueQuark) 1513b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XrmUniqueQuark"); 1514b877906bSopenharmony_ci _glfw.x11.xlib.UnregisterIMInstantiateCallback = (PFN_XUnregisterIMInstantiateCallback) 1515b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "XUnregisterIMInstantiateCallback"); 1516b877906bSopenharmony_ci _glfw.x11.xlib.utf8LookupString = (PFN_Xutf8LookupString) 1517b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "Xutf8LookupString"); 1518b877906bSopenharmony_ci _glfw.x11.xlib.utf8SetWMProperties = (PFN_Xutf8SetWMProperties) 1519b877906bSopenharmony_ci _glfwPlatformGetModuleSymbol(_glfw.x11.xlib.handle, "Xutf8SetWMProperties"); 1520b877906bSopenharmony_ci 1521b877906bSopenharmony_ci if (_glfw.x11.xlib.utf8LookupString && _glfw.x11.xlib.utf8SetWMProperties) 1522b877906bSopenharmony_ci _glfw.x11.xlib.utf8 = GLFW_TRUE; 1523b877906bSopenharmony_ci 1524b877906bSopenharmony_ci _glfw.x11.screen = DefaultScreen(_glfw.x11.display); 1525b877906bSopenharmony_ci _glfw.x11.root = RootWindow(_glfw.x11.display, _glfw.x11.screen); 1526b877906bSopenharmony_ci _glfw.x11.context = XUniqueContext(); 1527b877906bSopenharmony_ci 1528b877906bSopenharmony_ci getSystemContentScale(&_glfw.x11.contentScaleX, &_glfw.x11.contentScaleY); 1529b877906bSopenharmony_ci 1530b877906bSopenharmony_ci if (!createEmptyEventPipe()) 1531b877906bSopenharmony_ci return GLFW_FALSE; 1532b877906bSopenharmony_ci 1533b877906bSopenharmony_ci if (!initExtensions()) 1534b877906bSopenharmony_ci return GLFW_FALSE; 1535b877906bSopenharmony_ci 1536b877906bSopenharmony_ci _glfw.x11.helperWindowHandle = createHelperWindow(); 1537b877906bSopenharmony_ci _glfw.x11.hiddenCursorHandle = createHiddenCursor(); 1538b877906bSopenharmony_ci 1539b877906bSopenharmony_ci if (XSupportsLocale() && _glfw.x11.xlib.utf8) 1540b877906bSopenharmony_ci { 1541b877906bSopenharmony_ci XSetLocaleModifiers(""); 1542b877906bSopenharmony_ci 1543b877906bSopenharmony_ci // If an IM is already present our callback will be called right away 1544b877906bSopenharmony_ci XRegisterIMInstantiateCallback(_glfw.x11.display, 1545b877906bSopenharmony_ci NULL, NULL, NULL, 1546b877906bSopenharmony_ci inputMethodInstantiateCallback, 1547b877906bSopenharmony_ci NULL); 1548b877906bSopenharmony_ci } 1549b877906bSopenharmony_ci 1550b877906bSopenharmony_ci _glfwPollMonitorsX11(); 1551b877906bSopenharmony_ci return GLFW_TRUE; 1552b877906bSopenharmony_ci} 1553b877906bSopenharmony_ci 1554b877906bSopenharmony_civoid _glfwTerminateX11(void) 1555b877906bSopenharmony_ci{ 1556b877906bSopenharmony_ci if (_glfw.x11.helperWindowHandle) 1557b877906bSopenharmony_ci { 1558b877906bSopenharmony_ci if (XGetSelectionOwner(_glfw.x11.display, _glfw.x11.CLIPBOARD) == 1559b877906bSopenharmony_ci _glfw.x11.helperWindowHandle) 1560b877906bSopenharmony_ci { 1561b877906bSopenharmony_ci _glfwPushSelectionToManagerX11(); 1562b877906bSopenharmony_ci } 1563b877906bSopenharmony_ci 1564b877906bSopenharmony_ci XDestroyWindow(_glfw.x11.display, _glfw.x11.helperWindowHandle); 1565b877906bSopenharmony_ci _glfw.x11.helperWindowHandle = None; 1566b877906bSopenharmony_ci } 1567b877906bSopenharmony_ci 1568b877906bSopenharmony_ci if (_glfw.x11.hiddenCursorHandle) 1569b877906bSopenharmony_ci { 1570b877906bSopenharmony_ci XFreeCursor(_glfw.x11.display, _glfw.x11.hiddenCursorHandle); 1571b877906bSopenharmony_ci _glfw.x11.hiddenCursorHandle = (Cursor) 0; 1572b877906bSopenharmony_ci } 1573b877906bSopenharmony_ci 1574b877906bSopenharmony_ci _glfw_free(_glfw.x11.primarySelectionString); 1575b877906bSopenharmony_ci _glfw_free(_glfw.x11.clipboardString); 1576b877906bSopenharmony_ci 1577b877906bSopenharmony_ci XUnregisterIMInstantiateCallback(_glfw.x11.display, 1578b877906bSopenharmony_ci NULL, NULL, NULL, 1579b877906bSopenharmony_ci inputMethodInstantiateCallback, 1580b877906bSopenharmony_ci NULL); 1581b877906bSopenharmony_ci 1582b877906bSopenharmony_ci if (_glfw.x11.im) 1583b877906bSopenharmony_ci { 1584b877906bSopenharmony_ci XCloseIM(_glfw.x11.im); 1585b877906bSopenharmony_ci _glfw.x11.im = NULL; 1586b877906bSopenharmony_ci } 1587b877906bSopenharmony_ci 1588b877906bSopenharmony_ci if (_glfw.x11.display) 1589b877906bSopenharmony_ci { 1590b877906bSopenharmony_ci XCloseDisplay(_glfw.x11.display); 1591b877906bSopenharmony_ci _glfw.x11.display = NULL; 1592b877906bSopenharmony_ci } 1593b877906bSopenharmony_ci 1594b877906bSopenharmony_ci if (_glfw.x11.x11xcb.handle) 1595b877906bSopenharmony_ci { 1596b877906bSopenharmony_ci _glfwPlatformFreeModule(_glfw.x11.x11xcb.handle); 1597b877906bSopenharmony_ci _glfw.x11.x11xcb.handle = NULL; 1598b877906bSopenharmony_ci } 1599b877906bSopenharmony_ci 1600b877906bSopenharmony_ci if (_glfw.x11.xcursor.handle) 1601b877906bSopenharmony_ci { 1602b877906bSopenharmony_ci _glfwPlatformFreeModule(_glfw.x11.xcursor.handle); 1603b877906bSopenharmony_ci _glfw.x11.xcursor.handle = NULL; 1604b877906bSopenharmony_ci } 1605b877906bSopenharmony_ci 1606b877906bSopenharmony_ci if (_glfw.x11.randr.handle) 1607b877906bSopenharmony_ci { 1608b877906bSopenharmony_ci _glfwPlatformFreeModule(_glfw.x11.randr.handle); 1609b877906bSopenharmony_ci _glfw.x11.randr.handle = NULL; 1610b877906bSopenharmony_ci } 1611b877906bSopenharmony_ci 1612b877906bSopenharmony_ci if (_glfw.x11.xinerama.handle) 1613b877906bSopenharmony_ci { 1614b877906bSopenharmony_ci _glfwPlatformFreeModule(_glfw.x11.xinerama.handle); 1615b877906bSopenharmony_ci _glfw.x11.xinerama.handle = NULL; 1616b877906bSopenharmony_ci } 1617b877906bSopenharmony_ci 1618b877906bSopenharmony_ci if (_glfw.x11.xrender.handle) 1619b877906bSopenharmony_ci { 1620b877906bSopenharmony_ci _glfwPlatformFreeModule(_glfw.x11.xrender.handle); 1621b877906bSopenharmony_ci _glfw.x11.xrender.handle = NULL; 1622b877906bSopenharmony_ci } 1623b877906bSopenharmony_ci 1624b877906bSopenharmony_ci if (_glfw.x11.vidmode.handle) 1625b877906bSopenharmony_ci { 1626b877906bSopenharmony_ci _glfwPlatformFreeModule(_glfw.x11.vidmode.handle); 1627b877906bSopenharmony_ci _glfw.x11.vidmode.handle = NULL; 1628b877906bSopenharmony_ci } 1629b877906bSopenharmony_ci 1630b877906bSopenharmony_ci if (_glfw.x11.xi.handle) 1631b877906bSopenharmony_ci { 1632b877906bSopenharmony_ci _glfwPlatformFreeModule(_glfw.x11.xi.handle); 1633b877906bSopenharmony_ci _glfw.x11.xi.handle = NULL; 1634b877906bSopenharmony_ci } 1635b877906bSopenharmony_ci 1636b877906bSopenharmony_ci _glfwTerminateOSMesa(); 1637b877906bSopenharmony_ci // NOTE: These need to be unloaded after XCloseDisplay, as they register 1638b877906bSopenharmony_ci // cleanup callbacks that get called by that function 1639b877906bSopenharmony_ci _glfwTerminateEGL(); 1640b877906bSopenharmony_ci _glfwTerminateGLX(); 1641b877906bSopenharmony_ci 1642b877906bSopenharmony_ci if (_glfw.x11.xlib.handle) 1643b877906bSopenharmony_ci { 1644b877906bSopenharmony_ci _glfwPlatformFreeModule(_glfw.x11.xlib.handle); 1645b877906bSopenharmony_ci _glfw.x11.xlib.handle = NULL; 1646b877906bSopenharmony_ci } 1647b877906bSopenharmony_ci 1648b877906bSopenharmony_ci if (_glfw.x11.emptyEventPipe[0] || _glfw.x11.emptyEventPipe[1]) 1649b877906bSopenharmony_ci { 1650b877906bSopenharmony_ci close(_glfw.x11.emptyEventPipe[0]); 1651b877906bSopenharmony_ci close(_glfw.x11.emptyEventPipe[1]); 1652b877906bSopenharmony_ci } 1653b877906bSopenharmony_ci} 1654b877906bSopenharmony_ci 1655b877906bSopenharmony_ci#endif // _GLFW_X11 1656b877906bSopenharmony_ci 1657