1 /* Copyright (C) 1996-1997 Aleksey Volynskov
2 * Copyright (C) 2011 Rambo
3 * Copyright (C) 2020 SovietPony
5 * This program is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation, version 3 of the License ONLY.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program. If not, see <http://www.gnu.org/licenses/>.
35 static void *sndswn
, *sndswx
, *sndnoway
, *sndbdo
, *sndbdc
, *sndnotele
;
37 static byte cht
, chto
, chf
, f_ch
;
39 void SW_alloc (void) {
40 sndswn
=Z_getsnd("SWTCHN");
41 sndswx
=Z_getsnd("SWTCHX");
42 sndnoway
=Z_getsnd("NOWAY");
43 sndbdo
=Z_getsnd("BDOPN");
44 sndbdc
=Z_getsnd("BDCLS");
45 sndnotele
=Z_getsnd("NOTELE");
50 for (i
= 0; i
< MAXSW
; i
++) {
56 static void door(byte x
,byte y
) {
59 if(x
>=FLDW
|| y
>=FLDH
) return;
60 if(fld
[y
][x
]!=cht
) return;
62 for(;x
&& fld
[y
][x
-1]==cht
;--x
);
63 for(;ex
<FLDW
&& fld
[y
][ex
]==cht
;++ex
);
64 memset(fld
[y
]+x
,chto
,ex
-x
);
65 if(f_ch
) memset(fldf
[y
]+x
,chf
,ex
-x
);
72 void Z_water_trap (obj_t
*o
) {
75 if((y
=o
->y
)>=FLDH
*CELH
+o
->h
) return;
76 if((x
=o
->x
)<0 || o
->x
>FLDW
*CELW
) return;
84 cht
=5;chto
=255;f_ch
=0;
89 void Z_untrap (byte t
) {
93 for(p
=(byte
*)fld
,n
=FLDW
*FLDH
;n
;--n
,++p
)
97 static void opendoor(int i
) {
100 swsnd
=Z_sound(sndbdo
,128);
101 j
=fldf
[sw
[i
].b
][sw
[i
].a
];
102 cht
=2;chto
=3;chf
=0;f_ch
=1;
103 door(sw
[i
].a
,sw
[i
].b
);
104 fldf
[sw
[i
].b
][sw
[i
].a
]=j
;
108 static int shutdoor(int i
) {
111 cht
=3;chto
=255;chf
=fldf
[sw
[i
].b
][sw
[i
].a
];f_ch
=1;
112 door(sw
[i
].a
,sw
[i
].b
);
114 if(Z_chktrap(0,0,-3,HIT_SOME
)) {
115 j
=fldf
[sw
[i
].b
][sw
[i
].a
];
117 door(sw
[i
].a
,sw
[i
].b
);
118 fldf
[sw
[i
].b
][sw
[i
].a
]=j
;
122 door(sw
[i
].a
,sw
[i
].b
);
124 swsnd
=Z_sound(sndbdc
,128);
132 for(i
=0;i
<MAXSW
;++i
) if(sw
[i
].t
) {
133 if(sw
[i
].tm
) --sw
[i
].tm
;
135 case SW_DOOR5
: case SW_DOOR
: case SW_SHUTDOOR
:
137 if(fld
[sw
[i
].b
][sw
[i
].a
]!=3) {sw
[i
].d
=0;break;}
138 if(--sw
[i
].d
==0) if(!shutdoor(i
)) sw
[i
].d
=9;
142 if(fld
[sw
[i
].b
][sw
[i
].a
]!=2) {sw
[i
].d
=0;break;}
143 if(--sw
[i
].d
==0) {opendoor(i
);sw
[i
].tm
=18;}
149 static int doortime(int t
) {
151 case SW_DOOR5
: return 90;
156 void SW_cheat_open (void) {
159 for(i
=0;i
<MAXSW
;++i
) if(sw
[i
].t
&& !sw
[i
].tm
) switch(sw
[i
].t
) {
160 case SW_DOOR
: case SW_DOOR5
:
162 if(fld
[sw
[i
].b
][sw
[i
].a
]!=2) break;
163 SW_press(sw
[i
].x
*CELW
+4,sw
[i
].y
*CELH
+4,1,1,0xFF,-3);
168 int SW_press (int x
, int y
, int r
, int h
, byte t
, int o
) {
171 sx
=(x
-r
)/CELW
;sy
=(y
-h
+1)/CELH
;
172 x
=(x
+r
)/CELW
;y
/=CELH
;
173 for(i
=p
=0;i
<MAXSW
;++i
) if(sw
[i
].t
&& !sw
[i
].tm
) {
174 if(sw
[i
].x
>=sx
&& sw
[i
].x
<=x
&& sw
[i
].y
>=sy
&& sw
[i
].y
<=y
&& ((sw
[i
].f
&0x8F)&t
)) {
175 if(sw
[i
].f
&0x70) if((sw
[i
].f
&(t
&0x70))!=(sw
[i
].f
&0x70)) continue;
178 g_exit
=1;sw
[i
].tm
=9;swsnd
=Z_sound(sndswx
,128);break;
180 g_exit
=2;sw
[i
].tm
=9;swsnd
=Z_sound(sndswx
,128);break;
181 case SW_DOOR
: case SW_DOOR5
:
182 switch(fld
[sw
[i
].b
][sw
[i
].a
]) {
184 opendoor(i
);sw
[i
].tm
=9;sw
[i
].d
=doortime(sw
[i
].t
);break;
186 if(shutdoor(i
)) {sw
[i
].tm
=9;sw
[i
].d
=0;}
188 if(!swsnd
) swsnd
=Z_sound(sndnoway
,128);
194 SW_press((dword
)sw
[i
].a
*8+4,(dword
)sw
[i
].b
*8+12,8,16,(t
&0x70)|0x80,o
);
198 if(!Z_canfit((dword
)sw
[i
].a
*8+4,(dword
)sw
[i
].b
*8+7,r
,h
)) {
199 if(!swsnd
) swsnd
=Z_sound(sndnotele
,128);
201 }Z_teleobj(o
,(dword
)sw
[i
].a
*8+4,(dword
)sw
[i
].b
*8+7);
205 if(fld
[sw
[i
].b
][sw
[i
].a
]!=2) break;
210 if(fld
[sw
[i
].b
][sw
[i
].a
]!=3) break;
211 if(shutdoor(i
)) {sw
[i
].tm
=1;sw
[i
].d
=0;}
213 if(!swsnd
) swsnd
=Z_sound(sndnoway
,128);
216 case SW_SHUTTRAP
: case SW_TRAP
:
217 if(fld
[sw
[i
].b
][sw
[i
].a
]!=3) break;
218 cht
=3;chto
=255;chf
=fldf
[sw
[i
].b
][sw
[i
].a
];f_ch
=1;
219 door(sw
[i
].a
,sw
[i
].b
);
220 Z_chktrap(1,100,-3,HIT_TRAP
);
222 door(sw
[i
].a
,sw
[i
].b
);
224 swsnd
=Z_sound(sndswn
,128);
225 sw
[i
].tm
=1;sw
[i
].d
=20;
228 if(fld
[sw
[i
].b
][sw
[i
].a
]==10) {
229 cht
=10;chto
=9;f_ch
=0;
230 }else if(fld
[sw
[i
].b
][sw
[i
].a
]==9) {
231 cht
=9;chto
=10;f_ch
=0;
233 door(sw
[i
].a
,sw
[i
].b
);
235 swsnd
=Z_sound(sndswx
,128);
239 if(fld
[sw
[i
].b
][sw
[i
].a
]!=10) break;
240 cht
=10;chto
=9;f_ch
=0;
241 door(sw
[i
].a
,sw
[i
].b
);
243 swsnd
=Z_sound(sndswx
,128);
247 if(fld
[sw
[i
].b
][sw
[i
].a
]!=9) break;
248 cht
=9;chto
=10;f_ch
=0;
249 door(sw
[i
].a
,sw
[i
].b
);
251 swsnd
=Z_sound(sndswx
,128);
255 if(o
!=-1 && o
!=-2) break;
256 if(o
==-1) ++pl1
.secrets
;
258 sw
[i
].tm
=1;sw
[i
].t
=0;break;
261 R_switch_texture(sw
[i
].x
, sw
[i
].y
);
264 if(sw
[i
].tm
==1) sw
[i
].tm
=0;