1 /* XDigger  Copyright (C) 1988-99 Alexander Lang.
2 
3 XDigger is free software; you can redistribute it and/or modify
4 it under the terms of the GNU General Public License as published by
5 the Free Software Foundation; either version 2, or (at your option)
6 any later version.
7 
8 XDigger is distributed in the hope that it will be useful,
9 but WITHOUT ANY WARRANTY; without even the implied warranty of
10 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11 GNU General Public License for more details.
12 
13 You should have received a copy of the GNU General Public License
14 along with this program; see the file COPYING.  If not, write to
15 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
16 
17 #ifndef __STDC__
18 #include <malloc.h>
19 #else
20 #include <stdlib.h>
21 #endif
22 #include <stdio.h>
23 #include <string.h>
24 #include <X11/Xlib.h>
25 #include <X11/Xutil.h>
26 #include <X11/cursorfont.h>
27 
28 #include "xdigger.h"
29 #include "drawpixmaps.h"
30 #include "pixmaps.h"
31 
32 Pixmap /*main_win_icon_pixmap,*/ pixmaps[CountPixmaps],
33   iconpixmaps[CountIconPixmaps], xbm_charset[180],
34   /*xpm_charset,*/ xpm_cur_digger_s, xpm_cur_digger_m;
35 
36 Cursor cursor_digger, cursor_watch;
37 
38 Visual *visual;
39 XImage *image;
40 int xdefaultdepth;
41 Bool AllocColorFailed = False;
42 /* Colormap colormap; */
43 
MakePixmap(char ** pixmap_xpm,int mag)44 Pixmap MakePixmap(char **pixmap_xpm, int mag)
45 {
46   Pixmap pixmap;
47   /* Colormap colormap; */
48   XColor color; /*, exact;*/
49   int xpm_width, xpm_height, xpm_num_colors, xpm_chars_per_pixel;
50   int i, j, x, y, z, f, countpixel;
51   int char2color[256];
52   char c, *value;
53 /*   float red, green, blue; */
54 
55   sscanf(pixmap_xpm[0], "%d %d %d %d", &xpm_width, &xpm_height,
56 	 &xpm_num_colors, &xpm_chars_per_pixel);
57 
58   for (z=1; z<=xpm_num_colors; z++)
59     {
60       value = strchr(pixmap_xpm[z], '#');
61       XParseColor(display, colormap, value, &color);
62 /*       red = (float)color.red / 0x10000; */
63 /*       color.pixel = xstdclrmap.base_pixel + */
64 /* 	((unsigned long)(0.5+(red*xstdclrmap.red_max))*xstdclrmap.red_mult); */
65 /* 	(color.red * xstdclrmap.red_max / 0x10000) * xstdclrmap.red_mult + */
66 /* 	(color.green * xstdclrmap.green_max / 0x10000) * xstdclrmap.green_mult+ */
67 /* 	(color.blue * xstdclrmap.blue_max / 0x10000) * xstdclrmap.blue_mult; */
68       if (!XAllocColor(display, colormap, &color))
69 	AllocColorFailed = True;
70       char2color[(unsigned char)pixmap_xpm[z][0]] = color.pixel;
71     }
72 
73   countpixel = 0;
74 
75   for (y=0; y<xpm_height; y++) for (x=0; x<xpm_width; x++)
76     {
77       c = pixmap_xpm[y+xpm_num_colors+1][x];
78       f = char2color[(unsigned char)c];
79       for (j=0; j<mag; j++) for (i=0; i<mag; i++)
80 	{
81 	  XPutPixel(image, x*mag+i, y*mag+j, f);
82 	}
83     }
84 /*   pixmap = XCreatePixmap(display, mainwindow, 16*mag, 16*mag, xdefaultdepth); */
85   pixmap = XCreatePixmap(display, mainwindow, xpm_width*mag, xpm_height*mag, xdefaultdepth);
86   { /* Kontrolle ob pixmap gueltig: */
87     Window r;
88     int x, y, w, h, b, d;
89     if (XGetGeometry(display, mainwindow, &r, &x, &y, &w, &h, &b, &d) ==
90 	BadAlloc)
91       {
92 	fprintf(stderr, "%s: Unvorhergesehener Fehler beim Erzeugen der "
93                 "Pixmaps!\n", progname);
94 	exit(42);
95       }
96   }
97 /*   XPutImage(display, pixmap, gc, image, 0, 0, 0, 0, 16*mag, 16*mag); */
98   XPutImage(display, pixmap, gc, image, 0, 0, 0, 0, xpm_width*mag, xpm_height*mag);
99   return(pixmap);
100 } /* Pixmap MakePixmap(char **pixmap_xpm, int mag) */
101 
XCreateMagBitmapFromData(data,width,height,mag)102 Pixmap XCreateMagBitmapFromData(data, width, height, mag)
103 char *data;
104 unsigned int width, height, mag;
105 {
106   /*char *imdata;*/
107   XImage *image;
108   Pixmap pixmap;
109   GC gc;
110   XGCValues gcvalues;
111   unsigned long gcvaluemask;
112   unsigned char *src, b;
113   unsigned long f;
114   int i, j, k, x, y, dx, dy;
115   Bool p;
116 
117   /*
118   imdata = malloc(width*height*mag*mag/8);
119   image = XCreateImage(display, visual, 1, XYBitmap, 0, imdata,
120 		       width*mag, height*mag, 8, 0);
121   */
122   image = XCreateImage(display, visual, 1, XYBitmap, 0, NULL,
123 		       width*mag, height*mag, 8, 0);
124   if (image != NULL)
125     image->data = malloc(image->bytes_per_line * image->height);
126 
127   src = data;
128   for (y=0; y<height; y++)
129     for (x=0; x<(width+1)/8; x++)
130       {
131 	b = *src++;
132 	for (k=0; k<8; k++)
133 	  {
134 	    p = b & 1;
135 	    b = b >> 1;
136 	    dx = x*8 + k;
137 	    dy = y;
138 	    if (p) f = 1/*fg*/; else f = 0/*bg*/;
139 	    for (j=0; j<mag; j++) for (i=0; i<mag; i++)
140 	      XPutPixel(image, dx*mag+i, dy*mag+j, f);
141 	  }
142       }
143 
144   pixmap =
145     XCreatePixmap(display, mainwindow, width*mag, height*mag, 1);
146   gcvalues.foreground = 1;
147   gcvalues.background = 0;
148   gcvaluemask = GCForeground | GCBackground;
149   gc = XCreateGC(display, pixmap, gcvaluemask, &gcvalues);
150   XPutImage(display, pixmap, gc, image, 0, 0, 0, 0, width*mag, height*mag);
151   XDestroyImage(image);
152   XFreeGC(display, gc);
153 
154   return(pixmap);
155 } /* Pixmap XCreateMagBitmapFromData(data, width, height, mag) */
156 
CreateImage()157 void CreateImage()
158 {
159   /*char *data;*/
160   int maxsize;
161 
162   /* Image erzeugen */
163   maxsize = 32;
164   if (maxsize < 16*xpmmag) maxsize = 16*xpmmag;
165   if (maxsize < 16*iconmag) maxsize = 16*iconmag;
166   /*
167   data = malloc(maxsize*maxsize*xdefaultdepth/8);
168   image = XCreateImage(display, visual, xdefaultdepth, ZPixmap, 0, data,
169 		       maxsize, maxsize, 8, 0);
170   */
171   image = XCreateImage(display, visual, xdefaultdepth, ZPixmap, 0, NULL,
172 		       maxsize, maxsize, 8, 0);
173   if (image != NULL)
174     image->data = malloc(image->bytes_per_line * image->height);
175   else {
176     fprintf(stderr, "%s: Unvorhergesehener Fehler beim Erzeugen des Images!\n",
177             progname);
178     exit(42);
179   }
180 }
181 
Make16x16Pixmaps()182 void Make16x16Pixmaps()
183 {
184   pixmaps[PXID_NOTHING]          = MakePixmap(nothing_xpm, xpmmag);
185   pixmaps[PXID_STONE]            = MakePixmap(stone_xpm, xpmmag);
186   pixmaps[PXID_GROUND]           = MakePixmap(ground_xpm, xpmmag);
187   pixmaps[PXID_GHOST]            = MakePixmap(ghost_xpm, xpmmag);
188   pixmaps[PXID_GHOST_LEFT]       = MakePixmap(ghost_left_xpm, xpmmag);
189   pixmaps[PXID_GHOST_RIGHT]      = MakePixmap(ghost_right_xpm, xpmmag);
190   pixmaps[PXID_GHOST_UP]         = MakePixmap(ghost_up_xpm, xpmmag);
191   pixmaps[PXID_DIAMOND]          = MakePixmap(diamond_xpm, xpmmag);
192   pixmaps[PXID_DIAMOND_BLINK0]   = MakePixmap(diamond0_xpm, xpmmag);
193   pixmaps[PXID_DIAMOND_BLINK1]   = MakePixmap(diamond1_xpm, xpmmag);
194   pixmaps[PXID_DIAMOND_BLINK2]   = MakePixmap(diamond2_xpm, xpmmag);
195   pixmaps[PXID_DIAMOND_BLINK3]   = MakePixmap(diamond3_xpm, xpmmag);
196   pixmaps[PXID_DIAMOND_BLINK4]   = MakePixmap(diamond4_xpm, xpmmag);
197   pixmaps[PXID_DIAMOND_BLINK5]   = MakePixmap(diamond5_xpm, xpmmag);
198   pixmaps[PXID_WALL]             = MakePixmap(wall_xpm, xpmmag);
199   pixmaps[PXID_DIGGER]           = MakePixmap(digger_xpm, xpmmag);
200   pixmaps[PXID_DIGGER_LEFT0]     = MakePixmap(digger_left0_xpm, xpmmag);
201   pixmaps[PXID_DIGGER_LEFT1]     = MakePixmap(digger_left1_xpm, xpmmag);
202   pixmaps[PXID_DIGGER_LEFT2]     = MakePixmap(digger_left2_xpm, xpmmag);
203   pixmaps[PXID_DIGGER_LEFT3]     = MakePixmap(digger_left3_xpm, xpmmag);
204   pixmaps[PXID_DIGGER_RIGHT0]    = MakePixmap(digger_right0_xpm, xpmmag);
205   pixmaps[PXID_DIGGER_RIGHT1]    = MakePixmap(digger_right1_xpm, xpmmag);
206   pixmaps[PXID_DIGGER_RIGHT2]    = MakePixmap(digger_right2_xpm, xpmmag);
207   pixmaps[PXID_DIGGER_RIGHT3]    = MakePixmap(digger_right3_xpm, xpmmag);
208   pixmaps[PXID_DIGGER_UP1]       = MakePixmap(digger_up1_xpm, xpmmag);
209   pixmaps[PXID_DIGGER_UP2]       = MakePixmap(digger_up2_xpm, xpmmag);
210   pixmaps[PXID_DIGGER_DOWN1]     = MakePixmap(digger_down1_xpm, xpmmag);
211   pixmaps[PXID_DIGGER_DOWN2]     = MakePixmap(digger_down2_xpm, xpmmag);
212   pixmaps[PXID_DIGGER_FOOT]      = MakePixmap(digger_foot_xpm, xpmmag);
213   pixmaps[PXID_DIGGER_EYE1]      = MakePixmap(digger_eye1_xpm, xpmmag);
214   pixmaps[PXID_DIGGER_EYE2]      = MakePixmap(digger_eye2_xpm, xpmmag);
215   pixmaps[PXID_DIGGER_DEATH]     = MakePixmap(digger_death_xpm, xpmmag);
216   pixmaps[PXID_EXIT]             = MakePixmap(exit_xpm, xpmmag);
217   pixmaps[PXID_CHANGER]          = MakePixmap(changer_xpm, xpmmag);
218 }
219 
Make16x16Pixmaps_Editor()220 void Make16x16Pixmaps_Editor()
221 {
222   CreateImage();
223   pixmaps[PXID_GHOST_DOWN_180]   = MakePixmap(ghost_down_180_xpm, xpmmag);
224   pixmaps[PXID_GHOST_UP_180]     = MakePixmap(ghost_up_180_xpm, xpmmag);
225   pixmaps[PXID_GHOST_LEFT_180]   = MakePixmap(ghost_left_180_xpm, xpmmag);
226   pixmaps[PXID_GHOST_RIGHT_180]  = MakePixmap(ghost_right_180_xpm, xpmmag);
227   pixmaps[PXID_GHOST_DOWN_L]     = MakePixmap(ghost_down_l_xpm, xpmmag);
228   pixmaps[PXID_GHOST_UP_L]       = MakePixmap(ghost_up_l_xpm, xpmmag);
229   pixmaps[PXID_GHOST_LEFT_L]     = MakePixmap(ghost_left_l_xpm, xpmmag);
230   pixmaps[PXID_GHOST_RIGHT_L]    = MakePixmap(ghost_right_l_xpm, xpmmag);
231   pixmaps[PXID_GHOST_DOWN_R]     = MakePixmap(ghost_down_r_xpm, xpmmag);
232   pixmaps[PXID_GHOST_UP_R]       = MakePixmap(ghost_up_r_xpm, xpmmag);
233   pixmaps[PXID_GHOST_LEFT_R]     = MakePixmap(ghost_left_r_xpm, xpmmag);
234   pixmaps[PXID_GHOST_RIGHT_R]    = MakePixmap(ghost_right_r_xpm, xpmmag);
235   pixmaps[PXID_GHOST_DOWN_LR]    = MakePixmap(ghost_down_lr_xpm, xpmmag);
236   pixmaps[PXID_GHOST_UP_LR]      = MakePixmap(ghost_up_lr_xpm, xpmmag);
237   pixmaps[PXID_GHOST_LEFT_LR]    = MakePixmap(ghost_left_lr_xpm, xpmmag);
238   pixmaps[PXID_GHOST_RIGHT_LR]   = MakePixmap(ghost_right_lr_xpm, xpmmag);
239   XDestroyImage(image);
240 }
241 
Make16x16Pixmaps_Icon()242 void Make16x16Pixmaps_Icon()
243 {
244   iconpixmaps[PXID_ICON_NOTHING]     = MakePixmap(nothing_xpm, iconmag);
245   iconpixmaps[PXID_ICON_DIGGER]      = MakePixmap(digger_xpm, iconmag);
246   iconpixmaps[PXID_ICON_DIGGER_FOOT] = MakePixmap(digger_foot_xpm, iconmag);
247   iconpixmaps[PXID_ICON_DIGGER_EYE1] = MakePixmap(digger_eye1_xpm, iconmag);
248   iconpixmaps[PXID_ICON_DIGGER_EYE2] = MakePixmap(digger_eye2_xpm, iconmag);
249 }
250 
MakeXPixmaps(Bool first_time)251 void MakeXPixmaps(Bool first_time)
252 {
253   /*XColor fg_color, bg_color;*/
254   int i;
255 
256   if (first_time)
257   {
258     visual = XDefaultVisual(display, screen);
259     xdefaultdepth = XDefaultDepth(display, screen);
260     colormap = DefaultColormap(display, screen);
261   }
262 
263   /* Digger-Cursor */
264 /*  xpm_cur_digger_s =
265     XCreatePixmapFromBitmapData(display, mainwindow, cur_digger_s_bits,
266 				cur_digger_s_width, cur_digger_s_height,
267 				BlackPixel(display, screen),
268 				WhitePixel(display, screen), 1);
269 
270   xpm_cur_digger_m =
271     XCreatePixmapFromBitmapData(display, mainwindow, cur_digger_m_bits,
272 				cur_digger_m_width, cur_digger_m_height,
273 				BlackPixel(display, screen),
274 				WhitePixel(display, screen), 1);
275 
276   XParseColor(display, colormap, "Black", &fg_color);
277   XParseColor(display, colormap, "#c0c0c0", &bg_color);
278   cursor_digger =
279     XCreatePixmapCursor(display, xpm_cur_digger_s, xpm_cur_digger_m,
280 			&fg_color, &bg_color, 7, 7);
281   cursor_watch =
282     XCreateFontCursor(display, XC_watch);
283 
284   XDefineCursor(display, mainwindow, cursor_digger); */
285 
286   /* Charset */
287   for (i=0; i<180; i++)
288   {
289     xbm_charset[i] =
290       XCreateMagBitmapFromData(charset_bits+i*8, 8, 8, xpmmag);
291   }
292 
293   /* pixmaps erzeugen */
294   CreateImage();
295   bzero(pixmaps, sizeof(pixmaps));
296   Make16x16Pixmaps();
297   if (first_time)
298   {
299     Make16x16Pixmaps_Icon();
300     /*main_win_icon_pixmap = MakePixmap(xdigger_xpm, 1);*/
301   }
302   XDestroyImage(image);
303 
304   if (first_time && AllocColorFailed)
305     fprintf(stderr, "%s: can't alloc some colors.\n", progname);
306 } /* MakeXPixmaps() */
307 
FreeXPixmaps()308 void FreeXPixmaps()
309 {
310   int i;
311 
312   for (i=0; i<180; i++)
313     XFreePixmap(display, xbm_charset[i]);
314   for (i=0; i<CountPixmaps; i++)
315     if (pixmaps[i] != 0) XFreePixmap(display, pixmaps[i]);
316   bzero(pixmaps, sizeof(pixmaps));
317 }
318 
CopyOnePixmap_Window(Window window,unsigned char pixmap_id,int x,int y)319 void CopyOnePixmap_Window(Window window, unsigned char pixmap_id, int x, int y)
320 {
321   XCopyArea(display, pixmaps[pixmap_id], window, gc, 0, 0,
322 	    16*xpmmag, 16*xpmmag, x*16*xpmmag, y*16*xpmmag);
323 } /* CopyOnePixmap_Window(Window window, unsigned char pixmap_id,
324      int x, int y) */
325 
DrawOnePixmap(unsigned char pixmap_id,int x,int y)326 void DrawOnePixmap(unsigned char pixmap_id, int x, int y)
327 {
328   XCopyArea(display, pixmaps[pixmap_id], mainwindow, gc, 0, 0,
329 	    16*xpmmag, 16*xpmmag, x*16*xpmmag, (y+vertvar+1)*16*xpmmag);
330 }
331 
ResizeXPixmaps(int newmag)332 void ResizeXPixmaps(int newmag)
333 {
334   if (newmag == xpmmag) return;
335 
336   /*fprintf(stderr, "Resize %d -> %d \n", xpmmag, newmag);
337   fflush(stderr);*/
338 
339   xpmmag = newmag;
340   FreeXPixmaps();
341   MakeXPixmaps(False);
342   if (toolswindow != 0)
343   {
344     Make16x16Pixmaps_Editor();
345     XResizeWindow(display, toolswindow, 4*16*xpmmag, 6*16*xpmmag);
346   }
347 }
348