Missed update to private test repo version.
[dcpomatic.git] / src / lib / image.cc
1 /*
2     Copyright (C) 2012-2016 Carl Hetherington <cth@carlh.net>
3
4     This file is part of DCP-o-matic.
5
6     DCP-o-matic is free software; you can redistribute it and/or modify
7     it under the terms of the GNU General Public License as published by
8     the Free Software Foundation; either version 2 of the License, or
9     (at your option) any later version.
10
11     DCP-o-matic is distributed in the hope that it will be useful,
12     but WITHOUT ANY WARRANTY; without even the implied warranty of
13     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14     GNU General Public License for more details.
15
16     You should have received a copy of the GNU General Public License
17     along with DCP-o-matic.  If not, see <http://www.gnu.org/licenses/>.
18
19 */
20
21 /** @file src/image.cc
22  *  @brief A class to describe a video image.
23  */
24
25 #include "image.h"
26 #include "exceptions.h"
27 #include "timer.h"
28 #include "rect.h"
29 #include "util.h"
30 #include "compose.hpp"
31 #include "dcpomatic_socket.h"
32 #include <dcp/rgb_xyz.h>
33 #include <dcp/transfer_function.h>
34 extern "C" {
35 #include <libswscale/swscale.h>
36 #include <libavutil/pixfmt.h>
37 #include <libavutil/pixdesc.h>
38 #include <libavutil/frame.h>
39 }
40 #include <png.h>
41 #if HAVE_VALGRIND_MEMCHECK_H
42 #include <valgrind/memcheck.h>
43 #endif
44 #include <iostream>
45
46 #include "i18n.h"
47
48 using std::string;
49 using std::min;
50 using std::max;
51 using std::cout;
52 using std::cerr;
53 using std::list;
54 using std::runtime_error;
55 using boost::shared_ptr;
56 using dcp::Size;
57
58
59 /** The memory alignment, in bytes, used for each row of an image if aligment is requested */
60 #define ALIGNMENT 64
61
62 /* U/V black value for 8-bit colour */
63 static uint8_t const eight_bit_uv =     (1 << 7) - 1;
64 /* U/V black value for 9-bit colour */
65 static uint16_t const nine_bit_uv =     (1 << 8) - 1;
66 /* U/V black value for 10-bit colour */
67 static uint16_t const ten_bit_uv =      (1 << 9) - 1;
68 /* U/V black value for 16-bit colour */
69 static uint16_t const sixteen_bit_uv =  (1 << 15) - 1;
70
71
72 int
73 Image::vertical_factor (int n) const
74 {
75         if (n == 0) {
76                 return 1;
77         }
78
79         AVPixFmtDescriptor const * d = av_pix_fmt_desc_get(_pixel_format);
80         if (!d) {
81                 throw PixelFormatError ("line_factor()", _pixel_format);
82         }
83
84         return lrintf(powf(2.0f, d->log2_chroma_h));
85 }
86
87 int
88 Image::horizontal_factor (int n) const
89 {
90         if (n == 0) {
91                 return 1;
92         }
93
94         AVPixFmtDescriptor const * d = av_pix_fmt_desc_get(_pixel_format);
95         if (!d) {
96                 throw PixelFormatError ("sample_size()", _pixel_format);
97         }
98
99         return lrintf(powf(2.0f, d->log2_chroma_w));
100 }
101
102 /** @param n Component index.
103  *  @return Number of samples (i.e. pixels, unless sub-sampled) in each direction for this component.
104  */
105 dcp::Size
106 Image::sample_size (int n) const
107 {
108         return dcp::Size (
109                 lrint (ceil (static_cast<double>(size().width) / horizontal_factor (n))),
110                 lrint (ceil (static_cast<double>(size().height) / vertical_factor (n)))
111                 );
112 }
113
114 /** @return Number of planes */
115 int
116 Image::planes () const
117 {
118         AVPixFmtDescriptor const * d = av_pix_fmt_desc_get(_pixel_format);
119         if (!d) {
120                 throw PixelFormatError ("planes()", _pixel_format);
121         }
122
123         if (_pixel_format == AV_PIX_FMT_PAL8) {
124                 return 2;
125         }
126
127         if ((d->flags & AV_PIX_FMT_FLAG_PLANAR) == 0) {
128                 return 1;
129         }
130
131         return d->nb_components;
132 }
133
134
135 static
136 int
137 round_width_for_subsampling (int p, AVPixFmtDescriptor const * desc)
138 {
139         return p & ~ ((1 << desc->log2_chroma_w) - 1);
140 }
141
142
143 static
144 int
145 round_height_for_subsampling (int p, AVPixFmtDescriptor const * desc)
146 {
147         return p & ~ ((1 << desc->log2_chroma_h) - 1);
148 }
149
150
151 /** Crop this image, scale it to `inter_size' and then place it in a black frame of `out_size'.
152  *  @param crop Amount to crop by.
153  *  @param inter_size Size to scale the cropped image to.
154  *  @param out_size Size of output frame; if this is larger than inter_size there will be black padding.
155  *  @param yuv_to_rgb YUV to RGB transformation to use, if required.
156  *  @param out_format Output pixel format.
157  *  @param out_aligned true to make the output image aligned.
158  *  @param fast Try to be fast at the possible expense of quality; at present this means using
159  *  fast bilinear rather than bicubic scaling.
160  */
161 shared_ptr<Image>
162 Image::crop_scale_window (
163         Crop crop, dcp::Size inter_size, dcp::Size out_size, dcp::YUVToRGB yuv_to_rgb, AVPixelFormat out_format, bool out_aligned, bool fast
164         ) const
165 {
166         /* Empirical testing suggests that sws_scale() will crash if
167            the input image is not aligned.
168         */
169         DCPOMATIC_ASSERT (aligned ());
170
171         DCPOMATIC_ASSERT (out_size.width >= inter_size.width);
172         DCPOMATIC_ASSERT (out_size.height >= inter_size.height);
173
174         shared_ptr<Image> out (new Image(out_format, out_size, out_aligned));
175         out->make_black ();
176
177         AVPixFmtDescriptor const * in_desc = av_pix_fmt_desc_get (_pixel_format);
178         if (!in_desc) {
179                 throw PixelFormatError ("crop_scale_window()", _pixel_format);
180         }
181
182         /* Round down so that we crop only the number of pixels that is straightforward
183          * considering any subsampling.
184          */
185         Crop corrected_crop(
186                 round_width_for_subsampling(crop.left, in_desc),
187                 round_width_for_subsampling(crop.right, in_desc),
188                 round_height_for_subsampling(crop.top, in_desc),
189                 round_height_for_subsampling(crop.bottom, in_desc)
190                 );
191
192         /* Also check that we aren't cropping more image than there actually is */
193         if ((corrected_crop.left + corrected_crop.right) >= (size().width - 4)) {
194                 corrected_crop.left = 0;
195                 corrected_crop.right = size().width - 4;
196         }
197
198         if ((corrected_crop.top + corrected_crop.bottom) >= (size().height - 4)) {
199                 corrected_crop.top = 0;
200                 corrected_crop.bottom = size().height - 4;
201         }
202
203         /* Size of the image after any crop */
204         dcp::Size const cropped_size = corrected_crop.apply (size());
205
206         /* Hack: if we're not doing quite the crop that we were asked for, and we carry on scaling
207          * to the inter_size we were asked for, there is a small but noticeable wobble in the image
208          * luminance (#1872).  This hack means we will jump in steps of the subsampling distance
209          * in both crop and scale.
210          */
211         inter_size.width = round_width_for_subsampling(inter_size.width, in_desc);
212         inter_size.height = round_width_for_subsampling(inter_size.height, in_desc);
213
214         /* Scale context for a scale from cropped_size to inter_size */
215         struct SwsContext* scale_context = sws_getContext (
216                         cropped_size.width, cropped_size.height, pixel_format(),
217                         inter_size.width, inter_size.height, out_format,
218                         fast ? SWS_FAST_BILINEAR : SWS_BICUBIC, 0, 0, 0
219                 );
220
221         if (!scale_context) {
222                 throw runtime_error (N_("Could not allocate SwsContext"));
223         }
224
225         DCPOMATIC_ASSERT (yuv_to_rgb < dcp::YUV_TO_RGB_COUNT);
226         int const lut[dcp::YUV_TO_RGB_COUNT] = {
227                 SWS_CS_ITU601,
228                 SWS_CS_ITU709
229         };
230
231         /* The 3rd parameter here is:
232            0 -> source range MPEG (i.e. "video", 16-235)
233            1 -> source range JPEG (i.e. "full", 0-255)
234            And the 5th:
235            0 -> destination range MPEG (i.e. "video", 16-235)
236            1 -> destination range JPEG (i.e. "full", 0-255)
237
238            But remember: sws_setColorspaceDetails ignores
239            these parameters unless the image isYUV or isGray
240            (if it's neither, it uses video range for source
241            and destination).
242         */
243         sws_setColorspaceDetails (
244                 scale_context,
245                 sws_getCoefficients (lut[yuv_to_rgb]), 0,
246                 sws_getCoefficients (lut[yuv_to_rgb]), 0,
247                 0, 1 << 16, 1 << 16
248                 );
249
250         /* Prepare input data pointers with crop */
251         uint8_t* scale_in_data[planes()];
252         for (int c = 0; c < planes(); ++c) {
253                 int const x = lrintf(bytes_per_pixel(c) * corrected_crop.left);
254                 scale_in_data[c] = data()[c] + x + stride()[c] * (corrected_crop.top / vertical_factor(c));
255         }
256
257         AVPixFmtDescriptor const * out_desc = av_pix_fmt_desc_get (out_format);
258         if (!out_desc) {
259                 throw PixelFormatError ("crop_scale_window()", out_format);
260         }
261
262         /* Corner of the image within out_size */
263         Position<int> const corner (
264                 round_width_for_subsampling((out_size.width - inter_size.width) / 2, out_desc),
265                 round_height_for_subsampling((out_size.height - inter_size.height) / 2, out_desc)
266                 );
267
268         uint8_t* scale_out_data[out->planes()];
269         for (int c = 0; c < out->planes(); ++c) {
270                 int const x = lrintf(out->bytes_per_pixel(c) * corner.x);
271                 scale_out_data[c] = out->data()[c] + x + out->stride()[c] * (corner.y / out->vertical_factor(c));
272         }
273
274         sws_scale (
275                 scale_context,
276                 scale_in_data, stride(),
277                 0, cropped_size.height,
278                 scale_out_data, out->stride()
279                 );
280
281         sws_freeContext (scale_context);
282
283         if (corrected_crop != Crop() && cropped_size == inter_size) {
284                 /* We are cropping without any scaling or pixel format conversion, so FFmpeg may have left some
285                    data behind in our image.  Clear it out.  It may get to the point where we should just stop
286                    trying to be clever with cropping.
287                 */
288                 out->make_part_black (corner.x + cropped_size.width, out_size.width - cropped_size.width);
289         }
290
291         return out;
292 }
293
294 shared_ptr<Image>
295 Image::convert_pixel_format (dcp::YUVToRGB yuv_to_rgb, AVPixelFormat out_format, bool out_aligned, bool fast) const
296 {
297         return scale(size(), yuv_to_rgb, out_format, out_aligned, fast);
298 }
299
300 /** @param out_size Size to scale to.
301  *  @param yuv_to_rgb YUVToRGB transform transform to use, if required.
302  *  @param out_format Output pixel format.
303  *  @param out_aligned true to make an aligned output image.
304  *  @param fast Try to be fast at the possible expense of quality; at present this means using
305  *  fast bilinear rather than bicubic scaling.
306  */
307 shared_ptr<Image>
308 Image::scale (dcp::Size out_size, dcp::YUVToRGB yuv_to_rgb, AVPixelFormat out_format, bool out_aligned, bool fast) const
309 {
310         /* Empirical testing suggests that sws_scale() will crash if
311            the input image is not aligned.
312         */
313         DCPOMATIC_ASSERT (aligned ());
314
315         shared_ptr<Image> scaled (new Image (out_format, out_size, out_aligned));
316
317         struct SwsContext* scale_context = sws_getContext (
318                 size().width, size().height, pixel_format(),
319                 out_size.width, out_size.height, out_format,
320                 (fast ? SWS_FAST_BILINEAR : SWS_BICUBIC) | SWS_ACCURATE_RND, 0, 0, 0
321                 );
322
323         DCPOMATIC_ASSERT (yuv_to_rgb < dcp::YUV_TO_RGB_COUNT);
324         int const lut[dcp::YUV_TO_RGB_COUNT] = {
325                 SWS_CS_ITU601,
326                 SWS_CS_ITU709
327         };
328
329         /* The 3rd parameter here is:
330            0 -> source range MPEG (i.e. "video", 16-235)
331            1 -> source range JPEG (i.e. "full", 0-255)
332            And the 5th:
333            0 -> destination range MPEG (i.e. "video", 16-235)
334            1 -> destination range JPEG (i.e. "full", 0-255)
335
336            But remember: sws_setColorspaceDetails ignores
337            these parameters unless the image isYUV or isGray
338            (if it's neither, it uses video range for source
339            and destination).
340         */
341         sws_setColorspaceDetails (
342                 scale_context,
343                 sws_getCoefficients (lut[yuv_to_rgb]), 0,
344                 sws_getCoefficients (lut[yuv_to_rgb]), 0,
345                 0, 1 << 16, 1 << 16
346                 );
347
348         sws_scale (
349                 scale_context,
350                 data(), stride(),
351                 0, size().height,
352                 scaled->data(), scaled->stride()
353                 );
354
355         sws_freeContext (scale_context);
356
357         return scaled;
358 }
359
360 /** Blacken a YUV image whose bits per pixel is rounded up to 16 */
361 void
362 Image::yuv_16_black (uint16_t v, bool alpha)
363 {
364         memset (data()[0], 0, sample_size(0).height * stride()[0]);
365         for (int i = 1; i < 3; ++i) {
366                 int16_t* p = reinterpret_cast<int16_t*> (data()[i]);
367                 int const lines = sample_size(i).height;
368                 for (int y = 0; y < lines; ++y) {
369                         /* We divide by 2 here because we are writing 2 bytes at a time */
370                         for (int x = 0; x < line_size()[i] / 2; ++x) {
371                                 p[x] = v;
372                         }
373                         p += stride()[i] / 2;
374                 }
375         }
376
377         if (alpha) {
378                 memset (data()[3], 0, sample_size(3).height * stride()[3]);
379         }
380 }
381
382 uint16_t
383 Image::swap_16 (uint16_t v)
384 {
385         return ((v >> 8) & 0xff) | ((v & 0xff) << 8);
386 }
387
388
389 /* This was a lambda in the original code */
390 static
391 void
392 y_part (Image* image, int start, int width)
393 {
394         int const bpp = image->bytes_per_pixel(0);
395         int const h = image->sample_size(0).height;
396         int const s = image->stride()[0];
397         uint8_t* p = image->data()[0];
398         for (int y = 0; y < h; ++y) {
399                 memset (p + start * bpp, 0, width * bpp);
400                 p += s;
401         }
402 }
403
404
405 void
406 Image::make_part_black (int const start, int const width)
407 {
408         switch (_pixel_format) {
409         case AV_PIX_FMT_RGB24:
410         case AV_PIX_FMT_ARGB:
411         case AV_PIX_FMT_RGBA:
412         case AV_PIX_FMT_ABGR:
413         case AV_PIX_FMT_BGRA:
414         case AV_PIX_FMT_RGB555LE:
415         case AV_PIX_FMT_RGB48LE:
416         case AV_PIX_FMT_RGB48BE:
417         case AV_PIX_FMT_XYZ12LE:
418         {
419                 int const h = sample_size(0).height;
420                 int const bpp = bytes_per_pixel(0);
421                 int const s = stride()[0];
422                 uint8_t* p = data()[0];
423                 for (int y = 0; y < h; y++) {
424                         memset (p + start * bpp, 0, width * bpp);
425                         p += s;
426                 }
427                 break;
428         }
429         case AV_PIX_FMT_YUV420P:
430         {
431                 y_part (this, start, width);
432                 for (int i = 1; i < 3; ++i) {
433                         uint8_t* p = data()[i];
434                         int const h = sample_size(i).height;
435                         for (int y = 0; y < h; ++y) {
436                                 for (int x = start / 2; x < (start + width) / 2; ++x) {
437                                         p[x] = eight_bit_uv;
438                                 }
439                                 p += stride()[i];
440                         }
441                 }
442                 break;
443         }
444         case AV_PIX_FMT_YUV422P10LE:
445         {
446                 y_part (this, start, width);
447                 for (int i = 1; i < 3; ++i) {
448                         int16_t* p = reinterpret_cast<int16_t*>(data()[i]);
449                         int const h = sample_size(i).height;
450                         for (int y = 0; y < h; ++y) {
451                                 for (int x = start / 2; x < (start + width) / 2; ++x) {
452                                         p[x] = ten_bit_uv;
453                                 }
454                                 p += stride()[i] / 2;
455                         }
456                 }
457                 break;
458         }
459         default:
460                 throw PixelFormatError ("make_part_black()", _pixel_format);
461         }
462 }
463
464 void
465 Image::make_black ()
466 {
467         switch (_pixel_format) {
468         case AV_PIX_FMT_YUV420P:
469         case AV_PIX_FMT_YUV422P:
470         case AV_PIX_FMT_YUV444P:
471         case AV_PIX_FMT_YUV411P:
472                 memset (data()[0], 0, sample_size(0).height * stride()[0]);
473                 memset (data()[1], eight_bit_uv, sample_size(1).height * stride()[1]);
474                 memset (data()[2], eight_bit_uv, sample_size(2).height * stride()[2]);
475                 break;
476
477         case AV_PIX_FMT_YUVJ420P:
478         case AV_PIX_FMT_YUVJ422P:
479         case AV_PIX_FMT_YUVJ444P:
480                 memset (data()[0], 0, sample_size(0).height * stride()[0]);
481                 memset (data()[1], eight_bit_uv + 1, sample_size(1).height * stride()[1]);
482                 memset (data()[2], eight_bit_uv + 1, sample_size(2).height * stride()[2]);
483                 break;
484
485         case AV_PIX_FMT_YUV422P9LE:
486         case AV_PIX_FMT_YUV444P9LE:
487                 yuv_16_black (nine_bit_uv, false);
488                 break;
489
490         case AV_PIX_FMT_YUV422P9BE:
491         case AV_PIX_FMT_YUV444P9BE:
492                 yuv_16_black (swap_16 (nine_bit_uv), false);
493                 break;
494
495         case AV_PIX_FMT_YUV422P10LE:
496         case AV_PIX_FMT_YUV444P10LE:
497                 yuv_16_black (ten_bit_uv, false);
498                 break;
499
500         case AV_PIX_FMT_YUV422P16LE:
501         case AV_PIX_FMT_YUV444P16LE:
502                 yuv_16_black (sixteen_bit_uv, false);
503                 break;
504
505         case AV_PIX_FMT_YUV444P10BE:
506         case AV_PIX_FMT_YUV422P10BE:
507                 yuv_16_black (swap_16 (ten_bit_uv), false);
508                 break;
509
510         case AV_PIX_FMT_YUVA420P9BE:
511         case AV_PIX_FMT_YUVA422P9BE:
512         case AV_PIX_FMT_YUVA444P9BE:
513                 yuv_16_black (swap_16 (nine_bit_uv), true);
514                 break;
515
516         case AV_PIX_FMT_YUVA420P9LE:
517         case AV_PIX_FMT_YUVA422P9LE:
518         case AV_PIX_FMT_YUVA444P9LE:
519                 yuv_16_black (nine_bit_uv, true);
520                 break;
521
522         case AV_PIX_FMT_YUVA420P10BE:
523         case AV_PIX_FMT_YUVA422P10BE:
524         case AV_PIX_FMT_YUVA444P10BE:
525                 yuv_16_black (swap_16 (ten_bit_uv), true);
526                 break;
527
528         case AV_PIX_FMT_YUVA420P10LE:
529         case AV_PIX_FMT_YUVA422P10LE:
530         case AV_PIX_FMT_YUVA444P10LE:
531                 yuv_16_black (ten_bit_uv, true);
532                 break;
533
534         case AV_PIX_FMT_YUVA420P16BE:
535         case AV_PIX_FMT_YUVA422P16BE:
536         case AV_PIX_FMT_YUVA444P16BE:
537                 yuv_16_black (swap_16 (sixteen_bit_uv), true);
538                 break;
539
540         case AV_PIX_FMT_YUVA420P16LE:
541         case AV_PIX_FMT_YUVA422P16LE:
542         case AV_PIX_FMT_YUVA444P16LE:
543                 yuv_16_black (sixteen_bit_uv, true);
544                 break;
545
546         case AV_PIX_FMT_RGB24:
547         case AV_PIX_FMT_ARGB:
548         case AV_PIX_FMT_RGBA:
549         case AV_PIX_FMT_ABGR:
550         case AV_PIX_FMT_BGRA:
551         case AV_PIX_FMT_RGB555LE:
552         case AV_PIX_FMT_RGB48LE:
553         case AV_PIX_FMT_RGB48BE:
554         case AV_PIX_FMT_XYZ12LE:
555                 memset (data()[0], 0, sample_size(0).height * stride()[0]);
556                 break;
557
558         case AV_PIX_FMT_UYVY422:
559         {
560                 int const Y = sample_size(0).height;
561                 int const X = line_size()[0];
562                 uint8_t* p = data()[0];
563                 for (int y = 0; y < Y; ++y) {
564                         for (int x = 0; x < X / 4; ++x) {
565                                 *p++ = eight_bit_uv; // Cb
566                                 *p++ = 0;            // Y0
567                                 *p++ = eight_bit_uv; // Cr
568                                 *p++ = 0;            // Y1
569                         }
570                 }
571                 break;
572         }
573
574         default:
575                 throw PixelFormatError ("make_black()", _pixel_format);
576         }
577 }
578
579 void
580 Image::make_transparent ()
581 {
582         if (_pixel_format != AV_PIX_FMT_BGRA && _pixel_format != AV_PIX_FMT_RGBA) {
583                 throw PixelFormatError ("make_transparent()", _pixel_format);
584         }
585
586         memset (data()[0], 0, sample_size(0).height * stride()[0]);
587 }
588
589 void
590 Image::alpha_blend (shared_ptr<const Image> other, Position<int> position)
591 {
592         /* We're blending RGBA or BGRA images */
593         DCPOMATIC_ASSERT (other->pixel_format() == AV_PIX_FMT_BGRA || other->pixel_format() == AV_PIX_FMT_RGBA);
594         int const blue = other->pixel_format() == AV_PIX_FMT_BGRA ? 0 : 2;
595         int const red = other->pixel_format() == AV_PIX_FMT_BGRA ? 2 : 0;
596
597         int const other_bpp = 4;
598
599         int start_tx = position.x;
600         int start_ox = 0;
601
602         if (start_tx < 0) {
603                 start_ox = -start_tx;
604                 start_tx = 0;
605         }
606
607         int start_ty = position.y;
608         int start_oy = 0;
609
610         if (start_ty < 0) {
611                 start_oy = -start_ty;
612                 start_ty = 0;
613         }
614
615         switch (_pixel_format) {
616         case AV_PIX_FMT_RGB24:
617         {
618                 /* Going onto RGB24.  First byte is red, second green, third blue */
619                 int const this_bpp = 3;
620                 for (int ty = start_ty, oy = start_oy; ty < size().height && oy < other->size().height; ++ty, ++oy) {
621                         uint8_t* tp = data()[0] + ty * stride()[0] + start_tx * this_bpp;
622                         uint8_t* op = other->data()[0] + oy * other->stride()[0];
623                         for (int tx = start_tx, ox = start_ox; tx < size().width && ox < other->size().width; ++tx, ++ox) {
624                                 float const alpha = float (op[3]) / 255;
625                                 tp[0] = op[red] * alpha + tp[0] * (1 - alpha);
626                                 tp[1] = op[1] * alpha + tp[1] * (1 - alpha);
627                                 tp[2] = op[blue] * alpha + tp[2] * (1 - alpha);
628
629                                 tp += this_bpp;
630                                 op += other_bpp;
631                         }
632                 }
633                 break;
634         }
635         case AV_PIX_FMT_BGRA:
636         {
637                 int const this_bpp = 4;
638                 for (int ty = start_ty, oy = start_oy; ty < size().height && oy < other->size().height; ++ty, ++oy) {
639                         uint8_t* tp = data()[0] + ty * stride()[0] + start_tx * this_bpp;
640                         uint8_t* op = other->data()[0] + oy * other->stride()[0];
641                         for (int tx = start_tx, ox = start_ox; tx < size().width && ox < other->size().width; ++tx, ++ox) {
642                                 float const alpha = float (op[3]) / 255;
643                                 tp[0] = op[blue] * alpha + tp[0] * (1 - alpha);
644                                 tp[1] = op[1] * alpha + tp[1] * (1 - alpha);
645                                 tp[2] = op[red] * alpha + tp[2] * (1 - alpha);
646                                 tp[3] = op[3] * alpha + tp[3] * (1 - alpha);
647
648                                 tp += this_bpp;
649                                 op += other_bpp;
650                         }
651                 }
652                 break;
653         }
654         case AV_PIX_FMT_RGBA:
655         {
656                 int const this_bpp = 4;
657                 for (int ty = start_ty, oy = start_oy; ty < size().height && oy < other->size().height; ++ty, ++oy) {
658                         uint8_t* tp = data()[0] + ty * stride()[0] + start_tx * this_bpp;
659                         uint8_t* op = other->data()[0] + oy * other->stride()[0];
660                         for (int tx = start_tx, ox = start_ox; tx < size().width && ox < other->size().width; ++tx, ++ox) {
661                                 float const alpha = float (op[3]) / 255;
662                                 tp[0] = op[red] * alpha + tp[0] * (1 - alpha);
663                                 tp[1] = op[1] * alpha + tp[1] * (1 - alpha);
664                                 tp[2] = op[blue] * alpha + tp[2] * (1 - alpha);
665                                 tp[3] = op[3] * alpha + tp[3] * (1 - alpha);
666
667                                 tp += this_bpp;
668                                 op += other_bpp;
669                         }
670                 }
671                 break;
672         }
673         case AV_PIX_FMT_RGB48LE:
674         {
675                 int const this_bpp = 6;
676                 for (int ty = start_ty, oy = start_oy; ty < size().height && oy < other->size().height; ++ty, ++oy) {
677                         uint8_t* tp = data()[0] + ty * stride()[0] + start_tx * this_bpp;
678                         uint8_t* op = other->data()[0] + oy * other->stride()[0];
679                         for (int tx = start_tx, ox = start_ox; tx < size().width && ox < other->size().width; ++tx, ++ox) {
680                                 float const alpha = float (op[3]) / 255;
681                                 /* Blend high bytes */
682                                 tp[1] = op[red] * alpha + tp[1] * (1 - alpha);
683                                 tp[3] = op[1] * alpha + tp[3] * (1 - alpha);
684                                 tp[5] = op[blue] * alpha + tp[5] * (1 - alpha);
685
686                                 tp += this_bpp;
687                                 op += other_bpp;
688                         }
689                 }
690                 break;
691         }
692         case AV_PIX_FMT_XYZ12LE:
693         {
694                 dcp::ColourConversion conv = dcp::ColourConversion::srgb_to_xyz();
695                 double fast_matrix[9];
696                 dcp::combined_rgb_to_xyz (conv, fast_matrix);
697                 double const * lut_in = conv.in()->lut (8, false);
698                 double const * lut_out = conv.out()->lut (16, true);
699                 int const this_bpp = 6;
700                 for (int ty = start_ty, oy = start_oy; ty < size().height && oy < other->size().height; ++ty, ++oy) {
701                         uint16_t* tp = reinterpret_cast<uint16_t*> (data()[0] + ty * stride()[0] + start_tx * this_bpp);
702                         uint8_t* op = other->data()[0] + oy * other->stride()[0];
703                         for (int tx = start_tx, ox = start_ox; tx < size().width && ox < other->size().width; ++tx, ++ox) {
704                                 float const alpha = float (op[3]) / 255;
705
706                                 /* Convert sRGB to XYZ; op is BGRA.  First, input gamma LUT */
707                                 double const r = lut_in[op[red]];
708                                 double const g = lut_in[op[1]];
709                                 double const b = lut_in[op[blue]];
710
711                                 /* RGB to XYZ, including Bradford transform and DCI companding */
712                                 double const x = max (0.0, min (65535.0, r * fast_matrix[0] + g * fast_matrix[1] + b * fast_matrix[2]));
713                                 double const y = max (0.0, min (65535.0, r * fast_matrix[3] + g * fast_matrix[4] + b * fast_matrix[5]));
714                                 double const z = max (0.0, min (65535.0, r * fast_matrix[6] + g * fast_matrix[7] + b * fast_matrix[8]));
715
716                                 /* Out gamma LUT and blend */
717                                 tp[0] = lrint(lut_out[lrint(x)] * 65535) * alpha + tp[0] * (1 - alpha);
718                                 tp[1] = lrint(lut_out[lrint(y)] * 65535) * alpha + tp[1] * (1 - alpha);
719                                 tp[2] = lrint(lut_out[lrint(z)] * 65535) * alpha + tp[2] * (1 - alpha);
720
721                                 tp += this_bpp / 2;
722                                 op += other_bpp;
723                         }
724                 }
725                 break;
726         }
727         case AV_PIX_FMT_YUV420P:
728         {
729                 shared_ptr<Image> yuv = other->convert_pixel_format (dcp::YUV_TO_RGB_REC709, _pixel_format, false, false);
730                 dcp::Size const ts = size();
731                 dcp::Size const os = yuv->size();
732                 for (int ty = start_ty, oy = start_oy; ty < ts.height && oy < os.height; ++ty, ++oy) {
733                         int const hty = ty / 2;
734                         int const hoy = oy / 2;
735                         uint8_t* tY = data()[0] + (ty * stride()[0]) + start_tx;
736                         uint8_t* tU = data()[1] + (hty * stride()[1]) + start_tx / 2;
737                         uint8_t* tV = data()[2] + (hty * stride()[2]) + start_tx / 2;
738                         uint8_t* oY = yuv->data()[0] + (oy * yuv->stride()[0]) + start_ox;
739                         uint8_t* oU = yuv->data()[1] + (hoy * yuv->stride()[1]) + start_ox / 2;
740                         uint8_t* oV = yuv->data()[2] + (hoy * yuv->stride()[2]) + start_ox / 2;
741                         uint8_t* alpha = other->data()[0] + (oy * other->stride()[0]) + start_ox * 4;
742                         for (int tx = start_tx, ox = start_ox; tx < ts.width && ox < os.width; ++tx, ++ox) {
743                                 float const a = float(alpha[3]) / 255;
744                                 *tY = *oY * a + *tY * (1 - a);
745                                 *tU = *oU * a + *tU * (1 - a);
746                                 *tV = *oV * a + *tV * (1 - a);
747                                 ++tY;
748                                 ++oY;
749                                 if (tx % 2) {
750                                         ++tU;
751                                         ++tV;
752                                 }
753                                 if (ox % 2) {
754                                         ++oU;
755                                         ++oV;
756                                 }
757                                 alpha += 4;
758                         }
759                 }
760                 break;
761         }
762         case AV_PIX_FMT_YUV420P10:
763         {
764                 shared_ptr<Image> yuv = other->convert_pixel_format (dcp::YUV_TO_RGB_REC709, _pixel_format, false, false);
765                 dcp::Size const ts = size();
766                 dcp::Size const os = yuv->size();
767                 for (int ty = start_ty, oy = start_oy; ty < ts.height && oy < os.height; ++ty, ++oy) {
768                         int const hty = ty / 2;
769                         int const hoy = oy / 2;
770                         uint16_t* tY = ((uint16_t *) (data()[0] + (ty * stride()[0]))) + start_tx;
771                         uint16_t* tU = ((uint16_t *) (data()[1] + (hty * stride()[1]))) + start_tx / 2;
772                         uint16_t* tV = ((uint16_t *) (data()[2] + (hty * stride()[2]))) + start_tx / 2;
773                         uint16_t* oY = ((uint16_t *) (yuv->data()[0] + (oy * yuv->stride()[0]))) + start_ox;
774                         uint16_t* oU = ((uint16_t *) (yuv->data()[1] + (hoy * yuv->stride()[1]))) + start_ox / 2;
775                         uint16_t* oV = ((uint16_t *) (yuv->data()[2] + (hoy * yuv->stride()[2]))) + start_ox / 2;
776                         uint8_t* alpha = other->data()[0] + (oy * other->stride()[0]) + start_ox * 4;
777                         for (int tx = start_tx, ox = start_ox; tx < ts.width && ox < os.width; ++tx, ++ox) {
778                                 float const a = float(alpha[3]) / 255;
779                                 *tY = *oY * a + *tY * (1 - a);
780                                 *tU = *oU * a + *tU * (1 - a);
781                                 *tV = *oV * a + *tV * (1 - a);
782                                 ++tY;
783                                 ++oY;
784                                 if (tx % 2) {
785                                         ++tU;
786                                         ++tV;
787                                 }
788                                 if (ox % 2) {
789                                         ++oU;
790                                         ++oV;
791                                 }
792                                 alpha += 4;
793                         }
794                 }
795                 break;
796         }
797         case AV_PIX_FMT_YUV422P10LE:
798         {
799                 shared_ptr<Image> yuv = other->convert_pixel_format (dcp::YUV_TO_RGB_REC709, _pixel_format, false, false);
800                 dcp::Size const ts = size();
801                 dcp::Size const os = yuv->size();
802                 for (int ty = start_ty, oy = start_oy; ty < ts.height && oy < os.height; ++ty, ++oy) {
803                         uint16_t* tY = ((uint16_t *) (data()[0] + (ty * stride()[0]))) + start_tx;
804                         uint16_t* tU = ((uint16_t *) (data()[1] + (ty * stride()[1]))) + start_tx / 2;
805                         uint16_t* tV = ((uint16_t *) (data()[2] + (ty * stride()[2]))) + start_tx / 2;
806                         uint16_t* oY = ((uint16_t *) (yuv->data()[0] + (oy * yuv->stride()[0]))) + start_ox;
807                         uint16_t* oU = ((uint16_t *) (yuv->data()[1] + (oy * yuv->stride()[1]))) + start_ox / 2;
808                         uint16_t* oV = ((uint16_t *) (yuv->data()[2] + (oy * yuv->stride()[2]))) + start_ox / 2;
809                         uint8_t* alpha = other->data()[0] + (oy * other->stride()[0]) + start_ox * 4;
810                         for (int tx = start_tx, ox = start_ox; tx < ts.width && ox < os.width; ++tx, ++ox) {
811                                 float const a = float(alpha[3]) / 255;
812                                 *tY = *oY * a + *tY * (1 - a);
813                                 *tU = *oU * a + *tU * (1 - a);
814                                 *tV = *oV * a + *tV * (1 - a);
815                                 ++tY;
816                                 ++oY;
817                                 if (tx % 2) {
818                                         ++tU;
819                                         ++tV;
820                                 }
821                                 if (ox % 2) {
822                                         ++oU;
823                                         ++oV;
824                                 }
825                                 alpha += 4;
826                         }
827                 }
828                 break;
829         }
830         default:
831                 throw PixelFormatError ("alpha_blend()", _pixel_format);
832         }
833 }
834
835 void
836 Image::copy (shared_ptr<const Image> other, Position<int> position)
837 {
838         /* Only implemented for RGB24 onto RGB24 so far */
839         DCPOMATIC_ASSERT (_pixel_format == AV_PIX_FMT_RGB24 && other->pixel_format() == AV_PIX_FMT_RGB24);
840         DCPOMATIC_ASSERT (position.x >= 0 && position.y >= 0);
841
842         int const N = min (position.x + other->size().width, size().width) - position.x;
843         for (int ty = position.y, oy = 0; ty < size().height && oy < other->size().height; ++ty, ++oy) {
844                 uint8_t * const tp = data()[0] + ty * stride()[0] + position.x * 3;
845                 uint8_t * const op = other->data()[0] + oy * other->stride()[0];
846                 memcpy (tp, op, N * 3);
847         }
848 }
849
850 void
851 Image::read_from_socket (shared_ptr<Socket> socket)
852 {
853         for (int i = 0; i < planes(); ++i) {
854                 uint8_t* p = data()[i];
855                 int const lines = sample_size(i).height;
856                 for (int y = 0; y < lines; ++y) {
857                         socket->read (p, line_size()[i]);
858                         p += stride()[i];
859                 }
860         }
861 }
862
863 void
864 Image::write_to_socket (shared_ptr<Socket> socket) const
865 {
866         for (int i = 0; i < planes(); ++i) {
867                 uint8_t* p = data()[i];
868                 int const lines = sample_size(i).height;
869                 for (int y = 0; y < lines; ++y) {
870                         socket->write (p, line_size()[i]);
871                         p += stride()[i];
872                 }
873         }
874 }
875
876 float
877 Image::bytes_per_pixel (int c) const
878 {
879         AVPixFmtDescriptor const * d = av_pix_fmt_desc_get(_pixel_format);
880         if (!d) {
881                 throw PixelFormatError ("bytes_per_pixel()", _pixel_format);
882         }
883
884         if (c >= planes()) {
885                 return 0;
886         }
887
888         float bpp[4] = { 0, 0, 0, 0 };
889
890 #ifdef DCPOMATIC_HAVE_AVCOMPONENTDESCRIPTOR_DEPTH_MINUS1
891         bpp[0] = floor ((d->comp[0].depth_minus1 + 8) / 8);
892         if (d->nb_components > 1) {
893                 bpp[1] = floor ((d->comp[1].depth_minus1 + 8) / 8) / pow (2.0f, d->log2_chroma_w);
894         }
895         if (d->nb_components > 2) {
896                 bpp[2] = floor ((d->comp[2].depth_minus1 + 8) / 8) / pow (2.0f, d->log2_chroma_w);
897         }
898         if (d->nb_components > 3) {
899                 bpp[3] = floor ((d->comp[3].depth_minus1 + 8) / 8) / pow (2.0f, d->log2_chroma_w);
900         }
901 #else
902         bpp[0] = floor ((d->comp[0].depth + 7) / 8);
903         if (d->nb_components > 1) {
904                 bpp[1] = floor ((d->comp[1].depth + 7) / 8) / pow (2.0f, d->log2_chroma_w);
905         }
906         if (d->nb_components > 2) {
907                 bpp[2] = floor ((d->comp[2].depth + 7) / 8) / pow (2.0f, d->log2_chroma_w);
908         }
909         if (d->nb_components > 3) {
910                 bpp[3] = floor ((d->comp[3].depth + 7) / 8) / pow (2.0f, d->log2_chroma_w);
911         }
912 #endif
913
914         if ((d->flags & AV_PIX_FMT_FLAG_PLANAR) == 0) {
915                 /* Not planar; sum them up */
916                 return bpp[0] + bpp[1] + bpp[2] + bpp[3];
917         }
918
919         return bpp[c];
920 }
921
922 /** Construct a Image of a given size and format, allocating memory
923  *  as required.
924  *
925  *  @param p Pixel format.
926  *  @param s Size in pixels.
927  *  @param aligned true to make each row of this image aligned to a ALIGNMENT-byte boundary.
928  */
929 Image::Image (AVPixelFormat p, dcp::Size s, bool aligned)
930         : _size (s)
931         , _pixel_format (p)
932         , _aligned (aligned)
933 {
934         allocate ();
935 }
936
937 void
938 Image::allocate ()
939 {
940         _data = (uint8_t **) wrapped_av_malloc (4 * sizeof (uint8_t *));
941         _data[0] = _data[1] = _data[2] = _data[3] = 0;
942
943         _line_size = (int *) wrapped_av_malloc (4 * sizeof (int));
944         _line_size[0] = _line_size[1] = _line_size[2] = _line_size[3] = 0;
945
946         _stride = (int *) wrapped_av_malloc (4 * sizeof (int));
947         _stride[0] = _stride[1] = _stride[2] = _stride[3] = 0;
948
949         for (int i = 0; i < planes(); ++i) {
950                 _line_size[i] = ceil (_size.width * bytes_per_pixel(i));
951                 _stride[i] = stride_round_up (i, _line_size, _aligned ? ALIGNMENT : 1);
952
953                 /* The assembler function ff_rgb24ToY_avx (in libswscale/x86/input.asm)
954                    uses a 16-byte fetch to read three bytes (R/G/B) of image data.
955                    Hence on the last pixel of the last line it reads over the end of
956                    the actual data by 1 byte.  If the width of an image is a multiple
957                    of the stride alignment there will be no padding at the end of image lines.
958                    OS X crashes on this illegal read, though other operating systems don't
959                    seem to mind.  The nasty + 1 in this malloc makes sure there is always a byte
960                    for that instruction to read safely.
961
962                    Further to the above, valgrind is now telling me that ff_rgb24ToY_ssse3
963                    over-reads by more then _avx.  I can't follow the code to work out how much,
964                    so I'll just over-allocate by ALIGNMENT bytes and have done with it.  Empirical
965                    testing suggests that it works.
966
967                    In addition to these concerns, we may read/write as much as a whole extra line
968                    at the end of each plane in cases where we are messing with offsets in order to
969                    do pad or crop.  To solve this we over-allocate by an extra _stride[i] bytes.
970
971                    As an example: we may write to images starting at an offset so we get some padding.
972                    Hence we want to write in the following pattern:
973
974                    block start   write start                                  line end
975                    |..(padding)..|<------line-size------------->|..(padding)..|
976                    |..(padding)..|<------line-size------------->|..(padding)..|
977                    |..(padding)..|<------line-size------------->|..(padding)..|
978
979                    where line-size is of the smaller (inter_size) image and the full padded line length is that of
980                    out_size.  To get things to work we have to tell FFmpeg that the stride is that of out_size.
981                    However some parts of FFmpeg (notably rgb48Toxyz12 in swscale.c) process data for the full
982                    specified *stride*.  This does not matter until we get to the last line:
983
984                    block start   write start                                  line end
985                    |..(padding)..|<------line-size------------->|XXXwrittenXXX|
986                    |XXXwrittenXXX|<------line-size------------->|XXXwrittenXXX|
987                    |XXXwrittenXXX|<------line-size------------->|XXXwrittenXXXXXXwrittenXXX
988                                                                                ^^^^ out of bounds
989                 */
990                 _data[i] = (uint8_t *) wrapped_av_malloc (_stride[i] * (sample_size(i).height + 1) + ALIGNMENT);
991 #if HAVE_VALGRIND_MEMCHECK_H
992                 /* The data between the end of the line size and the stride is undefined but processed by
993                    libswscale, causing lots of valgrind errors.  Mark it all defined to quell these errors.
994                 */
995                 VALGRIND_MAKE_MEM_DEFINED (_data[i], _stride[i] * (sample_size(i).height + 1) + ALIGNMENT);
996 #endif
997         }
998 }
999
1000 Image::Image (Image const & other)
1001         : boost::enable_shared_from_this<Image>(other)
1002         , _size (other._size)
1003         , _pixel_format (other._pixel_format)
1004         , _aligned (other._aligned)
1005 {
1006         allocate ();
1007
1008         for (int i = 0; i < planes(); ++i) {
1009                 uint8_t* p = _data[i];
1010                 uint8_t* q = other._data[i];
1011                 int const lines = sample_size(i).height;
1012                 for (int j = 0; j < lines; ++j) {
1013                         memcpy (p, q, _line_size[i]);
1014                         p += stride()[i];
1015                         q += other.stride()[i];
1016                 }
1017         }
1018 }
1019
1020 Image::Image (AVFrame* frame)
1021         : _size (frame->width, frame->height)
1022         , _pixel_format (static_cast<AVPixelFormat> (frame->format))
1023         , _aligned (true)
1024 {
1025         allocate ();
1026
1027         for (int i = 0; i < planes(); ++i) {
1028                 uint8_t* p = _data[i];
1029                 uint8_t* q = frame->data[i];
1030                 int const lines = sample_size(i).height;
1031                 for (int j = 0; j < lines; ++j) {
1032                         memcpy (p, q, _line_size[i]);
1033                         p += stride()[i];
1034                         /* AVFrame's linesize is what we call `stride' */
1035                         q += frame->linesize[i];
1036                 }
1037         }
1038 }
1039
1040 Image::Image (shared_ptr<const Image> other, bool aligned)
1041         : _size (other->_size)
1042         , _pixel_format (other->_pixel_format)
1043         , _aligned (aligned)
1044 {
1045         allocate ();
1046
1047         for (int i = 0; i < planes(); ++i) {
1048                 DCPOMATIC_ASSERT (line_size()[i] == other->line_size()[i]);
1049                 uint8_t* p = _data[i];
1050                 uint8_t* q = other->data()[i];
1051                 int const lines = sample_size(i).height;
1052                 for (int j = 0; j < lines; ++j) {
1053                         memcpy (p, q, line_size()[i]);
1054                         p += stride()[i];
1055                         q += other->stride()[i];
1056                 }
1057         }
1058 }
1059
1060 Image&
1061 Image::operator= (Image const & other)
1062 {
1063         if (this == &other) {
1064                 return *this;
1065         }
1066
1067         Image tmp (other);
1068         swap (tmp);
1069         return *this;
1070 }
1071
1072 void
1073 Image::swap (Image & other)
1074 {
1075         std::swap (_size, other._size);
1076         std::swap (_pixel_format, other._pixel_format);
1077
1078         for (int i = 0; i < 4; ++i) {
1079                 std::swap (_data[i], other._data[i]);
1080                 std::swap (_line_size[i], other._line_size[i]);
1081                 std::swap (_stride[i], other._stride[i]);
1082         }
1083
1084         std::swap (_aligned, other._aligned);
1085 }
1086
1087 /** Destroy a Image */
1088 Image::~Image ()
1089 {
1090         for (int i = 0; i < planes(); ++i) {
1091                 av_free (_data[i]);
1092         }
1093
1094         av_free (_data);
1095         av_free (_line_size);
1096         av_free (_stride);
1097 }
1098
1099 uint8_t * const *
1100 Image::data () const
1101 {
1102         return _data;
1103 }
1104
1105 int const *
1106 Image::line_size () const
1107 {
1108         return _line_size;
1109 }
1110
1111 int const *
1112 Image::stride () const
1113 {
1114         return _stride;
1115 }
1116
1117 dcp::Size
1118 Image::size () const
1119 {
1120         return _size;
1121 }
1122
1123 bool
1124 Image::aligned () const
1125 {
1126         return _aligned;
1127 }
1128
1129 PositionImage
1130 merge (list<PositionImage> images)
1131 {
1132         if (images.empty ()) {
1133                 return PositionImage ();
1134         }
1135
1136         if (images.size() == 1) {
1137                 return images.front ();
1138         }
1139
1140         dcpomatic::Rect<int> all (images.front().position, images.front().image->size().width, images.front().image->size().height);
1141         for (list<PositionImage>::const_iterator i = images.begin(); i != images.end(); ++i) {
1142                 all.extend (dcpomatic::Rect<int> (i->position, i->image->size().width, i->image->size().height));
1143         }
1144
1145         shared_ptr<Image> merged (new Image (images.front().image->pixel_format (), dcp::Size (all.width, all.height), true));
1146         merged->make_transparent ();
1147         for (list<PositionImage>::const_iterator i = images.begin(); i != images.end(); ++i) {
1148                 merged->alpha_blend (i->image, i->position - all.position());
1149         }
1150
1151         return PositionImage (merged, all.position ());
1152 }
1153
1154 bool
1155 operator== (Image const & a, Image const & b)
1156 {
1157         if (a.planes() != b.planes() || a.pixel_format() != b.pixel_format() || a.aligned() != b.aligned()) {
1158                 return false;
1159         }
1160
1161         for (int c = 0; c < a.planes(); ++c) {
1162                 if (a.sample_size(c).height != b.sample_size(c).height || a.line_size()[c] != b.line_size()[c] || a.stride()[c] != b.stride()[c]) {
1163                         return false;
1164                 }
1165
1166                 uint8_t* p = a.data()[c];
1167                 uint8_t* q = b.data()[c];
1168                 int const lines = a.sample_size(c).height;
1169                 for (int y = 0; y < lines; ++y) {
1170                         if (memcmp (p, q, a.line_size()[c]) != 0) {
1171                                 return false;
1172                         }
1173
1174                         p += a.stride()[c];
1175                         q += b.stride()[c];
1176                 }
1177         }
1178
1179         return true;
1180 }
1181
1182 /** Fade the image.
1183  *  @param f Amount to fade by; 0 is black, 1 is no fade.
1184  */
1185 void
1186 Image::fade (float f)
1187 {
1188         /* U/V black value for 8-bit colour */
1189         static int const eight_bit_uv =    (1 << 7) - 1;
1190         /* U/V black value for 10-bit colour */
1191         static uint16_t const ten_bit_uv = (1 << 9) - 1;
1192
1193         switch (_pixel_format) {
1194         case AV_PIX_FMT_YUV420P:
1195         {
1196                 /* Y */
1197                 uint8_t* p = data()[0];
1198                 int const lines = sample_size(0).height;
1199                 for (int y = 0; y < lines; ++y) {
1200                         uint8_t* q = p;
1201                         for (int x = 0; x < line_size()[0]; ++x) {
1202                                 *q = int(float(*q) * f);
1203                                 ++q;
1204                         }
1205                         p += stride()[0];
1206                 }
1207
1208                 /* U, V */
1209                 for (int c = 1; c < 3; ++c) {
1210                         uint8_t* p = data()[c];
1211                         int const lines = sample_size(c).height;
1212                         for (int y = 0; y < lines; ++y) {
1213                                 uint8_t* q = p;
1214                                 for (int x = 0; x < line_size()[c]; ++x) {
1215                                         *q = eight_bit_uv + int((int(*q) - eight_bit_uv) * f);
1216                                         ++q;
1217                                 }
1218                                 p += stride()[c];
1219                         }
1220                 }
1221
1222                 break;
1223         }
1224
1225         case AV_PIX_FMT_RGB24:
1226         {
1227                 /* 8-bit */
1228                 uint8_t* p = data()[0];
1229                 int const lines = sample_size(0).height;
1230                 for (int y = 0; y < lines; ++y) {
1231                         uint8_t* q = p;
1232                         for (int x = 0; x < line_size()[0]; ++x) {
1233                                 *q = int (float (*q) * f);
1234                                 ++q;
1235                         }
1236                         p += stride()[0];
1237                 }
1238                 break;
1239         }
1240
1241         case AV_PIX_FMT_XYZ12LE:
1242         case AV_PIX_FMT_RGB48LE:
1243                 /* 16-bit little-endian */
1244                 for (int c = 0; c < 3; ++c) {
1245                         int const stride_pixels = stride()[c] / 2;
1246                         int const line_size_pixels = line_size()[c] / 2;
1247                         uint16_t* p = reinterpret_cast<uint16_t*> (data()[c]);
1248                         int const lines = sample_size(c).height;
1249                         for (int y = 0; y < lines; ++y) {
1250                                 uint16_t* q = p;
1251                                 for (int x = 0; x < line_size_pixels; ++x) {
1252                                         *q = int (float (*q) * f);
1253                                         ++q;
1254                                 }
1255                                 p += stride_pixels;
1256                         }
1257                 }
1258                 break;
1259
1260         case AV_PIX_FMT_YUV422P10LE:
1261         {
1262                 /* Y */
1263                 {
1264                         int const stride_pixels = stride()[0] / 2;
1265                         int const line_size_pixels = line_size()[0] / 2;
1266                         uint16_t* p = reinterpret_cast<uint16_t*> (data()[0]);
1267                         int const lines = sample_size(0).height;
1268                         for (int y = 0; y < lines; ++y) {
1269                                 uint16_t* q = p;
1270                                 for (int x = 0; x < line_size_pixels; ++x) {
1271                                         *q = int(float(*q) * f);
1272                                         ++q;
1273                                 }
1274                                 p += stride_pixels;
1275                         }
1276                 }
1277
1278                 /* U, V */
1279                 for (int c = 1; c < 3; ++c) {
1280                         int const stride_pixels = stride()[c] / 2;
1281                         int const line_size_pixels = line_size()[c] / 2;
1282                         uint16_t* p = reinterpret_cast<uint16_t*> (data()[c]);
1283                         int const lines = sample_size(c).height;
1284                         for (int y = 0; y < lines; ++y) {
1285                                 uint16_t* q = p;
1286                                 for (int x = 0; x < line_size_pixels; ++x) {
1287                                         *q = ten_bit_uv + int((int(*q) - ten_bit_uv) * f);
1288                                         ++q;
1289                                 }
1290                                 p += stride_pixels;
1291                         }
1292                 }
1293                 break;
1294
1295         }
1296
1297         default:
1298                 throw PixelFormatError ("fade()", _pixel_format);
1299         }
1300 }
1301
1302 shared_ptr<const Image>
1303 Image::ensure_aligned (shared_ptr<const Image> image)
1304 {
1305         if (image->aligned()) {
1306                 return image;
1307         }
1308
1309         return shared_ptr<Image> (new Image (image, true));
1310 }
1311
1312 size_t
1313 Image::memory_used () const
1314 {
1315         size_t m = 0;
1316         for (int i = 0; i < planes(); ++i) {
1317                 m += _stride[i] * sample_size(i).height;
1318         }
1319         return m;
1320 }
1321
1322 class Memory
1323 {
1324 public:
1325         Memory ()
1326                 : data(0)
1327                 , size(0)
1328         {}
1329
1330         ~Memory ()
1331         {
1332                 free (data);
1333         }
1334
1335         uint8_t* data;
1336         size_t size;
1337 };
1338
1339 static void
1340 png_write_data (png_structp png_ptr, png_bytep data, png_size_t length)
1341 {
1342         Memory* mem = reinterpret_cast<Memory*>(png_get_io_ptr(png_ptr));
1343         size_t size = mem->size + length;
1344
1345         if (mem->data) {
1346                 mem->data = reinterpret_cast<uint8_t*>(realloc(mem->data, size));
1347         } else {
1348                 mem->data = reinterpret_cast<uint8_t*>(malloc(size));
1349         }
1350
1351         if (!mem->data) {
1352                 throw EncodeError (N_("could not allocate memory for PNG"));
1353         }
1354
1355         memcpy (mem->data + mem->size, data, length);
1356         mem->size += length;
1357 }
1358
1359 static void
1360 png_flush (png_structp)
1361 {
1362
1363 }
1364
1365 static void
1366 png_error_fn (png_structp png_ptr, char const * message)
1367 {
1368         reinterpret_cast<Image*>(png_get_error_ptr(png_ptr))->png_error (message);
1369 }
1370
1371 void
1372 Image::png_error (char const * message)
1373 {
1374         throw EncodeError (String::compose ("Error during PNG write: %1", message));
1375 }
1376
1377 dcp::Data
1378 Image::as_png () const
1379 {
1380         DCPOMATIC_ASSERT (bytes_per_pixel(0) == 4);
1381         DCPOMATIC_ASSERT (planes() == 1);
1382         if (pixel_format() != AV_PIX_FMT_RGBA) {
1383                 return convert_pixel_format(dcp::YUV_TO_RGB_REC709, AV_PIX_FMT_RGBA, true, false)->as_png();
1384         }
1385
1386         /* error handling? */
1387         png_structp png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING, reinterpret_cast<void*>(const_cast<Image*>(this)), png_error_fn, 0);
1388         if (!png_ptr) {
1389                 throw EncodeError (N_("could not create PNG write struct"));
1390         }
1391
1392         Memory state;
1393
1394         png_set_write_fn (png_ptr, &state, png_write_data, png_flush);
1395
1396         png_infop info_ptr = png_create_info_struct(png_ptr);
1397         if (!info_ptr) {
1398                 png_destroy_write_struct (&png_ptr, &info_ptr);
1399                 throw EncodeError (N_("could not create PNG info struct"));
1400         }
1401
1402         png_set_IHDR (png_ptr, info_ptr, size().width, size().height, 8, PNG_COLOR_TYPE_RGBA, PNG_INTERLACE_NONE, PNG_COMPRESSION_TYPE_DEFAULT, PNG_FILTER_TYPE_DEFAULT);
1403
1404         png_byte ** row_pointers = reinterpret_cast<png_byte **>(png_malloc(png_ptr, size().height * sizeof(png_byte *)));
1405         for (int i = 0; i < size().height; ++i) {
1406                 row_pointers[i] = (png_byte *) (data()[0] + i * stride()[0]);
1407         }
1408
1409         png_write_info (png_ptr, info_ptr);
1410         png_write_image (png_ptr, row_pointers);
1411         png_write_end (png_ptr, info_ptr);
1412
1413         png_destroy_write_struct (&png_ptr, &info_ptr);
1414         png_free (png_ptr, row_pointers);
1415
1416         return dcp::Data (state.data, state.size);
1417 }