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.295 by root, Mon Dec 21 03:30:22 2009 UTC vs.
Revision 1.312 by root, Thu Dec 29 07:13:44 2011 UTC

41#include <SDL_opengl.h> 41#include <SDL_opengl.h>
42 42
43/* work around os x broken headers */ 43/* work around os x broken headers */
44#ifdef __MACOSX__ 44#ifdef __MACOSX__
45typedef void (APIENTRYP PFNGLBLENDFUNCSEPARATEPROC) (GLenum sfactorRGB, GLenum dfactorRGB, GLenum sfactorAlpha, GLenum dfactorAlpha); 45typedef void (APIENTRYP PFNGLBLENDFUNCSEPARATEPROC) (GLenum sfactorRGB, GLenum dfactorRGB, GLenum sfactorAlpha, GLenum dfactorAlpha);
46typedef void (APIENTRYP PFNGLACTIVETEXTUREPROC) (GLenum texture);
47typedef void (APIENTRYP PFNGLMULTITEXCOORD2FPROC) (GLenum target, GLfloat s, GLfloat t);
46#endif 48#endif
47 49
48#define PANGO_ENABLE_BACKEND 50#define PANGO_ENABLE_BACKEND
49#define G_DISABLE_CAST_CHECKS 51#define G_DISABLE_CAST_CHECKS
50 52
80#define expect_false(expr) expect ((expr) != 0, 0) 82#define expect_false(expr) expect ((expr) != 0, 0)
81#define expect_true(expr) expect ((expr) != 0, 1) 83#define expect_true(expr) expect ((expr) != 0, 1)
82 84
83#define OBJ_STR "\xef\xbf\xbc" /* U+FFFC, object replacement character */ 85#define OBJ_STR "\xef\xbf\xbc" /* U+FFFC, object replacement character */
84 86
87/* this is used as fow flag as well, so has to have a different value */
88/* then anything that is computed by incoming darkness */
85#define FOW_DARKNESS 64 89#define FOW_DARKNESS 50
86#define DARKNESS_ADJUST(n) ((29 * (int)(n)) >> 5) /* times 0.9 */ 90#define DARKNESS_ADJUST(n) (n)
87 91
88#define MAP_EXTEND_X 32 92#define MAP_EXTEND_X 32
89#define MAP_EXTEND_Y 512 93#define MAP_EXTEND_Y 512
90 94
91#define MIN_FONT_HEIGHT 10 95#define MIN_FONT_HEIGHT 10
95 99
96#define KMOD_LRAM 0x10000 // our extension 100#define KMOD_LRAM 0x10000 // our extension
97 101
98#define TEXID_SPEECH 1 102#define TEXID_SPEECH 1
99#define TEXID_NOFACE 2 103#define TEXID_NOFACE 2
100#define TEXID_HIDDEN 3 104
105static char *
106fast_sv_grow (SV *sv, STRLEN need)
107{
108 STRLEN len = SvLEN (sv);
109 STRLEN want = SvCUR (sv) + need;
110
111 if (expect_false (len < want))
112 {
113 do
114 len *= 2;
115 while (len < want);
116
117 sv_grow (sv, len);
118 }
119
120 SvCUR_set (sv, want);
121 return SvEND (sv) - need;
122}
101 123
102static AV *texture_av; 124static AV *texture_av;
103 125
104static struct 126static struct
105{ 127{
460 482
461 SDL_PushEvent ((SDL_Event *)&ev); 483 SDL_PushEvent ((SDL_Event *)&ev);
462} 484}
463 485
464static unsigned int 486static unsigned int
487div255 (unsigned int n)
488{
489 return (n + (n >> 8)) >> 8;
490}
491
492static unsigned int
465minpot (unsigned int n) 493minpot (unsigned int n)
466{ 494{
467 if (!n) 495 if (!n)
468 return 0; 496 return 0;
469 497
552 580
553static void 581static void
554deliantra_main () 582deliantra_main ()
555{ 583{
556 char *argv[] = { 0 }; 584 char *argv[] = { 0 };
557 call_argv ("::main", G_DISCARD | G_VOID, argv); 585 call_argv ("DC::Main::main", G_DISCARD | G_VOID, argv);
558} 586}
559 587
560#ifdef __MACOSX__ 588#ifdef __MACOSX__
561 /* to due surprising braindamage on the side of SDL design, we 589 /* to due surprising braindamage on the side of SDL design, we
562 * do some mind-boggling hack here: SDL requires a custom main() 590 * do some mind-boggling hack here: SDL requires a custom main()
563 * on OS X, so... we provide one and call the original main(), which, 591 * on OS X, so... we provide one and call the original main(), which,
564 * due to share dlibrary magic, calls -lSDLmain's main, not perl's main, 592 * due to shared library magic, calls -lSDLmain's main, not perl's main,
565 * and which calls our main (== SDL_main) back. 593 * and which calls our main (== SDL_main) back.
566 */ 594 */
567 extern C_LINKAGE int 595 extern C_LINKAGE int
568 main (int argc, char *argv[]) 596 main (int argc, char *argv[])
569 { 597 {
793 821
794 const_iv (FOW_DARKNESS) 822 const_iv (FOW_DARKNESS)
795# undef const_iv 823# undef const_iv
796 }; 824 };
797 825
798 for (civ = const_iv + sizeof (const_iv) / sizeof (const_iv [0]); civ-- > const_iv; ) 826 for (civ = const_iv + sizeof (const_iv) / sizeof (const_iv [0]); civ > const_iv; civ--)
799 newCONSTSUB (stash, (char *)civ->name, newSViv (civ->iv)); 827 newCONSTSUB (stash, (char *)civ[-1].name, newSViv (civ[-1].iv));
800 828
801 assert (SDLK_MODIFIER_MIN == SDLK_NUMLOCK); 829 assert (SDLK_MODIFIER_MIN == SDLK_NUMLOCK);
802 assert (SDLK_MODIFIER_MAX == SDLK_COMPOSE); 830 assert (SDLK_MODIFIER_MAX == SDLK_COMPOSE);
803} 831}
804 832
927 955
928 SDL_WM_SetCaption ("Deliantra MORPG Client " VERSION, "Deliantra"); 956 SDL_WM_SetCaption ("Deliantra MORPG Client " VERSION, "Deliantra");
929#define GL_FUNC(ptr,name) gl.name = (ptr)SDL_GL_GetProcAddress ("gl" # name); 957#define GL_FUNC(ptr,name) gl.name = (ptr)SDL_GL_GetProcAddress ("gl" # name);
930#include "glfunc.h" 958#include "glfunc.h"
931#undef GL_FUNC 959#undef GL_FUNC
960
961 if (!gl.ActiveTexture ) gl.ActiveTexture = gl.ActiveTextureARB;
962 if (!gl.MultiTexCoord2f) gl.MultiTexCoord2f = gl.MultiTexCoord2fARB;
932 } 963 }
933} 964}
934 OUTPUT: 965 OUTPUT:
935 RETVAL 966 RETVAL
936 967
944SDL_GetAppState () 975SDL_GetAppState ()
945 976
946int 977int
947SDL_GetModState () 978SDL_GetModState ()
948 979
980int
981SDL_WaitEvent ()
982 C_ARGS: 0
983
949void 984void
985SDL_PumpEvents ()
986
987void
950poll_events () 988peep_events ()
951 PPCODE: 989 PPCODE:
952{ 990{
953 SDL_Event ev; 991 SDL_Event ev;
954 992
955 SDL_PumpEvents (); 993 SDL_PumpEvents ();
1021 1059
1022 XPUSHs (sv_2mortal (sv_bless (newRV_noinc ((SV *)hv), gv_stashpv ("DC::UI::Event", 1)))); 1060 XPUSHs (sv_2mortal (sv_bless (newRV_noinc ((SV *)hv), gv_stashpv ("DC::UI::Event", 1))));
1023 } 1061 }
1024} 1062}
1025 1063
1064char *
1065SDL_AudioDriverName ()
1066 CODE:
1067{
1068 char buf [256];
1069 if (!SDL_AudioDriverName (buf, sizeof (buf)))
1070 XSRETURN_UNDEF;
1071
1072 RETVAL = buf;
1073}
1074 OUTPUT:
1075 RETVAL
1076
1026int 1077int
1027Mix_OpenAudio (int frequency = 44100, int format = MIX_DEFAULT_FORMAT, int channels = 2, int chunksize = 4096) 1078Mix_OpenAudio (int frequency = 44100, int format = MIX_DEFAULT_FORMAT, int channels = 2, int chunksize = 4096)
1028 POSTCALL: 1079 POSTCALL:
1029 Mix_HookMusicFinished (music_finished); 1080 Mix_HookMusicFinished (music_finished);
1030 Mix_ChannelFinished (channel_finished); 1081 Mix_ChannelFinished (channel_finished);
1092add_font (char *file) 1143add_font (char *file)
1093 CODE: 1144 CODE:
1094 RETVAL = FcConfigAppFontAddFile (0, (const FcChar8 *)file); 1145 RETVAL = FcConfigAppFontAddFile (0, (const FcChar8 *)file);
1095 OUTPUT: 1146 OUTPUT:
1096 RETVAL 1147 RETVAL
1148
1149void
1150IMG_Init (int flags = IMG_INIT_JPG | IMG_INIT_PNG)
1151
1152# MIX_INIT_MP3 gives smpeg + libstdc++ + libgcc_s
1153void
1154Mix_Init (int flags = MIX_INIT_MOD | MIX_INIT_OGG)
1097 1155
1098void 1156void
1099load_image_inline (SV *image_) 1157load_image_inline (SV *image_)
1100 ALIAS: 1158 ALIAS:
1101 load_image_file = 1 1159 load_image_file = 1
1665 glDisable (GL_BLEND); 1723 glDisable (GL_BLEND);
1666 } 1724 }
1667} 1725}
1668 1726
1669void 1727void
1670draw_fow_texture (float intensity, int name1, float s1, float t1, float w1, float h1, float blend = 0.f, float dx = 0.f, float dy = 0.f, int name2 = 0, float s2 = 0.f, float t2 = 0.f, float w2 = 0.f, float h2 = 0.f) 1728draw_fow_texture (float intensity, int hidden_tex, int name1, uint8_t *data1, float s, float t, int w, int h, float blend = 0.f, int dx = 0, int dy = 0, int name2 = 0, uint8_t *data2 = data1)
1671 PROTOTYPE: @ 1729 PROTOTYPE: @
1672 CODE: 1730 CODE:
1673{ 1731{
1732 glEnable (GL_BLEND);
1733 glBlendFunc (intensity ? GL_SRC_ALPHA : GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
1674 glEnable (GL_TEXTURE_2D); 1734 glEnable (GL_TEXTURE_2D);
1675 glEnable (GL_BLEND);
1676 glBlendFunc (GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
1677 glBindTexture (GL_TEXTURE_2D, name1); 1735 glBindTexture (GL_TEXTURE_2D, name1);
1678 1736
1679 glColor3f (intensity, intensity, intensity); 1737 glColor3f (intensity, intensity, intensity);
1680 glPushMatrix (); 1738 glPushMatrix ();
1681 glScalef (1./3, 1./3, 1.); 1739 glScalef (1./3, 1./3, 1.);
1682 1740
1683 if (blend > 0.f) 1741 if (blend > 0.f)
1684 { 1742 {
1685 float S2, T2; /* 0. 0. for texture 2 */ 1743 float dx3 = dx * -3.f / w;
1686 float w = w1 > w2 ? w1 : w2; 1744 float dy3 = dy * -3.f / h;
1687 float h = h1 > h2 ? h1 : h2;
1688 GLfloat env_color[4] = { 0., 0., 0., blend }; 1745 GLfloat env_color[4] = { 0., 0., 0., blend };
1689 1746
1690 /* interpolate the two shadow textures */ 1747 /* interpolate the two shadow textures */
1691 /* stage 0 == rgb(glcolor) + alpha(t0) */ 1748 /* stage 0 == rgb(glcolor) + alpha(t0) */
1692 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); 1749 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
1697 glBindTexture (GL_TEXTURE_2D, name2); 1754 glBindTexture (GL_TEXTURE_2D, name2);
1698 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE); 1755 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);
1699 1756
1700 /* rgb == rgb(glcolor) */ 1757 /* rgb == rgb(glcolor) */
1701 glTexEnvi (GL_TEXTURE_ENV, GL_COMBINE_RGB, GL_REPLACE); 1758 glTexEnvi (GL_TEXTURE_ENV, GL_COMBINE_RGB, GL_REPLACE);
1702 glTexEnvi (GL_TEXTURE_ENV, GL_SOURCE0_RGB, GL_CONSTANT); 1759 glTexEnvi (GL_TEXTURE_ENV, GL_SOURCE0_RGB, GL_PRIMARY_COLOR);
1703 glTexEnvi (GL_TEXTURE_ENV, GL_OPERAND0_RGB, GL_SRC_COLOR); 1760 glTexEnvi (GL_TEXTURE_ENV, GL_OPERAND0_RGB, GL_SRC_COLOR);
1704 1761
1705 /* alpha = interpolate t0, t1 by env_alpha */ 1762 /* alpha = interpolate t0, t1 by env_alpha */
1706 glTexEnvfv (GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, env_color); 1763 glTexEnvfv (GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, env_color);
1707 1764
1713 glTexEnvi (GL_TEXTURE_ENV, GL_OPERAND1_ALPHA, GL_SRC_ALPHA); 1770 glTexEnvi (GL_TEXTURE_ENV, GL_OPERAND1_ALPHA, GL_SRC_ALPHA);
1714 1771
1715 glTexEnvi (GL_TEXTURE_ENV, GL_SOURCE2_ALPHA, GL_CONSTANT); 1772 glTexEnvi (GL_TEXTURE_ENV, GL_SOURCE2_ALPHA, GL_CONSTANT);
1716 glTexEnvi (GL_TEXTURE_ENV, GL_OPERAND2_ALPHA, GL_SRC_ALPHA); 1773 glTexEnvi (GL_TEXTURE_ENV, GL_OPERAND2_ALPHA, GL_SRC_ALPHA);
1717 1774
1718 s1 *= w / w1;
1719 t1 *= h / h1;
1720
1721 dx *= -3.f / w2;
1722 dy *= -3.f / h2;
1723 dx *= w / w2;
1724 dy *= h / h2;
1725
1726 s2 *= w / w2;
1727 t2 *= h / h2;
1728
1729 glBegin (GL_QUADS); 1775 glBegin (GL_QUADS);
1730 gl.MultiTexCoord2f (GL_TEXTURE0, 0, 0); gl.MultiTexCoord2f (GL_TEXTURE1, dx , dy ); glVertex2f ( 0, 0); 1776 gl.MultiTexCoord2f (GL_TEXTURE0, 0, 0); gl.MultiTexCoord2f (GL_TEXTURE1, dx3 , dy3 ); glVertex2i (0, 0);
1731 gl.MultiTexCoord2f (GL_TEXTURE0, 0, t1); gl.MultiTexCoord2f (GL_TEXTURE1, dx , dy + t2); glVertex2f ( 0, h1); 1777 gl.MultiTexCoord2f (GL_TEXTURE0, 0, t); gl.MultiTexCoord2f (GL_TEXTURE1, dx3 , dy3 + t); glVertex2i (0, h);
1732 gl.MultiTexCoord2f (GL_TEXTURE0, s1, t1); gl.MultiTexCoord2f (GL_TEXTURE1, dx + s2, dy + t2); glVertex2f (w1, h1); 1778 gl.MultiTexCoord2f (GL_TEXTURE0, s, t); gl.MultiTexCoord2f (GL_TEXTURE1, dx3 + s, dy3 + t); glVertex2i (w, h);
1733 gl.MultiTexCoord2f (GL_TEXTURE0, s1, 0); gl.MultiTexCoord2f (GL_TEXTURE1, dx + s2, dy ); glVertex2f (w1, 0); 1779 gl.MultiTexCoord2f (GL_TEXTURE0, s, 0); gl.MultiTexCoord2f (GL_TEXTURE1, dx3 + s, dy3 ); glVertex2i (w, 0);
1734 glEnd (); 1780 glEnd ();
1735 1781
1736 glDisable (GL_TEXTURE_2D); 1782 glDisable (GL_TEXTURE_2D);
1737 gl.ActiveTexture (GL_TEXTURE0); 1783 gl.ActiveTexture (GL_TEXTURE0);
1738 } 1784 }
1740 { 1786 {
1741 /* simple blending of one texture, also opengl <1.3 path */ 1787 /* simple blending of one texture, also opengl <1.3 path */
1742 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); 1788 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
1743 1789
1744 glBegin (GL_QUADS); 1790 glBegin (GL_QUADS);
1745 glTexCoord2f ( 0, 0); glVertex2f ( 0, 0); 1791 glTexCoord2f (0, 0); glVertex2f (0, 0);
1746 glTexCoord2f ( 0, t1); glVertex2f ( 0, h1); 1792 glTexCoord2f (0, t); glVertex2f (0, h);
1747 glTexCoord2f (s1, t1); glVertex2f (w1, h1); 1793 glTexCoord2f (s, t); glVertex2f (w, h);
1748 glTexCoord2f (s1, 0); glVertex2f (w1, 0); 1794 glTexCoord2f (s, 0); glVertex2f (w, 0);
1749 glEnd (); 1795 glEnd ();
1750 } 1796 }
1797
1798 /* draw ?-marks or equivalent, this is very clumsy code :/ */
1799 {
1800 int x, y;
1801 int dx3 = dx * 3;
1802 int dy3 = dy * 3;
1803
1804 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
1805 glBindTexture (GL_TEXTURE_2D, hidden_tex);
1806 glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
1807 glTranslatef (-1., -1., 0);
1808 glBegin (GL_QUADS);
1809
1810 for (y = 1; y < h; y += 3)
1811 {
1812 int y1 = y - dy3;
1813 int y1valid = y1 >= 0 && y1 < h;
1814
1815 for (x = 1; x < w; x += 3)
1816 {
1817 int x1 = x - dx3;
1818 uint8_t h1 = data1 [x + y * w] == DARKNESS_ADJUST (255 - FOW_DARKNESS);
1819 uint8_t h2;
1820
1821 if (y1valid && x1 >= 0 && x1 < w)
1822 h2 = data2 [x1 + y1 * w] == DARKNESS_ADJUST (255 - FOW_DARKNESS);
1823 else
1824 h2 = 1; /* out of range == invisible */
1825
1826 if (h1 || h2)
1827 {
1828 float alpha = h1 == h2 ? 1.f : h1 ? 1.f - blend : blend;
1829 glColor4f (1., 1., 1., alpha);
1830
1831 glTexCoord2f (0, 0.); glVertex2i (x , y );
1832 glTexCoord2f (0, 1.); glVertex2i (x , y + 3);
1833 glTexCoord2f (1, 1.); glVertex2i (x + 3, y + 3);
1834 glTexCoord2f (1, 0.); glVertex2i (x + 3, y );
1835 }
1836 }
1837 }
1838 }
1839
1840 glEnd ();
1751 1841
1752 glPopMatrix (); 1842 glPopMatrix ();
1753 1843
1754 glDisable (GL_TEXTURE_2D); 1844 glDisable (GL_TEXTURE_2D);
1755 glDisable (GL_BLEND); 1845 glDisable (GL_BLEND);
1976 { 2066 {
1977 ext = *data++; 2067 ext = *data++;
1978 cmd = ext & 0x7f; 2068 cmd = ext & 0x7f;
1979 2069
1980 if (cmd < 4) 2070 if (cmd < 4)
1981 cell->darkness = 255 - ext * 64 + 1; 2071 cell->darkness = 255 - ext * 64 + 1; /* make sure this doesn't collide with FOW_DARKNESS */
1982 else if (cmd == 5) // health 2072 else if (cmd == 5) // health
1983 { 2073 {
1984 cell->stat_width = 1; 2074 cell->stat_width = 1;
1985 cell->stat_hp = *data++; 2075 cell->stat_hp = *data++;
1986 } 2076 }
2061 ? self->row + y 2151 ? self->row + y
2062 : 0; 2152 : 0;
2063 2153
2064 for (x = x0; x < x1; x++) 2154 for (x = x0; x < x1; x++)
2065 { 2155 {
2066 int r = 32, g = 32, b = 32, a = 192; 2156 unsigned int r = 32, g = 32, b = 32, a = 192;
2067 2157
2068 if (row && row->c0 <= x && x < row->c1) 2158 if (row && row->c0 <= x && x < row->c1)
2069 { 2159 {
2070 mapcell *cell = row->col + (x - row->c0); 2160 mapcell *cell = row->col + (x - row->c0);
2071 2161
2073 { 2163 {
2074 maptex tex = self->tex [cell->tile [z]]; 2164 maptex tex = self->tex [cell->tile [z]];
2075 int a0 = 255 - tex.a; 2165 int a0 = 255 - tex.a;
2076 int a1 = tex.a; 2166 int a1 = tex.a;
2077 2167
2078 r = (r * a0 + tex.r * a1) / 255; 2168 r = div255 (r * a0 + tex.r * a1);
2079 g = (g * a0 + tex.g * a1) / 255; 2169 g = div255 (g * a0 + tex.g * a1);
2080 b = (b * a0 + tex.b * a1) / 255; 2170 b = div255 (b * a0 + tex.b * a1);
2081 a = (a * a0 + tex.a * a1) / 255; 2171 a = div255 (a * a0 + tex.a * a1);
2082 } 2172 }
2083 } 2173 }
2084 2174
2085 *map++ = (r ) 2175 *map++ = (r )
2086 | (g << 8) 2176 | (g << 8)
2093} 2183}
2094 OUTPUT: 2184 OUTPUT:
2095 RETVAL 2185 RETVAL
2096 2186
2097void 2187void
2098draw (DC::Map self, int mx, int my, int sw, int sh, int T, U32 player = 0xffffffff, int sdx = 0, int sdy = 0) 2188draw (DC::Map self, int mx, int my, int sw, int sh, int Tw, int Th, U32 player = 0xffffffff, int sdx = 0, int sdy = 0)
2099 CODE: 2189 CODE:
2100{ 2190{
2101 int x, y, z; 2191 int x, y, z;
2102 2192
2103 HV *smooth = (HV *)sv_2mortal ((SV *)newHV ()); 2193 HV *smooth = (HV *)sv_2mortal ((SV *)newHV ());
2107 int pl_x, pl_y; 2197 int pl_x, pl_y;
2108 maptex pl_tex; 2198 maptex pl_tex;
2109 rc_t *rc = rc_alloc (); 2199 rc_t *rc = rc_alloc ();
2110 rc_t *rc_ov = rc_alloc (); 2200 rc_t *rc_ov = rc_alloc ();
2111 rc_key_t key; 2201 rc_key_t key;
2112 rc_array_t *arr, *arr_hidden; 2202 rc_array_t *arr;
2113 2203
2114 pl_tex.name = 0; 2204 pl_tex.name = 0;
2115 2205
2116 // that's current max. sorry. 2206 // that's current max. sorry.
2117 if (sw > 255) sw = 255; 2207 if (sw > 255) sw = 255;
2154 } 2244 }
2155 2245
2156 glEnable (GL_BLEND); 2246 glEnable (GL_BLEND);
2157 glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); 2247 glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
2158 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); 2248 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
2159
2160 key.texname = self->tex [TEXID_HIDDEN].name;
2161 arr_hidden = rc_array (rc_ov, &key);
2162 2249
2163 for (z = 0; z <= 2; z++) 2250 for (z = 0; z <= 2; z++)
2164 { 2251 {
2165 memset (smooth_level, 0, sizeof (smooth_level)); 2252 memset (smooth_level, 0, sizeof (smooth_level));
2166 key.texname = -1; 2253 key.texname = -1;
2190 2277
2191 key.texname = tex.name; 2278 key.texname = tex.name;
2192 arr = rc_array (rc, &key); 2279 arr = rc_array (rc, &key);
2193 } 2280 }
2194 2281
2195 px = (x + 1) * T - tex.w; 2282 px = (x + 1) * Th - tex.w;
2196 py = (y + 1) * T - tex.h; 2283 py = (y + 1) * Tw - tex.h;
2197 2284
2198 if (expect_false (cell->player == player) && expect_false (z == 2)) 2285 if (expect_false (cell->player == player) && expect_false (z == 2))
2199 { 2286 {
2200 pl_x = px; 2287 pl_x = px;
2201 pl_y = py; 2288 pl_y = py;
2246 skey.x = x ; skey.y = y ; smooth_or_bits (smooth, &skey, 0x0400); 2333 skey.x = x ; skey.y = y ; smooth_or_bits (smooth, &skey, 0x0400);
2247 skey.x = x + 2; skey.y = y ; smooth_or_bits (smooth, &skey, 0x0800); 2334 skey.x = x + 2; skey.y = y ; smooth_or_bits (smooth, &skey, 0x0800);
2248 } 2335 }
2249 } 2336 }
2250 2337
2251 if (expect_false (z == 2)) 2338 if (expect_false (z == 2) && expect_false (cell->flags))
2252 { 2339 {
2253 /* draw question marks on top of hidden spaces */ 2340 // overlays such as the speech bubble, probably more to come
2254 if (!cell->darkness) 2341 if (cell->flags & 1)
2255 { 2342 {
2256 maptex tex = self->tex [TEXID_HIDDEN];
2257 int px = (x + 1) * T - tex.w;
2258 int py = (y + 1) * T - tex.h;
2259
2260 rc_t2f_v3f (arr_hidden, 0 , 0 , px , py , 0);
2261 rc_t2f_v3f (arr_hidden, 0 , tex.t, px , py + tex.h, 0);
2262 rc_t2f_v3f (arr_hidden, tex.s, tex.t, px + tex.w, py + tex.h, 0);
2263 rc_t2f_v3f (arr_hidden, tex.s, 0 , px + tex.w, py , 0);
2264 }
2265
2266 if (expect_false (cell->flags))
2267 {
2268 // overlays such as the speech bubble, probably more to come
2269 if (cell->flags & 1)
2270 {
2271 rc_key_t key_ov = key; 2343 rc_key_t key_ov = key;
2272 maptex tex = self->tex [TEXID_SPEECH]; 2344 maptex tex = self->tex [TEXID_SPEECH];
2273 rc_array_t *arr; 2345 rc_array_t *arr;
2274 int px = x * T + T * 2 / 32; 2346 int px = x * Tw + Tw * 2 / 32;
2275 int py = y * T - T * 6 / 32; 2347 int py = y * Th - Th * 6 / 32;
2276 2348
2277 key_ov.texname = tex.name; 2349 key_ov.texname = tex.name;
2278 arr = rc_array (rc_ov, &key_ov); 2350 arr = rc_array (rc_ov, &key_ov);
2279 2351
2280 rc_t2f_v3f (arr, 0 , 0 , px , py , 0); 2352 rc_t2f_v3f (arr, 0 , 0 , px , py , 0);
2281 rc_t2f_v3f (arr, 0 , tex.t, px , py + T, 0); 2353 rc_t2f_v3f (arr, 0 , tex.t, px , py + Th, 0);
2282 rc_t2f_v3f (arr, tex.s, tex.t, px + T, py + T, 0); 2354 rc_t2f_v3f (arr, tex.s, tex.t, px + Tw, py + Th, 0);
2283 rc_t2f_v3f (arr, tex.s, 0 , px + T, py , 0); 2355 rc_t2f_v3f (arr, tex.s, 0 , px + Tw, py , 0);
2284 }
2285 } 2356 }
2286 } 2357 }
2287 } 2358 }
2288 } 2359 }
2289 2360
2316 if (!(bits & 0x1000) 2387 if (!(bits & 0x1000)
2317 && skey->level == level 2388 && skey->level == level
2318 && level > smooth_max [skey->x][skey->y]) 2389 && level > smooth_max [skey->x][skey->y])
2319 { 2390 {
2320 maptex tex = self->tex [skey->tile]; 2391 maptex tex = self->tex [skey->tile];
2321 int px = (((int)skey->x) - 1) * T; 2392 int px = (((int)skey->x) - 1) * Tw;
2322 int py = (((int)skey->y) - 1) * T; 2393 int py = (((int)skey->y) - 1) * Th;
2323 int border = bits & 15; 2394 int border = bits & 15;
2324 int corner = (bits >> 8) & ~(bits >> 4) & 15; 2395 int corner = (bits >> 8) & ~(bits >> 4) & 15;
2325 float dx = tex.s * .0625f; // 16 images/row 2396 float dx = tex.s * .0625f; // 16 images/row
2326 float dy = tex.t * .5f ; // 2 images/column 2397 float dy = tex.t * .5f ; // 2 images/column
2327 2398
2340 2411
2341 if (border) 2412 if (border)
2342 { 2413 {
2343 float ox = border * dx; 2414 float ox = border * dx;
2344 2415
2345 glTexCoord2f (ox , 0.f ); glVertex2i (px , py ); 2416 glTexCoord2f (ox , 0.f ); glVertex2i (px , py );
2346 glTexCoord2f (ox , dy ); glVertex2i (px , py + T); 2417 glTexCoord2f (ox , dy ); glVertex2i (px , py + Th);
2347 glTexCoord2f (ox + dx, dy ); glVertex2i (px + T, py + T); 2418 glTexCoord2f (ox + dx, dy ); glVertex2i (px + Tw, py + Th);
2348 glTexCoord2f (ox + dx, 0.f ); glVertex2i (px + T, py ); 2419 glTexCoord2f (ox + dx, 0.f ); glVertex2i (px + Tw, py );
2349 } 2420 }
2350 2421
2351 if (corner) 2422 if (corner)
2352 { 2423 {
2353 float ox = corner * dx; 2424 float ox = corner * dx;
2354 2425
2355 glTexCoord2f (ox , dy ); glVertex2i (px , py ); 2426 glTexCoord2f (ox , dy ); glVertex2i (px , py );
2356 glTexCoord2f (ox , dy * 2.f); glVertex2i (px , py + T); 2427 glTexCoord2f (ox , dy * 2.f); glVertex2i (px , py + Th);
2357 glTexCoord2f (ox + dx, dy * 2.f); glVertex2i (px + T, py + T); 2428 glTexCoord2f (ox + dx, dy * 2.f); glVertex2i (px + Tw, py + Th);
2358 glTexCoord2f (ox + dx, dy ); glVertex2i (px + T, py ); 2429 glTexCoord2f (ox + dx, dy ); glVertex2i (px + Tw, py );
2359 } 2430 }
2360 } 2431 }
2361 } 2432 }
2362 } 2433 }
2363 } 2434 }
2404 for (x = 0; x < sw; x++) 2475 for (x = 0; x < sw; x++)
2405 if (row->c0 <= x + mx && x + mx < row->c1) 2476 if (row->c0 <= x + mx && x + mx < row->c1)
2406 { 2477 {
2407 mapcell *cell = row->col + (x + mx - row->c0); 2478 mapcell *cell = row->col + (x + mx - row->c0);
2408 2479
2409 int px = x * T; 2480 int px = x * Tw;
2410 int py = y * T; 2481 int py = y * Th;
2411 2482
2412 if (expect_false (cell->player == player)) 2483 if (expect_false (cell->player == player))
2413 { 2484 {
2414 px += sdx; 2485 px += sdx;
2415 py += sdy; 2486 py += sdy;
2416 } 2487 }
2417 2488
2418 if (cell->stat_hp) 2489 if (cell->stat_hp)
2419 { 2490 {
2420 int width = cell->stat_width * T; 2491 int width = cell->stat_width * Tw;
2421 int thick = (sh * T / 32 + 27) / 28 + 1 + cell->stat_width; 2492 int thick = (sh * Th / 32 + 27) / 28 + 1 + cell->stat_width;
2422 2493
2423 glColor3ub (0, 0, 0); 2494 glColor3ub (0, 0, 0);
2424 glRectf (px + 1, py - thick - 2, 2495 glRectf (px + 1, py - thick - 2,
2425 px + width - 1, py); 2496 px + width - 1, py);
2426 2497
2463 int x, y; 2534 int x, y;
2464 2535
2465 glEnable (GL_TEXTURE_2D); 2536 glEnable (GL_TEXTURE_2D);
2466 /* GL_REPLACE would be correct, as we don't need to modulate alpha, 2537 /* GL_REPLACE would be correct, as we don't need to modulate alpha,
2467 * but the nvidia driver (185.18.14) mishandles alpha textures 2538 * but the nvidia driver (185.18.14) mishandles alpha textures
2468 * ansd takes the colour from god knows where instead of using 2539 * and takes the colour from god knows where instead of using
2469 * Cp. MODULATE results in the same colour, but slightly different 2540 * Cp. MODULATE results in the same colour, but slightly different
2470 * alpha, but atcually gives us the correct colour with nvidia. 2541 * alpha, but atcually gives us the correct colour with nvidia.
2471 */ 2542 */
2472 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); 2543 glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
2473 glEnable (GL_BLEND); 2544 glEnable (GL_BLEND);
2502void 2573void
2503fow_texture (DC::Map self, int mx, int my, int sw, int sh) 2574fow_texture (DC::Map self, int mx, int my, int sw, int sh)
2504 PPCODE: 2575 PPCODE:
2505{ 2576{
2506 int x, y; 2577 int x, y;
2507 int sw1 = sw + 2; 2578 int sw1 = sw + 2;
2508 int sh1 = sh + 2; 2579 int sh1 = sh + 2;
2509 int sh3 = sh * 3; 2580 int sh3 = sh * 3;
2510 int sw34 = (sw * 3 + 3) & ~3; 2581 int sw3 = sw * 3;
2582 SV *darkness3_sv = sv_2mortal (newSV (sw3 * sh3));
2583 uint8_t *darkness3 = (uint8_t *)SvPVX (darkness3_sv);
2511 uint8_t *darkness1 = (uint8_t *)malloc (sw1 * sh1); 2584 uint8_t *darkness1 = (uint8_t *)malloc (sw1 * sh1);
2512 SV *darkness3_sv = sv_2mortal (newSV (sw34 * sh3)); 2585 memset (darkness1, 0, sw1*sh1);
2513 uint8_t *darkness3 = (uint8_t *)SvPVX (darkness3_sv);
2514 2586
2515 SvPOK_only (darkness3_sv); 2587 SvPOK_only (darkness3_sv);
2516 SvCUR_set (darkness3_sv, sw34 * sh3); 2588 SvCUR_set (darkness3_sv, sw3 * sh3);
2517 2589
2518 mx += self->x - 1; 2590 mx += self->x - 1;
2519 my += self->y - 1; 2591 my += self->y - 1;
2520
2521 memset (darkness1, DARKNESS_ADJUST (255 - FOW_DARKNESS), sw1 * sh1);
2522 2592
2523 for (y = 0; y < sh1; y++) 2593 for (y = 0; y < sh1; y++)
2524 if (0 <= y + my && y + my < self->rows) 2594 if (0 <= y + my && y + my < self->rows)
2525 { 2595 {
2526 maprow *row = self->row + (y + my); 2596 maprow *row = self->row + (y + my);
2559 2629
2560 uint8_t r13 = (d13 + d23 + d12) / 3; 2630 uint8_t r13 = (d13 + d23 + d12) / 3;
2561 uint8_t r23 = d23; 2631 uint8_t r23 = d23;
2562 uint8_t r33 = (d23 + d33 + d32) / 3; 2632 uint8_t r33 = (d23 + d33 + d32) / 3;
2563 2633
2564 darkness3 [(y * 3 ) * sw34 + (x * 3 )] = MAX (d22, r11); 2634 darkness3 [(y * 3 ) * sw3 + (x * 3 )] = MAX (d22, r11);
2565 darkness3 [(y * 3 ) * sw34 + (x * 3 + 1)] = MAX (d22, r21); 2635 darkness3 [(y * 3 ) * sw3 + (x * 3 + 1)] = MAX (d22, r21);
2566 darkness3 [(y * 3 ) * sw34 + (x * 3 + 2)] = MAX (d22, r31); 2636 darkness3 [(y * 3 ) * sw3 + (x * 3 + 2)] = MAX (d22, r31);
2567 darkness3 [(y * 3 + 1) * sw34 + (x * 3 )] = MAX (d22, r12); 2637 darkness3 [(y * 3 + 1) * sw3 + (x * 3 )] = MAX (d22, r12);
2568 darkness3 [(y * 3 + 1) * sw34 + (x * 3 + 1)] = MAX (d22, r22); 2638 darkness3 [(y * 3 + 1) * sw3 + (x * 3 + 1)] = MAX (d22, r22); /* this MUST be == d22 */
2569 darkness3 [(y * 3 + 1) * sw34 + (x * 3 + 2)] = MAX (d22, r32); 2639 darkness3 [(y * 3 + 1) * sw3 + (x * 3 + 2)] = MAX (d22, r32);
2570 darkness3 [(y * 3 + 2) * sw34 + (x * 3 )] = MAX (d22, r13); 2640 darkness3 [(y * 3 + 2) * sw3 + (x * 3 )] = MAX (d22, r13);
2571 darkness3 [(y * 3 + 2) * sw34 + (x * 3 + 1)] = MAX (d22, r23); 2641 darkness3 [(y * 3 + 2) * sw3 + (x * 3 + 1)] = MAX (d22, r23);
2572 darkness3 [(y * 3 + 2) * sw34 + (x * 3 + 2)] = MAX (d22, r33); 2642 darkness3 [(y * 3 + 2) * sw3 + (x * 3 + 2)] = MAX (d22, r33);
2573 } 2643 }
2574 2644
2575 free (darkness1); 2645 free (darkness1);
2576 2646
2577 EXTEND (SP, 3); 2647 EXTEND (SP, 3);
2578 PUSHs (sv_2mortal (newSViv (sw34))); 2648 PUSHs (sv_2mortal (newSViv (sw3)));
2579 PUSHs (sv_2mortal (newSViv (sh3))); 2649 PUSHs (sv_2mortal (newSViv (sh3)));
2580 PUSHs (darkness3_sv); 2650 PUSHs (darkness3_sv);
2581} 2651}
2582 2652
2583SV * 2653SV *
2781 if (RETVAL < 0) 2851 if (RETVAL < 0)
2782 { 2852 {
2783 RETVAL = Mix_GroupOldest (-1); 2853 RETVAL = Mix_GroupOldest (-1);
2784 2854
2785 if (RETVAL < 0) 2855 if (RETVAL < 0)
2856 {
2857 // happens sometimes, maybe it just stopped playing(?)
2858 RETVAL = Mix_GroupAvailable (-1);
2859
2860 if (RETVAL < 0)
2786 XSRETURN_UNDEF; 2861 XSRETURN_UNDEF;
2787 2862 }
2863 else
2788 Mix_HaltChannel (RETVAL); 2864 Mix_HaltChannel (RETVAL);
2789 } 2865 }
2790 2866
2791 Mix_UnregisterAllEffects (RETVAL); 2867 Mix_UnregisterAllEffects (RETVAL);
2792 Mix_Volume (RETVAL, 128); 2868 Mix_Volume (RETVAL, 128);
2793} 2869}
2852 Mix_SetReverseStereo (self, flip); 2928 Mix_SetReverseStereo (self, flip);
2853 2929
2854MODULE = Deliantra::Client PACKAGE = DC::MixChunk 2930MODULE = Deliantra::Client PACKAGE = DC::MixChunk
2855 2931
2856PROTOTYPES: DISABLE 2932PROTOTYPES: DISABLE
2933
2934void
2935decoders ()
2936 PPCODE:
2937#if SDL_MIXER_MAJOR_VERSION > 1 || SDL_MIXER_MINOR_VERSION > 2 || SDL_MIXER_PATCHLEVEL >= 10
2938 int i, num = Mix_GetNumChunkDecoders ();
2939 EXTEND (SP, num);
2940 for (i = 0; i < num; ++i)
2941 PUSHs (sv_2mortal (newSVpv (Mix_GetChunkDecoder (i), 0)));
2942#else
2943 XPUSHs (sv_2mortal (newSVpv ("(sdl mixer too old)", 0)));
2944#endif
2857 2945
2858DC::MixChunk 2946DC::MixChunk
2859new (SV *class, DC::RW rwops) 2947new (SV *class, DC::RW rwops)
2860 CODE: 2948 CODE:
2861 RETVAL = Mix_LoadWAV_RW (rwops, 1); 2949 RETVAL = Mix_LoadWAV_RW (rwops, 1);
2894 OUTPUT: 2982 OUTPUT:
2895 RETVAL 2983 RETVAL
2896 2984
2897MODULE = Deliantra::Client PACKAGE = DC::MixMusic 2985MODULE = Deliantra::Client PACKAGE = DC::MixMusic
2898 2986
2987void
2988decoders ()
2989 PPCODE:
2990#if SDL_MIXER_MAJOR_VERSION > 1 || SDL_MIXER_MINOR_VERSION > 2 || SDL_MIXER_PATCHLEVEL >= 10
2991 int i, num = Mix_GetNumMusicDecoders ();
2992 EXTEND (SP, num);
2993 for (i = 0; i < num; ++i)
2994 PUSHs (sv_2mortal (newSVpv (Mix_GetMusicDecoder (i), 0)));
2995#else
2996 XPUSHs (sv_2mortal (newSVpv ("(sdl mixer too old)", 0)));
2997#endif
2998
2899int 2999int
2900volume (int volume = -1) 3000volume (int volume = -1)
2901 PROTOTYPE: ;$ 3001 PROTOTYPE: ;$
2902 CODE: 3002 CODE:
2903 if (items > 0) 3003 if (items > 0)
2913 3013
2914void 3014void
2915halt () 3015halt ()
2916 CODE: 3016 CODE:
2917 Mix_HaltMusic (); 3017 Mix_HaltMusic ();
3018
3019int
3020playing ()
3021 CODE:
3022 RETVAL = Mix_PlayingMusic ();
3023 OUTPUT:
3024 RETVAL
2918 3025
2919DC::MixMusic 3026DC::MixMusic
2920new (SV *class, DC::RW rwops) 3027new (SV *class, DC::RW rwops)
2921 CODE: 3028 CODE:
2922 RETVAL = Mix_LoadMUS_RW (rwops); 3029 RETVAL = Mix_LoadMUS_RW (rwops);
3062 const_iv (GL_FUNC_SUBTRACT), 3169 const_iv (GL_FUNC_SUBTRACT),
3063 const_iv (GL_FUNC_REVERSE_SUBTRACT), 3170 const_iv (GL_FUNC_REVERSE_SUBTRACT),
3064# undef const_iv 3171# undef const_iv
3065 }; 3172 };
3066 3173
3067 for (civ = const_iv + sizeof (const_iv) / sizeof (const_iv [0]); civ-- > const_iv; ) 3174 for (civ = const_iv + sizeof (const_iv) / sizeof (const_iv [0]); civ > const_iv; civ--)
3068 newCONSTSUB (stash, (char *)civ->name, newSViv (civ->iv)); 3175 newCONSTSUB (stash, (char *)civ[-1].name, newSViv (civ[-1].iv));
3069 3176
3070 texture_av = newAV (); 3177 texture_av = newAV ();
3071 AvREAL_off (texture_av); 3178 AvREAL_off (texture_av);
3072} 3179}
3073 3180
3116 RETVAL 3223 RETVAL
3117 3224
3118int glGetError () 3225int glGetError ()
3119 3226
3120void glFinish () 3227void glFinish ()
3228
3229void glFlush ()
3121 3230
3122void glClear (int mask) 3231void glClear (int mask)
3123 3232
3124void glClearColor (float r, float g, float b, float a = 1.0) 3233void glClearColor (float r, float g, float b, float a = 1.0)
3125 PROTOTYPE: @ 3234 PROTOTYPE: @
3296void glNewList (int list, int mode = GL_COMPILE) 3405void glNewList (int list, int mode = GL_COMPILE)
3297 3406
3298void glEndList () 3407void glEndList ()
3299 3408
3300void glCallList (int list) 3409void glCallList (int list)
3410
3411void c_init ()
3412 CODE:
3413 glPixelStorei (GL_PACK_ALIGNMENT , 1);
3414 glPixelStorei (GL_UNPACK_ALIGNMENT, 1);
3301 3415
3302MODULE = Deliantra::Client PACKAGE = DC::UI::Base 3416MODULE = Deliantra::Client PACKAGE = DC::UI::Base
3303 3417
3304PROTOTYPES: DISABLE 3418PROTOTYPES: DISABLE
3305 3419

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines