Mercurial > sdl-ios-xcode
annotate src/video/SDL_blit_0.c @ 1643:51038e80ae59
More general fix for bug #189
The clipping is done at a higher level, and the low level functions are
passed clipped rectangles. Drivers which don't support source clipping
have not been changed, so the image will be squished instead of clipped,
but at least they will no longer crash when the destination rect was out
of bounds.
author | Sam Lantinga <slouken@libsdl.org> |
---|---|
date | Mon, 17 Apr 2006 06:47:23 +0000 |
parents | d910939febfa |
children | 782fd950bd46 c121d94672cb a1b03ba2fcd0 |
rev | line source |
---|---|
0 | 1 /* |
2 SDL - Simple DirectMedia Layer | |
1312
c9b51268668f
Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents:
1058
diff
changeset
|
3 Copyright (C) 1997-2006 Sam Lantinga |
0 | 4 |
5 This library is free software; you can redistribute it and/or | |
1312
c9b51268668f
Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents:
1058
diff
changeset
|
6 modify it under the terms of the GNU Lesser General Public |
0 | 7 License as published by the Free Software Foundation; either |
1312
c9b51268668f
Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents:
1058
diff
changeset
|
8 version 2.1 of the License, or (at your option) any later version. |
0 | 9 |
10 This library is distributed in the hope that it will be useful, | |
11 but WITHOUT ANY WARRANTY; without even the implied warranty of | |
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
1312
c9b51268668f
Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents:
1058
diff
changeset
|
13 Lesser General Public License for more details. |
0 | 14 |
1312
c9b51268668f
Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents:
1058
diff
changeset
|
15 You should have received a copy of the GNU Lesser General Public |
c9b51268668f
Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents:
1058
diff
changeset
|
16 License along with this library; if not, write to the Free Software |
c9b51268668f
Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents:
1058
diff
changeset
|
17 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA |
0 | 18 |
19 Sam Lantinga | |
252
e8157fcb3114
Updated the source with the correct e-mail address
Sam Lantinga <slouken@libsdl.org>
parents:
91
diff
changeset
|
20 slouken@libsdl.org |
0 | 21 */ |
1402
d910939febfa
Use consistent identifiers for the various platforms we support.
Sam Lantinga <slouken@libsdl.org>
parents:
1358
diff
changeset
|
22 #include "SDL_config.h" |
0 | 23 |
24 #include "SDL_video.h" | |
25 #include "SDL_blit.h" | |
26 | |
27 /* Functions to blit from bitmaps to other surfaces */ | |
28 | |
29 static void BlitBto1(SDL_BlitInfo *info) | |
30 { | |
31 int c; | |
32 int width, height; | |
33 Uint8 *src, *map, *dst; | |
34 int srcskip, dstskip; | |
35 | |
36 /* Set up some basic variables */ | |
37 width = info->d_width; | |
38 height = info->d_height; | |
39 src = info->s_pixels; | |
40 srcskip = info->s_skip; | |
41 dst = info->d_pixels; | |
42 dstskip = info->d_skip; | |
43 map = info->table; | |
44 srcskip += width-(width+7)/8; | |
45 | |
46 if ( map ) { | |
47 while ( height-- ) { | |
48 Uint8 byte = 0, bit; | |
49 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
50 if ( (c&7) == 0 ) { |
0 | 51 byte = *src++; |
52 } | |
53 bit = (byte&0x80)>>7; | |
54 if ( 1 ) { | |
55 *dst = map[bit]; | |
56 } | |
57 dst++; | |
58 byte <<= 1; | |
59 } | |
60 src += srcskip; | |
61 dst += dstskip; | |
62 } | |
63 } else { | |
64 while ( height-- ) { | |
65 Uint8 byte = 0, bit; | |
66 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
67 if ( (c&7) == 0 ) { |
0 | 68 byte = *src++; |
69 } | |
70 bit = (byte&0x80)>>7; | |
71 if ( 1 ) { | |
72 *dst = bit; | |
73 } | |
74 dst++; | |
75 byte <<= 1; | |
76 } | |
77 src += srcskip; | |
78 dst += dstskip; | |
79 } | |
80 } | |
81 } | |
82 static void BlitBto2(SDL_BlitInfo *info) | |
83 { | |
84 int c; | |
85 int width, height; | |
86 Uint8 *src; | |
87 Uint16 *map, *dst; | |
88 int srcskip, dstskip; | |
89 | |
90 /* Set up some basic variables */ | |
91 width = info->d_width; | |
92 height = info->d_height; | |
93 src = info->s_pixels; | |
94 srcskip = info->s_skip; | |
95 dst = (Uint16 *)info->d_pixels; | |
96 dstskip = info->d_skip/2; | |
97 map = (Uint16 *)info->table; | |
98 srcskip += width-(width+7)/8; | |
99 | |
100 while ( height-- ) { | |
101 Uint8 byte = 0, bit; | |
102 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
103 if ( (c&7) == 0 ) { |
0 | 104 byte = *src++; |
105 } | |
106 bit = (byte&0x80)>>7; | |
107 if ( 1 ) { | |
108 *dst = map[bit]; | |
109 } | |
110 byte <<= 1; | |
111 dst++; | |
112 } | |
113 src += srcskip; | |
114 dst += dstskip; | |
115 } | |
116 } | |
117 static void BlitBto3(SDL_BlitInfo *info) | |
118 { | |
119 int c, o; | |
120 int width, height; | |
121 Uint8 *src, *map, *dst; | |
122 int srcskip, dstskip; | |
123 | |
124 /* Set up some basic variables */ | |
125 width = info->d_width; | |
126 height = info->d_height; | |
127 src = info->s_pixels; | |
128 srcskip = info->s_skip; | |
129 dst = info->d_pixels; | |
130 dstskip = info->d_skip; | |
131 map = info->table; | |
132 srcskip += width-(width+7)/8; | |
133 | |
134 while ( height-- ) { | |
135 Uint8 byte = 0, bit; | |
136 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
137 if ( (c&7) == 0 ) { |
0 | 138 byte = *src++; |
139 } | |
140 bit = (byte&0x80)>>7; | |
141 if ( 1 ) { | |
142 o = bit * 4; | |
143 dst[0] = map[o++]; | |
144 dst[1] = map[o++]; | |
145 dst[2] = map[o++]; | |
146 } | |
147 byte <<= 1; | |
148 dst += 3; | |
149 } | |
150 src += srcskip; | |
151 dst += dstskip; | |
152 } | |
153 } | |
154 static void BlitBto4(SDL_BlitInfo *info) | |
155 { | |
156 int width, height; | |
157 Uint8 *src; | |
158 Uint32 *map, *dst; | |
159 int srcskip, dstskip; | |
160 int c; | |
161 | |
162 /* Set up some basic variables */ | |
163 width = info->d_width; | |
164 height = info->d_height; | |
165 src = info->s_pixels; | |
166 srcskip = info->s_skip; | |
167 dst = (Uint32 *)info->d_pixels; | |
168 dstskip = info->d_skip/4; | |
169 map = (Uint32 *)info->table; | |
170 srcskip += width-(width+7)/8; | |
171 | |
172 while ( height-- ) { | |
173 Uint8 byte = 0, bit; | |
174 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
175 if ( (c&7) == 0 ) { |
0 | 176 byte = *src++; |
177 } | |
178 bit = (byte&0x80)>>7; | |
179 if ( 1 ) { | |
180 *dst = map[bit]; | |
181 } | |
182 byte <<= 1; | |
183 dst++; | |
184 } | |
185 src += srcskip; | |
186 dst += dstskip; | |
187 } | |
188 } | |
189 | |
190 static void BlitBto1Key(SDL_BlitInfo *info) | |
191 { | |
192 int width = info->d_width; | |
193 int height = info->d_height; | |
194 Uint8 *src = info->s_pixels; | |
195 Uint8 *dst = info->d_pixels; | |
196 int srcskip = info->s_skip; | |
197 int dstskip = info->d_skip; | |
198 Uint32 ckey = info->src->colorkey; | |
199 Uint8 *palmap = info->table; | |
200 int c; | |
201 | |
202 /* Set up some basic variables */ | |
203 srcskip += width-(width+7)/8; | |
204 | |
205 if ( palmap ) { | |
206 while ( height-- ) { | |
207 Uint8 byte = 0, bit; | |
208 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
209 if ( (c&7) == 0 ) { |
0 | 210 byte = *src++; |
211 } | |
212 bit = (byte&0x80)>>7; | |
213 if ( bit != ckey ) { | |
214 *dst = palmap[bit]; | |
215 } | |
216 dst++; | |
217 byte <<= 1; | |
218 } | |
219 src += srcskip; | |
220 dst += dstskip; | |
221 } | |
222 } else { | |
223 while ( height-- ) { | |
224 Uint8 byte = 0, bit; | |
225 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
226 if ( (c&7) == 0 ) { |
0 | 227 byte = *src++; |
228 } | |
229 bit = (byte&0x80)>>7; | |
230 if ( bit != ckey ) { | |
231 *dst = bit; | |
232 } | |
233 dst++; | |
234 byte <<= 1; | |
235 } | |
236 src += srcskip; | |
237 dst += dstskip; | |
238 } | |
239 } | |
240 } | |
241 | |
242 static void BlitBto2Key(SDL_BlitInfo *info) | |
243 { | |
244 int width = info->d_width; | |
245 int height = info->d_height; | |
246 Uint8 *src = info->s_pixels; | |
247 Uint16 *dstp = (Uint16 *)info->d_pixels; | |
248 int srcskip = info->s_skip; | |
249 int dstskip = info->d_skip; | |
250 Uint32 ckey = info->src->colorkey; | |
251 Uint8 *palmap = info->table; | |
252 int c; | |
253 | |
254 /* Set up some basic variables */ | |
255 srcskip += width-(width+7)/8; | |
256 dstskip /= 2; | |
257 | |
258 while ( height-- ) { | |
259 Uint8 byte = 0, bit; | |
260 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
261 if ( (c&7) == 0 ) { |
0 | 262 byte = *src++; |
263 } | |
264 bit = (byte&0x80)>>7; | |
265 if ( bit != ckey ) { | |
266 *dstp=((Uint16 *)palmap)[bit]; | |
267 } | |
268 byte <<= 1; | |
269 dstp++; | |
270 } | |
271 src += srcskip; | |
272 dstp += dstskip; | |
273 } | |
274 } | |
275 | |
276 static void BlitBto3Key(SDL_BlitInfo *info) | |
277 { | |
278 int width = info->d_width; | |
279 int height = info->d_height; | |
280 Uint8 *src = info->s_pixels; | |
281 Uint8 *dst = info->d_pixels; | |
282 int srcskip = info->s_skip; | |
283 int dstskip = info->d_skip; | |
284 Uint32 ckey = info->src->colorkey; | |
285 Uint8 *palmap = info->table; | |
286 int c; | |
287 | |
288 /* Set up some basic variables */ | |
289 srcskip += width-(width+7)/8; | |
290 | |
291 while ( height-- ) { | |
292 Uint8 byte = 0, bit; | |
293 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
294 if ( (c&7) == 0 ) { |
0 | 295 byte = *src++; |
296 } | |
297 bit = (byte&0x80)>>7; | |
298 if ( bit != ckey ) { | |
1336
3692456e7b0f
Use SDL_ prefixed versions of C library functions.
Sam Lantinga <slouken@libsdl.org>
parents:
1330
diff
changeset
|
299 SDL_memcpy(dst, &palmap[bit*4], 3); |
0 | 300 } |
301 byte <<= 1; | |
302 dst += 3; | |
303 } | |
304 src += srcskip; | |
305 dst += dstskip; | |
306 } | |
307 } | |
308 | |
309 static void BlitBto4Key(SDL_BlitInfo *info) | |
310 { | |
311 int width = info->d_width; | |
312 int height = info->d_height; | |
313 Uint8 *src = info->s_pixels; | |
314 Uint32 *dstp = (Uint32 *)info->d_pixels; | |
315 int srcskip = info->s_skip; | |
316 int dstskip = info->d_skip; | |
317 Uint32 ckey = info->src->colorkey; | |
318 Uint8 *palmap = info->table; | |
319 int c; | |
320 | |
321 /* Set up some basic variables */ | |
322 srcskip += width-(width+7)/8; | |
323 dstskip /= 4; | |
324 | |
325 while ( height-- ) { | |
326 Uint8 byte = 0, bit; | |
327 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
328 if ( (c&7) == 0 ) { |
0 | 329 byte = *src++; |
330 } | |
331 bit = (byte&0x80)>>7; | |
332 if ( bit != ckey ) { | |
333 *dstp=((Uint32 *)palmap)[bit]; | |
334 } | |
335 byte <<= 1; | |
336 dstp++; | |
337 } | |
338 src += srcskip; | |
339 dstp += dstskip; | |
340 } | |
341 } | |
342 | |
343 static void BlitBtoNAlpha(SDL_BlitInfo *info) | |
344 { | |
345 int width = info->d_width; | |
346 int height = info->d_height; | |
347 Uint8 *src = info->s_pixels; | |
348 Uint8 *dst = info->d_pixels; | |
349 int srcskip = info->s_skip; | |
350 int dstskip = info->d_skip; | |
351 const SDL_Color *srcpal = info->src->palette->colors; | |
352 SDL_PixelFormat *dstfmt = info->dst; | |
353 int dstbpp; | |
354 int c; | |
355 const int A = info->src->alpha; | |
356 | |
357 /* Set up some basic variables */ | |
358 dstbpp = dstfmt->BytesPerPixel; | |
359 srcskip += width-(width+7)/8; | |
360 | |
361 while ( height-- ) { | |
362 Uint8 byte = 0, bit; | |
363 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
364 if ( (c&7) == 0 ) { |
0 | 365 byte = *src++; |
366 } | |
367 bit = (byte&0x80)>>7; | |
368 if ( 1 ) { | |
369 Uint32 pixel; | |
370 unsigned sR, sG, sB; | |
371 unsigned dR, dG, dB; | |
372 sR = srcpal[bit].r; | |
373 sG = srcpal[bit].g; | |
374 sB = srcpal[bit].b; | |
375 DISEMBLE_RGB(dst, dstbpp, dstfmt, | |
376 pixel, dR, dG, dB); | |
377 ALPHA_BLEND(sR, sG, sB, A, dR, dG, dB); | |
378 ASSEMBLE_RGB(dst, dstbpp, dstfmt, dR, dG, dB); | |
379 } | |
380 byte <<= 1; | |
381 dst += dstbpp; | |
382 } | |
383 src += srcskip; | |
384 dst += dstskip; | |
385 } | |
386 } | |
387 | |
388 static void BlitBtoNAlphaKey(SDL_BlitInfo *info) | |
389 { | |
390 int width = info->d_width; | |
391 int height = info->d_height; | |
392 Uint8 *src = info->s_pixels; | |
393 Uint8 *dst = info->d_pixels; | |
394 int srcskip = info->s_skip; | |
395 int dstskip = info->d_skip; | |
396 SDL_PixelFormat *srcfmt = info->src; | |
397 SDL_PixelFormat *dstfmt = info->dst; | |
398 const SDL_Color *srcpal = srcfmt->palette->colors; | |
399 int dstbpp; | |
400 int c; | |
401 const int A = srcfmt->alpha; | |
402 Uint32 ckey = srcfmt->colorkey; | |
403 | |
404 /* Set up some basic variables */ | |
405 dstbpp = dstfmt->BytesPerPixel; | |
406 srcskip += width-(width+7)/8; | |
407 | |
408 while ( height-- ) { | |
409 Uint8 byte = 0, bit; | |
410 for ( c=0; c<width; ++c ) { | |
91
e85e03f195b4
From: "Markus F.X.J. Oberhumer"
Sam Lantinga <slouken@lokigames.com>
parents:
0
diff
changeset
|
411 if ( (c&7) == 0 ) { |
0 | 412 byte = *src++; |
413 } | |
414 bit = (byte&0x80)>>7; | |
415 if ( bit != ckey ) { | |
416 int sR, sG, sB; | |
417 int dR, dG, dB; | |
418 Uint32 pixel; | |
419 sR = srcpal[bit].r; | |
420 sG = srcpal[bit].g; | |
421 sB = srcpal[bit].b; | |
422 DISEMBLE_RGB(dst, dstbpp, dstfmt, | |
423 pixel, dR, dG, dB); | |
424 ALPHA_BLEND(sR, sG, sB, A, dR, dG, dB); | |
425 ASSEMBLE_RGB(dst, dstbpp, dstfmt, dR, dG, dB); | |
426 } | |
427 byte <<= 1; | |
428 dst += dstbpp; | |
429 } | |
430 src += srcskip; | |
431 dst += dstskip; | |
432 } | |
433 } | |
434 | |
435 static SDL_loblit bitmap_blit[] = { | |
436 NULL, BlitBto1, BlitBto2, BlitBto3, BlitBto4 | |
437 }; | |
438 | |
439 static SDL_loblit colorkey_blit[] = { | |
440 NULL, BlitBto1Key, BlitBto2Key, BlitBto3Key, BlitBto4Key | |
441 }; | |
442 | |
443 SDL_loblit SDL_CalculateBlit0(SDL_Surface *surface, int blit_index) | |
444 { | |
445 int which; | |
446 | |
1058 | 447 if ( surface->format->BitsPerPixel != 1 ) { |
1057
e9d23bb80140
Date: Mon, 02 May 2005 04:23:16 -0500
Sam Lantinga <slouken@libsdl.org>
parents:
769
diff
changeset
|
448 /* We don't support sub 8-bit packed pixel modes */ |
e9d23bb80140
Date: Mon, 02 May 2005 04:23:16 -0500
Sam Lantinga <slouken@libsdl.org>
parents:
769
diff
changeset
|
449 return NULL; |
e9d23bb80140
Date: Mon, 02 May 2005 04:23:16 -0500
Sam Lantinga <slouken@libsdl.org>
parents:
769
diff
changeset
|
450 } |
0 | 451 if ( surface->map->dst->format->BitsPerPixel < 8 ) { |
452 which = 0; | |
453 } else { | |
454 which = surface->map->dst->format->BytesPerPixel; | |
455 } | |
456 switch(blit_index) { | |
457 case 0: /* copy */ | |
458 return bitmap_blit[which]; | |
459 | |
460 case 1: /* colorkey */ | |
461 return colorkey_blit[which]; | |
462 | |
463 case 2: /* alpha */ | |
464 return which >= 2 ? BlitBtoNAlpha : NULL; | |
465 | |
466 case 4: /* alpha + colorkey */ | |
467 return which >= 2 ? BlitBtoNAlphaKey : NULL; | |
468 } | |
469 return NULL; | |
470 } | |
471 |