ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/deliantra/Deliantra-Client/Client.xs
(Generate patch)

Comparing deliantra/Deliantra-Client/Client.xs (file contents):
Revision 1.43 by root, Mon Apr 17 06:50:26 2006 UTC vs.
Revision 1.55 by root, Thu Apr 20 08:11:56 2006 UTC

1#ifdef _WIN32
2# include <malloc.h>
3#endif
4
1#include "EXTERN.h" 5#include "EXTERN.h"
2#include "perl.h" 6#include "perl.h"
3#include "XSUB.h" 7#include "XSUB.h"
4 8
5#include <string.h> 9#include <string.h>
6#include <stdio.h> 10#include <stdio.h>
7 11
8#include <SDL.h> 12#include <SDL.h>
9#include <SDL_image.h> 13#include <SDL_image.h>
14#include <SDL_mixer.h>
10#include <SDL_opengl.h> 15#include <SDL_opengl.h>
11 16
12#include <glib/gmacros.h> 17#include <glib/gmacros.h>
13 18
14#include <pango/pango.h> 19#include <pango/pango.h>
15#include <pango/pangofc-fontmap.h> 20#include <pango/pangofc-fontmap.h>
16#include <pango/pangoft2.h> 21#include <pango/pangoft2.h>
17 22
23#ifndef _WIN32
18#include <sys/types.h> 24# include <sys/types.h>
19#include <sys/socket.h> 25# include <sys/socket.h>
20#include <netinet/in.h> 26# include <netinet/in.h>
21#include <netinet/tcp.h> 27# include <netinet/tcp.h>
22
23#include <inttypes.h> 28# include <inttypes.h>
29#else
30 typedef unsigned char uint8_t;
31 typedef unsigned short uint16_t;
32 typedef unsigned int uint32_t;
33 typedef signed char int8_t;
34 typedef signed short int16_t;
35 typedef signed int int32_t;
36#endif
24 37
25#define FOW_DARKNESS 32 38#define FOW_DARKNESS 32
26 39
27#define MAP_EXTEND_X 32 40#define MAP_EXTEND_X 32
28#define MAP_EXTEND_Y 512 41#define MAP_EXTEND_Y 512
42
43typedef Mix_Chunk *CFClient__MixChunk;
44typedef Mix_Music *CFClient__MixMusic;
29 45
30static PangoContext *context; 46static PangoContext *context;
31static PangoFontMap *fontmap; 47static PangoFontMap *fontmap;
32 48
33typedef struct cf_layout { 49typedef struct cf_layout {
47{ 63{
48 /* use a random scale factor to account for unknown descenders, 0.8 works 64 /* use a random scale factor to account for unknown descenders, 0.8 works
49 * reasonably well with bitstream vera 65 * reasonably well with bitstream vera
50 */ 66 */
51 PangoFontDescription *font = pango_context_get_font_description (context); 67 PangoFontDescription *font = pango_context_get_font_description (context);
52 pango_font_description_set_absolute_size (font, self->base_height * (PANGO_SCALE * 8 / 10)); 68
69 int height = self->base_height * (PANGO_SCALE * 8 / 10);
70
71 if (pango_font_description_get_size (font) != height)
72 {
73 pango_font_description_set_absolute_size (font, height);
74 pango_layout_context_changed (self->pl);
75 }
53} 76}
54 77
55static void 78static void
56layout_get_pixel_size (CFClient__Layout self, int *w, int *h) 79layout_get_pixel_size (CFClient__Layout self, int *w, int *h)
57{ 80{
83 mapcell *col; 106 mapcell *col;
84} maprow; 107} maprow;
85 108
86typedef struct map { 109typedef struct map {
87 int x, y, w, h; 110 int x, y, w, h;
88 int dx, dy; /* delayed map scrolling */
89 int ox, oy; /* offset to virtual global coordinate system */ 111 int ox, oy; /* offset to virtual global coordinate system */
90 int faces; 112 int faces;
91 mapface *face; 113 mapface *face;
92 114
93 int texs; 115 int texs;
94 maptex *tex; 116 maptex *tex;
95 117
96 uint32_t rows; 118 int32_t rows;
97 maprow *row; 119 maprow *row;
98} *CFClient__Map; 120} *CFClient__Map;
99 121
100static char * 122static char *
101prepend (char *ptr, int sze, int inc) 123prepend (char *ptr, int sze, int inc)
196 218
197static void 219static void
198map_blank (CFClient__Map self, int x0, int y0, int w, int h) 220map_blank (CFClient__Map self, int x0, int y0, int w, int h)
199{ 221{
200 int x, y; 222 int x, y;
223 maprow *row;
201 224
202 for (y = y0; y < y0 + h; y++) 225 for (y = y0; y < y0 + h; y++)
203 if (y >= 0) 226 if (y >= 0)
204 { 227 {
205 if (y >= self->rows) 228 if (y >= self->rows)
206 break; 229 break;
207 230
208 maprow *row = self->row + y; 231 row = self->row + y;
209 232
210 for (x = x0; x < x0 + w; x++) 233 for (x = x0; x < x0 + w; x++)
211 if (x >= row->c0) 234 if (x >= row->c0)
212 { 235 {
213 if (x >= row->c1) 236 if (x >= row->c1)
222 245
223PROTOTYPES: ENABLE 246PROTOTYPES: ENABLE
224 247
225BOOT: 248BOOT:
226{ 249{
250 HV *stash = gv_stashpv ("CFClient", 1);
251 static const struct {
252 const char *name;
253 IV iv;
254 } *civ, const_iv[] = {
255# define const_iv(name) { # name, (IV)name }
256 const_iv (SDL_ACTIVEEVENT),
257 const_iv (SDL_KEYDOWN),
258 const_iv (SDL_KEYUP),
259 const_iv (SDL_MOUSEMOTION),
260 const_iv (SDL_MOUSEBUTTONDOWN),
261 const_iv (SDL_MOUSEBUTTONUP),
262 const_iv (SDL_JOYAXISMOTION),
263 const_iv (SDL_JOYBALLMOTION),
264 const_iv (SDL_JOYHATMOTION),
265 const_iv (SDL_JOYBUTTONDOWN),
266 const_iv (SDL_JOYBUTTONUP),
267 const_iv (SDL_QUIT),
268 const_iv (SDL_SYSWMEVENT),
269 const_iv (SDL_EVENT_RESERVEDA),
270 const_iv (SDL_EVENT_RESERVEDB),
271 const_iv (SDL_VIDEORESIZE),
272 const_iv (SDL_VIDEOEXPOSE),
273 const_iv (SDL_USEREVENT),
274 const_iv (SDLK_KP0),
275 const_iv (SDLK_KP1),
276 const_iv (SDLK_KP2),
277 const_iv (SDLK_KP3),
278 const_iv (SDLK_KP4),
279 const_iv (SDLK_KP5),
280 const_iv (SDLK_KP6),
281 const_iv (SDLK_KP7),
282 const_iv (SDLK_KP8),
283 const_iv (SDLK_KP9),
284 const_iv (SDLK_KP_PERIOD),
285 const_iv (SDLK_KP_DIVIDE),
286 const_iv (SDLK_KP_MULTIPLY),
287 const_iv (SDLK_KP_MINUS),
288 const_iv (SDLK_KP_PLUS),
289 const_iv (SDLK_KP_ENTER),
290 const_iv (SDLK_KP_EQUALS),
291 const_iv (SDLK_UP),
292 const_iv (SDLK_DOWN),
293 const_iv (SDLK_RIGHT),
294 const_iv (SDLK_LEFT),
295 const_iv (SDLK_INSERT),
296 const_iv (SDLK_HOME),
297 const_iv (SDLK_END),
298 const_iv (SDLK_PAGEUP),
299 const_iv (SDLK_PAGEDOWN),
300 const_iv (SDLK_F1),
301 const_iv (SDLK_F2),
302 const_iv (SDLK_F3),
303 const_iv (SDLK_F4),
304 const_iv (SDLK_F5),
305 const_iv (SDLK_F6),
306 const_iv (SDLK_F7),
307 const_iv (SDLK_F8),
308 const_iv (SDLK_F9),
309 const_iv (SDLK_F10),
310 const_iv (SDLK_F11),
311 const_iv (SDLK_F12),
312 const_iv (SDLK_F13),
313 const_iv (SDLK_F14),
314 const_iv (SDLK_F15),
315 const_iv (SDLK_NUMLOCK),
316 const_iv (SDLK_CAPSLOCK),
317 const_iv (SDLK_SCROLLOCK),
318 const_iv (SDLK_RSHIFT),
319 const_iv (SDLK_LSHIFT),
320 const_iv (SDLK_RCTRL),
321 const_iv (SDLK_LCTRL),
322 const_iv (SDLK_RALT),
323 const_iv (SDLK_LALT),
324 const_iv (SDLK_RMETA),
325 const_iv (SDLK_LMETA),
326 const_iv (SDLK_LSUPER),
327 const_iv (SDLK_RSUPER),
328 const_iv (SDLK_MODE),
329 const_iv (SDLK_COMPOSE),
330 const_iv (SDLK_HELP),
331 const_iv (SDLK_PRINT),
332 const_iv (SDLK_SYSREQ),
333 const_iv (SDLK_BREAK),
334 const_iv (SDLK_MENU),
335 const_iv (SDLK_POWER),
336 const_iv (SDLK_EURO),
337 const_iv (SDLK_UNDO),
338 const_iv (KMOD_NONE),
339 const_iv (KMOD_LSHIFT),
340 const_iv (KMOD_RSHIFT),
341 const_iv (KMOD_LCTRL),
342 const_iv (KMOD_RCTRL),
343 const_iv (KMOD_LALT),
344 const_iv (KMOD_RALT),
345 const_iv (KMOD_LMETA),
346 const_iv (KMOD_RMETA),
347 const_iv (KMOD_NUM),
348 const_iv (KMOD_CAPS),
349 const_iv (KMOD_MODE),
350 const_iv (KMOD_CTRL),
351 const_iv (KMOD_SHIFT),
352 const_iv (KMOD_ALT),
353 const_iv (KMOD_META)
354# undef const_iv
355 };
356
357 for (civ = const_iv + sizeof (const_iv) / sizeof (const_iv [0]); civ-- > const_iv; )
358 newCONSTSUB (stash, (char *)civ->name, newSViv (civ->iv));
359
227 fontmap = pango_ft2_font_map_new (); 360 fontmap = pango_ft2_font_map_new ();
228 pango_ft2_font_map_set_default_substitute ((PangoFT2FontMap *)fontmap, substitute_func, 0, 0); 361 pango_ft2_font_map_set_default_substitute ((PangoFT2FontMap *)fontmap, substitute_func, 0, 0);
229 context = pango_ft2_font_map_create_context ((PangoFT2FontMap *)fontmap); 362 context = pango_ft2_font_map_create_context ((PangoFT2FontMap *)fontmap);
230} 363}
364
365int
366SDL_Init (U32 flags = SDL_INIT_VIDEO | SDL_INIT_AUDIO)
367
368void
369SDL_Quit ()
370
371void
372SDL_ListModes ()
373 PPCODE:
374{
375 SDL_Rect **m;
376
377 SDL_GL_SetAttribute (SDL_GL_RED_SIZE, 5);
378 SDL_GL_SetAttribute (SDL_GL_GREEN_SIZE, 5);
379 SDL_GL_SetAttribute (SDL_GL_BLUE_SIZE, 5);
380 SDL_GL_SetAttribute (SDL_GL_ALPHA_SIZE, 1);
381
382 SDL_GL_SetAttribute (SDL_GL_ACCUM_RED_SIZE, 0);
383 SDL_GL_SetAttribute (SDL_GL_ACCUM_GREEN_SIZE, 0);
384 SDL_GL_SetAttribute (SDL_GL_ACCUM_BLUE_SIZE, 0);
385 SDL_GL_SetAttribute (SDL_GL_ACCUM_ALPHA_SIZE, 0);
386
387 SDL_GL_SetAttribute (SDL_GL_DOUBLEBUFFER, 1);
388 SDL_GL_SetAttribute (SDL_GL_BUFFER_SIZE, 15);
389 SDL_GL_SetAttribute (SDL_GL_DEPTH_SIZE, 0);
390
391 SDL_EnableUNICODE (1);
392 SDL_EnableKeyRepeat (SDL_DEFAULT_REPEAT_DELAY, SDL_DEFAULT_REPEAT_INTERVAL);
393
394 m = SDL_ListModes (0, SDL_FULLSCREEN | SDL_OPENGL);
395
396 if (m && m != (SDL_Rect **)-1)
397 while (*m)
398 {
399 AV *av = newAV ();
400 av_push (av, newSViv ((*m)->w));
401 av_push (av, newSViv ((*m)->h));
402 XPUSHs (sv_2mortal (newRV_noinc ((SV *)av)));
403
404 ++m;
405 }
406}
407
408int
409SDL_SetVideoMode (int w, int h, int fullscreen)
410 CODE:
411 RETVAL = !!SDL_SetVideoMode (
412 w, h, 0, SDL_OPENGL | (fullscreen ? SDL_FULLSCREEN : 0)
413 );
414 SDL_WM_SetCaption ("Crossfire+ Client " VERSION, "Crossfire+");
415 OUTPUT:
416 RETVAL
417
418void
419SDL_GL_SwapBuffers ()
420
421void
422SDL_PollEvent ()
423 PPCODE:
424{
425 SDL_Event ev;
426
427 while (SDL_PollEvent (&ev))
428 {
429 HV *hv = newHV ();
430 hv_store (hv, "type", 4, newSViv (ev.type), 0);
431 switch (ev.type)
432 {
433 case SDL_KEYDOWN:
434 case SDL_KEYUP:
435 hv_store (hv, "state", 5, newSViv (ev.key.state), 0);
436 hv_store (hv, "sym", 3, newSViv (ev.key.keysym.sym), 0);
437 hv_store (hv, "mod", 3, newSViv (ev.key.keysym.mod), 0);
438 hv_store (hv, "unicode", 7, newSViv (ev.key.keysym.unicode), 0);
439 break;
440
441 case SDL_ACTIVEEVENT:
442 hv_store (hv, "gain", 4, newSViv (ev.active.gain), 0);
443 hv_store (hv, "state", 5, newSViv (ev.active.state), 0);
444 break;
445
446 case SDL_MOUSEMOTION:
447 hv_store (hv, "state", 5, newSViv (ev.motion.state), 0);
448 hv_store (hv, "x", 1, newSViv (ev.motion.x), 0);
449 hv_store (hv, "y", 1, newSViv (ev.motion.y), 0);
450 hv_store (hv, "xrel", 4, newSViv (ev.motion.xrel), 0);
451 hv_store (hv, "yrel", 4, newSViv (ev.motion.yrel), 0);
452 break;
453
454 case SDL_MOUSEBUTTONDOWN:
455 case SDL_MOUSEBUTTONUP:
456 hv_store (hv, "button", 6, newSViv (ev.button.button), 0);
457 hv_store (hv, "state", 5, newSViv (ev.button.state), 0);
458 hv_store (hv, "x", 1, newSViv (ev.button.x), 0);
459 hv_store (hv, "y", 1, newSViv (ev.button.y), 0);
460 }
461
462 XPUSHs (sv_2mortal (newRV_noinc ((SV *)hv)));
463 }
464}
465
466int
467Mix_OpenAudio (int frequency = 22050, int format = MIX_DEFAULT_FORMAT, int channels = 1, int chunksize = 512)
468
469void
470Mix_CloseAudio ()
471
472int
473Mix_AllocateChannels (int numchans = -1)
231 474
232void 475void
233lowdelay (int fd, int val = 1) 476lowdelay (int fd, int val = 1)
234 CODE: 477 CODE:
478#ifndef _WIN32
235 setsockopt (fd, IPPROTO_TCP, TCP_NODELAY, &val, sizeof (val)); 479 setsockopt (fd, IPPROTO_TCP, TCP_NODELAY, &val, sizeof (val));
480#endif
236 481
237char * 482char *
238gl_version () 483gl_version ()
239 CODE: 484 CODE:
240 RETVAL = (char *)glGetString (GL_VERSION); 485 RETVAL = (char *)glGetString (GL_VERSION);
286 croak ("load_image: %s", SDL_GetError ()); 531 croak ("load_image: %s", SDL_GetError ());
287 532
288 fmt.palette = NULL; 533 fmt.palette = NULL;
289 fmt.BitsPerPixel = 32; 534 fmt.BitsPerPixel = 32;
290 fmt.BytesPerPixel = 4; 535 fmt.BytesPerPixel = 4;
536#if SDL_BYTEORDER == SDL_LIL_ENDIAN
291 fmt.Rmask = 0x000000ff; 537 fmt.Rmask = 0x000000ff;
292 fmt.Gmask = 0x0000ff00; 538 fmt.Gmask = 0x0000ff00;
293 fmt.Bmask = 0x00ff0000; 539 fmt.Bmask = 0x00ff0000;
294 fmt.Amask = 0xff000000; 540 fmt.Amask = 0xff000000;
541#else
542 fmt.Rmask = 0xff000000;
543 fmt.Gmask = 0x00ff0000;
544 fmt.Bmask = 0x0000ff00;
545 fmt.Amask = 0x000000ff;
546#endif
295 fmt.Rloss = 0; 547 fmt.Rloss = 0;
296 fmt.Gloss = 0; 548 fmt.Gloss = 0;
297 fmt.Bloss = 0; 549 fmt.Bloss = 0;
298 fmt.Aloss = 0; 550 fmt.Aloss = 0;
299 fmt.Rshift = 0; 551 fmt.Rshift = 0;
313 SDL_LockSurface (surface2); 565 SDL_LockSurface (surface2);
314 PUSHs (sv_2mortal (newSVpvn (surface2->pixels, surface2->h * surface2->pitch))); 566 PUSHs (sv_2mortal (newSVpvn (surface2->pixels, surface2->h * surface2->pitch)));
315 SDL_UnlockSurface (surface2); 567 SDL_UnlockSurface (surface2);
316 PUSHs (sv_2mortal (newSViv (surface->flags & (SDL_SRCCOLORKEY | SDL_SRCALPHA) ? GL_RGBA : GL_RGB))); 568 PUSHs (sv_2mortal (newSViv (surface->flags & (SDL_SRCCOLORKEY | SDL_SRCALPHA) ? GL_RGBA : GL_RGB)));
317 PUSHs (sv_2mortal (newSViv (GL_RGBA))); 569 PUSHs (sv_2mortal (newSViv (GL_RGBA)));
318 PUSHs (sv_2mortal (newSViv (GL_UNSIGNED_INT_8_8_8_8_REV))); 570 PUSHs (sv_2mortal (newSViv (GL_UNSIGNED_BYTE)));
319 571
320 SDL_FreeSurface (surface); 572 SDL_FreeSurface (surface);
321 SDL_FreeSurface (surface2); 573 SDL_FreeSurface (surface2);
322} 574}
323 575
347} 599}
348 600
349void 601void
350fatal (char *message) 602fatal (char *message)
351 CODE: 603 CODE:
352#ifdef WIN32 604#ifdef _WIN32
353 MessageBox (0, message, "Crossfire+ Fatal Error", MB_OK | MB_ICONERROR | MB_SETFOREGROUND); 605 MessageBox (0, message, "Crossfire+ Fatal Error", MB_OK | MB_ICONERROR | MB_SETFOREGROUND);
354#else 606#else
355 fprintf (stderr, "FATAL: %s\n", message); 607 fprintf (stderr, "FATAL: %s\n", message);
356#endif 608#endif
357 exit (1); 609 exit (1);
391 STRLEN textlen; 643 STRLEN textlen;
392 char *text = SvPVutf8 (text_, textlen); 644 char *text = SvPVutf8 (text_, textlen);
393 645
394 pango_layout_set_markup (self->pl, text, textlen); 646 pango_layout_set_markup (self->pl, text, textlen);
395} 647}
648
649SV *
650get_text (CFClient::Layout self)
651 CODE:
652 RETVAL = newSVpv (pango_layout_get_text (self->pl), 0);
653 SvUTF8_on (RETVAL);
654 OUTPUT:
655 RETVAL
396 656
397void 657void
398set_height (CFClient::Layout self, int base_height) 658set_height (CFClient::Layout self, int base_height)
399 CODE: 659 CODE:
400 self->base_height = base_height; 660 self->base_height = base_height;
566 { 826 {
567 Append (maptex, self->tex, self->texs, self->texs); 827 Append (maptex, self->tex, self->texs, self->texs);
568 self->texs *= 2; 828 self->texs *= 2;
569 } 829 }
570 830
831 {
571 maptex *tex = self->tex + texid; 832 maptex *tex = self->tex + texid;
572 833
573 tex->name = name; 834 tex->name = name;
574 tex->w = w; 835 tex->w = w;
575 tex->h = h; 836 tex->h = h;
576 tex->s = s; 837 tex->s = s;
577 tex->t = t; 838 tex->t = t;
578 tex->r = r; 839 tex->r = r;
579 tex->g = g; 840 tex->g = g;
580 tex->b = b; 841 tex->b = b;
581 tex->a = a; 842 tex->a = a;
843 }
582} 844}
583 845
584int 846int
585ox (CFClient::Map self) 847ox (CFClient::Map self)
586 ALIAS: 848 ALIAS:
596 858
597void 859void
598scroll (CFClient::Map self, int dx, int dy) 860scroll (CFClient::Map self, int dx, int dy)
599 CODE: 861 CODE:
600{ 862{
601 self->dx += dx; self->ox += dx;
602 self->dy += dy; self->oy += dy;
603}
604
605void
606map1a_update (CFClient::Map self, SV *data_)
607 CODE:
608{
609 if (self->dx > 0) 863 if (dx > 0)
610 map_blank (self, self->x, self->y, self->dx - 1, self->h); 864 map_blank (self, self->x, self->y, dx - 1, self->h);
611 else if (self->dx < 0) 865 else if (dx < 0)
612 map_blank (self, self->x + self->w + self->dx + 1, self->y, 1 - self->dx, self->h); 866 map_blank (self, self->x + self->w + dx + 1, self->y, 1 - dx, self->h);
613 867
614 if (self->dy > 0) 868 if (dy > 0)
615 map_blank (self, self->x, self->y, self->w, self->dy - 1); 869 map_blank (self, self->x, self->y, self->w, dy - 1);
616 else if (self->dy < 0) 870 else if (dy < 0)
617 map_blank (self, self->x, self->y + self->h + self->dy + 1, self->w, 1 - self->dy); 871 map_blank (self, self->x, self->y + self->h + dy + 1, self->w, 1 - dy);
618 872
619 self->x += self->dx; self->dx = 0; 873 self->ox += dx; self->x += dx;
620 self->y += self->dy; self->dy = 0; 874 self->oy += dy; self->y += dy;
621 875
622 while (self->y < 0) 876 while (self->y < 0)
623 { 877 {
624 Prepend (maprow, self->row, self->rows, MAP_EXTEND_Y); 878 Prepend (maprow, self->row, self->rows, MAP_EXTEND_Y);
625 879
626 self->rows += MAP_EXTEND_Y; 880 self->rows += MAP_EXTEND_Y;
627 self->y += MAP_EXTEND_Y; 881 self->y += MAP_EXTEND_Y;
628 } 882 }
883}
629 884
885void
886map1a_update (CFClient::Map self, SV *data_)
887 CODE:
888{
630 uint8_t *data = (uint8_t *)SvPVbyte_nolen (data_); 889 uint8_t *data = (uint8_t *)SvPVbyte_nolen (data_);
631 uint8_t *data_end = (uint8_t *)SvEND (data_); 890 uint8_t *data_end = (uint8_t *)SvEND (data_);
891 mapcell *cell;
892 int x, y, flags;
632 893
633 while (data < data_end) 894 while (data < data_end)
634 { 895 {
635 int flags = (data [0] << 8) + data [1]; data += 2; 896 flags = (data [0] << 8) + data [1]; data += 2;
636 897
637 int x = ((flags >> 10) & 63) + self->x; 898 x = ((flags >> 10) & 63) + self->x;
638 int y = ((flags >> 4) & 63) + self->y; 899 y = ((flags >> 4) & 63) + self->y;
639 900
640 mapcell *cell = map_get_cell (self, x, y); 901 cell = map_get_cell (self, x, y);
641 902
642 if (flags & 15) 903 if (flags & 15)
643 { 904 {
644 if (cell->darkness < 0) // && x < self->w && y < self->h) 905 if (cell->darkness < 0)
645 { 906 {
646 cell->darkness = 0; 907 cell->darkness = 0;
647 cell->face [0] = 0; 908 cell->face [0] = 0;
648 cell->face [1] = 0; 909 cell->face [1] = 0;
649 cell->face [2] = 0; 910 cell->face [2] = 0;
650 } 911 }
651 912
652 cell->darkness = flags & 8 ? *data++ : 255; 913 cell->darkness = flags & 8 ? *data++ : 255;
653 914
654 //TODO: don't trust server data to be in-range(!) 915 //TODO: don't trust server data to be in-range(!)
655 916
656 if (flags & 4) 917 if (flags & 4)
672 cell->darkness = -1; 933 cell->darkness = -1;
673 } 934 }
674} 935}
675 936
676SV * 937SV *
677mapmap (CFClient::Map self, int w, int h) 938mapmap (CFClient::Map self, int x0, int y0, int w, int h)
678 CODE: 939 CODE:
679{ 940{
680 int x0, x1, x; 941 int x1, x;
681 int y0, y1, y; 942 int y1, y;
682 int z; 943 int z;
683 SV *map_sv = newSV (w * h * sizeof (uint32_t)); 944 SV *map_sv = newSV (w * h * sizeof (uint32_t));
684 uint32_t *map = (uint32_t *)SvPVX (map_sv); 945 uint32_t *map = (uint32_t *)SvPVX (map_sv);
685 946
686 SvPOK_only (map_sv); 947 SvPOK_only (map_sv);
687 SvCUR_set (map_sv, w * h * sizeof (uint32_t)); 948 SvCUR_set (map_sv, w * h * sizeof (uint32_t));
688 949
689 x0 = self->x - w / 2; x1 = x0 + w; 950 x0 += self->x; x1 = x0 + w;
690 y0 = self->y - h / 2; y1 = y0 + h; 951 y0 += self->y; y1 = y0 + h;
691 952
692 for (y = y0; y < y1; y++) 953 for (y = y0; y < y1; y++)
693 { 954 {
694 maprow *row = 0 <= y && y < self->rows 955 maprow *row = 0 <= y && y < self->rows
695 ? self->row + y 956 ? self->row + y
735 996
736void 997void
737draw (CFClient::Map self, int shift_x, int shift_y, int x0, int y0, int sw, int sh) 998draw (CFClient::Map self, int shift_x, int shift_y, int x0, int y0, int sw, int sh)
738 PPCODE: 999 PPCODE:
739{ 1000{
1001 int vx, vy;
1002 int x, y, z;
1003 int last_name;
1004 mapface face;
740 int sw4 = (sw + 3) & ~3; 1005 int sw4 = (sw + 3) & ~3;
741 SV *darkness_sv = sv_2mortal (newSV (sw4 * sh)); 1006 SV *darkness_sv = sv_2mortal (newSV (sw4 * sh));
742 uint8_t *darkness = (uint8_t *)SvPVX (darkness_sv); 1007 uint8_t *darkness = (uint8_t *)SvPVX (darkness_sv);
1008
743 memset (darkness, 255, sw4 * sh); 1009 memset (darkness, 255, sw4 * sh);
744 SvPOK_only (darkness_sv); 1010 SvPOK_only (darkness_sv);
745 SvCUR_set (darkness_sv, sw4 * sh); 1011 SvCUR_set (darkness_sv, sw4 * sh);
746 1012
747 int vx = self->x + (self->w - sw) / 2 - shift_x; 1013 vx = self->x + (self->w - sw) / 2 - shift_x;
748 int vy = self->y + (self->h - sh) / 2 - shift_y; 1014 vy = self->y + (self->h - sh) / 2 - shift_y;
749 1015
750 /* 1016 /*
751 int vx = self->vx = self->w >= sw 1017 int vx = self->vx = self->w >= sw
752 ? self->x + (self->w - sw) / 2 1018 ? self->x + (self->w - sw) / 2
753 : MIN (self->x, MAX (self->x + self->w - sw + 1, self->vx)); 1019 : MIN (self->x, MAX (self->x + self->w - sw + 1, self->vx));
762 glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); 1028 glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
763 glEnable (GL_BLEND); 1029 glEnable (GL_BLEND);
764 glEnable (GL_TEXTURE_2D); 1030 glEnable (GL_TEXTURE_2D);
765 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); 1031 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
766 1032
767 int x, y, z;
768
769 int last_name = 0;
770
771 glBegin (GL_QUADS); 1033 glBegin (GL_QUADS);
1034
1035 last_name = 0;
772 1036
773 for (z = 0; z < 3; z++) 1037 for (z = 0; z < 3; z++)
774 for (y = 0; y < sh; y++) 1038 for (y = 0; y < sh; y++)
775 if (0 <= y + vy && y + vy < self->rows) 1039 if (0 <= y + vy && y + vy < self->rows)
776 { 1040 {
783 1047
784 darkness[y * sw4 + x] = cell->darkness < 0 1048 darkness[y * sw4 + x] = cell->darkness < 0
785 ? 255 - FOW_DARKNESS 1049 ? 255 - FOW_DARKNESS
786 : 255 - cell->darkness; 1050 : 255 - cell->darkness;
787 1051
788 mapface face = cell->face [z]; 1052 face = cell->face [z];
789 1053
790 if (face) 1054 if (face)
791 { 1055 {
792 maptex tex = self->tex [face]; 1056 maptex tex = self->tex [face];
793 1057
832 *data++ = 0; /* version 0 format */ 1096 *data++ = 0; /* version 0 format */
833 *data++ = w >> 8; *data++ = w; 1097 *data++ = w >> 8; *data++ = w;
834 *data++ = h >> 8; *data++ = h; 1098 *data++ = h >> 8; *data++ = h;
835 1099
836 // we need to do this 'cause we don't keep an absolute coord system for rows 1100 // we need to do this 'cause we don't keep an absolute coord system for rows
837 // TODO: treat rows as we treat 1101 // TODO: treat rows as we treat columns
838 map_get_row (self, y0 + self->y - self->oy);//D 1102 map_get_row (self, y0 + self->y - self->oy);//D
839 map_get_row (self, y0 + self->y - self->oy + h - 1);//D 1103 map_get_row (self, y0 + self->y - self->oy + h - 1);//D
840 1104
841 x0 += self->x - self->ox; 1105 x0 += self->x - self->ox;
842 y0 += self->y - self->oy; 1106 y0 += self->y - self->oy;
853 for (x = x0; x < x1; x++) 1117 for (x = x0; x < x1; x++)
854 { 1118 {
855 if (row && row->c0 <= x && x < row->c1) 1119 if (row && row->c0 <= x && x < row->c1)
856 { 1120 {
857 mapcell *cell = row->col + (x - row->c0); 1121 mapcell *cell = row->col + (x - row->c0);
858
859 uint8_t flags = 0; 1122 uint8_t flags = 0;
860 1123
861 if (cell->face [0]) flags |= 1; 1124 if (cell->face [0]) flags |= 1;
862 if (cell->face [1]) flags |= 2; 1125 if (cell->face [1]) flags |= 2;
863 if (cell->face [2]) flags |= 4; 1126 if (cell->face [2]) flags |= 4;
897void 1160void
898set_rect (CFClient::Map self, int x0, int y0, uint8_t *data) 1161set_rect (CFClient::Map self, int x0, int y0, uint8_t *data)
899 PPCODE: 1162 PPCODE:
900{ 1163{
901 int x, y, z; 1164 int x, y, z;
1165 int w, h;
902 int x1, y1; 1166 int x1, y1;
903 1167
904 if (*data++ != 0) 1168 if (*data++ != 0)
905 return; /* version mismatch */ 1169 return; /* version mismatch */
906 1170
907 int w = *data++ << 8; w |= *data++; 1171 w = *data++ << 8; w |= *data++;
908 int h = *data++ << 8; h |= *data++; 1172 h = *data++ << 8; h |= *data++;
909 1173
910 // we need to do this 'cause we don't keep an absolute coord system for rows 1174 // we need to do this 'cause we don't keep an absolute coord system for rows
911 // TODO: treat rows as we treat 1175 // TODO: treat rows as we treat columns
912 map_get_row (self, y0 + self->y - self->oy);//D 1176 map_get_row (self, y0 + self->y - self->oy);//D
913 map_get_row (self, y0 + self->y - self->oy + h - 1);//D 1177 map_get_row (self, y0 + self->y - self->oy + h - 1);//D
914 1178
915 x0 += self->x - self->ox; 1179 x0 += self->x - self->ox;
916 y0 += self->y - self->oy; 1180 y0 += self->y - self->oy;
951 } 1215 }
952 } 1216 }
953 } 1217 }
954} 1218}
955 1219
1220MODULE = CFClient PACKAGE = CFClient::MixChunk
1221
1222CFClient::MixChunk
1223new_from_file (SV *class, char *path)
1224 CODE:
1225 RETVAL = Mix_LoadWAV (path);
1226 OUTPUT:
1227 RETVAL
1228
1229void
1230DESTROY (CFClient::MixChunk self)
1231 CODE:
1232 Mix_FreeChunk (self);
1233
1234int
1235volume (CFClient::MixChunk self, int volume = -1)
1236 CODE:
1237 RETVAL = Mix_VolumeChunk (self, volume);
1238 OUTPUT:
1239 RETVAL
1240
1241int
1242play (CFClient::MixChunk self, int channel = -1, int loops = 0, int ticks = -1)
1243 CODE:
1244 RETVAL = Mix_PlayChannelTimed (channel, self, loops, ticks);
1245 OUTPUT:
1246 RETVAL
1247
1248MODULE = CFClient PACKAGE = CFClient::MixMusic
1249
1250int
1251volume (int volume = -1)
1252 CODE:
1253 RETVAL = Mix_VolumeMusic (volume);
1254 OUTPUT:
1255 RETVAL
1256
1257CFClient::MixMusic
1258new_from_file (SV *class, char *path)
1259 CODE:
1260 RETVAL = Mix_LoadMUS (path);
1261 OUTPUT:
1262 RETVAL
1263
1264void
1265DESTROY (CFClient::MixMusic self)
1266 CODE:
1267 Mix_FreeMusic (self);
1268
1269int
1270play (CFClient::MixMusic self, int loops = -1)
1271 CODE:
1272 RETVAL = Mix_PlayMusic (self, loops);
1273 OUTPUT:
1274 RETVAL
1275
1276MODULE = CFClient PACKAGE = CFClient::OpenGL
1277
1278BOOT:
1279{
1280 HV *stash = gv_stashpv ("CFClient::OpenGL", 1);
1281 static const struct {
1282 const char *name;
1283 IV iv;
1284 } *civ, const_iv[] = {
1285# define const_iv(name) { # name, (IV)name }
1286 const_iv (GL_COLOR_MATERIAL),
1287 const_iv (GL_SMOOTH),
1288 const_iv (GL_FLAT),
1289 const_iv (GL_BLEND),
1290 const_iv (GL_AND),
1291 const_iv (GL_SRC_ALPHA),
1292 const_iv (GL_ONE_MINUS_SRC_ALPHA),
1293 const_iv (GL_RGB),
1294 const_iv (GL_RGBA),
1295 const_iv (GL_UNSIGNED_BYTE),
1296 const_iv (GL_ALPHA4),
1297 const_iv (GL_ALPHA),
1298 const_iv (GL_FLOAT),
1299 const_iv (GL_UNSIGNED_INT_8_8_8_8_REV),
1300 const_iv (GL_COMPILE),
1301 const_iv (GL_TEXTURE_1D),
1302 const_iv (GL_TEXTURE_2D),
1303 const_iv (GL_TEXTURE_ENV),
1304 const_iv (GL_TEXTURE_MAG_FILTER),
1305 const_iv (GL_TEXTURE_MIN_FILTER),
1306 const_iv (GL_TEXTURE_ENV_MODE),
1307 const_iv (GL_TEXTURE_WRAP_S),
1308 const_iv (GL_TEXTURE_WRAP_T),
1309 const_iv (GL_CLAMP),
1310 const_iv (GL_REPEAT),
1311 const_iv (GL_NEAREST),
1312 const_iv (GL_LINEAR),
1313 const_iv (GL_MODULATE),
1314 const_iv (GL_REPLACE),
1315 const_iv (GL_COLOR_BUFFER_BIT),
1316 const_iv (GL_PROJECTION),
1317 const_iv (GL_MODELVIEW),
1318 const_iv (GL_COLOR_LOGIC_OP),
1319 const_iv (GL_CONVOLUTION_2D),
1320 const_iv (GL_CONVOLUTION_BORDER_MODE),
1321 const_iv (GL_CONSTANT_BORDER),
1322 const_iv (GL_LINES),
1323 const_iv (GL_QUADS),
1324 const_iv (GL_LINE_LOOP),
1325 const_iv (GL_PERSPECTIVE_CORRECTION_HINT),
1326 const_iv (GL_FASTEST),
1327# undef const_iv
1328 };
1329
1330 for (civ = const_iv + sizeof (const_iv) / sizeof (const_iv [0]); civ-- > const_iv; )
1331 newCONSTSUB (stash, (char *)civ->name, newSViv (civ->iv));
1332}
1333
1334int glGetError ()
1335
1336void glClear (int mask)
1337
1338void glClearColor (float r, float g, float b, float a = 1.0)
1339 PROTOTYPE: @
1340
1341void glEnable (int cap)
1342
1343void glDisable (int cap)
1344
1345void glShadeModel (int mode)
1346
1347void glHint (int target, int mode)
1348
1349void glBlendFunc (int sfactor, int dfactor)
1350
1351void glLogicOp (int opcode)
1352
1353void glMatrixMode (int mode)
1354
1355void glPushMatrix ()
1356
1357void glPopMatrix ()
1358
1359void glLoadIdentity ()
1360
1361void glOrtho (double left, double right, double bottom, double top, double near, double far)
1362
1363void glViewport (int x, int y, int width, int height)
1364
1365void glTranslate (float x, float y, float z = 0.)
1366 CODE:
1367 glTranslatef (x, y, z);
1368
1369void glScale (float x, float y, float z)
1370 CODE:
1371 glScalef (x, y, z);
1372
1373void glRotate (float angle, float x, float y, float z)
1374 CODE:
1375 glRotatef (angle, x, y, z);
1376
1377void glBegin (int mode)
1378
1379void glEnd ()
1380
1381void glColor (float r, float g, float b, float a = 1.0)
1382 PROTOTYPE: @
1383 CODE:
1384 glColor4f (r, g, b, a);
1385
1386void glVertex (float x, float y, float z = 0.)
1387 CODE:
1388 glVertex3f (x, y, z);
1389
1390void glTexCoord (float s, float t)
1391 CODE:
1392 glTexCoord2f (s, t);
1393
1394void glTexEnv (int target, int pname, float param)
1395 CODE:
1396 glTexEnvf (target, pname, param);
1397
1398void glTexParameter (int target, int pname, float param)
1399 CODE:
1400 glTexParameterf (target, pname, param);
1401
1402void glBindTexture (int target, int name)
1403
1404void glConvolutionParameter (int target, int pname, float params)
1405 CODE:
1406 glConvolutionParameterf (target, pname, params);
1407
1408void glConvolutionFilter2D (int target, int internalformat, int width, int height, int format, int type, char *data)
1409
1410void glTexImage2D (int target, int level, int internalformat, int width, int height, int border, int format, int type, char *data)
1411
1412void glCopyTexImage2D (int target, int level, int internalformat, int x, int y, int width, int height, int border)
1413
1414int glGenTexture ()
1415 CODE:
1416{
1417 GLuint name;
1418 glGenTextures (1, &name);
1419 RETVAL = name;
1420}
1421 OUTPUT:
1422 RETVAL
1423
1424void glDeleteTexture (int name)
1425 CODE:
1426{
1427 GLuint name_ = name;
1428 glDeleteTextures (1, &name_);
1429}
1430
1431int glGenList ()
1432 CODE:
1433 RETVAL = glGenLists (1);
1434 OUTPUT:
1435 RETVAL
1436
1437void glDeleteList (int list)
1438 CODE:
1439 glDeleteLists (list, 1);
1440
1441void glNewList (int list, int mode = GL_COMPILE)
1442
1443void glEndList ()
1444
1445void glCallList (int list)
1446

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines