xlib_playground

Xlib playground for experiments.
Log | Files | Refs

commit 3ef1e747d8e742f2f63e31183f52cdcec5ba3d50
parent 062ae436f429e77fe0b1a45b043e27f072399f6c
Author: Matsuda Kenji <info@mtkn.jp>
Date:   Fri, 23 Dec 2022 09:53:42 +0900

receive resize event

Diffstat:
Mex3/Makefile | 2+-
Dex3/ex2.c | 215-------------------------------------------------------------------------------
Aex3/ex3.c | 229+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
3 files changed, 230 insertions(+), 216 deletions(-)

diff --git a/ex3/Makefile b/ex3/Makefile @@ -2,7 +2,7 @@ INCS=-I/usr/X11R6/include CFLAGS=-Wall -Wextra -std=c11 LIBS=-L/usr/X11R6/lib -lX11 -lXext -lm IN=*.c -OUT=ex2 +OUT=ex3 all: $(IN) $(CC) $(INCS) $(CFLAGS) -o $(OUT) $(IN) $(LIBS) diff --git a/ex3/ex2.c b/ex3/ex2.c @@ -1,215 +0,0 @@ -#include <stdio.h> -#include <stdlib.h> -#include <time.h> -#include <unistd.h> -#include <math.h> - -#include <X11/Xlib.h> - -/* macros */ -#define INIT_WIDTH 800 -#define INIT_HEIGHT 600 -#define FPS 60 - -/* -#define COUNT_FPS -*/ - - -enum Keys { - Key_D, - Key_S, - Key_A, - Key_W, - Key_Space, - Num_Key, //number of keys in this enum -}; -enum Key_State { - Key_Up, - Key_Down, -}; - -/* variables */ -Display *display; -Window window; -unsigned int win_width = INIT_WIDTH, win_height = INIT_HEIGHT; -GC gc; -Atom wm_delete_window; -int key_state[Num_Key]; -int quit; -float px = 200, py = 200; -float vx = 0, vy = 0; -int width = 40, height = 40; - - -/* function prototypes */ -void setup(void); -void cleanup(void); -void handle_inputs(void); - - -void -setup(void) -{ - if ((display = XOpenDisplay(NULL)) == NULL){ - fprintf(stderr, "ERROR: could not open display\n"); - exit(1); - } - window = XCreateSimpleWindow( - display, - XDefaultRootWindow(display), - 0, 0, - win_width, win_height, - 0, 0, - 0); - XStoreName(display, window, "UNKO"); - gc = XCreateGC(display, window, 0, NULL); - - wm_delete_window = XInternAtom(display, - "WM_DELETE_WINDOW", False); - XSetWMProtocols(display, window, &wm_delete_window, 1); - - XSelectInput(display, window, - ExposureMask|KeyPressMask|KeyReleaseMask); - - XSetForeground(display, gc, 0x00FFFF); - XMapWindow(display, window); -} - -void -handle_inputs(void) -{ - XEvent event; - while (XPending(display) > 0) { - XNextEvent(display, &event); - switch (event.type) { - case KeyPress: { - switch (XLookupKeysym(&event.xkey, 0)) { - case 'q': - quit = 1; - break; - case 'd': - key_state[Key_D] = Key_Down; - break; - case 'a': - key_state[Key_A] = Key_Down; - break; - case 'w': - key_state[Key_W] = Key_Down; - break; - case 's': - key_state[Key_S] = Key_Down; - break; - default: - break; - } - } break; - case KeyRelease: { - switch (XLookupKeysym(&event.xkey, 0)) { - case 'd': - key_state[Key_D] = Key_Up; - break; - case 'a': - key_state[Key_A] = Key_Up; - break; - case 'w': - key_state[Key_W] = Key_Up; - break; - case 's': - key_state[Key_S] = Key_Up; - break; - default: - break; - } - } break; - case ClientMessage: { - if ((Atom) event.xclient.data.l[0] == wm_delete_window) { - quit = 1; - } - } break; - default: - break; - } - } - - - vx = vy = 0; - if (key_state[Key_D] == Key_Down) - vx += 300; - if (key_state[Key_A] == Key_Down) - vx += -300; - if (key_state[Key_S] == Key_Down) - vy += 300; - if (key_state[Key_W] == Key_Down) - vy += -300; - -} - -void -cleanup(void) -{ - XCloseDisplay(display); -} - -int -main(void) -{ - long t0, t1, dt; -#ifdef COUNT_FPS - int fps_count = 0; -#endif - struct timespec ts; - - setup(); - quit = 0; - clock_gettime(CLOCK_MONOTONIC, &ts); - t0 = ts.tv_nsec; - - while (!quit){ - handle_inputs(); - - // fix fps - dt = 0; - while (dt < 1.0 * 1000 * 1000 * 1000 / FPS){ - clock_gettime(CLOCK_MONOTONIC, &ts); - t1 = ts.tv_nsec; - dt = t1 > t0 ? t1 - t0 : t1 - t0 + 1000 * 1000 * 1000; - } -#ifdef COUNT_FPS - // count fps. - // simple but not precise. - fps_count++; - if (t1 < t0){ - printf("fps: %u\n", fps_count); - fps_count = 0; - } -#endif - - clock_gettime(CLOCK_MONOTONIC, &ts); - t0 = ts.tv_nsec; - - px = px + vx * dt / 1000 / 1000 / 1000; - py = py + vy * dt / 1000 / 1000 / 1000; - // bind within the window - if (px < 0) - px = 0; - if (win_width < px + width) - px = win_width - width; - if (py < 0) - py = 0; - if (win_height < py + height) - py = win_height - height; - - XClearArea(display, window, - 0, 0, // position - win_width, win_height, // width and height - False); - XFillRectangle(display, window, gc, - px, py, // position - width, height); // width and height - - } - - cleanup(); - return 0; -} diff --git a/ex3/ex3.c b/ex3/ex3.c @@ -0,0 +1,229 @@ +#include <stdio.h> +#include <stdlib.h> +#include <time.h> +#include <unistd.h> +#include <math.h> + +#include <X11/Xlib.h> + +/* macros */ +#define INIT_WIDTH 800 +#define INIT_HEIGHT 600 +#define FPS 60 + +/* +#define COUNT_FPS +*/ + + +enum Keys { + Key_D, + Key_S, + Key_A, + Key_W, + Key_Space, + Num_Key, //number of keys in this enum +}; +enum Key_State { + Key_Up, + Key_Down, +}; + +/* variables */ +Display *display; +Window window; +unsigned int win_width = INIT_WIDTH, win_height = INIT_HEIGHT; +GC gc; +Atom wm_delete_window; +int key_state[Num_Key]; +int quit; +float px = 200, py = 200; +float vx = 0, vy = 0; +int width = 40, height = 40; + + +/* function prototypes */ +void setup(void); +void cleanup(void); +void receive_events(void); +void handle_inputs(void); + + +void +setup(void) +{ + if ((display = XOpenDisplay(NULL)) == NULL){ + fprintf(stderr, "ERROR: could not open display\n"); + exit(1); + } + window = XCreateSimpleWindow( + display, + XDefaultRootWindow(display), + 0, 0, + win_width, win_height, + 0, 0, + 0); + XStoreName(display, window, "UNKO"); + gc = XCreateGC(display, window, 0, NULL); + + wm_delete_window = XInternAtom(display, + "WM_DELETE_WINDOW", False); + XSetWMProtocols(display, window, &wm_delete_window, 1); + + XSelectInput(display, window, + ExposureMask|KeyPressMask|KeyReleaseMask); + + XSetForeground(display, gc, 0x00FFFF); + XMapWindow(display, window); +} + +void +receive_events(void) +{ + XEvent event; + XWindowAttributes wattr; + + + + while (XPending(display) > 0) { + XNextEvent(display, &event); + switch (event.type) { + case Expose: { + XGetWindowAttributes(display, window, &wattr); + win_width = wattr.width; + win_height = wattr.height; + } break; + case KeyPress: { + switch (XLookupKeysym(&event.xkey, 0)) { + case 'q': + quit = 1; + break; + case 'd': + key_state[Key_D] = Key_Down; + break; + case 'a': + key_state[Key_A] = Key_Down; + break; + case 'w': + key_state[Key_W] = Key_Down; + break; + case 's': + key_state[Key_S] = Key_Down; + break; + default: + break; + } + } break; + case KeyRelease: { + switch (XLookupKeysym(&event.xkey, 0)) { + case 'd': + key_state[Key_D] = Key_Up; + break; + case 'a': + key_state[Key_A] = Key_Up; + break; + case 'w': + key_state[Key_W] = Key_Up; + break; + case 's': + key_state[Key_S] = Key_Up; + break; + default: + break; + } + } break; + case ClientMessage: { + if ((Atom) event.xclient.data.l[0] == wm_delete_window) { + quit = 1; + } + } break; + default: + break; + } + } +} + +void +handle_inputs(void) +{ + vx = vy = 0; + if (key_state[Key_D] == Key_Down) + vx += 300; + if (key_state[Key_A] == Key_Down) + vx += -300; + if (key_state[Key_S] == Key_Down) + vy += 300; + if (key_state[Key_W] == Key_Down) + vy += -300; + +} + +void +cleanup(void) +{ + XCloseDisplay(display); +} + +int +main(void) +{ + long t0, t1, dt; +#ifdef COUNT_FPS + int fps_count = 0; +#endif + struct timespec ts; + + setup(); + quit = 0; + clock_gettime(CLOCK_MONOTONIC, &ts); + t0 = ts.tv_nsec; + + while (!quit){ + receive_events(); + handle_inputs(); + + // fix fps + dt = 0; + while (dt < 1.0 * 1000 * 1000 * 1000 / FPS){ + clock_gettime(CLOCK_MONOTONIC, &ts); + t1 = ts.tv_nsec; + dt = t1 > t0 ? t1 - t0 : t1 - t0 + 1000 * 1000 * 1000; + } +#ifdef COUNT_FPS + // count fps. + // simple but not precise. + fps_count++; + if (t1 < t0){ + printf("fps: %u\n", fps_count); + fps_count = 0; + } +#endif + + clock_gettime(CLOCK_MONOTONIC, &ts); + t0 = ts.tv_nsec; + + px = px + vx * dt / 1000 / 1000 / 1000; + py = py + vy * dt / 1000 / 1000 / 1000; + // bind within the window + if (px < 0) + px = 0; + if (win_width < px + width) + px = win_width - width; + if (py < 0) + py = 0; + if (win_height < py + height) + py = win_height - height; + + XClearArea(display, window, + 0, 0, // position + win_width, win_height, // width and height + False); + XFillRectangle(display, window, gc, + px, py, // position + width, height); // width and height + + } + + cleanup(); + return 0; +}