summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--backend.mk2
-rw-r--r--libwinnie/src/event.h4
-rw-r--r--libwinnie/src/fbdev/event.cc87
3 files changed, 85 insertions, 8 deletions
diff --git a/backend.mk b/backend.mk
index 7fc38b6..e25dc62 100644
--- a/backend.mk
+++ b/backend.mk
@@ -1,4 +1,4 @@
-backend = SDL
+backend = FBDEV
ifeq ($(backend), SDL)
def = -DWINNIE_SDL
diff --git a/libwinnie/src/event.h b/libwinnie/src/event.h
index 46c3b77..5c1db45 100644
--- a/libwinnie/src/event.h
+++ b/libwinnie/src/event.h
@@ -24,8 +24,8 @@ Author: Eleni Maria Stea <elene.mst@gmail.com>
class Window;
-typedef void (*DisplayFuncType)(Window* win);
-typedef void (*KeyboardFuncType)(Window* win, int key, bool pressed);
+typedef void (*DisplayFuncType)(Window *win);
+typedef void (*KeyboardFuncType)(Window *win, int key, bool pressed);
typedef void (*MouseButtonFuncType)(Window *win, int bn, bool pressed, int x, int y);
typedef void (*MouseMotionFuncType)(Window *win, int x, int y);
typedef void (*TimerFuncType)(Window *win);
diff --git a/libwinnie/src/fbdev/event.cc b/libwinnie/src/fbdev/event.cc
index 00e12cd..18e363c 100644
--- a/libwinnie/src/fbdev/event.cc
+++ b/libwinnie/src/fbdev/event.cc
@@ -20,17 +20,30 @@ Author: Eleni Maria Stea <elene.mst@gmail.com>
*/
#ifdef WINNIE_FBDEV
+#include <list>
#include <stdio.h>
#include <errno.h>
#include <unistd.h>
#include <sys/select.h>
+#include <sys/time.h>
#include "event.h"
#include "wm.h"
#include "keyboard.h"
#include "mouse.h"
+struct TimerEvent {
+ long time;
+ Window *win;
+ TimerMode mode;
+ long interval;
+
+ bool operator <(const TimerEvent &rhs) const { return time < rhs.time; }
+};
+
+static std::list<TimerEvent> timers;
+
void process_events()
{
int keyb_fd = get_keyboard_fd();
@@ -47,14 +60,78 @@ void process_events()
int maxfd = keyb_fd > mouse_fd ? keyb_fd : mouse_fd;
- while(select(maxfd + 1, &read_set, 0, 0, 0) == -1 && errno == EINTR);
+ struct timeval *timeout = 0;
+ struct timeval tv;
+ if(!timers.empty()) {
+ long now = winnie_get_time();
+ long next_timer = timers.front().time - now;
+
+ tv.tv_sec = next_timer / 1000;
+ tv.tv_usec = next_timer % 1000;
+ timeout = &tv;
+ }
+
+ int numfd;
+ while((numfd = select(maxfd + 1, &read_set, 0, 0, timeout)) == -1) {
+ if(errno != EINTR) {
+ break;
+ }
+ }
- if(FD_ISSET(keyb_fd, &read_set)) {
- process_keyboard_event();
+ if(numfd > 0) {
+ if(FD_ISSET(keyb_fd, &read_set)) {
+ process_keyboard_event();
+ }
+ if(FD_ISSET(mouse_fd, &read_set)) {
+ process_mouse_event();
+ }
}
- if(FD_ISSET(mouse_fd, &read_set)) {
- process_mouse_event();
+
+ bool added_timer = false;
+ long now = winnie_get_time();
+ while(!timers.empty() && now >= timers.front().time) {
+ TimerEvent ev = timers.front();
+ timers.pop_front();
+
+ if(ev.mode == TIMER_REPEAT) {
+ ev.time = now + ev.interval;
+ timers.push_back(ev);
+ added_timer = true;
+ }
+
+ Window *win = ev.win;
+ TimerFuncType func = win->get_timer_callback();
+ if(func) {
+ func(win);
+ } else {
+ fprintf(stderr, "timer gone off but window has no timer callback\n");
+ }
+ }
+
+ if(added_timer) {
+ timers.sort();
}
}
}
+
+void set_window_timer(Window *win, unsigned int msec, TimerMode mode)
+{
+ if(!win) {
+ fprintf(stderr, "set_window_timer null window\n");
+ return;
+ }
+ if(!win->get_timer_callback()) {
+ fprintf(stderr, "trying to start a timer without having a timer callback\n");
+ return;
+ }
+
+ TimerEvent ev;
+ ev.interval = (long)msec;
+ ev.time = winnie_get_time() + ev.interval;
+ ev.win = win;
+ ev.mode = mode;
+ timers.push_back(ev);
+ timers.sort();
+}
+
#endif // WINNIE_FBDEV