1 /* 2 Copyright 2012-2014 David Robillard <http://drobilla.net> 3 Copyright 2012-2019 Filipe Coelho <falktx@falktx.com> 4 5 Permission to use, copy, modify, and/or distribute this software for any 6 purpose with or without fee is hereby granted, provided that the above 7 copyright notice and this permission notice appear in all copies. 8 9 THIS SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 10 WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 11 MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 12 ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 13 WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 14 ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 15 OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 16 */ 17 18 /** 19 @file pugl.h API for Pugl, a minimal portable API for OpenGL. 20 */ 21 22 #ifndef PUGL_H_INCLUDED 23 #define PUGL_H_INCLUDED 24 25 #include <stdint.h> 26 27 /* 28 This API is pure portable C and contains no platform specific elements, or 29 even a GL dependency. However, unfortunately GL includes vary across 30 platforms so they are included here to allow for pure portable programs. 31 */ 32 #ifdef __APPLE__ 33 # include <OpenGL/gl.h> 34 #else 35 # ifdef _WIN32 36 # include <winsock2.h> 37 # include <windows.h> /* Broken Windows GL headers require this */ 38 # endif 39 # include <GL/gl.h> 40 #endif 41 42 #ifdef __cplusplus 43 extern "C" { 44 #else 45 # include <stdbool.h> 46 #endif 47 48 /** 49 @defgroup pugl Pugl 50 A minimal portable API for OpenGL. 51 @{ 52 */ 53 54 /** 55 A Pugl view. 56 */ 57 typedef struct PuglViewImpl PuglView; 58 59 /** 60 A native window handle. 61 62 On X11, this is a Window. 63 On OSX, this is an NSView*. 64 On Windows, this is a HWND. 65 */ 66 typedef intptr_t PuglNativeWindow; 67 68 /** 69 Return status code. 70 */ 71 typedef enum { 72 PUGL_SUCCESS = 0 73 } PuglStatus; 74 75 /** 76 Convenience symbols for ASCII control characters. 77 */ 78 typedef enum { 79 PUGL_CHAR_BACKSPACE = 0x08, 80 PUGL_CHAR_ESCAPE = 0x1B, 81 PUGL_CHAR_DELETE = 0x7F 82 } PuglChar; 83 84 /** 85 Special (non-Unicode) keyboard keys. 86 */ 87 typedef enum { 88 PUGL_KEY_F1 = 1, 89 PUGL_KEY_F2, 90 PUGL_KEY_F3, 91 PUGL_KEY_F4, 92 PUGL_KEY_F5, 93 PUGL_KEY_F6, 94 PUGL_KEY_F7, 95 PUGL_KEY_F8, 96 PUGL_KEY_F9, 97 PUGL_KEY_F10, 98 PUGL_KEY_F11, 99 PUGL_KEY_F12, 100 PUGL_KEY_LEFT, 101 PUGL_KEY_UP, 102 PUGL_KEY_RIGHT, 103 PUGL_KEY_DOWN, 104 PUGL_KEY_PAGE_UP, 105 PUGL_KEY_PAGE_DOWN, 106 PUGL_KEY_HOME, 107 PUGL_KEY_END, 108 PUGL_KEY_INSERT, 109 PUGL_KEY_SHIFT, 110 PUGL_KEY_CTRL, 111 PUGL_KEY_ALT, 112 PUGL_KEY_SUPER 113 } PuglKey; 114 115 /** 116 Keyboard modifier flags. 117 */ 118 typedef enum { 119 PUGL_MOD_SHIFT = 1 << 0, /**< Shift key */ 120 PUGL_MOD_CTRL = 1 << 1, /**< Control key */ 121 PUGL_MOD_ALT = 1 << 2, /**< Alt/Option key */ 122 PUGL_MOD_SUPER = 1 << 3 /**< Mod4/Command/Windows key */ 123 } PuglMod; 124 125 /** 126 Handle for opaque user data. 127 */ 128 typedef void* PuglHandle; 129 130 /** 131 A function called when the window is closed. 132 */ 133 typedef void (*PuglCloseFunc)(PuglView* view); 134 135 /** 136 A function called to draw the view contents with OpenGL. 137 */ 138 typedef void (*PuglDisplayFunc)(PuglView* view); 139 140 /** 141 A function called when a key is pressed or released. 142 @param view The view the event occured in. 143 @param press True if the key was pressed, false if released. 144 @param key Unicode point of the key pressed. 145 @return 0 if event was handled, otherwise send event to parent window. 146 */ 147 typedef int (*PuglKeyboardFunc)(PuglView* view, bool press, uint32_t key); 148 149 /** 150 A function called when the pointer moves. 151 @param view The view the event occured in. 152 @param x The window-relative x coordinate of the pointer. 153 @param y The window-relative y coordinate of the pointer. 154 */ 155 typedef void (*PuglMotionFunc)(PuglView* view, int x, int y); 156 157 /** 158 A function called when a mouse button is pressed or released. 159 @param view The view the event occured in. 160 @param button The button number (1 = left, 2 = middle, 3 = right). 161 @param press True if the key was pressed, false if released. 162 @param x The window-relative x coordinate of the pointer. 163 @param y The window-relative y coordinate of the pointer. 164 */ 165 typedef void (*PuglMouseFunc)( 166 PuglView* view, int button, bool press, int x, int y); 167 168 /** 169 A function called when the view is resized. 170 @param view The view being resized. 171 @param width The new view width. 172 @param height The new view height. 173 */ 174 typedef void (*PuglReshapeFunc)(PuglView* view, int width, int height); 175 176 /** 177 A function called outside of gl-context when the plugin schedules a resize via puglPostResize. 178 179 @param view The view being resized. 180 @param width The new width to resize to (variable is initialized to current size) 181 @param height The new height to resize to (variable is initialized to current size) 182 @param set_hints If not null, set window-hints 183 */ 184 typedef void (*PuglResizeFunc)(PuglView* view, int *width, int *height, int *set_hints); 185 186 /** 187 A function called on scrolling (e.g. mouse wheel or track pad). 188 189 The distances used here are in "lines", a single tick of a clicking mouse 190 wheel. For example, @p dy = 1.0 scrolls 1 line up. Some systems and 191 devices support finer resolution and/or higher values for fast scrolls, 192 so programs should handle any value gracefully. 193 194 @param view The view being scrolled. 195 @param x The window-relative x coordinate of the pointer. 196 @param y The window-relative y coordinate of the pointer. 197 @param dx The scroll x distance. 198 @param dx The scroll y distance. 199 */ 200 typedef void (*PuglScrollFunc)(PuglView* view, int x, int y, float dx, float dy); 201 202 /** 203 A function called when a special key is pressed or released. 204 205 This callback allows the use of keys that do not have unicode points. 206 Note that some are non-printable keys. 207 208 @param view The view the event occured in. 209 @param press True if the key was pressed, false if released. 210 @param key The key pressed. 211 @return 0 if event was handled, otherwise send event to parent window. 212 */ 213 typedef int (*PuglSpecialFunc)(PuglView* view, bool press, PuglKey key); 214 215 /** 216 A function called when a filename is selected via file-browser. 217 218 @param view The view the event occured in. 219 @param filename The selected file name or NULL if the dialog was canceled. 220 */ 221 typedef void (*PuglFileSelectedFunc)(PuglView* view, const char* filename); 222 223 /** 224 @name Initialization 225 Configuration functions which must be called before creating a window. 226 @{ 227 */ 228 229 /** 230 Create a Pugl context. 231 232 To create a window, call the various puglInit* functions as necessary, then 233 call puglCreateWindow(). 234 */ 235 PuglView* 236 puglInit(void); 237 238 /** 239 Set the parent window before creating a window (for embedding). 240 */ 241 void 242 puglInitWindowParent(PuglView* view, PuglNativeWindow parent); 243 244 /** 245 Set the window size before creating a window. 246 */ 247 void 248 puglInitWindowSize(PuglView* view, int width, int height); 249 250 /** 251 Set the minimum window size before creating a window. 252 */ 253 void 254 puglInitWindowMinSize(PuglView* view, int width, int height); 255 256 /** 257 Enable or disable resizing before creating a window. 258 */ 259 void 260 puglInitUserResizable(PuglView* view, bool resizable); 261 262 /** 263 Set transient parent before creating a window. 264 265 On X11, parent_id must be a Window. 266 On OSX, parent_id must be an NSView*. 267 */ 268 void 269 puglInitTransientFor(PuglView* view, uintptr_t parent); 270 271 /** 272 @} 273 */ 274 275 /** 276 @name Windows 277 Window management functions. 278 @{ 279 */ 280 281 /** 282 Create a window with the settings given by the various puglInit functions. 283 284 @return 1 (pugl does not currently support multiple windows). 285 */ 286 int 287 puglCreateWindow(PuglView* view, const char* title); 288 289 /** 290 Create a new GL window. 291 @param parent Parent window, or 0 for top level. 292 @param title Window title, or NULL. 293 @param width Window width in pixels. 294 @param height Window height in pixels. 295 @param resizable Whether window should be user resizable. 296 */ 297 PuglView* 298 puglCreate(PuglNativeWindow parent, 299 const char* title, 300 int min_width, 301 int min_height, 302 int width, 303 int height, 304 bool resizable, 305 unsigned long transientId); 306 307 /** 308 Show Window (external ui) 309 */ 310 void 311 puglShowWindow(PuglView* view); 312 313 /** 314 Hide Window (external ui) 315 */ 316 void 317 puglHideWindow(PuglView* view); 318 319 /** 320 Return the native window handle. 321 */ 322 PuglNativeWindow 323 puglGetNativeWindow(PuglView* view); 324 325 /** 326 @} 327 */ 328 329 /** 330 Set the handle to be passed to all callbacks. 331 332 This is generally a pointer to a struct which contains all necessary state. 333 Everything needed in callbacks should be here, not in static variables. 334 335 Note the lack of this facility makes GLUT unsuitable for plugins or 336 non-trivial programs; this mistake is largely why Pugl exists. 337 */ 338 void 339 puglSetHandle(PuglView* view, PuglHandle handle); 340 341 /** 342 Get the handle to be passed to all callbacks. 343 */ 344 PuglHandle 345 puglGetHandle(PuglView* view); 346 347 /** 348 Get the drawing context. 349 For Cairo contexts, this returns a pointer to a cairo_t. 350 For everything else, this is unused and returns NULL. 351 */ 352 void* 353 puglGetContext(PuglView* view); 354 355 /** 356 Return the timestamp (if any) of the currently-processing event. 357 */ 358 uint32_t 359 puglGetEventTimestamp(PuglView* view); 360 361 /** 362 Get the currently active modifiers (PuglMod flags). 363 364 This should only be called from an event handler. 365 */ 366 int 367 puglGetModifiers(PuglView* view); 368 369 /** 370 Ignore synthetic repeated key events. 371 */ 372 void 373 puglIgnoreKeyRepeat(PuglView* view, bool ignore); 374 375 /** 376 @name Event Callbacks 377 Functions to set event callbacks for handling user input. 378 @{ 379 */ 380 381 /** 382 Set the function to call when the window is closed. 383 */ 384 void 385 puglSetCloseFunc(PuglView* view, PuglCloseFunc closeFunc); 386 387 /** 388 Set the display function which should draw the UI using GL. 389 */ 390 void 391 puglSetDisplayFunc(PuglView* view, PuglDisplayFunc displayFunc); 392 393 /** 394 Set the function to call on keyboard events. 395 */ 396 void 397 puglSetKeyboardFunc(PuglView* view, PuglKeyboardFunc keyboardFunc); 398 399 /** 400 Set the function to call on mouse motion. 401 */ 402 void 403 puglSetMotionFunc(PuglView* view, PuglMotionFunc motionFunc); 404 405 /** 406 Set the function to call on mouse button events. 407 */ 408 void 409 puglSetMouseFunc(PuglView* view, PuglMouseFunc mouseFunc); 410 411 /** 412 Set the function to call on scroll events. 413 */ 414 void 415 puglSetScrollFunc(PuglView* view, PuglScrollFunc scrollFunc); 416 417 /** 418 Set the function to call on special events. 419 */ 420 void 421 puglSetSpecialFunc(PuglView* view, PuglSpecialFunc specialFunc); 422 423 /** 424 Set the function to call when the window size changes. 425 */ 426 void 427 puglSetReshapeFunc(PuglView* view, PuglReshapeFunc reshapeFunc); 428 429 /** 430 Set callback function to change window size. 431 */ 432 void 433 puglSetResizeFunc(PuglView* view, PuglResizeFunc resizeFunc); 434 435 /** 436 Set the function to call on file-browser selections. 437 */ 438 void 439 puglSetFileSelectedFunc(PuglView* view, PuglFileSelectedFunc fileSelectedFunc); 440 441 /** 442 @} 443 */ 444 445 /** 446 TODO document this. 447 */ 448 int 449 puglUpdateGeometryConstraints(PuglView* view, int min_width, int min_height, bool aspect); 450 451 /** 452 Grab the input focus. 453 */ 454 void 455 puglGrabFocus(PuglView* view); 456 457 /** 458 Process all pending window events. 459 460 This handles input events as well as rendering, so it should be called 461 regularly and rapidly enough to keep the UI responsive. 462 */ 463 PuglStatus 464 puglProcessEvents(PuglView* view); 465 466 /** 467 Request a redisplay on the next call to puglProcessEvents(). 468 */ 469 void 470 puglPostRedisplay(PuglView* view); 471 472 /** 473 Request a resize on the next call to puglProcessEvents(). 474 */ 475 void 476 puglPostResize(PuglView* view); 477 478 /** 479 Destroy a GL window. 480 */ 481 void 482 puglDestroy(PuglView* view); 483 484 /** 485 @} 486 */ 487 488 #ifdef __cplusplus 489 } /* extern "C" */ 490 #endif 491 492 #endif /* PUGL_H_INCLUDED */ 493