1 /* QuakeSpasm: kept only the jpg writer, the only thing we use, and removed all others. */
2
3 /* stb_image_write - v1.07 - public domain - http://nothings.org/stb/stb_image_write.h
4 writes out PNG/BMP/TGA/JPEG/HDR images to C stdio - Sean Barrett 2010-2015
5 no warranty implied; use at your own risk
6
7 Before #including,
8
9 #define STB_IMAGE_WRITE_IMPLEMENTATION
10
11 in the file that you want to have the implementation.
12
13 Will probably not work correctly with strict-aliasing optimizations.
14
15 ABOUT:
16
17 This header file is a library for writing images to C stdio. It could be
18 adapted to write to memory or a general streaming interface; let me know.
19
20 The PNG output is not optimal; it is 20-50% larger than the file
21 written by a decent optimizing implementation. This library is designed
22 for source code compactness and simplicity, not optimal image file size
23 or run-time performance.
24
25 BUILDING:
26
27 You can #define STBIW_ASSERT(x) before the #include to avoid using assert.h.
28 You can #define STBIW_MALLOC(), STBIW_REALLOC(), and STBIW_FREE() to replace
29 malloc,realloc,free.
30 You can define STBIW_MEMMOVE() to replace memmove()
31
32 USAGE:
33
34 There are four functions, one for each image file format:
35
36 int stbi_write_png(char const *filename, int w, int h, int comp, const void *data, int stride_in_bytes);
37 int stbi_write_bmp(char const *filename, int w, int h, int comp, const void *data);
38 int stbi_write_tga(char const *filename, int w, int h, int comp, const void *data);
39 int stbi_write_hdr(char const *filename, int w, int h, int comp, const float *data);
40 int stbi_write_jpg(char const *filename, int w, int h, int comp, const float *data);
41
42 There are also four equivalent functions that use an arbitrary write function. You are
43 expected to open/close your file-equivalent before and after calling these:
44
45 int stbi_write_png_to_func(stbi_write_func *func, void *context, int w, int h, int comp, const void *data, int stride_in_bytes);
46 int stbi_write_bmp_to_func(stbi_write_func *func, void *context, int w, int h, int comp, const void *data);
47 int stbi_write_tga_to_func(stbi_write_func *func, void *context, int w, int h, int comp, const void *data);
48 int stbi_write_hdr_to_func(stbi_write_func *func, void *context, int w, int h, int comp, const float *data);
49 int stbi_write_jpg_to_func(stbi_write_func *func, void *context, int x, int y, int comp, const void *data, int quality);
50
51 where the callback is:
52 void stbi_write_func(void *context, void *data, int size);
53
54 You can define STBI_WRITE_NO_STDIO to disable the file variant of these
55 functions, so the library will not use stdio.h at all. However, this will
56 also disable HDR writing, because it requires stdio for formatted output.
57
58 Each function returns 0 on failure and non-0 on success.
59
60 The functions create an image file defined by the parameters. The image
61 is a rectangle of pixels stored from left-to-right, top-to-bottom.
62 Each pixel contains 'comp' channels of data stored interleaved with 8-bits
63 per channel, in the following order: 1=Y, 2=YA, 3=RGB, 4=RGBA. (Y is
64 monochrome color.) The rectangle is 'w' pixels wide and 'h' pixels tall.
65 The *data pointer points to the first byte of the top-left-most pixel.
66 For PNG, "stride_in_bytes" is the distance in bytes from the first byte of
67 a row of pixels to the first byte of the next row of pixels.
68
69 PNG creates output files with the same number of components as the input.
70 The BMP format expands Y to RGB in the file format and does not
71 output alpha.
72
73 PNG supports writing rectangles of data even when the bytes storing rows of
74 data are not consecutive in memory (e.g. sub-rectangles of a larger image),
75 by supplying the stride between the beginning of adjacent rows. The other
76 formats do not. (Thus you cannot write a native-format BMP through the BMP
77 writer, both because it is in BGR order and because it may have padding
78 at the end of the line.)
79
80 HDR expects linear float data. Since the format is always 32-bit rgb(e)
81 data, alpha (if provided) is discarded, and for monochrome data it is
82 replicated across all three channels.
83
84 TGA supports RLE or non-RLE compressed data. To use non-RLE-compressed
85 data, set the global variable 'stbi_write_tga_with_rle' to 0.
86
87 JPEG does ignore alpha channels in input data; quality is between 1 and 100.
88 Higher quality looks better but results in a bigger image.
89 JPEG baseline (no JPEG progressive).
90
91 CREDITS:
92
93 PNG/BMP/TGA
94 Sean Barrett
95 HDR
96 Baldur Karlsson
97 TGA monochrome:
98 Jean-Sebastien Guay
99 misc enhancements:
100 Tim Kelsey
101 TGA RLE
102 Alan Hickman
103 initial file IO callback implementation
104 Emmanuel Julien
105 JPEG
106 Jon Olick (original jo_jpeg.cpp code)
107 Daniel Gibson
108 bugfixes:
109 github:Chribba
110 Guillaume Chereau
111 github:jry2
112 github:romigrou
113 Sergio Gonzalez
114 Jonas Karlsson
115 Filip Wasil
116 Thatcher Ulrich
117 github:poppolopoppo
118 Patrick Boettcher
119
120 LICENSE
121
122 See end of file for license information.
123
124 */
125
126 #ifndef INCLUDE_STB_IMAGE_WRITE_H
127 #define INCLUDE_STB_IMAGE_WRITE_H
128
129 #ifdef __cplusplus
130 extern "C" {
131 #endif
132
133 #ifdef STB_IMAGE_WRITE_STATIC
134 #define STBIWDEF static
135 #else
136 #define STBIWDEF extern
137 #endif
138
139 #ifndef STBI_WRITE_NO_STDIO
140 STBIWDEF int stbi_write_jpg(char const *filename, int x, int y, int comp, const void *data, int quality);
141 #endif
142
143 typedef void stbi_write_func(void *context, void *data, int size);
144
145 #if 0 /* not used in QuakeSpasm */
146 STBIWDEF int stbi_write_jpg_to_func(stbi_write_func *func, void *context, int x, int y, int comp, const void *data, int quality);
147 #endif
148
149 #ifdef __cplusplus
150 }
151 #endif
152
153 #endif//INCLUDE_STB_IMAGE_WRITE_H
154
155 #ifdef STB_IMAGE_WRITE_IMPLEMENTATION
156
157 #ifdef _WIN32
158 #ifndef _CRT_SECURE_NO_WARNINGS
159 #define _CRT_SECURE_NO_WARNINGS
160 #endif
161 #ifndef _CRT_NONSTDC_NO_DEPRECATE
162 #define _CRT_NONSTDC_NO_DEPRECATE
163 #endif
164 #endif
165
166 #ifndef STBI_WRITE_NO_STDIO
167 #include <stdio.h>
168 #endif // STBI_WRITE_NO_STDIO
169
170 #include <stdarg.h>
171 #include <stdlib.h>
172 #include <string.h>
173 #include <math.h>
174
175 #if defined(STBIW_MALLOC) && defined(STBIW_FREE) && (defined(STBIW_REALLOC) || defined(STBIW_REALLOC_SIZED))
176 // ok
177 #elif !defined(STBIW_MALLOC) && !defined(STBIW_FREE) && !defined(STBIW_REALLOC) && !defined(STBIW_REALLOC_SIZED)
178 // ok
179 #else
180 #error "Must define all or none of STBIW_MALLOC, STBIW_FREE, and STBIW_REALLOC (or STBIW_REALLOC_SIZED)."
181 #endif
182
183 #ifndef STBIW_MALLOC
184 #define STBIW_MALLOC(sz) malloc(sz)
185 #define STBIW_REALLOC(p,newsz) realloc(p,newsz)
186 #define STBIW_FREE(p) free(p)
187 #endif
188
189 #ifndef STBIW_REALLOC_SIZED
190 #define STBIW_REALLOC_SIZED(p,oldsz,newsz) STBIW_REALLOC(p,newsz)
191 #endif
192
193
194 #ifndef STBIW_MEMMOVE
195 #define STBIW_MEMMOVE(a,b,sz) memmove(a,b,sz)
196 #endif
197
198
199 #ifndef STBIW_ASSERT
200 #include <assert.h>
201 #define STBIW_ASSERT(x) assert(x)
202 #endif
203
204 #define STBIW_UCHAR(x) (unsigned char) ((x) & 0xff)
205
206 typedef struct
207 {
208 stbi_write_func *func;
209 void *context;
210 } stbi__write_context;
211
212 // initialize a callback-based context
stbi__start_write_callbacks(stbi__write_context * s,stbi_write_func * c,void * context)213 static void stbi__start_write_callbacks(stbi__write_context *s, stbi_write_func *c, void *context)
214 {
215 s->func = c;
216 s->context = context;
217 }
218
219 #ifndef STBI_WRITE_NO_STDIO
220
stbi__stdio_write(void * context,void * data,int size)221 static void stbi__stdio_write(void *context, void *data, int size)
222 {
223 fwrite(data,1,size,(FILE*) context);
224 }
225
stbi__start_write_file(stbi__write_context * s,const char * filename)226 static int stbi__start_write_file(stbi__write_context *s, const char *filename)
227 {
228 FILE *f = fopen(filename, "wb");
229 stbi__start_write_callbacks(s, stbi__stdio_write, (void *) f);
230 return f != NULL;
231 }
232
stbi__end_write_file(stbi__write_context * s)233 static void stbi__end_write_file(stbi__write_context *s)
234 {
235 fclose((FILE *)s->context);
236 }
237
238 #endif // !STBI_WRITE_NO_STDIO
239
240 typedef unsigned int stbiw_uint32;
241 typedef int stb_image_write_test[sizeof(stbiw_uint32)==4 ? 1 : -1];
242
stbiw__putc(stbi__write_context * s,unsigned char c)243 static void stbiw__putc(stbi__write_context *s, unsigned char c)
244 {
245 s->func(s->context, &c, 1);
246 }
247
248 /* ***************************************************************************
249 *
250 * JPEG writer
251 *
252 * This is based on Jon Olick's jo_jpeg.cpp:
253 * public domain Simple, Minimalistic JPEG writer - http://www.jonolick.com/code.html
254 */
255
256 static const unsigned char stbiw__jpg_ZigZag[] = { 0,1,5,6,14,15,27,28,2,4,7,13,16,26,29,42,3,8,12,17,25,30,41,43,9,11,18,
257 24,31,40,44,53,10,19,23,32,39,45,52,54,20,22,33,38,46,51,55,60,21,34,37,47,50,56,59,61,35,36,48,49,57,58,62,63 };
258
stbiw__jpg_writeBits(stbi__write_context * s,int * bitBufP,int * bitCntP,const unsigned short * bs)259 static void stbiw__jpg_writeBits(stbi__write_context *s, int *bitBufP, int *bitCntP, const unsigned short *bs) {
260 int bitBuf = *bitBufP, bitCnt = *bitCntP;
261 bitCnt += bs[1];
262 bitBuf |= bs[0] << (24 - bitCnt);
263 while(bitCnt >= 8) {
264 unsigned char c = (bitBuf >> 16) & 255;
265 stbiw__putc(s, c);
266 if(c == 255) {
267 stbiw__putc(s, 0);
268 }
269 bitBuf <<= 8;
270 bitCnt -= 8;
271 }
272 *bitBufP = bitBuf;
273 *bitCntP = bitCnt;
274 }
275
stbiw__jpg_DCT(float * d0p,float * d1p,float * d2p,float * d3p,float * d4p,float * d5p,float * d6p,float * d7p)276 static void stbiw__jpg_DCT(float *d0p, float *d1p, float *d2p, float *d3p, float *d4p, float *d5p, float *d6p, float *d7p) {
277 float d0 = *d0p, d1 = *d1p, d2 = *d2p, d3 = *d3p, d4 = *d4p, d5 = *d5p, d6 = *d6p, d7 = *d7p;
278 float z1, z2, z3, z4, z5, z11, z13;
279
280 float tmp0 = d0 + d7;
281 float tmp7 = d0 - d7;
282 float tmp1 = d1 + d6;
283 float tmp6 = d1 - d6;
284 float tmp2 = d2 + d5;
285 float tmp5 = d2 - d5;
286 float tmp3 = d3 + d4;
287 float tmp4 = d3 - d4;
288
289 // Even part
290 float tmp10 = tmp0 + tmp3; // phase 2
291 float tmp13 = tmp0 - tmp3;
292 float tmp11 = tmp1 + tmp2;
293 float tmp12 = tmp1 - tmp2;
294
295 d0 = tmp10 + tmp11; // phase 3
296 d4 = tmp10 - tmp11;
297
298 z1 = (tmp12 + tmp13) * 0.707106781f; // c4
299 d2 = tmp13 + z1; // phase 5
300 d6 = tmp13 - z1;
301
302 // Odd part
303 tmp10 = tmp4 + tmp5; // phase 2
304 tmp11 = tmp5 + tmp6;
305 tmp12 = tmp6 + tmp7;
306
307 // The rotator is modified from fig 4-8 to avoid extra negations.
308 z5 = (tmp10 - tmp12) * 0.382683433f; // c6
309 z2 = tmp10 * 0.541196100f + z5; // c2-c6
310 z4 = tmp12 * 1.306562965f + z5; // c2+c6
311 z3 = tmp11 * 0.707106781f; // c4
312
313 z11 = tmp7 + z3; // phase 5
314 z13 = tmp7 - z3;
315
316 *d5p = z13 + z2; // phase 6
317 *d3p = z13 - z2;
318 *d1p = z11 + z4;
319 *d7p = z11 - z4;
320
321 *d0p = d0; *d2p = d2; *d4p = d4; *d6p = d6;
322 }
323
stbiw__jpg_calcBits(int val,unsigned short bits[2])324 static void stbiw__jpg_calcBits(int val, unsigned short bits[2]) {
325 int tmp1 = val < 0 ? -val : val;
326 val = val < 0 ? val-1 : val;
327 bits[1] = 1;
328 while(tmp1 >>= 1) {
329 ++bits[1];
330 }
331 bits[0] = val & ((1<<bits[1])-1);
332 }
333
stbiw__jpg_processDU(stbi__write_context * s,int * bitBuf,int * bitCnt,float * CDU,float * fdtbl,int DC,const unsigned short HTDC[256][2],const unsigned short HTAC[256][2])334 static int stbiw__jpg_processDU(stbi__write_context *s, int *bitBuf, int *bitCnt, float *CDU, float *fdtbl, int DC, const unsigned short HTDC[256][2], const unsigned short HTAC[256][2]) {
335 unsigned short EOB[2];
336 unsigned short M16zeroes[2];
337 int dataOff, i, diff, end0pos;
338 int DU[64];
339
340 EOB[0] = HTAC[0x00][0];
341 EOB[1] = HTAC[0x00][1];
342 M16zeroes[0] = HTAC[0xF0][0];
343 M16zeroes[1] = HTAC[0xF0][1];
344
345 // DCT rows
346 for(dataOff=0; dataOff<64; dataOff+=8) {
347 stbiw__jpg_DCT(&CDU[dataOff], &CDU[dataOff+1], &CDU[dataOff+2], &CDU[dataOff+3], &CDU[dataOff+4], &CDU[dataOff+5], &CDU[dataOff+6], &CDU[dataOff+7]);
348 }
349 // DCT columns
350 for(dataOff=0; dataOff<8; ++dataOff) {
351 stbiw__jpg_DCT(&CDU[dataOff], &CDU[dataOff+8], &CDU[dataOff+16], &CDU[dataOff+24], &CDU[dataOff+32], &CDU[dataOff+40], &CDU[dataOff+48], &CDU[dataOff+56]);
352 }
353 // Quantize/descale/zigzag the coefficients
354 for(i=0; i<64; ++i) {
355 float v = CDU[i]*fdtbl[i];
356 // DU[stbiw__jpg_ZigZag[i]] = (int)(v < 0 ? ceilf(v - 0.5f) : floorf(v + 0.5f));
357 // ceilf() and floorf() are C99, not C89, but I /think/ they're not needed here anyway?
358 DU[stbiw__jpg_ZigZag[i]] = (int)(v < 0 ? v - 0.5f : v + 0.5f);
359 }
360
361 // Encode DC
362 diff = DU[0] - DC;
363 if (diff == 0) {
364 stbiw__jpg_writeBits(s, bitBuf, bitCnt, HTDC[0]);
365 } else {
366 unsigned short bits[2];
367 stbiw__jpg_calcBits(diff, bits);
368 stbiw__jpg_writeBits(s, bitBuf, bitCnt, HTDC[bits[1]]);
369 stbiw__jpg_writeBits(s, bitBuf, bitCnt, bits);
370 }
371 // Encode ACs
372 end0pos = 63;
373 for(; (end0pos>0)&&(DU[end0pos]==0); --end0pos) {
374 }
375 // end0pos = first element in reverse order !=0
376 if(end0pos == 0) {
377 stbiw__jpg_writeBits(s, bitBuf, bitCnt, EOB);
378 return DU[0];
379 }
380 for(i = 1; i <= end0pos; ++i) {
381 int startpos = i;
382 int nrzeroes;
383 unsigned short bits[2];
384 for (; DU[i]==0 && i<=end0pos; ++i) {
385 }
386 nrzeroes = i-startpos;
387 if ( nrzeroes >= 16 ) {
388 int lng = nrzeroes>>4;
389 int nrmarker;
390 for (nrmarker=1; nrmarker <= lng; ++nrmarker)
391 stbiw__jpg_writeBits(s, bitBuf, bitCnt, M16zeroes);
392 nrzeroes &= 15;
393 }
394 stbiw__jpg_calcBits(DU[i], bits);
395 stbiw__jpg_writeBits(s, bitBuf, bitCnt, HTAC[(nrzeroes<<4)+bits[1]]);
396 stbiw__jpg_writeBits(s, bitBuf, bitCnt, bits);
397 }
398 if(end0pos != 63) {
399 stbiw__jpg_writeBits(s, bitBuf, bitCnt, EOB);
400 }
401 return DU[0];
402 }
403
stbi_write_jpg_core(stbi__write_context * s,int width,int height,int comp,const void * data,int quality)404 static int stbi_write_jpg_core(stbi__write_context *s, int width, int height, int comp, const void* data, int quality) {
405 // Constants that don't pollute global namespace
406 static const unsigned char std_dc_luminance_nrcodes[] = {0,0,1,5,1,1,1,1,1,1,0,0,0,0,0,0,0};
407 static const unsigned char std_dc_luminance_values[] = {0,1,2,3,4,5,6,7,8,9,10,11};
408 static const unsigned char std_ac_luminance_nrcodes[] = {0,0,2,1,3,3,2,4,3,5,5,4,4,0,0,1,0x7d};
409 static const unsigned char std_ac_luminance_values[] = {
410 0x01,0x02,0x03,0x00,0x04,0x11,0x05,0x12,0x21,0x31,0x41,0x06,0x13,0x51,0x61,0x07,0x22,0x71,0x14,0x32,0x81,0x91,0xa1,0x08,
411 0x23,0x42,0xb1,0xc1,0x15,0x52,0xd1,0xf0,0x24,0x33,0x62,0x72,0x82,0x09,0x0a,0x16,0x17,0x18,0x19,0x1a,0x25,0x26,0x27,0x28,
412 0x29,0x2a,0x34,0x35,0x36,0x37,0x38,0x39,0x3a,0x43,0x44,0x45,0x46,0x47,0x48,0x49,0x4a,0x53,0x54,0x55,0x56,0x57,0x58,0x59,
413 0x5a,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6a,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0x7a,0x83,0x84,0x85,0x86,0x87,0x88,0x89,
414 0x8a,0x92,0x93,0x94,0x95,0x96,0x97,0x98,0x99,0x9a,0xa2,0xa3,0xa4,0xa5,0xa6,0xa7,0xa8,0xa9,0xaa,0xb2,0xb3,0xb4,0xb5,0xb6,
415 0xb7,0xb8,0xb9,0xba,0xc2,0xc3,0xc4,0xc5,0xc6,0xc7,0xc8,0xc9,0xca,0xd2,0xd3,0xd4,0xd5,0xd6,0xd7,0xd8,0xd9,0xda,0xe1,0xe2,
416 0xe3,0xe4,0xe5,0xe6,0xe7,0xe8,0xe9,0xea,0xf1,0xf2,0xf3,0xf4,0xf5,0xf6,0xf7,0xf8,0xf9,0xfa
417 };
418 static const unsigned char std_dc_chrominance_nrcodes[] = {0,0,3,1,1,1,1,1,1,1,1,1,0,0,0,0,0};
419 static const unsigned char std_dc_chrominance_values[] = {0,1,2,3,4,5,6,7,8,9,10,11};
420 static const unsigned char std_ac_chrominance_nrcodes[] = {0,0,2,1,2,4,4,3,4,7,5,4,4,0,1,2,0x77};
421 static const unsigned char std_ac_chrominance_values[] = {
422 0x00,0x01,0x02,0x03,0x11,0x04,0x05,0x21,0x31,0x06,0x12,0x41,0x51,0x07,0x61,0x71,0x13,0x22,0x32,0x81,0x08,0x14,0x42,0x91,
423 0xa1,0xb1,0xc1,0x09,0x23,0x33,0x52,0xf0,0x15,0x62,0x72,0xd1,0x0a,0x16,0x24,0x34,0xe1,0x25,0xf1,0x17,0x18,0x19,0x1a,0x26,
424 0x27,0x28,0x29,0x2a,0x35,0x36,0x37,0x38,0x39,0x3a,0x43,0x44,0x45,0x46,0x47,0x48,0x49,0x4a,0x53,0x54,0x55,0x56,0x57,0x58,
425 0x59,0x5a,0x63,0x64,0x65,0x66,0x67,0x68,0x69,0x6a,0x73,0x74,0x75,0x76,0x77,0x78,0x79,0x7a,0x82,0x83,0x84,0x85,0x86,0x87,
426 0x88,0x89,0x8a,0x92,0x93,0x94,0x95,0x96,0x97,0x98,0x99,0x9a,0xa2,0xa3,0xa4,0xa5,0xa6,0xa7,0xa8,0xa9,0xaa,0xb2,0xb3,0xb4,
427 0xb5,0xb6,0xb7,0xb8,0xb9,0xba,0xc2,0xc3,0xc4,0xc5,0xc6,0xc7,0xc8,0xc9,0xca,0xd2,0xd3,0xd4,0xd5,0xd6,0xd7,0xd8,0xd9,0xda,
428 0xe2,0xe3,0xe4,0xe5,0xe6,0xe7,0xe8,0xe9,0xea,0xf2,0xf3,0xf4,0xf5,0xf6,0xf7,0xf8,0xf9,0xfa
429 };
430 // Huffman tables
431 static const unsigned short YDC_HT[256][2] = { {0,2},{2,3},{3,3},{4,3},{5,3},{6,3},{14,4},{30,5},{62,6},{126,7},{254,8},{510,9}};
432 static const unsigned short UVDC_HT[256][2] = { {0,2},{1,2},{2,2},{6,3},{14,4},{30,5},{62,6},{126,7},{254,8},{510,9},{1022,10},{2046,11}};
433 static const unsigned short YAC_HT[256][2] = {
434 {10,4},{0,2},{1,2},{4,3},{11,4},{26,5},{120,7},{248,8},{1014,10},{65410,16},{65411,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
435 {12,4},{27,5},{121,7},{502,9},{2038,11},{65412,16},{65413,16},{65414,16},{65415,16},{65416,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
436 {28,5},{249,8},{1015,10},{4084,12},{65417,16},{65418,16},{65419,16},{65420,16},{65421,16},{65422,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
437 {58,6},{503,9},{4085,12},{65423,16},{65424,16},{65425,16},{65426,16},{65427,16},{65428,16},{65429,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
438 {59,6},{1016,10},{65430,16},{65431,16},{65432,16},{65433,16},{65434,16},{65435,16},{65436,16},{65437,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
439 {122,7},{2039,11},{65438,16},{65439,16},{65440,16},{65441,16},{65442,16},{65443,16},{65444,16},{65445,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
440 {123,7},{4086,12},{65446,16},{65447,16},{65448,16},{65449,16},{65450,16},{65451,16},{65452,16},{65453,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
441 {250,8},{4087,12},{65454,16},{65455,16},{65456,16},{65457,16},{65458,16},{65459,16},{65460,16},{65461,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
442 {504,9},{32704,15},{65462,16},{65463,16},{65464,16},{65465,16},{65466,16},{65467,16},{65468,16},{65469,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
443 {505,9},{65470,16},{65471,16},{65472,16},{65473,16},{65474,16},{65475,16},{65476,16},{65477,16},{65478,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
444 {506,9},{65479,16},{65480,16},{65481,16},{65482,16},{65483,16},{65484,16},{65485,16},{65486,16},{65487,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
445 {1017,10},{65488,16},{65489,16},{65490,16},{65491,16},{65492,16},{65493,16},{65494,16},{65495,16},{65496,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
446 {1018,10},{65497,16},{65498,16},{65499,16},{65500,16},{65501,16},{65502,16},{65503,16},{65504,16},{65505,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
447 {2040,11},{65506,16},{65507,16},{65508,16},{65509,16},{65510,16},{65511,16},{65512,16},{65513,16},{65514,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
448 {65515,16},{65516,16},{65517,16},{65518,16},{65519,16},{65520,16},{65521,16},{65522,16},{65523,16},{65524,16},{0,0},{0,0},{0,0},{0,0},{0,0},
449 {2041,11},{65525,16},{65526,16},{65527,16},{65528,16},{65529,16},{65530,16},{65531,16},{65532,16},{65533,16},{65534,16},{0,0},{0,0},{0,0},{0,0},{0,0}
450 };
451 static const unsigned short UVAC_HT[256][2] = {
452 {0,2},{1,2},{4,3},{10,4},{24,5},{25,5},{56,6},{120,7},{500,9},{1014,10},{4084,12},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
453 {11,4},{57,6},{246,8},{501,9},{2038,11},{4085,12},{65416,16},{65417,16},{65418,16},{65419,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
454 {26,5},{247,8},{1015,10},{4086,12},{32706,15},{65420,16},{65421,16},{65422,16},{65423,16},{65424,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
455 {27,5},{248,8},{1016,10},{4087,12},{65425,16},{65426,16},{65427,16},{65428,16},{65429,16},{65430,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
456 {58,6},{502,9},{65431,16},{65432,16},{65433,16},{65434,16},{65435,16},{65436,16},{65437,16},{65438,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
457 {59,6},{1017,10},{65439,16},{65440,16},{65441,16},{65442,16},{65443,16},{65444,16},{65445,16},{65446,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
458 {121,7},{2039,11},{65447,16},{65448,16},{65449,16},{65450,16},{65451,16},{65452,16},{65453,16},{65454,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
459 {122,7},{2040,11},{65455,16},{65456,16},{65457,16},{65458,16},{65459,16},{65460,16},{65461,16},{65462,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
460 {249,8},{65463,16},{65464,16},{65465,16},{65466,16},{65467,16},{65468,16},{65469,16},{65470,16},{65471,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
461 {503,9},{65472,16},{65473,16},{65474,16},{65475,16},{65476,16},{65477,16},{65478,16},{65479,16},{65480,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
462 {504,9},{65481,16},{65482,16},{65483,16},{65484,16},{65485,16},{65486,16},{65487,16},{65488,16},{65489,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
463 {505,9},{65490,16},{65491,16},{65492,16},{65493,16},{65494,16},{65495,16},{65496,16},{65497,16},{65498,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
464 {506,9},{65499,16},{65500,16},{65501,16},{65502,16},{65503,16},{65504,16},{65505,16},{65506,16},{65507,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
465 {2041,11},{65508,16},{65509,16},{65510,16},{65511,16},{65512,16},{65513,16},{65514,16},{65515,16},{65516,16},{0,0},{0,0},{0,0},{0,0},{0,0},{0,0},
466 {16352,14},{65517,16},{65518,16},{65519,16},{65520,16},{65521,16},{65522,16},{65523,16},{65524,16},{65525,16},{0,0},{0,0},{0,0},{0,0},{0,0},
467 {1018,10},{32707,15},{65526,16},{65527,16},{65528,16},{65529,16},{65530,16},{65531,16},{65532,16},{65533,16},{65534,16},{0,0},{0,0},{0,0},{0,0},{0,0}
468 };
469 static const int YQT[] = {16,11,10,16,24,40,51,61,12,12,14,19,26,58,60,55,14,13,16,24,40,57,69,56,14,17,22,29,51,87,80,62,18,22,
470 37,56,68,109,103,77,24,35,55,64,81,104,113,92,49,64,78,87,103,121,120,101,72,92,95,98,112,100,103,99};
471 static const int UVQT[] = {17,18,24,47,99,99,99,99,18,21,26,66,99,99,99,99,24,26,56,99,99,99,99,99,47,66,99,99,99,99,99,99,
472 99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99,99};
473 static const float aasf[] = { 1.0f * 2.828427125f, 1.387039845f * 2.828427125f, 1.306562965f * 2.828427125f, 1.175875602f * 2.828427125f,
474 1.0f * 2.828427125f, 0.785694958f * 2.828427125f, 0.541196100f * 2.828427125f, 0.275899379f * 2.828427125f };
475
476 int row, col, i, k;
477 float fdtbl_Y[64], fdtbl_UV[64];
478 unsigned char YTable[64], UVTable[64];
479
480 if(!data || !width || !height || comp > 4 || comp < 1) {
481 return 0;
482 }
483
484 quality = quality ? quality : 90;
485 quality = quality < 1 ? 1 : quality > 100 ? 100 : quality;
486 quality = quality < 50 ? 5000 / quality : 200 - quality * 2;
487
488 for(i = 0; i < 64; ++i) {
489 int uvti, yti = (YQT[i]*quality+50)/100;
490 YTable[stbiw__jpg_ZigZag[i]] = (unsigned char) (yti < 1 ? 1 : yti > 255 ? 255 : yti);
491 uvti = (UVQT[i]*quality+50)/100;
492 UVTable[stbiw__jpg_ZigZag[i]] = (unsigned char) (uvti < 1 ? 1 : uvti > 255 ? 255 : uvti);
493 }
494
495 for(row = 0, k = 0; row < 8; ++row) {
496 for(col = 0; col < 8; ++col, ++k) {
497 fdtbl_Y[k] = 1 / (YTable [stbiw__jpg_ZigZag[k]] * aasf[row] * aasf[col]);
498 fdtbl_UV[k] = 1 / (UVTable[stbiw__jpg_ZigZag[k]] * aasf[row] * aasf[col]);
499 }
500 }
501
502 // Write Headers
503 {
504 static const unsigned char head0[] = { 0xFF,0xD8,0xFF,0xE0,0,0x10,'J','F','I','F',0,1,1,0,0,1,0,1,0,0,0xFF,0xDB,0,0x84,0 };
505 static const unsigned char head2[] = { 0xFF,0xDA,0,0xC,3,1,0,2,0x11,3,0x11,0,0x3F,0 };
506 unsigned char head1[] = { 0xFF,0xC0,0,0x11,8, /*[5]*/0,/*[6]*/0,/*[7]*/0,/*[8]*/0,
507 3,1,0x11,0,2,0x11,1,3,0x11,1,0xFF,0xC4,0x01,0xA2,0 };
508 head1[5] = (unsigned char)(height>>8);
509 head1[6] = STBIW_UCHAR(height);
510 head1[7] = (unsigned char)(width>>8);
511 head1[8] = STBIW_UCHAR(width);
512 s->func(s->context, (void*)head0, sizeof(head0));
513 s->func(s->context, (void*)YTable, sizeof(YTable));
514 stbiw__putc(s, 1);
515 s->func(s->context, UVTable, sizeof(UVTable));
516 s->func(s->context, (void*)head1, sizeof(head1));
517 s->func(s->context, (void*)(std_dc_luminance_nrcodes+1), sizeof(std_dc_luminance_nrcodes)-1);
518 s->func(s->context, (void*)std_dc_luminance_values, sizeof(std_dc_luminance_values));
519 stbiw__putc(s, 0x10); // HTYACinfo
520 s->func(s->context, (void*)(std_ac_luminance_nrcodes+1), sizeof(std_ac_luminance_nrcodes)-1);
521 s->func(s->context, (void*)std_ac_luminance_values, sizeof(std_ac_luminance_values));
522 stbiw__putc(s, 1); // HTUDCinfo
523 s->func(s->context, (void*)(std_dc_chrominance_nrcodes+1), sizeof(std_dc_chrominance_nrcodes)-1);
524 s->func(s->context, (void*)std_dc_chrominance_values, sizeof(std_dc_chrominance_values));
525 stbiw__putc(s, 0x11); // HTUACinfo
526 s->func(s->context, (void*)(std_ac_chrominance_nrcodes+1), sizeof(std_ac_chrominance_nrcodes)-1);
527 s->func(s->context, (void*)std_ac_chrominance_values, sizeof(std_ac_chrominance_values));
528 s->func(s->context, (void*)head2, sizeof(head2));
529 }
530
531 // Encode 8x8 macroblocks
532 {
533 static const unsigned short fillBits[] = {0x7F, 7};
534 const unsigned char *imageData = (const unsigned char *)data;
535 int DCY=0, DCU=0, DCV=0;
536 int bitBuf=0, bitCnt=0;
537 // comp == 2 is grey+alpha (alpha is ignored)
538 int ofsG = comp > 2 ? 1 : 0, ofsB = comp > 2 ? 2 : 0;
539 int x, y, pos;
540 for(y = 0; y < height; y += 8) {
541 for(x = 0; x < width; x += 8) {
542 float YDU[64], UDU[64], VDU[64];
543 for(row = y, pos = 0; row < y+8; ++row) {
544 for(col = x; col < x+8; ++col, ++pos) {
545 int p = row*width*comp + col*comp;
546 float r, g, b;
547 if(row >= height) {
548 p -= width*comp*(row+1 - height);
549 }
550 if(col >= width) {
551 p -= comp*(col+1 - width);
552 }
553
554 r = imageData[p+0];
555 g = imageData[p+ofsG];
556 b = imageData[p+ofsB];
557 YDU[pos]=+0.29900f*r+0.58700f*g+0.11400f*b-128;
558 UDU[pos]=-0.16874f*r-0.33126f*g+0.50000f*b;
559 VDU[pos]=+0.50000f*r-0.41869f*g-0.08131f*b;
560 }
561 }
562
563 DCY = stbiw__jpg_processDU(s, &bitBuf, &bitCnt, YDU, fdtbl_Y, DCY, YDC_HT, YAC_HT);
564 DCU = stbiw__jpg_processDU(s, &bitBuf, &bitCnt, UDU, fdtbl_UV, DCU, UVDC_HT, UVAC_HT);
565 DCV = stbiw__jpg_processDU(s, &bitBuf, &bitCnt, VDU, fdtbl_UV, DCV, UVDC_HT, UVAC_HT);
566 }
567 }
568
569 // Do the bit alignment of the EOI marker
570 stbiw__jpg_writeBits(s, &bitBuf, &bitCnt, fillBits);
571 }
572
573 // EOI
574 stbiw__putc(s, 0xFF);
575 stbiw__putc(s, 0xD9);
576
577 return 1;
578 }
579
580 #if 0 /* not used in QuakeSpasm */
581 STBIWDEF int stbi_write_jpg_to_func(stbi_write_func *func, void *context, int x, int y, int comp, const void *data, int quality)
582 {
583 stbi__write_context s;
584 stbi__start_write_callbacks(&s, func, context);
585 return stbi_write_jpg_core(&s, x, y, comp, (void *) data, quality);
586 }
587 #endif
588
589
590 #ifndef STBI_WRITE_NO_STDIO
stbi_write_jpg(char const * filename,int x,int y,int comp,const void * data,int quality)591 STBIWDEF int stbi_write_jpg(char const *filename, int x, int y, int comp, const void *data, int quality)
592 {
593 stbi__write_context s;
594 if (stbi__start_write_file(&s,filename)) {
595 int r = stbi_write_jpg_core(&s, x, y, comp, data, quality);
596 stbi__end_write_file(&s);
597 return r;
598 } else
599 return 0;
600 }
601 #endif
602
603 #endif // STB_IMAGE_WRITE_IMPLEMENTATION
604
605 /* Revision history
606 1.07 (2017-07-24)
607 doc fix
608 1.06 (2017-07-23)
609 writing JPEG (using Jon Olick's code)
610 1.05 ???
611 1.04 (2017-03-03)
612 monochrome BMP expansion
613 1.03 ???
614 1.02 (2016-04-02)
615 avoid allocating large structures on the stack
616 1.01 (2016-01-16)
617 STBIW_REALLOC_SIZED: support allocators with no realloc support
618 avoid race-condition in crc initialization
619 minor compile issues
620 1.00 (2015-09-14)
621 installable file IO function
622 0.99 (2015-09-13)
623 warning fixes; TGA rle support
624 0.98 (2015-04-08)
625 added STBIW_MALLOC, STBIW_ASSERT etc
626 0.97 (2015-01-18)
627 fixed HDR asserts, rewrote HDR rle logic
628 0.96 (2015-01-17)
629 add HDR output
630 fix monochrome BMP
631 0.95 (2014-08-17)
632 add monochrome TGA output
633 0.94 (2014-05-31)
634 rename private functions to avoid conflicts with stb_image.h
635 0.93 (2014-05-27)
636 warning fixes
637 0.92 (2010-08-01)
638 casts to unsigned char to fix warnings
639 0.91 (2010-07-17)
640 first public release
641 0.90 first internal release
642 */
643
644 /*
645 ------------------------------------------------------------------------------
646 This software is available under 2 licenses -- choose whichever you prefer.
647 ------------------------------------------------------------------------------
648 ALTERNATIVE A - MIT License
649 Copyright (c) 2017 Sean Barrett
650 Permission is hereby granted, free of charge, to any person obtaining a copy of
651 this software and associated documentation files (the "Software"), to deal in
652 the Software without restriction, including without limitation the rights to
653 use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
654 of the Software, and to permit persons to whom the Software is furnished to do
655 so, subject to the following conditions:
656 The above copyright notice and this permission notice shall be included in all
657 copies or substantial portions of the Software.
658 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
659 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
660 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
661 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
662 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
663 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
664 SOFTWARE.
665 ------------------------------------------------------------------------------
666 ALTERNATIVE B - Public Domain (www.unlicense.org)
667 This is free and unencumbered software released into the public domain.
668 Anyone is free to copy, modify, publish, use, compile, sell, or distribute this
669 software, either in source code form or as a compiled binary, for any purpose,
670 commercial or non-commercial, and by any means.
671 In jurisdictions that recognize copyright laws, the author or authors of this
672 software dedicate any and all copyright interest in the software to the public
673 domain. We make this dedication for the benefit of the public at large and to
674 the detriment of our heirs and successors. We intend this dedication to be an
675 overt act of relinquishment in perpetuity of all present and future rights to
676 this software under copyright law.
677 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
678 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
679 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
680 AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
681 ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
682 WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
683 ------------------------------------------------------------------------------
684 */
685