sdlterm/src/sdlterm.cc
changeset 72 6e0656600754
parent 71 cfd3445107b4
child 73 85a282b5e4fc
--- a/sdlterm/src/sdlterm.cc	Wed Jan 30 00:38:48 2013 +0100
+++ b/sdlterm/src/sdlterm.cc	Wed Jan 30 19:44:01 2013 +0100
@@ -371,6 +371,17 @@
 
 bool Terminal::wait_event(Event &event, Uint32 timeout)
 {
+    SDL_Event sdl_event;
+    bool translated;
+
+    // any events pending?
+    while (SDL_PollEvent(&sdl_event))
+    {
+        translated = _handle_event(sdl_event, event);
+        if (translated)
+            return true;
+    }
+
     // use timer to simulate SDL_WaitEventTimeout, which is not available in SDL 1.2
     SDL_TimerID timer_id = NULL;
     if (timeout)
@@ -379,104 +390,25 @@
     }
 
     // loop until we have something to return
-    SDL_Event sdl_event;
     bool event_ready = false;
-    while (SDL_WaitEvent(&sdl_event) && !event_ready)
+    while (!event_ready && SDL_WaitEvent(&sdl_event))
     {
-        switch (sdl_event.type)
+        do
         {
-            case SDL_USEREVENT:
-                // timeout
-                if (sdl_event.user.code == 1)
-                {
-                    SDL_RemoveTimer(timer_id);
-                    return false;
-                }
-                // toggle blink
-                if (sdl_event.user.code == 2)
-                {
-                    _screen.toggle_blink();
-                }
-                break; // continue loop
-
-            case SDL_QUIT:
-                event.type = Event::QUIT;
-                event_ready = true;
-                break;
-
-            case SDL_VIDEORESIZE:
-                event.type = Event::RESIZE;
-                _screen.resize(sdl_event.resize.w, sdl_event.resize.h);
-                event_ready = true;
-                break;
-
-            case SDL_VIDEOEXPOSE:
-                _screen.redraw();
-                break;
-
-            case SDL_KEYDOWN:
+            translated = _handle_event(sdl_event, event);
+            if (translated)
             {
-                //switch(event.key.keysym.sym)
-                event.type = Event::KEYPRESS;
-                const char *keyname = _translate_keyname(sdl_event.key.keysym.sym);
-                // return only keyname or unicode, never both
-                if (keyname)
-                {
-                    strncpy(event.key.keyname, keyname, 10);
-                    event.key.unicode = 0;
-                }
-                else
-                {
-                    event.key.keyname[0] = 0;
-                    event.key.unicode = sdl_event.key.keysym.unicode;
-                    if (!event.key.unicode)
-                        break; // continue loop (unknown key)
-                }
-                event.key.mod = _translate_mod(sdl_event.key.keysym.mod);
                 event_ready = true;
                 break;
             }
-
-            case SDL_MOUSEBUTTONDOWN:
-            case SDL_MOUSEBUTTONUP:
-                event.type = (sdl_event.type == SDL_MOUSEBUTTONDOWN) ? Event::MOUSEDOWN : Event::MOUSEUP;
-                event.mouse.x = sdl_event.button.x / _screen.get_cell_width();
-                event.mouse.y = sdl_event.button.y / _screen.get_cell_height();
-                event.mouse.button = sdl_event.button.button;
-                if (sdl_event.button.button == SDL_BUTTON_WHEELUP || sdl_event.button.button == SDL_BUTTON_WHEELDOWN)
-                {
-                    if (sdl_event.type == SDL_MOUSEBUTTONUP)
-                        break; // do not report button-up events for mouse wheel
-                    event.type = Event::MOUSEWHEEL;
-                }
-                _mousemove_last_x = -1;
-                event_ready = true;
-                break;
-
-            case SDL_MOUSEMOTION:
-                if (sdl_event.motion.state == 0)
-                    break; // continue loop, do not report move events when no button is pressed
-                event.type = Event::MOUSEMOVE;
-                event.mouse.x = sdl_event.motion.x / _screen.get_cell_width();
-                event.mouse.y = sdl_event.motion.y / _screen.get_cell_height();
-                if (_mousemove_last_x != event.mouse.x ||
-                    _mousemove_last_y != event.mouse.y)
-                {
-                    if (_mousemove_last_x != -1)
-                    {
-                        event.mouse.relx = event.mouse.x - _mousemove_last_x;
-                        event.mouse.rely = event.mouse.y - _mousemove_last_y;
-                        event_ready = true;
-                    }
-                    _mousemove_last_x = event.mouse.x;
-                    _mousemove_last_y = event.mouse.y;
-                    break;
-                }
-                break; // continue loop when mouse position did not change
-
-            default:
-                break; // continue loop
+            // timeout?
+            if (sdl_event.type == SDL_USEREVENT && sdl_event.user.code == 1)
+            {
+                SDL_RemoveTimer(timer_id);
+                return false;
+            }
         }
+        while (!event_ready && SDL_PollEvent(&sdl_event));
     }
 
     // remove timer when other event came before timeout
@@ -497,6 +429,104 @@
 }
 
 
+// return true when SDL_Event was translated to our Event
+bool Terminal::_handle_event(const SDL_Event &sdl_event, Event &event)
+{
+    switch (sdl_event.type)
+    {
+        case SDL_USEREVENT:
+            // toggle blink
+            if (sdl_event.user.code == 2)
+            {
+                _screen.toggle_blink();
+            }
+            return false;
+
+        case SDL_QUIT:
+            event.type = Event::QUIT;
+            return true;
+
+        case SDL_VIDEORESIZE:
+            event.type = Event::RESIZE;
+            _screen.resize(sdl_event.resize.w, sdl_event.resize.h);
+            return true;
+
+        case SDL_VIDEOEXPOSE:
+            _screen.redraw();
+            return false;
+
+        case SDL_KEYDOWN:
+        {
+            //switch(event.key.keysym.sym)
+            event.type = Event::KEYPRESS;
+            const char *keyname = _translate_keyname(sdl_event.key.keysym.sym);
+            // return only keyname or unicode, never both
+            if (keyname)
+            {
+                strncpy(event.key.keyname, keyname, 10);
+                event.key.unicode = 0;
+            }
+            else
+            {
+                event.key.keyname[0] = 0;
+                event.key.unicode = sdl_event.key.keysym.unicode;
+                if (!event.key.unicode)
+                {
+                    // unknown key
+                    return false;
+                }
+            }
+            event.key.mod = _translate_mod(sdl_event.key.keysym.mod);
+            return true;
+        }
+
+        case SDL_MOUSEBUTTONDOWN:
+        case SDL_MOUSEBUTTONUP:
+            event.type = (sdl_event.type == SDL_MOUSEBUTTONDOWN) ? Event::MOUSEDOWN : Event::MOUSEUP;
+            event.mouse.x = sdl_event.button.x / _screen.get_cell_width();
+            event.mouse.y = sdl_event.button.y / _screen.get_cell_height();
+            event.mouse.button = sdl_event.button.button;
+            if (sdl_event.button.button == SDL_BUTTON_WHEELUP || sdl_event.button.button == SDL_BUTTON_WHEELDOWN)
+            {
+                if (sdl_event.type == SDL_MOUSEBUTTONUP)
+                {
+                    // do not report button-up events for mouse wheel
+                    return false;
+                }
+                event.type = Event::MOUSEWHEEL;
+            }
+            _mousemove_last_x = event.mouse.x;
+            _mousemove_last_y = event.mouse.y;
+            return true;
+
+        case SDL_MOUSEMOTION:
+            if (sdl_event.motion.state == 0 || _mousemove_last_x == -1)
+            {
+                // do not report move events when no button is pressed
+                return false;
+            }
+            event.type = Event::MOUSEMOVE;
+            event.mouse.x = sdl_event.motion.x / _screen.get_cell_width();
+            event.mouse.y = sdl_event.motion.y / _screen.get_cell_height();
+            if (_mousemove_last_x != event.mouse.x ||
+                _mousemove_last_y != event.mouse.y)
+            {
+                event.mouse.relx = event.mouse.x - _mousemove_last_x;
+                event.mouse.rely = event.mouse.y - _mousemove_last_y;
+                _mousemove_last_x = event.mouse.x;
+                _mousemove_last_y = event.mouse.y;
+                return true;
+            }
+            // mouse position did not change
+            return false;
+
+        default:
+            // unknown event
+            return false;
+    }
+}
+
+
 const char *Terminal::_translate_keyname(SDLKey sym)
 {
     switch (sym)