main.c 8.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277
  1. /*
  2. * MIT License
  3. *
  4. * Copyright (c) 2016-2017 Patrick Rudolph <[email protected]>
  5. *
  6. * Permission is hereby granted, free of charge, to any person obtaining a copy
  7. * of this software and associated documentation files (the "Software"), to deal
  8. * in the Software without restriction, including without limitation the rights
  9. * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  10. * copies of the Software, and to permit persons to whom the Software is
  11. * furnished to do so, subject to the following conditions:
  12. * The above copyright notice and this permission notice shall be included in all
  13. * copies or substantial portions of the Software.
  14. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  15. * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  16. * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  17. * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  18. * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  19. * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  20. * SOFTWARE.
  21. *
  22. * Based on x11/main.c.
  23. *
  24. */
  25. #include <assert.h>
  26. #include <stdio.h>
  27. #include <stdlib.h>
  28. #include <stdarg.h>
  29. #include <string.h>
  30. #include <limits.h>
  31. #include <math.h>
  32. #include <sys/time.h>
  33. #include <unistd.h>
  34. #include <time.h>
  35. #define NK_INCLUDE_FIXED_TYPES
  36. #define NK_INCLUDE_STANDARD_IO
  37. #define NK_INCLUDE_STANDARD_VARARGS
  38. #define NK_INCLUDE_DEFAULT_ALLOCATOR
  39. #define NK_IMPLEMENTATION
  40. #define NK_XLIBSHM_IMPLEMENTATION
  41. #define NK_RAWFB_IMPLEMENTATION
  42. #define NK_INCLUDE_FONT_BAKING
  43. #define NK_INCLUDE_DEFAULT_FONT
  44. #define NK_INCLUDE_SOFTWARE_FONT
  45. #include "../../../nuklear.h"
  46. #include "../nuklear_rawfb.h"
  47. #include "nuklear_xlib.h"
  48. #define DTIME 20
  49. #define WINDOW_WIDTH 800
  50. #define WINDOW_HEIGHT 600
  51. #define UNUSED(a) (void)a
  52. #define MIN(a,b) ((a) < (b) ? (a) : (b))
  53. #define MAX(a,b) ((a) < (b) ? (b) : (a))
  54. #define LEN(a) (sizeof(a)/sizeof(a)[0])
  55. typedef struct XWindow XWindow;
  56. struct XWindow {
  57. Display *dpy;
  58. Window root;
  59. Visual *vis;
  60. Colormap cmap;
  61. XWindowAttributes attr;
  62. XSetWindowAttributes swa;
  63. Window win;
  64. int screen;
  65. unsigned int width;
  66. unsigned int height;
  67. };
  68. static void
  69. die(const char *fmt, ...)
  70. {
  71. va_list ap;
  72. va_start(ap, fmt);
  73. vfprintf(stderr, fmt, ap);
  74. va_end(ap);
  75. fputs("\n", stderr);
  76. exit(EXIT_FAILURE);
  77. }
  78. static long
  79. timestamp(void)
  80. {
  81. struct timeval tv;
  82. if (gettimeofday(&tv, NULL) < 0) return 0;
  83. return (long)((long)tv.tv_sec * 1000 + (long)tv.tv_usec/1000);
  84. }
  85. static void
  86. sleep_for(long t)
  87. {
  88. struct timespec req;
  89. const time_t sec = (int)(t/1000);
  90. const long ms = t - (sec * 1000);
  91. req.tv_sec = sec;
  92. req.tv_nsec = ms * 1000000L;
  93. while(-1 == nanosleep(&req, &req));
  94. }
  95. /* ===============================================================
  96. *
  97. * EXAMPLE
  98. *
  99. * ===============================================================*/
  100. /* This are some code examples to provide a small overview of what can be
  101. * done with this library. To try out an example uncomment the defines */
  102. /*#define INCLUDE_ALL */
  103. /*#define INCLUDE_STYLE */
  104. /*#define INCLUDE_CALCULATOR */
  105. /*#define INCLUDE_CANVAS */
  106. #define INCLUDE_OVERVIEW
  107. /*#define INCLUDE_CONFIGURATOR */
  108. /*#define INCLUDE_NODE_EDITOR */
  109. #ifdef INCLUDE_ALL
  110. #define INCLUDE_STYLE
  111. #define INCLUDE_CALCULATOR
  112. #define INCLUDE_CANVAS
  113. #define INCLUDE_OVERVIEW
  114. #define INCLUDE_CONFIGURATOR
  115. #define INCLUDE_NODE_EDITOR
  116. #endif
  117. #ifdef INCLUDE_STYLE
  118. #include "../../common/style.c"
  119. #endif
  120. #ifdef INCLUDE_CALCULATOR
  121. #include "../../common/calculator.c"
  122. #endif
  123. #ifdef INCLUDE_CANVAS
  124. #include "../../common/canvas.c"
  125. #endif
  126. #ifdef INCLUDE_OVERVIEW
  127. #include "../../common/overview.c"
  128. #endif
  129. #ifdef INCLUDE_CONFIGURATOR
  130. #include "../../common/style_configurator.c"
  131. #endif
  132. #ifdef INCLUDE_NODE_EDITOR
  133. #include "../../common/node_editor.c"
  134. #endif
  135. /* ===============================================================
  136. *
  137. * DEMO
  138. *
  139. * ===============================================================*/
  140. int
  141. main(void)
  142. {
  143. long dt;
  144. long started;
  145. int running = 1;
  146. int status;
  147. XWindow xw;
  148. struct rawfb_context *rawfb;
  149. void *fb = NULL;
  150. struct rawfb_pl pl;
  151. unsigned char tex_scratch[512 * 512];
  152. #ifdef INCLUDE_CONFIGURATOR
  153. static struct nk_color color_table[NK_COLOR_COUNT];
  154. memcpy(color_table, nk_default_color_style, sizeof(color_table));
  155. #endif
  156. /* X11 */
  157. memset(&xw, 0, sizeof xw);
  158. xw.dpy = XOpenDisplay(NULL);
  159. if (!xw.dpy) die("Could not open a display; perhaps $DISPLAY is not set?");
  160. xw.root = DefaultRootWindow(xw.dpy);
  161. xw.screen = XDefaultScreen(xw.dpy);
  162. xw.vis = XDefaultVisual(xw.dpy, xw.screen);
  163. xw.cmap = XCreateColormap(xw.dpy,xw.root,xw.vis,AllocNone);
  164. xw.swa.colormap = xw.cmap;
  165. xw.swa.event_mask =
  166. ExposureMask | KeyPressMask | KeyReleaseMask |
  167. ButtonPress | ButtonReleaseMask| ButtonMotionMask |
  168. Button1MotionMask | Button3MotionMask | Button4MotionMask | Button5MotionMask|
  169. PointerMotionMask | KeymapStateMask | EnterWindowMask | LeaveWindowMask;
  170. xw.win = XCreateWindow(xw.dpy, xw.root, 0, 0, WINDOW_WIDTH, WINDOW_HEIGHT, 0,
  171. XDefaultDepth(xw.dpy, xw.screen), InputOutput,
  172. xw.vis, CWEventMask | CWColormap, &xw.swa);
  173. XStoreName(xw.dpy, xw.win, "X11");
  174. XMapWindow(xw.dpy, xw.win);
  175. XGetWindowAttributes(xw.dpy, xw.win, &xw.attr);
  176. xw.width = (unsigned int)xw.attr.width;
  177. xw.height = (unsigned int)xw.attr.height;
  178. /* Framebuffer emulator */
  179. status = nk_xlib_init(xw.dpy, xw.vis, xw.screen, xw.win, xw.width, xw.height, &fb, &pl);
  180. if (!status || !fb)
  181. return 0;
  182. /* GUI */
  183. rawfb = nk_rawfb_init(fb, tex_scratch, xw.width, xw.height, xw.width * 4, pl);
  184. if (!rawfb) running = 0;
  185. while (running) {
  186. /* Input */
  187. XEvent evt;
  188. started = timestamp();
  189. nk_input_begin(&rawfb->ctx);
  190. while (XCheckWindowEvent(xw.dpy, xw.win, xw.swa.event_mask, &evt)) {
  191. if (XFilterEvent(&evt, xw.win)) continue;
  192. nk_xlib_handle_event(xw.dpy, xw.screen, xw.win, &evt, rawfb);
  193. }
  194. nk_input_end(&rawfb->ctx);
  195. /* GUI */
  196. if (nk_begin(&rawfb->ctx, "Demo", nk_rect(50, 50, 200, 200),
  197. NK_WINDOW_BORDER|NK_WINDOW_MOVABLE|
  198. NK_WINDOW_CLOSABLE|NK_WINDOW_MINIMIZABLE|NK_WINDOW_TITLE)) {
  199. enum {EASY, HARD};
  200. static int op = EASY;
  201. static int property = 20;
  202. nk_layout_row_static(&rawfb->ctx, 30, 80, 1);
  203. if (nk_button_label(&rawfb->ctx, "button"))
  204. fprintf(stdout, "button pressed\n");
  205. nk_layout_row_dynamic(&rawfb->ctx, 30, 2);
  206. if (nk_option_label(&rawfb->ctx, "easy", op == EASY)) op = EASY;
  207. if (nk_option_label(&rawfb->ctx, "hard", op == HARD)) op = HARD;
  208. nk_layout_row_dynamic(&rawfb->ctx, 25, 1);
  209. nk_property_int(&rawfb->ctx, "Compression:", 0, &property, 100, 10, 1);
  210. }
  211. nk_end(&rawfb->ctx);
  212. if (nk_window_is_closed(&rawfb->ctx, "Demo")) break;
  213. /* -------------- EXAMPLES ---------------- */
  214. #ifdef INCLUDE_CALCULATOR
  215. calculator(&rawfb->ctx);
  216. #endif
  217. #ifdef INCLUDE_CANVAS
  218. canvas(&rawfb->ctx);
  219. #endif
  220. #ifdef INCLUDE_OVERVIEW
  221. overview(&rawfb->ctx);
  222. #endif
  223. #ifdef INCLUDE_CONFIGURATOR
  224. style_configurator(&rawfb->ctx, color_table);
  225. #endif
  226. #ifdef INCLUDE_NODE_EDITOR
  227. node_editor(&rawfb->ctx);
  228. #endif
  229. /* ----------------------------------------- */
  230. /* Draw framebuffer */
  231. nk_rawfb_render(rawfb, nk_rgb(30,30,30), 1);
  232. /* Emulate framebuffer */
  233. XClearWindow(xw.dpy, xw.win);
  234. nk_xlib_render(xw.win);
  235. XFlush(xw.dpy);
  236. /* Timing */
  237. dt = timestamp() - started;
  238. if (dt < DTIME)
  239. sleep_for(DTIME - dt);
  240. }
  241. nk_rawfb_shutdown(rawfb);
  242. nk_xlib_shutdown();
  243. XUnmapWindow(xw.dpy, xw.win);
  244. XFreeColormap(xw.dpy, xw.cmap);
  245. XDestroyWindow(xw.dpy, xw.win);
  246. XCloseDisplay(xw.dpy);
  247. return 0;
  248. }