|
1 /* $Id$ */ |
|
2 |
|
3 #include "../../stdafx.h" |
|
4 #include "../../openttd.h" |
|
5 #include "../../variables.h" |
|
6 #include "../../macros.h" |
|
7 #include "../../debug.h" |
|
8 #include "../../functions.h" |
|
9 #include "../../gfx.h" |
|
10 #include "../../fileio.h" |
|
11 |
|
12 #include "splash.h" |
|
13 |
|
14 #ifdef WITH_PNG |
|
15 |
|
16 #include <png.h> |
|
17 |
|
18 static void PNGAPI png_my_error(png_structp png_ptr, png_const_charp message) |
|
19 { |
|
20 DEBUG(misc, 0, "[libpng] error: %s - %s", message, (char *)png_get_error_ptr(png_ptr)); |
|
21 longjmp(png_ptr->jmpbuf, 1); |
|
22 } |
|
23 |
|
24 static void PNGAPI png_my_warning(png_structp png_ptr, png_const_charp message) |
|
25 { |
|
26 DEBUG(misc, 1, "[libpng] warning: %s - %s", message, (char *)png_get_error_ptr(png_ptr)); |
|
27 } |
|
28 |
|
29 void DisplaySplashImage(void) |
|
30 { |
|
31 png_byte header[8]; |
|
32 FILE *f; |
|
33 png_structp png_ptr; |
|
34 png_infop info_ptr, end_info; |
|
35 uint width, height, bit_depth, color_type; |
|
36 png_colorp palette; |
|
37 int num_palette; |
|
38 png_bytep *row_pointers; |
|
39 uint8 *src, *dst; |
|
40 uint y; |
|
41 uint xoff, yoff; |
|
42 int i; |
|
43 |
|
44 f = FioFOpenFile(SPLASH_IMAGE_FILE); |
|
45 if (f == NULL) return; |
|
46 |
|
47 fread(header, 1, 8, f); |
|
48 if (png_sig_cmp(header, 0, 8) != 0) { |
|
49 fclose(f); |
|
50 return; |
|
51 } |
|
52 |
|
53 png_ptr = png_create_read_struct (PNG_LIBPNG_VER_STRING, (png_voidp) NULL, png_my_error, png_my_warning); |
|
54 |
|
55 if (png_ptr == NULL) { |
|
56 fclose(f); |
|
57 return; |
|
58 } |
|
59 |
|
60 info_ptr = png_create_info_struct(png_ptr); |
|
61 if (info_ptr == NULL) { |
|
62 png_destroy_read_struct(&png_ptr, (png_infopp)NULL, (png_infopp)NULL); |
|
63 fclose(f); |
|
64 return; |
|
65 } |
|
66 |
|
67 end_info = png_create_info_struct(png_ptr); |
|
68 if (end_info == NULL) { |
|
69 png_destroy_read_struct(&png_ptr, &info_ptr, (png_infopp)NULL); |
|
70 fclose(f); |
|
71 return; |
|
72 } |
|
73 |
|
74 if (setjmp(png_jmpbuf(png_ptr))) { |
|
75 png_destroy_read_struct(&png_ptr, &info_ptr, &end_info); |
|
76 fclose(f); |
|
77 return; |
|
78 } |
|
79 |
|
80 png_init_io(png_ptr, f); |
|
81 png_set_sig_bytes(png_ptr, 8); |
|
82 |
|
83 png_read_png(png_ptr, info_ptr, PNG_TRANSFORM_IDENTITY, NULL); |
|
84 |
|
85 width = png_get_image_width(png_ptr, info_ptr); |
|
86 height = png_get_image_height(png_ptr, info_ptr); |
|
87 bit_depth = png_get_bit_depth(png_ptr, info_ptr); |
|
88 color_type = png_get_color_type(png_ptr, info_ptr); |
|
89 |
|
90 if (color_type != PNG_COLOR_TYPE_PALETTE || bit_depth != 8) { |
|
91 png_destroy_read_struct(&png_ptr, &info_ptr, &end_info); |
|
92 fclose(f); |
|
93 return; |
|
94 } |
|
95 |
|
96 if (!png_get_valid(png_ptr, info_ptr, PNG_INFO_PLTE)) { |
|
97 png_destroy_read_struct(&png_ptr, &info_ptr, &end_info); |
|
98 fclose(f); |
|
99 return; |
|
100 } |
|
101 |
|
102 png_get_PLTE(png_ptr, info_ptr, &palette, &num_palette); |
|
103 |
|
104 row_pointers = png_get_rows(png_ptr, info_ptr); |
|
105 |
|
106 memset(_screen.dst_ptr, 0xff, _screen.pitch * _screen.height); |
|
107 |
|
108 if (width > (uint) _screen.width) width = _screen.width; |
|
109 if (height > (uint) _screen.height) height = _screen.height; |
|
110 |
|
111 xoff = (_screen.width - width) / 2; |
|
112 yoff = (_screen.height - height) / 2; |
|
113 for (y = 0; y < height; y++) { |
|
114 src = row_pointers[y]; |
|
115 dst = ((uint8 *) _screen.dst_ptr) + (yoff + y) * _screen.pitch + xoff; |
|
116 |
|
117 memcpy(dst, src, width); |
|
118 } |
|
119 |
|
120 for (i = 0; i < num_palette; i++) { |
|
121 _cur_palette[i].r = palette[i].red; |
|
122 _cur_palette[i].g = palette[i].green; |
|
123 _cur_palette[i].b = palette[i].blue; |
|
124 } |
|
125 |
|
126 _cur_palette[0xff].r = 0; |
|
127 _cur_palette[0xff].g = 0; |
|
128 _cur_palette[0xff].b = 0; |
|
129 |
|
130 _pal_first_dirty = 0; |
|
131 _pal_last_dirty = 0xff; |
|
132 |
|
133 png_destroy_read_struct(&png_ptr, &info_ptr, &end_info); |
|
134 fclose(f); |
|
135 return; |
|
136 } |
|
137 |
|
138 |
|
139 |
|
140 #else /* WITH_PNG */ |
|
141 |
|
142 void DisplaySplashImage(void) {} |
|
143 |
|
144 #endif /* WITH_PNG */ |