rnd-20000718-1-src
[rocksndiamonds.git] / src / events.c
index b9e4e9a2a5127bcd3a007623d04672f7aab6e3fb..1866e7ae79d00373ecab208209ad6cd5765c596b 100644 (file)
@@ -68,7 +68,8 @@ void EventLoop(void)
     if (game_status != PLAYING)
     {
       XSync(display, FALSE);
-      Delay(10);
+      if (!XPending(display))  /* delay only if no pending events */
+       Delay(10);
     }
 
     /* refresh window contents from drawing buffer, if needed */
@@ -169,7 +170,7 @@ void SleepWhileUnmapped()
     }
   }
 
-  if (game_status==PLAYING)
+  if (game_status == PLAYING)
     XAutoRepeatOff(display);
 }
 
@@ -216,7 +217,7 @@ void HandleButtonEvent(XButtonEvent *event)
 {
   motion_status = FALSE;
 
-  if (event->type==ButtonPress)
+  if (event->type == ButtonPress)
     button_status = event->button;
   else
     button_status = MB_RELEASED;
@@ -226,9 +227,21 @@ void HandleButtonEvent(XButtonEvent *event)
 
 void HandleMotionEvent(XMotionEvent *event)
 {
+  Window root, child;
+  int root_x, root_y;
+  int win_x, win_y;
+  unsigned int mask;
+
+  if (!XQueryPointer(display, window, &root, &child, &root_x, &root_y,
+                    &win_x, &win_y, &mask))
+    return;
+
+  if (!button_status && game_status != LEVELED)
+    return;
+
   motion_status = TRUE;
 
-  HandleButton(event->x, event->y, button_status);
+  HandleButton(win_x, win_y, button_status);
 }
 
 void HandleKeyEvent(XKeyEvent *event)
@@ -262,15 +275,40 @@ void HandleFocusEvent(XFocusChangeEvent *event)
 
   if (event->type == FocusOut)
   {
+    int i;
+
     XAutoRepeatOn(display);
     old_joystick_status = joystick_status;
     joystick_status = JOYSTICK_OFF;
+
+    /* simulate key release events for still pressed keys */
     key_joystick_mapping = 0;
+    for (i=0; i<MAX_PLAYERS; i++)
+      stored_player[i].action = 0;
   }
   else if (event->type == FocusIn)
   {
+    /* When there are two Rocks'n'Diamonds windows which overlap and
+       the player moves the pointer from one game window to the other,
+       a 'FocusOut' event is generated for the window the pointer is
+       leaving and a 'FocusIn' event is generated for the window the
+       pointer is entering. In some cases, it can happen that the
+       'FocusIn' event is handled by the one game process before the
+       'FocusOut' event by the other game process. In this case the
+       X11 environment would end up with activated keyboard auto repeat,
+       because unfortunately this is a global setting and not (which
+       would be far better) set for each X11 window individually.
+       The effect would be keyboard auto repeat while playing the game
+       (game_status == PLAYING), which is not desired.
+       To avoid this special case, we just wait 1/10 second before
+       processing the 'FocusIn' event.
+    */
+
     if (game_status == PLAYING)
+    {
+      Delay(100);
       XAutoRepeatOff(display);
+    }
     if (old_joystick_status != -1)
       joystick_status = old_joystick_status;
   }
@@ -299,10 +337,6 @@ void HandleButton(int mx, int my, int button)
   {
     old_mx = mx;
     old_my = my;
-
-    HandleVideoButtons(mx,my, button);
-    HandleSoundButtons(mx,my, button);
-    HandleGameButtons(mx,my, button);
   }
 
   HandleGadgets(mx, my, button);
@@ -322,11 +356,10 @@ void HandleButton(int mx, int my, int button)
       break;
 
     case HALLOFFAME:
-      HandleHallOfFame(button);
+      HandleHallOfFame(0,0, 0,0, button);
       break;
 
     case LEVELED:
-      LevelEd(mx,my, button);
       break;
 
     case HELPSCREEN:
@@ -444,7 +477,8 @@ void HandleKey(KeySym key, int key_status)
   if (key_status == KEY_RELEASED)
     return;
 
-  if (key == XK_Return && game_status == PLAYING && AllPlayersGone)
+  if ((key == XK_Return || key == XK_space) &&
+      game_status == PLAYING && AllPlayersGone)
   {
     CloseDoor(DOOR_CLOSE_1);
     game_status = MAINMENU;
@@ -455,16 +489,6 @@ void HandleKey(KeySym key, int key_status)
   /* allow quick escape to the main menu with the Escape key */
   if (key == XK_Escape && game_status != MAINMENU)
   {
-    if (game_status == LEVELED)
-    {
-      /* draw smaller door */
-      XCopyArea(display, pix[PIX_DOOR], drawto, gc,
-               DOOR_GFX_PAGEX7, 64,
-               108, 64,
-               EX - 4, EY - 12);
-      redraw_mask |= REDRAW_ALL;
-    }
-
     CloseDoor(DOOR_CLOSE_1 | DOOR_OPEN_2 | DOOR_NO_DELAY);
     game_status = MAINMENU;
     DrawMainMenu();
@@ -497,6 +521,7 @@ void HandleKey(KeySym key, int key_status)
       switch(key)
       {
        case XK_Return:
+       case XK_space:
          if (game_status == MAINMENU)
            HandleMainMenu(0,0, 0,0, MB_MENU_CHOICE);
           else if (game_status == CHOOSELEVEL)
@@ -507,6 +532,16 @@ void HandleKey(KeySym key, int key_status)
            HandleSetupInputScreen(0,0, 0,0, MB_MENU_CHOICE);
          break;
 
+        case XK_Page_Up:
+          if (game_status == CHOOSELEVEL)
+            HandleChooseLevel(0,0, 0,-SCR_FIELDY, MB_MENU_MARK);
+         break;
+
+        case XK_Page_Down:
+          if (game_status == CHOOSELEVEL)
+            HandleChooseLevel(0,0, 0,SCR_FIELDY, MB_MENU_MARK);
+         break;
+
        default:
          break;
       }
@@ -520,11 +555,20 @@ void HandleKey(KeySym key, int key_status)
       switch(key)
       {
        case XK_Return:
+       case XK_space:
          game_status = MAINMENU;
          DrawMainMenu();
          BackToFront();
          break;
 
+        case XK_Page_Up:
+         HandleHallOfFame(0,0, 0,-SCR_FIELDY, MB_MENU_MARK);
+         break;
+
+        case XK_Page_Down:
+         HandleHallOfFame(0,0, 0,SCR_FIELDY, MB_MENU_MARK);
+         break;
+
        default:
          break;
       }
@@ -532,7 +576,6 @@ void HandleKey(KeySym key, int key_status)
 
     case LEVELED:
       HandleLevelEditorKeyInput(key);
-      LevelNameTyping(key);
       break;
 
     case PLAYING:
@@ -575,7 +618,7 @@ void HandleKey(KeySym key, int key_status)
          break;
 #endif
 
-#if 1
+#if 0
        case XK_m:
          if (MoveSpeed == 8)
          {
@@ -738,7 +781,7 @@ void HandleJoystick()
     }
 
     case HALLOFFAME:
-      HandleHallOfFame(!newbutton);
+      HandleHallOfFame(0,0, dx,dy, !newbutton);
       break;
 
     case HELPSCREEN: