Reformat whole codebase with astyle.options (#128)
[openjpeg.git] / src / lib / openmj2 / mj2_convert.c
1 /*
2 * Copyright (c) 2002-2014, Universite catholique de Louvain (UCL), Belgium
3 * Copyright (c) 2002-2014, Professor Benoit Macq
4 * Copyright (c) 2003-2007, Francois-Olivier Devaux and Antonin Descampe
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 *    notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 *    notice, this list of conditions and the following disclaimer in the
14 *    documentation and/or other materials provided with the distribution.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS `AS IS'
17 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
20 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26 * POSSIBILITY OF SUCH DAMAGE.
27 */
28
29 #include "opj_includes.h"
30 #include "mj2_convert.h"
31
32 /*  -----------------------       */
33 /*                    */
34 /*                    */
35 /*  Count the number of frames        */
36 /*  in a YUV file             */
37 /*                    */
38 /*  -----------------------       */
39
40 unsigned int OPJ_CALLCONV yuv_num_frames(mj2_tk_t * tk, char *infile)
41 {
42     unsigned int prec_size;
43     long end_of_f, frame_size;
44     FILE *f;
45
46     f = fopen(infile, "rb");
47     if (!f) {
48         fprintf(stderr, "failed to open %s for reading\n", infile);
49         return 0;
50     }
51     prec_size = (tk->depth + 7) / 8; /* bytes of precision */
52
53     frame_size = (long)(tk->w * tk->h * (1.0 + (double) 2 / (double)(
54             tk->CbCr_subsampling_dx *
55             tk->CbCr_subsampling_dy)));  /* Calculate frame size */
56     frame_size *= prec_size;
57
58     fseek(f, 0, SEEK_END);
59     end_of_f = ftell(f);      /* Calculate file size */
60
61     if (end_of_f < frame_size) {
62         fprintf(stderr,
63                 "YUV does not contains any frame of %d x %d size\n", tk->w,
64                 tk->h);
65         return 0;
66     }
67     fclose(f);
68
69     return (unsigned int)(end_of_f / frame_size);
70 }
71
72 /*  ----------------------- */
73 /* */
74 /* */
75 /*  YUV to IMAGE */
76 /* */
77 /*  ----------------------- */
78
79 opj_image_t * OPJ_CALLCONV mj2_image_create(mj2_tk_t * tk,
80         opj_cparameters_t *parameters)
81 {
82     opj_image_cmptparm_t cmptparm[3];
83     opj_image_t * img;
84     int i;
85     int numcomps = 3;
86     int subsampling_dx = parameters->subsampling_dx;
87     int subsampling_dy = parameters->subsampling_dy;
88
89     /* initialize image components */
90     memset(&cmptparm[0], 0, 3 * sizeof(opj_image_cmptparm_t));
91     for (i = 0; i < numcomps; i++) {
92         cmptparm[i].prec = tk->depth;
93         cmptparm[i].bpp = tk->depth;
94         cmptparm[i].sgnd = 0;
95         cmptparm[i].dx = i ? subsampling_dx * tk->CbCr_subsampling_dx : subsampling_dx;
96         cmptparm[i].dy = i ? subsampling_dy * tk->CbCr_subsampling_dy : subsampling_dy;
97         cmptparm[i].w = tk->w;
98         cmptparm[i].h = tk->h;
99     }
100     /* create the image */
101     img = opj_image_create(numcomps, cmptparm, CLRSPC_SRGB);
102     return img;
103 }
104
105 char OPJ_CALLCONV yuvtoimage(mj2_tk_t * tk, opj_image_t * img, int frame_num,
106                              opj_cparameters_t *parameters, char* infile)
107 {
108     int i, compno;
109     int offset, size, max, prec_bytes, is_16, v;
110     long end_of_f, position;
111     int numcomps = 3;
112     int subsampling_dx = parameters->subsampling_dx;
113     int subsampling_dy = parameters->subsampling_dy;
114     FILE *yuvfile;
115     int *data;
116     unsigned char uc;
117
118     yuvfile = fopen(infile, "rb");
119     if (!yuvfile) {
120         fprintf(stderr, "failed to open %s for readings\n", parameters->infile);
121         return 1;
122     }
123     is_16 = (tk->depth > 8);
124     prec_bytes = (is_16 ? 2 : 1);
125
126     offset = (int)((double)(frame_num * tk->w * tk->h) * (1.0 +
127                    1.0 * (double) 2 / (double)(tk->CbCr_subsampling_dx *
128                            tk->CbCr_subsampling_dy)));
129     offset *= prec_bytes;
130
131     fseek(yuvfile, 0, SEEK_END);
132     end_of_f = ftell(yuvfile);
133     fseek(yuvfile, sizeof(unsigned char) * offset, SEEK_SET);
134     position = ftell(yuvfile);
135     if (position >= end_of_f) {
136         fprintf(stderr, "Cannot reach frame number %d in yuv file !!\n",
137                 frame_num);
138         fclose(yuvfile);
139         return 1;
140     }
141
142     img->x0 = tk->Dim[0];
143     img->y0 = tk->Dim[1];
144     img->x1 = !tk->Dim[0] ? (tk->w - 1) * subsampling_dx + 1 : tk->Dim[0] +
145               (tk->w - 1) * subsampling_dx + 1;
146     img->y1 = !tk->Dim[1] ? (tk->h - 1) * subsampling_dy + 1 : tk->Dim[1] +
147               (tk->h - 1) * subsampling_dy + 1;
148
149     size = tk->w * tk->h * prec_bytes;
150
151     for (compno = 0; compno < numcomps; compno++) {
152         max = size / (img->comps[compno].dx * img->comps[compno].dy);
153         data = img->comps[compno].data;
154
155         for (i = 0; i < max && !feof(yuvfile); i++) {
156             v = 0;
157             fread(&uc, 1, 1, yuvfile);
158             v = uc;
159
160             if (is_16) {
161                 fread(&uc, 1, 1, yuvfile);
162                 v |= (uc << 8);
163             }
164             *data++ = v;
165         }
166     }
167     fclose(yuvfile);
168
169     return 0;
170 }
171
172
173
174 /*  ----------------------- */
175 /* */
176 /* */
177 /*  IMAGE to YUV */
178 /* */
179 /*  ----------------------- */
180
181
182 opj_bool OPJ_CALLCONV imagetoyuv(opj_image_t * img, char *outfile)
183 {
184     FILE *f;
185     int *data;
186     int i, v, is_16, prec_bytes;
187     unsigned char buf[2];
188
189     if (img->numcomps == 3) {
190         if (img->comps[0].dx != img->comps[1].dx / 2
191                 || img->comps[1].dx != img->comps[2].dx) {
192             fprintf(stderr,
193                     "Error with the input image components size: cannot create yuv file)\n");
194             return OPJ_FALSE;
195         }
196     } else if (!(img->numcomps == 1)) {
197         fprintf(stderr,
198                 "Error with the number of image components(must be one or three)\n");
199         return OPJ_FALSE;
200     }
201
202     f = fopen(outfile, "a+b");
203     if (!f) {
204         fprintf(stderr, "failed to open %s for writing\n", outfile);
205         return OPJ_FALSE;
206     }
207     is_16 = (img->comps[0].prec > 8);
208     prec_bytes = (is_16 ? 2 : 1);
209     data = img->comps[0].data;
210
211     for (i = 0; i < (img->comps[0].w * img->comps[0].h); i++) {
212         v = *data++;
213         buf[0] = (unsigned char)v;
214
215         if (is_16) {
216             buf[1] = (unsigned char)(v >> 8);
217         }
218
219         fwrite(buf, 1, prec_bytes, f);
220     }
221
222
223     if (img->numcomps == 3) {
224         data = img->comps[1].data;
225
226         for (i = 0; i < (img->comps[1].w * img->comps[1].h); i++) {
227             v = *data++;
228             buf[0] = (unsigned char)v;
229
230             if (is_16) {
231                 buf[1] = (unsigned char)(v >> 8);
232             }
233
234             fwrite(buf, 1, prec_bytes, f);
235         }
236         data = img->comps[2].data;
237
238         for (i = 0; i < (img->comps[2].w * img->comps[2].h); i++) {
239             v = *data++;
240             buf[0] = (unsigned char)v;
241
242             if (is_16) {
243                 buf[1] = (unsigned char)(v >> 8);
244             }
245
246             fwrite(buf, 1, prec_bytes, f);
247         }
248     } else if (img->numcomps == 1) {
249         /* fake CbCr values */
250         if (is_16) {
251             buf[0] = 255;
252             if (img->comps[0].prec == 10) {
253                 buf[1] = 1;
254             } else if (img->comps[0].prec == 12) {
255                 buf[1] = 3;
256             } else {
257                 buf[1] = 125;
258             }
259         } else {
260             buf[0] = 125;
261         }
262
263         for (i = 0; i < (img->comps[0].w * img->comps[0].h * 0.25); i++) {
264             fwrite(buf, 1, prec_bytes, f);
265         }
266
267
268         for (i = 0; i < (img->comps[0].w * img->comps[0].h * 0.25); i++) {
269             fwrite(buf, 1, prec_bytes, f);
270         }
271     }
272     fclose(f);
273     return OPJ_TRUE;
274 }
275
276 /*  ----------------------- */
277 /* */
278 /* */
279 /*  IMAGE to BMP */
280 /* */
281 /*  ----------------------- */
282
283 int OPJ_CALLCONV imagetobmp(opj_image_t * img, char *outfile)
284 {
285     int w, wr, h, hr, i, pad;
286     FILE *f;
287
288     if (img->numcomps == 3 && img->comps[0].dx == img->comps[1].dx
289             && img->comps[1].dx == img->comps[2].dx
290             && img->comps[0].dy == img->comps[1].dy
291             && img->comps[1].dy == img->comps[2].dy
292             && img->comps[0].prec == img->comps[1].prec
293             && img->comps[1].prec == img->comps[2].prec) {
294         /* -->> -->> -->> -->>
295
296           24 bits color
297
298         <<-- <<-- <<-- <<-- */
299
300         f = fopen(outfile, "wb");
301         if (!f) {
302             fprintf(stderr, "failed to open %s for writing\n", outfile);
303             return 1;
304         }
305
306         w = img->comps[0].w;
307         wr = int_ceildivpow2(img->comps[0].w, img->comps[0].factor);
308
309         h = img->comps[0].h;
310         hr = int_ceildivpow2(img->comps[0].h, img->comps[0].factor);
311
312         fprintf(f, "BM");
313
314         /* FILE HEADER */
315         /* ------------- */
316         fprintf(f, "%c%c%c%c",
317                 (unsigned char)(hr * wr * 3 + 3 * hr * (wr % 2) +
318                                 54) & 0xff,
319                 (unsigned char)((hr * wr * 3 + 3 * hr * (wr % 2) + 54)
320                                 >> 8) & 0xff,
321                 (unsigned char)((hr * wr * 3 + 3 * hr * (wr % 2) + 54)
322                                 >> 16) & 0xff,
323                 (unsigned char)((hr * wr * 3 + 3 * hr * (wr % 2) + 54)
324                                 >> 24) & 0xff);
325         fprintf(f, "%c%c%c%c", (0) & 0xff, ((0) >> 8) & 0xff,
326                 ((0) >> 16) & 0xff, ((0) >> 24) & 0xff);
327         fprintf(f, "%c%c%c%c", (54) & 0xff, ((54) >> 8) & 0xff,
328                 ((54) >> 16) & 0xff, ((54) >> 24) & 0xff);
329
330         /* INFO HEADER   */
331         /* ------------- */
332         fprintf(f, "%c%c%c%c", (40) & 0xff, ((40) >> 8) & 0xff,
333                 ((40) >> 16) & 0xff, ((40) >> 24) & 0xff);
334         fprintf(f, "%c%c%c%c", (unsigned char)((wr) & 0xff),
335                 (unsigned char)((wr) >> 8) & 0xff,
336                 (unsigned char)((wr) >> 16) & 0xff,
337                 (unsigned char)((wr) >> 24) & 0xff);
338         fprintf(f, "%c%c%c%c", (unsigned char)((hr) & 0xff),
339                 (unsigned char)((hr) >> 8) & 0xff,
340                 (unsigned char)((hr) >> 16) & 0xff,
341                 (unsigned char)((hr) >> 24) & 0xff);
342         fprintf(f, "%c%c", (1) & 0xff, ((1) >> 8) & 0xff);
343         fprintf(f, "%c%c", (24) & 0xff, ((24) >> 8) & 0xff);
344         fprintf(f, "%c%c%c%c", (0) & 0xff, ((0) >> 8) & 0xff,
345                 ((0) >> 16) & 0xff, ((0) >> 24) & 0xff);
346         fprintf(f, "%c%c%c%c",
347                 (unsigned char)(3 * hr * wr +
348                                 3 * hr * (wr % 2)) & 0xff,
349                 (unsigned char)((hr * wr * 3 + 3 * hr * (wr % 2)) >>
350                                 8) & 0xff,
351                 (unsigned char)((hr * wr * 3 + 3 * hr * (wr % 2)) >>
352                                 16) & 0xff,
353                 (unsigned char)((hr * wr * 3 + 3 * hr * (wr % 2)) >>
354                                 24) & 0xff);
355         fprintf(f, "%c%c%c%c", (7834) & 0xff, ((7834) >> 8) & 0xff,
356                 ((7834) >> 16) & 0xff, ((7834) >> 24) & 0xff);
357         fprintf(f, "%c%c%c%c", (7834) & 0xff, ((7834) >> 8) & 0xff,
358                 ((7834) >> 16) & 0xff, ((7834) >> 24) & 0xff);
359         fprintf(f, "%c%c%c%c", (0) & 0xff, ((0) >> 8) & 0xff,
360                 ((0) >> 16) & 0xff, ((0) >> 24) & 0xff);
361         fprintf(f, "%c%c%c%c", (0) & 0xff, ((0) >> 8) & 0xff,
362                 ((0) >> 16) & 0xff, ((0) >> 24) & 0xff);
363
364         for (i = 0; i < wr * hr; i++) {
365             unsigned char R, G, B;
366             /* a modifier */
367             /* R = img->comps[0].data[w * h - ((i) / (w) + 1) * w + (i) % (w)];*/
368             R = img->comps[0].data[w * hr - ((i) / (wr) + 1) * w + (i) % (wr)];
369             /* G = img->comps[1].data[w * h - ((i) / (w) + 1) * w + (i) % (w)];*/
370             G = img->comps[1].data[w * hr - ((i) / (wr) + 1) * w + (i) % (wr)];
371             /* B = img->comps[2].data[w * h - ((i) / (w) + 1) * w + (i) % (w)];*/
372             B = img->comps[2].data[w * hr - ((i) / (wr) + 1) * w + (i) % (wr)];
373             fprintf(f, "%c%c%c", B, G, R);
374
375             if ((i + 1) % wr == 0) {
376                 for (pad = (3 * wr) % 4 ? 4 - (3 * wr) % 4 : 0; pad > 0; pad--) { /* ADD */
377                     fprintf(f, "%c", 0);
378                 }
379             }
380         }
381         fclose(f);
382     }
383     return 0;
384 }