rnd-20030411-1-src
[rocksndiamonds.git] / src / events.c
index 66e5ec642fd6fa4c88453257e7a22fd5fbe4f430..ffe1d4f0b09b306762c9560bab9a8ccf66a264c7 100644 (file)
@@ -1,7 +1,7 @@
 /***********************************************************
 * Rocks'n'Diamonds -- McDuffin Strikes Back!               *
 *----------------------------------------------------------*
-* (c) 1995-2001 Artsoft Entertainment                      *
+* (c) 1995-2002 Artsoft Entertainment                      *
 *               Holger Schemel                             *
 *               Detmolder Strasse 189                      *
 *               33604 Bielefeld                            *
 #define KEY_PRESSED            TRUE
 
 
+static boolean cursor_inside_playfield = FALSE;
+static boolean playfield_cursor_set = FALSE;
+static unsigned long playfield_cursor_delay = 0;
+
+
 /* event filter especially needed for SDL event filtering due to
-   delay problems with lots of mouse motion events when mouse
-   button not pressed */
+   delay problems with lots of mouse motion events when mouse button
+   not pressed (X11 can handle this with 'PointerMotionHintMask') */
 
 int FilterMouseMotionEvents(const Event *event)
 {
+  MotionEvent *motion;
+
+  /* non-motion events are directly passed to event handler functions */
   if (event->type != EVENT_MOTIONNOTIFY)
     return 1;
 
-  /* get mouse motion events without pressed button only in level editor */
+  motion = (MotionEvent *)event;
+  cursor_inside_playfield = (motion->x >= SX && motion->x < SX + SXSIZE &&
+                            motion->y >= SY && motion->y < SY + SYSIZE);
+
+  if (game_status == PLAYING && playfield_cursor_set)
+  {
+    SetMouseCursor(CURSOR_DEFAULT);
+    playfield_cursor_set = FALSE;
+    DelayReached(&playfield_cursor_delay, 0);
+  }
+
+  /* skip mouse motion events without pressed button outside level editor */
   if (button_status == MB_RELEASED && game_status != LEVELED)
     return 0;
   else
@@ -95,7 +114,25 @@ void EventLoop(void)
       }
     }
     else
+    {
+      /* when playing, display a special mouse pointer inside the playfield */
+      if (game_status == PLAYING)
+      {
+       if (!playfield_cursor_set && cursor_inside_playfield &&
+           DelayReached(&playfield_cursor_delay, 1000))
+       {
+         SetMouseCursor(CURSOR_PLAYFIELD);
+         playfield_cursor_set = TRUE;
+       }
+      }
+      else if (playfield_cursor_set)
+      {
+       SetMouseCursor(CURSOR_DEFAULT);
+       playfield_cursor_set = FALSE;
+      }
+
       HandleNoEvent();
+    }
 
     /* don't use all CPU time when idle; the main loop while playing
        has its own synchronization and is CPU friendly, too */
@@ -126,7 +163,11 @@ void HandleOtherEvents(Event *event)
       break;
 
     case EVENT_UNMAPNOTIFY:
+#if 0
+      /* This causes the game to stop not only when iconified, but also
+        when on another virtual desktop, which might be not desired. */
       SleepWhileUnmapped();
+#endif
       break;
 
     case EVENT_FOCUSIN:
@@ -542,14 +583,14 @@ void HandleKey(Key key, int key_status)
       TapeTogglePause(TAPE_TOGGLE_MANUAL);
   }
 
-
+#if 0
 #ifndef DEBUG
 
   if (game_status == PLAYING && (tape.playing || tape.pausing))
     return;
 
 #endif
-
+#endif
 
 
   HandleGadgetsKeyInput(key);
@@ -584,11 +625,15 @@ void HandleKey(Key key, int key_status)
         case KSYM_Page_Up:
           if (game_status == CHOOSELEVEL)
             HandleChooseLevel(0,0, 0,-SCR_FIELDY, MB_MENU_MARK);
+         else if (game_status == SETUP)
+           HandleSetupScreen(0,0, 0,-SCR_FIELDY, MB_MENU_MARK);
          break;
 
         case KSYM_Page_Down:
           if (game_status == CHOOSELEVEL)
             HandleChooseLevel(0,0, 0,SCR_FIELDY, MB_MENU_MARK);
+         else if (game_status == SETUP)
+           HandleSetupScreen(0,0, 0,SCR_FIELDY, MB_MENU_MARK);
          break;
 
 #ifdef DEBUG
@@ -850,11 +895,11 @@ void HandleJoystick()
          !DelayReached(&joystickmove_delay, GADGET_FRAME_DELAY))
        newbutton = dx = dy = 0;
 
-      if (game_status==MAINMENU)
+      if (game_status == MAINMENU)
        HandleMainMenu(0,0,dx,dy,newbutton ? MB_MENU_CHOICE : MB_MENU_MARK);
-      else if (game_status==CHOOSELEVEL)
+      else if (game_status == CHOOSELEVEL)
         HandleChooseLevel(0,0,dx,dy,newbutton ? MB_MENU_CHOICE : MB_MENU_MARK);
-      else if (game_status==SETUP)
+      else if (game_status == SETUP)
        HandleSetupScreen(0,0,dx,dy,newbutton ? MB_MENU_CHOICE : MB_MENU_MARK);
       break;
     }
@@ -867,6 +912,10 @@ void HandleJoystick()
       HandleHelpScreen(!newbutton);
       break;
 
+    case LEVELED:
+      HandleLevelEditorIdle();
+      break;
+
     case PLAYING:
       if (tape.playing || keyboard)
        newbutton = ((joy & JOY_BUTTON) != 0);