rnd-19990201-1
[rocksndiamonds.git] / src / msdos.c
index b64b9fab6ea36349c54a43f72d239d2409c1cad9..598aa5d2c5b3081c39b1cca2bd0514cacb96eb5d 100644 (file)
@@ -37,6 +37,7 @@ extern JOYSTICK_INFO joy[];
 extern int i_love_bill;
 
 /* internal variables of msdos.c */
 extern int i_love_bill;
 
 /* internal variables of msdos.c */
+static boolean keyboard_auto_repeat = TRUE;
 static int key_press_state[MAX_SCANCODES];
 static XEvent event_buffer[MAX_EVENT_BUFFER];
 static int pending_events;
 static int key_press_state[MAX_SCANCODES];
 static XEvent event_buffer[MAX_EVENT_BUFFER];
 static int pending_events;
@@ -250,6 +251,42 @@ void XMapWindow(Display *display, Window window)
     unhide_mouse(display);
 }
 
     unhide_mouse(display);
 }
 
+static unsigned long AllocColorCell(int r, int g, int b)
+{
+  byte pixel_mapping = 0;
+  int i;
+
+  r >>= 10;
+  g >>= 10;
+  b >>= 10;
+
+  /* try to use existing colors from the global colormap */
+  for (i=0; i<global_colormap_entries_used; i++)
+  {
+    if (r == global_colormap[i].r &&
+       g == global_colormap[i].g &&
+       b == global_colormap[i].b)              /* color found */
+    {
+      pixel_mapping = i;
+      break;
+    }
+  }
+
+  if (i == global_colormap_entries_used)       /* color not found */
+  {
+    if (global_colormap_entries_used < MAX_COLORS)
+      global_colormap_entries_used++;
+
+    global_colormap[i].r = r;
+    global_colormap[i].g = g;
+    global_colormap[i].b = b;
+
+    pixel_mapping = i;
+  }
+
+  return pixel_mapping;
+}
+
 Display *XOpenDisplay(char *display_name)
 {
   Screen *screen;
 Display *XOpenDisplay(char *display_name)
 {
   Screen *screen;
@@ -271,8 +308,13 @@ Display *XOpenDisplay(char *display_name)
 
   screen[0].cmap = 0;
   screen[0].root = 0;
 
   screen[0].cmap = 0;
   screen[0].root = 0;
+#if 0
   screen[0].white_pixel = 0xFF;
   screen[0].black_pixel = 0x00;
   screen[0].white_pixel = 0xFF;
   screen[0].black_pixel = 0x00;
+#else
+  screen[0].white_pixel = AllocColorCell(0xFFFF, 0xFFFF, 0xFFFF);
+  screen[0].black_pixel = AllocColorCell(0x0000, 0x0000, 0x0000);
+#endif
   screen[0].video_bitmap = NULL;
 
   display->default_screen = 0;
   screen[0].video_bitmap = NULL;
 
   display->default_screen = 0;
@@ -385,7 +427,7 @@ void XFillRectangle(Display *display, Drawable d, GC gc, int x, int y,
     mouse_off = hide_mouse(display, x, y, width, height);
   }
 
     mouse_off = hide_mouse(display, x, y, width, height);
   }
 
-  rectfill((BITMAP *)d, x, y, x + width, y + height,
+  rectfill((BITMAP *)d, x, y, x + width - 1, y + height - 1,
           ((XGCValues *)gc)->foreground);
 
   if (mouse_off)
           ((XGCValues *)gc)->foreground);
 
   if (mouse_off)
@@ -460,7 +502,12 @@ static BITMAP *Image_to_AllegroBitmap(Image *image)
   byte *src_ptr = image->data;
   byte pixel_mapping[MAX_COLORS];
   unsigned int depth = 8;
   byte *src_ptr = image->data;
   byte pixel_mapping[MAX_COLORS];
   unsigned int depth = 8;
+
+#if 0
   int i, j, x, y;
   int i, j, x, y;
+#else
+  int i, x, y;
+#endif
 
   /* allocate new allegro bitmap structure */
   if ((bitmap = create_bitmap_ex(depth, image->width, image->height)) == NULL)
 
   /* allocate new allegro bitmap structure */
   if ((bitmap = create_bitmap_ex(depth, image->width, image->height)) == NULL)
@@ -471,11 +518,16 @@ static BITMAP *Image_to_AllegroBitmap(Image *image)
   /* try to use existing colors from the global colormap */
   for (i=0; i<MAX_COLORS; i++)
   {
   /* try to use existing colors from the global colormap */
   for (i=0; i<MAX_COLORS; i++)
   {
+
+#if 0
     int r, g, b;
     int r, g, b;
+#endif
 
     if (!image->rgb.color_used[i])
       continue;
 
 
     if (!image->rgb.color_used[i])
       continue;
 
+
+#if 0
     r = image->rgb.red[i] >> 10;
     g = image->rgb.green[i] >> 10;
     b = image->rgb.blue[i] >> 10;
     r = image->rgb.red[i] >> 10;
     g = image->rgb.green[i] >> 10;
     b = image->rgb.blue[i] >> 10;
@@ -502,6 +554,12 @@ static BITMAP *Image_to_AllegroBitmap(Image *image)
 
       pixel_mapping[i] = j;
     }
 
       pixel_mapping[i] = j;
     }
+#else
+    pixel_mapping[i] = AllocColorCell(image->rgb.red[i],
+                                     image->rgb.green[i],
+                                     image->rgb.blue[i]);
+#endif
+
   }
 
   /* copy bitmap data */
   }
 
   /* copy bitmap data */
@@ -633,7 +691,7 @@ static void NewKeyEvent(int key_press_state, KeySym keysym)
   xkey->state = (unsigned int)keysym;
 }
 
   xkey->state = (unsigned int)keysym;
 }
 
-#define HANDLE_RAW_KB_ALL_KEYS         0
+#define HANDLE_RAW_KB_ALL_KEYS                 0
 #define HANDLE_RAW_KB_MODIFIER_KEYS_ONLY       1
 
 static int modifier_scancode[] =
 #define HANDLE_RAW_KB_MODIFIER_KEYS_ONLY       1
 
 static int modifier_scancode[] =
@@ -701,6 +759,26 @@ static void HandleKeyboardEvent()
       else if (ascii == '.')
        keysym = XK_KP_Separator;
     }
       else if (ascii == '.')
        keysym = XK_KP_Separator;
     }
+    else if (ascii >= ' ' && ascii <= 'Z')
+      keysym = XK_space + (KeySym)(ascii - ' ');
+    else if (ascii == '^')
+      keysym = XK_asciicircum;
+    else if (ascii == '_')
+      keysym = XK_underscore;
+    else if (ascii == 'Ä')
+      keysym = XK_Adiaeresis;
+    else if (ascii == 'Ö')
+      keysym = XK_Odiaeresis;
+    else if (ascii == 'Ü')
+      keysym = XK_Udiaeresis;
+    else if (ascii == 'ä')
+      keysym = XK_adiaeresis;
+    else if (ascii == 'ö')
+      keysym = XK_odiaeresis;
+    else if (ascii == 'ü')
+      keysym = XK_udiaeresis;
+    else if (ascii == 'ß')
+      keysym = XK_ssharp;
 
     NewKeyEvent(KeyPress, keysym);
   }
 
     NewKeyEvent(KeyPress, keysym);
   }
@@ -720,15 +798,22 @@ int XPending(Display *display)
   XMotionEvent *xmotion;
   int i;
 
   XMotionEvent *xmotion;
   int i;
 
+  /* When using 'HandleKeyboardRaw()', keyboard input is also stored in
+     the allegro keyboard input buffer and would be available a second
+     time by calling 'HandleKeyboardEvent()'. To avoid double keyboard
+     events, the allegro function 'clear_keybuf()' must be called each
+     time when switching from calling 'HandleKeyboardRaw()' to calling
+     'HandleKeyboardEvent()' to get keyboard input, which is actually
+     done by 'XAutoRepeatOn()' which sets keyboard_auto_repeat to TRUE. */
+
   /* keyboard event */
   /* keyboard event */
-  if (game_status == PLAYING)
-    HandleKeyboardRaw(HANDLE_RAW_KB_ALL_KEYS);
-  else
+  if (keyboard_auto_repeat)
     HandleKeyboardEvent();
     HandleKeyboardEvent();
+  else
+    HandleKeyboardRaw(HANDLE_RAW_KB_ALL_KEYS);
 
   /* mouse motion event */
 
   /* mouse motion event */
-  /* generate mouse motion event only if any mouse buttons are pressed */
-  if (mouse_pos != last_mouse_pos && mouse_b)
+  if (mouse_pos != last_mouse_pos)
   {
     last_mouse_pos = mouse_pos;
     pending_events++;
   {
     last_mouse_pos = mouse_pos;
     pending_events++;
@@ -812,6 +897,27 @@ void XDestroyImage(XImage *ximage)
 {
 }
 
 {
 }
 
+Bool XQueryPointer(Display *display, Window window,
+                  Window *root, Window *child, int *root_x, int *root_y,
+                  int *win_x, int *win_y, unsigned int *mask)
+{
+  *win_x = mouse_x - display->screens[display->default_screen].x;
+  *win_y = mouse_y - display->screens[display->default_screen].y;
+
+  return True;
+}
+
+void XAutoRepeatOn(Display *display)
+{
+  keyboard_auto_repeat = TRUE;
+  clear_keybuf();
+}
+
+void XAutoRepeatOff(Display *display)
+{
+  keyboard_auto_repeat = FALSE;
+}
+
 void NetworkServer(int port, int serveronly)
 {
   Error(ERR_WARN, "networking not supported in DOS version");
 void NetworkServer(int port, int serveronly)
 {
   Error(ERR_WARN, "networking not supported in DOS version");