diff options
Diffstat (limited to 'src/f_wipe.c')
-rw-r--r-- | src/f_wipe.c | 202 |
1 files changed, 202 insertions, 0 deletions
diff --git a/src/f_wipe.c b/src/f_wipe.c new file mode 100644 index 0000000..fc3ac1d --- /dev/null +++ b/src/f_wipe.c | |||
@@ -0,0 +1,202 @@ | |||
1 | /* Emacs style mode select -*- C++ -*- | ||
2 | *----------------------------------------------------------------------------- | ||
3 | * | ||
4 | * | ||
5 | * PrBoom: a Doom port merged with LxDoom and LSDLDoom | ||
6 | * based on BOOM, a modified and improved DOOM engine | ||
7 | * Copyright (C) 1999 by | ||
8 | * id Software, Chi Hoang, Lee Killough, Jim Flynn, Rand Phares, Ty Halderman | ||
9 | * Copyright (C) 1999-2000 by | ||
10 | * Jess Haas, Nicolas Kalkhof, Colin Phipps, Florian Schulze | ||
11 | * Copyright 2005, 2006 by | ||
12 | * Florian Schulze, Colin Phipps, Neil Stevens, Andrey Budko | ||
13 | * | ||
14 | * This program is free software; you can redistribute it and/or | ||
15 | * modify it under the terms of the GNU General Public License | ||
16 | * as published by the Free Software Foundation; either version 2 | ||
17 | * of the License, or (at your option) any later version. | ||
18 | * | ||
19 | * This program is distributed in the hope that it will be useful, | ||
20 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
21 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
22 | * GNU General Public License for more details. | ||
23 | * | ||
24 | * You should have received a copy of the GNU General Public License | ||
25 | * along with this program; if not, write to the Free Software | ||
26 | * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA | ||
27 | * 02111-1307, USA. | ||
28 | * | ||
29 | * DESCRIPTION: | ||
30 | * Mission begin melt/wipe screen special effect. | ||
31 | * | ||
32 | *----------------------------------------------------------------------------- | ||
33 | */ | ||
34 | |||
35 | |||
36 | #ifdef HAVE_CONFIG_H | ||
37 | #include "config.h" | ||
38 | #endif | ||
39 | |||
40 | #include "z_zone.h" | ||
41 | #include "doomdef.h" | ||
42 | #include "i_video.h" | ||
43 | #include "v_video.h" | ||
44 | #include "m_random.h" | ||
45 | #include "f_wipe.h" | ||
46 | |||
47 | // | ||
48 | // SCREEN WIPE PACKAGE | ||
49 | // | ||
50 | |||
51 | // Parts re-written to support true-color video modes. Column-major | ||
52 | // formatting removed. - POPE | ||
53 | |||
54 | // CPhipps - macros for the source and destination screens | ||
55 | #define SRC_SCR 2 | ||
56 | #define DEST_SCR 3 | ||
57 | |||
58 | static screeninfo_t wipe_scr_start; | ||
59 | static screeninfo_t wipe_scr_end; | ||
60 | static screeninfo_t wipe_scr; | ||
61 | |||
62 | static int y_lookup[MAX_SCREENWIDTH]; | ||
63 | |||
64 | |||
65 | static int wipe_initMelt(int ticks) | ||
66 | { | ||
67 | int i; | ||
68 | |||
69 | // copy start screen to main screen | ||
70 | for(i=0;i<SCREENHEIGHT;i++) | ||
71 | memcpy(wipe_scr.data+i*wipe_scr.byte_pitch, | ||
72 | wipe_scr_start.data+i*wipe_scr.byte_pitch, | ||
73 | SCREENWIDTH*V_GetPixelDepth()); | ||
74 | |||
75 | // setup initial column positions (y<0 => not ready to scroll yet) | ||
76 | y_lookup[0] = -(M_Random()%16); | ||
77 | for (i=1;i<SCREENWIDTH;i++) | ||
78 | { | ||
79 | int r = (M_Random()%3) - 1; | ||
80 | y_lookup[i] = y_lookup[i-1] + r; | ||
81 | if (y_lookup[i] > 0) | ||
82 | y_lookup[i] = 0; | ||
83 | else | ||
84 | if (y_lookup[i] == -16) | ||
85 | y_lookup[i] = -15; | ||
86 | } | ||
87 | return 0; | ||
88 | } | ||
89 | |||
90 | static int wipe_doMelt(int ticks) | ||
91 | { | ||
92 | boolean done = true; | ||
93 | int i; | ||
94 | const int depth = V_GetPixelDepth(); | ||
95 | |||
96 | while (ticks--) { | ||
97 | for (i=0;i<(SCREENWIDTH);i++) { | ||
98 | if (y_lookup[i]<0) { | ||
99 | y_lookup[i]++; | ||
100 | done = false; | ||
101 | continue; | ||
102 | } | ||
103 | if (y_lookup[i] < SCREENHEIGHT) { | ||
104 | byte *s, *d; | ||
105 | int j, k, dy; | ||
106 | |||
107 | /* cph 2001/07/29 - | ||
108 | * The original melt rate was 8 pixels/sec, i.e. 25 frames to melt | ||
109 | * the whole screen, so make the melt rate depend on SCREENHEIGHT | ||
110 | * so it takes no longer in high res | ||
111 | */ | ||
112 | dy = (y_lookup[i] < 16) ? y_lookup[i]+1 : SCREENHEIGHT/25; | ||
113 | if (y_lookup[i]+dy >= SCREENHEIGHT) | ||
114 | dy = SCREENHEIGHT - y_lookup[i]; | ||
115 | |||
116 | s = wipe_scr_end.data + (y_lookup[i]*wipe_scr_end.byte_pitch+(i*depth)); | ||
117 | d = wipe_scr.data + (y_lookup[i]*wipe_scr.byte_pitch+(i*depth)); | ||
118 | for (j=dy;j;j--) { | ||
119 | for (k=0; k<depth; k++) | ||
120 | d[k] = s[k]; | ||
121 | d += wipe_scr.byte_pitch; | ||
122 | s += wipe_scr_end.byte_pitch; | ||
123 | } | ||
124 | y_lookup[i] += dy; | ||
125 | s = wipe_scr_start.data + (i*depth); | ||
126 | d = wipe_scr.data + (y_lookup[i]*wipe_scr.byte_pitch+(i*depth)); | ||
127 | for (j=SCREENHEIGHT-y_lookup[i];j;j--) { | ||
128 | for (k=0; k<depth; k++) | ||
129 | d[k] = s[k]; | ||
130 | d += wipe_scr.byte_pitch; | ||
131 | s += wipe_scr_end.byte_pitch; | ||
132 | } | ||
133 | done = false; | ||
134 | } | ||
135 | } | ||
136 | } | ||
137 | return done; | ||
138 | } | ||
139 | |||
140 | // CPhipps - modified to allocate and deallocate screens[2 to 3] as needed, saving memory | ||
141 | |||
142 | static int wipe_exitMelt(int ticks) | ||
143 | { | ||
144 | V_FreeScreen(&wipe_scr_start); | ||
145 | wipe_scr_start.width = 0; | ||
146 | wipe_scr_start.height = 0; | ||
147 | V_FreeScreen(&wipe_scr_end); | ||
148 | wipe_scr_end.width = 0; | ||
149 | wipe_scr_end.height = 0; | ||
150 | // Paranoia | ||
151 | screens[SRC_SCR] = wipe_scr_start; | ||
152 | screens[DEST_SCR] = wipe_scr_end; | ||
153 | return 0; | ||
154 | } | ||
155 | |||
156 | int wipe_StartScreen(void) | ||
157 | { | ||
158 | wipe_scr_start.width = SCREENWIDTH; | ||
159 | wipe_scr_start.height = SCREENHEIGHT; | ||
160 | wipe_scr_start.byte_pitch = screens[0].byte_pitch; | ||
161 | wipe_scr_start.short_pitch = screens[0].short_pitch; | ||
162 | wipe_scr_start.int_pitch = screens[0].int_pitch; | ||
163 | wipe_scr_start.not_on_heap = false; | ||
164 | V_AllocScreen(&wipe_scr_start); | ||
165 | screens[SRC_SCR] = wipe_scr_start; | ||
166 | V_CopyRect(0, 0, 0, SCREENWIDTH, SCREENHEIGHT, 0, 0, SRC_SCR, VPT_NONE ); // Copy start screen to buffer | ||
167 | return 0; | ||
168 | } | ||
169 | |||
170 | int wipe_EndScreen(void) | ||
171 | { | ||
172 | wipe_scr_end.width = SCREENWIDTH; | ||
173 | wipe_scr_end.height = SCREENHEIGHT; | ||
174 | wipe_scr_end.byte_pitch = screens[0].byte_pitch; | ||
175 | wipe_scr_end.short_pitch = screens[0].short_pitch; | ||
176 | wipe_scr_end.int_pitch = screens[0].int_pitch; | ||
177 | wipe_scr_end.not_on_heap = false; | ||
178 | V_AllocScreen(&wipe_scr_end); | ||
179 | screens[DEST_SCR] = wipe_scr_end; | ||
180 | V_CopyRect(0, 0, 0, SCREENWIDTH, SCREENHEIGHT, 0, 0, DEST_SCR, VPT_NONE); // Copy end screen to buffer | ||
181 | V_CopyRect(0, 0, SRC_SCR, SCREENWIDTH, SCREENHEIGHT, 0, 0, 0 , VPT_NONE); // restore start screen | ||
182 | return 0; | ||
183 | } | ||
184 | |||
185 | // killough 3/5/98: reformatted and cleaned up | ||
186 | int wipe_ScreenWipe(int ticks) | ||
187 | { | ||
188 | static boolean go; // when zero, stop the wipe | ||
189 | if (!go) // initial stuff | ||
190 | { | ||
191 | go = 1; | ||
192 | wipe_scr = screens[0]; | ||
193 | wipe_initMelt(ticks); | ||
194 | } | ||
195 | // do a piece of wipe-in | ||
196 | if (wipe_doMelt(ticks)) // final stuff | ||
197 | { | ||
198 | wipe_exitMelt(ticks); | ||
199 | go = 0; | ||
200 | } | ||
201 | return !go; | ||
202 | } | ||