Freeciv-3.2
Loading...
Searching...
No Matches
graphics.h
Go to the documentation of this file.
1/***********************************************************************
2 Freeciv - Copyright (C) 1996 - A Kjeldberg, L Gregersen, P Unold
3 This program is free software; you can redistribute it and/or modify
4 it under the terms of the GNU General Public License as published by
5 the Free Software Foundation; either version 2, or (at your option)
6 any later version.
7
8 This program is distributed in the hope that it will be useful,
9 but WITHOUT ANY WARRANTY; without even the implied warranty of
10 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 GNU General Public License for more details.
12***********************************************************************/
13
14/***********************************************************************
15 graphics.h - description
16 -------------------
17 begin : Mon Jul 1 2002
18 copyright : (C) 2000 by Michael Speck
19 : (C) 2002 by Rafał Bursig
20 email : Michael Speck <kulkanie@gmx.net>
21 : Rafał Bursig <bursig@poczta.fm>
22***********************************************************************/
23
24#ifndef FC__GRAPHICS_H
25#define FC__GRAPHICS_H
26
27/* SDL3 */
29
30/* client */
31#include "graphics_g.h"
32
33/* gui-sdl3 */
34#include "canvas.h"
35#include "gui_main.h"
36
37#define RECT_LIMIT 80
38
39/* DUFFS LOOPs come from SDL lib (LGPL) */
40/* DUFFS_LOOP_DOUBLE2 and DUFFS_LOOP_QUATRO2 was created by Rafal Bursig under GPL */
41
42/* This is a very useful loop for optimizing blitters */
43#if defined(_MSC_VER) && (_MSC_VER == 1300)
44/* There's a bug in the Visual C++ 7 optimizer when compiling this code */
45#else
46#define USE_DUFFS_LOOP
47#endif
48
49#ifdef USE_DUFFS_LOOP
50
51/* 8-times unrolled loop */
52#define DUFFS_LOOP8(pixel_copy_increment, width) \
53{ int n = (width + 7) / 8; \
54 switch (width & 7) { \
55 case 0: do { pixel_copy_increment; \
56 fc__fallthrough; \
57 case 7: pixel_copy_increment; \
58 fc__fallthrough; \
59 case 6: pixel_copy_increment; \
60 fc__fallthrough; \
61 case 5: pixel_copy_increment; \
62 fc__fallthrough; \
63 case 4: pixel_copy_increment; \
64 fc__fallthrough; \
65 case 3: pixel_copy_increment; \
66 fc__fallthrough; \
67 case 2: pixel_copy_increment; \
68 fc__fallthrough; \
69 case 1: pixel_copy_increment; \
70 } while ( --n > 0 ); \
71 } \
72}
73
74/* 4-times unrolled loop */
75#define DUFFS_LOOP4(pixel_copy_increment, width) \
76{ int n = (width + 3) / 4; \
77 switch (width & 3) { \
78 case 0: do { pixel_copy_increment; \
79 fc__fallthrough; \
80 case 3: pixel_copy_increment; \
81 fc__fallthrough; \
82 case 2: pixel_copy_increment; \
83 fc__fallthrough; \
84 case 1: pixel_copy_increment; \
85 } while ( --n > 0 ); \
86 } \
87}
88
89/* 2 - times unrolled loop */
90#define DUFFS_LOOP_DOUBLE2(pixel_copy_increment, \
91 double_pixel_copy_increment, width) \
92{ int n, w = width; \
93 if ( w & 1 ) { \
94 pixel_copy_increment; \
95 w--; \
96 } \
97 if ( w > 0 ) { \
98 n = ( w + 2 ) / 4; \
99 switch ( w & 2 ) { \
100 case 0: do { double_pixel_copy_increment; \
101 fc__fallthrough; \
102 case 2: double_pixel_copy_increment; \
103 } while ( --n > 0 ); \
104 } \
105 } \
106}
107
108/* 2 - times unrolled loop 4 pixels */
109#define DUFFS_LOOP_QUATRO2(pixel_copy_increment, \
110 double_pixel_copy_increment, \
111 quatro_pixel_copy_increment, width) \
112{ int n, w = width; \
113 if (w & 1) { \
114 pixel_copy_increment; \
115 w--; \
116 } \
117 if (w & 2) { \
118 double_pixel_copy_increment; \
119 w -= 2; \
120 } \
121 if ( w > 0 ) { \
122 n = ( w + 7 ) / 8; \
123 switch ( w & 4 ) { \
124 case 0: do { quatro_pixel_copy_increment; \
125 case 4: quatro_pixel_copy_increment; \
126 } while ( --n > 0 ); \
127 } \
128 } \
129}
130
131/* Use the 8-times version of the loop by default */
132#define DUFFS_LOOP(pixel_copy_increment, width) \
133 DUFFS_LOOP8(pixel_copy_increment, width)
134
135#else
136
137/* Don't use Duff's device to unroll loops */
138#define DUFFS_LOOP_DOUBLE2(pixel_copy_increment, \
139 double_pixel_copy_increment, width) \
140{ int n = width; \
141 if ( n & 1 ) { \
142 pixel_copy_increment; \
143 n--; \
144 } \
145 for (; n > 0; --n) { \
146 double_pixel_copy_increment; \
147 n--; \
148 } \
149}
150
151/* Don't use Duff's device to unroll loops */
152#define DUFFS_LOOP_QUATRO2(pixel_copy_increment, \
153 double_pixel_copy_increment, \
154 quatro_pixel_copy_increment, width) \
155{ int n = width; \
156 if (n & 1) { \
157 pixel_copy_increment; \
158 n--; \
159 } \
160 if (n & 2) { \
161 double_pixel_copy_increment; \
162 n -= 2; \
163 } \
164 for (; n > 0; --n) { \
165 quatro_pixel_copy_increment; \
166 n -= 3; \
167 } \
168}
169
170/* Don't use Duff's device to unroll loops */
171#define DUFFS_LOOP(pixel_copy_increment, width) \
172{ int n; \
173 for ( n=width; n > 0; --n ) { \
174 pixel_copy_increment; \
175 } \
176}
177
178#define DUFFS_LOOP8(pixel_copy_increment, width) \
179 DUFFS_LOOP(pixel_copy_increment, width)
180#define DUFFS_LOOP4(pixel_copy_increment, width) \
181 DUFFS_LOOP(pixel_copy_increment, width)
182
183#endif /* USE_DUFFS_LOOP */
184
185/* Shrink surface on 320x240 screen */
186#ifdef SMALL_SCREEN
187#define DEFAULT_ZOOM 0.5
188#define adj_surf(surf) zoomSurface((surf), DEFAULT_ZOOM, DEFAULT_ZOOM, 0)
189#else
190#define DEFAULT_ZOOM 1.0
191/* Cannot return the original as callers free what we return */
192#define adj_surf(surf) copy_surface(surf)
193#endif
194
195struct gui_layer;
196
197struct sdl3_data {
198 int rects_count; /* Update rect. array counter */
199 int guis_count; /* Gui buffers array counter */
200 SDL_Rect rects[RECT_LIMIT]; /* Update rect. list */
201 SDL_Window *screen; /* Main screen buffer */
202 SDL_Surface *map; /* Map buffer */
203 SDL_Surface *dummy; /* Dummy surface for missing sprites */
207 struct gui_layer *gui; /* Gui buffer */
208 struct gui_layer **guis; /* Gui buffers used by sdl3-client widgets window menager */
209 SDL_Event event; /* Main event struct */
210};
211
212extern struct sdl3_data main_data;
213
214/* GUI layer */
215/* A gui_layer is a surface with its own origin. Each widget belongs
216 * to a gui_layer. gui_layers are stored in an array main_data.guis
217 * (a "window manager"). */
218
219struct gui_layer {
220 SDL_Rect dest_rect; /* origin: only x and y are used */
222};
223
224struct gui_layer *gui_layer_new(int x, int y, SDL_Surface *surface);
226
228
229struct gui_layer *add_gui_layer(int width, int height);
231
234
235/* ---------- */
236
239 unsigned char alpha_mod);
241 unsigned char alpha_mod);
242
243SDL_Surface *load_surf(const char *fname);
244
246 int width, int height);
249
251
253 SDL_Rect *prect);
254
257
259
262
265
266void create_frame(SDL_Surface *dest, Sint16 left, Sint16 top,
267 Sint16 right, Sint16 bottom,
269
272
273/* SDL */
274void init_sdl(int f);
275void quit_sdl(void);
276bool set_video_mode(unsigned width, unsigned height, unsigned flags);
277bool create_surfaces(int width, int height);
278
279void update_main_screen(void);
280
281int main_window_width(void);
282int main_window_height(void);
283
284/* Rect */
286bool is_in_rect_area(int x, int y, const SDL_Rect *rect);
287
290
292
293/* ================================================================= */
294
297
300 int smooth, bool scale_up,
302
305
306#define map_rgba_details(details, color) \
307 SDL_MapRGBA(details, NULL, (color).r, (color).g, (color).b, (color).a)
308#define map_rgba(format, color) \
309 map_rgba_details(SDL_GetPixelFormatDetails(format), color)
310
311#define crop_rect_from_screen(rect) \
312 crop_rect_from_surface(main_data.screen, &rect)
313
314/* Free surface with check and clear pointer */
315#define FREESURFACE(ptr) \
316do { \
317 if (ptr) { \
318 SDL_DestroySurface(ptr); \
319 ptr = NULL; \
320 } \
321} while (FALSE)
322
323/*
324 * Lock surface
325 */
326#define lock_surf(surf) \
327do { \
328 if (SDL_MUSTLOCK(surf)) { \
329 SDL_LockSurface(surf); \
330 } \
331} while (FALSE)
332
333
334/*
335 * Unlock surface
336 */
337#define unlock_surf(surf) \
338do { \
339 if (SDL_MUSTLOCK(surf)) { \
340 SDL_UnlockSurface(surf); \
341 } \
342} while (FALSE)
343
344/*
345 * Lock screen surface
346 */
347#define lock_screen() lock_surf(main_data.screen)
348
349/*
350 * Unlock screen surface
351 */
352#define unlock_screen() unlock_surf(main_data.screen)
353
354#define putpixel(surf, x, y, pixel) \
355do { \
356 Uint8 *buf_ptr = ((Uint8 *)surf->pixels + (y * surf->pitch)); \
357 switch (surf->format->BytesPerPixel) { \
358 case 1: \
359 buf_ptr += x; \
360 *(Uint8 *)buf_ptr = pixel; \
361 break; \
362 case 2: \
363 buf_ptr += x << 1; \
364 *((Uint16 *)buf_ptr) = pixel; \
365 break; \
366 case 3: \
367 buf_ptr += (x << 1) + x; \
368 if (is_bigendian()) { \
369 buf_ptr[0] = (pixel >> 16) & 0xff; \
370 buf_ptr[1] = (pixel >> 8) & 0xff; \
371 buf_ptr[2] = pixel & 0xff; \
372 } else { \
373 buf_ptr[0] = pixel & 0xff; \
374 buf_ptr[1] = (pixel >> 8) & 0xff; \
375 buf_ptr[2] = (pixel >> 16) & 0xff; \
376 } \
377 break; \
378 case 4: \
379 buf_ptr += x << 2; \
380 *((Uint32 *)buf_ptr) = pixel; \
381 break; \
382 } \
383} while (FALSE)
384
385/* Blend the RGB values of two pixels based on a source alpha value */
386#define ALPHA_BLEND(sR, sG, sB, A, dR, dG, dB) \
387do { \
388 dR = (((sR-dR)*(A))>>8)+dR; \
389 dG = (((sG-dG)*(A))>>8)+dG; \
390 dB = (((sB-dB)*(A))>>8)+dB; \
391} while (FALSE)
392
393#define ALPHA_BLEND128(sR, sG, sB, dR, dG, dB) \
394do { \
395 Uint32 __Src = (sR << 16 | sG << 8 | sB); \
396 Uint32 __Dst = (dR << 16 | dG << 8 | dB); \
397 __Dst = ((((__Src & 0x00fefefe) + (__Dst & 0x00fefefe)) >> 1) \
398 + (__Src & __Dst & 0x00010101)) | 0xFF000000; \
399 dR = (__Dst >> 16) & 0xFF; \
400 dG = (__Dst >> 8 ) & 0xFF; \
401 dB = (__Dst ) & 0xFF; \
402} while (FALSE)
403
404#endif /* FC__GRAPHICS_H */
struct canvas int int struct sprite int int int int height
Definition canvas_g.h:44
struct canvas int int int int struct sprite *sprite struct canvas struct color * pcolor
Definition canvas_g.h:56
struct canvas int int struct sprite int int int width
Definition canvas_g.h:44
char * incite_cost
Definition comments.c:75
SDL_Surface * resize_surface(const SDL_Surface *psrc, Uint16 new_width, Uint16 new_height, int smooth)
Definition graphics.c:1237
int main_window_width(void)
Definition graphics.c:685
void layer_rect_to_screen_rect(struct gui_layer *gui_layer, SDL_Rect *dest_rect)
Definition graphics.c:185
SDL_Surface * load_surf(const char *fname)
Definition graphics.c:307
SDL_Surface * create_surf_with_format(SDL_PixelFormat *pf, int width, int height, Uint32 flags)
Definition graphics.c:328
void update_main_screen(void)
Definition graphics.c:669
void remove_gui_layer(struct gui_layer *gui_layer)
Definition graphics.c:148
SDL_Surface * create_filled_surface(Uint16 w, Uint16 h, Uint32 flags, SDL_Color *pcolor)
Definition graphics.c:368
int fill_rect_alpha(SDL_Surface *surf, SDL_Rect *prect, SDL_Color *pcolor)
Definition graphics.c:865
void gui_layer_destroy(struct gui_layer **gui_layer)
Definition graphics.c:81
void create_line(SDL_Surface *dest, Sint16 x0, Sint16 y0, Sint16 x1, Sint16 y1, SDL_Color *pcolor)
Definition graphics.c:1379
SDL_Surface * copy_surface(SDL_Surface *src)
Definition graphics.c:1309
bool set_video_mode(unsigned width, unsigned height, unsigned flags)
Definition graphics.c:636
SDL_Surface * mask_surface(SDL_Surface *src, SDL_Surface *mask, int mask_offset_x, int mask_offset_y)
Definition graphics.c:262
struct gui_layer * gui_layer_new(int x, int y, SDL_Surface *surface)
Definition graphics.c:66
void quit_sdl(void)
Definition graphics.c:622
SDL_Surface * crop_visible_part_from_surface(SDL_Surface *psrc)
Definition graphics.c:1225
SDL_Surface * crop_rect_from_surface(SDL_Surface *psource, SDL_Rect *prect)
Definition graphics.c:236
void init_sdl(int f)
Definition graphics.c:506
int alphablit(SDL_Surface *src, SDL_Rect *srcrect, SDL_Surface *dst, SDL_Rect *dstrect, unsigned char alpha_mod)
Definition graphics.c:199
void create_frame(SDL_Surface *dest, Sint16 left, Sint16 top, Sint16 right, Sint16 bottom, SDL_Color *pcolor)
Definition graphics.c:1348
struct gui_layer * get_gui_layer(SDL_Surface *surface)
Definition graphics.c:90
bool is_in_rect_area(int x, int y, const SDL_Rect *rect)
Definition graphics.c:925
int screen_blit(SDL_Surface *src, SDL_Rect *srcrect, SDL_Rect *dstrect, unsigned char alpha_mod)
Definition graphics.c:223
struct sdl2_data main_data
Definition graphics.c:57
int blit_entire_src(SDL_Surface *psrc, SDL_Surface *pdest, Sint16 dest_x, Sint16 dest_y)
Definition graphics.c:417
Uint32 get_first_pixel(SDL_Surface *surf)
Definition graphics.c:468
SDL_Surface * convert_surf(SDL_Surface *surf_in)
Definition graphics.c:359
SDL_Surface * create_surf(int width, int height, Uint32 flags)
Definition graphics.c:351
void get_smaller_surface_rect(SDL_Surface *surf, SDL_Rect *rect)
Definition graphics.c:936
struct gui_layer * add_gui_layer(int width, int height)
Definition graphics.c:112
int clear_surface(SDL_Surface *surf, SDL_Rect *dstrect)
Definition graphics.c:400
bool correct_rect_region(SDL_Rect *prect)
Definition graphics.c:888
void screen_rect_to_layer_rect(struct gui_layer *gui_layer, SDL_Rect *dest_rect)
Definition graphics.c:173
bool create_surfaces(int width, int height)
Definition graphics.c:556
int main_window_height(void)
Definition graphics.c:693
SDL_Surface * resize_surface_box(const SDL_Surface *psrc, Uint16 new_width, Uint16 new_height, int smooth, bool scale_up, bool absolute_dimensions)
Definition graphics.c:1257
Uint32 get_pixel(SDL_Surface *surf, Sint16 x, Sint16 y)
Definition graphics.c:430
#define RECT_LIMIT
Definition graphics.h:37
struct sprite int int int int struct sprite * mask
Definition sprite_g.h:32
struct sprite int int y
Definition sprite_g.h:31
struct sprite int int int int struct sprite int mask_offset_x
Definition sprite_g.h:32
struct sprite int x
Definition sprite_g.h:31
struct sprite int int int int struct sprite int int mask_offset_y
Definition sprite_g.h:32
SDL_Surface * surface
Definition graphics.h:229
SDL_Rect dest_rect
Definition graphics.h:228
struct gui_layer ** guis
Definition graphics.h:208
int guis_count
Definition graphics.h:199
struct canvas map_canvas
Definition graphics.h:206
SDL_Rect rects[RECT_LIMIT]
Definition graphics.h:200
SDL_Renderer * renderer
Definition graphics.h:205
SDL_Event event
Definition graphics.h:209
SDL_Window * screen
Definition graphics.h:201
SDL_Surface * map
Definition graphics.h:202
SDL_Texture * maintext
Definition graphics.h:204
struct gui_layer * gui
Definition graphics.h:207
int rects_count
Definition graphics.h:198
SDL_Surface * dummy
Definition graphics.h:203