FFmpeg
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
pngenc.c
Go to the documentation of this file.
1 /*
2  * PNG image format
3  * Copyright (c) 2003 Fabrice Bellard
4  *
5  * This file is part of FFmpeg.
6  *
7  * FFmpeg is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2.1 of the License, or (at your option) any later version.
11  *
12  * FFmpeg is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public
18  * License along with FFmpeg; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20  */
21 
22 #include "avcodec.h"
23 #include "internal.h"
24 #include "bytestream.h"
25 #include "huffyuvencdsp.h"
26 #include "png.h"
27 #include "apng.h"
28 
29 #include "libavutil/avassert.h"
30 #include "libavutil/crc.h"
31 #include "libavutil/libm.h"
32 #include "libavutil/opt.h"
33 #include "libavutil/color_utils.h"
34 
35 #include <zlib.h>
36 
37 #define IOBUF_SIZE 4096
38 
39 typedef struct APNGFctlChunk {
40  uint32_t sequence_number;
41  uint32_t width, height;
42  uint32_t x_offset, y_offset;
43  uint16_t delay_num, delay_den;
46 
47 typedef struct PNGEncContext {
48  AVClass *class;
50 
54 
56 
57  z_stream zstream;
59  int dpi; ///< Physical pixel density, in dots per inch, if set
60  int dpm; ///< Physical pixel density, in dots per meter, if set
61 
63  int bit_depth;
66 
67  // APNG
68  uint32_t palette_checksum; // Used to ensure a single unique palette
69  uint32_t sequence_number;
70 
77 
78 static void png_get_interlaced_row(uint8_t *dst, int row_size,
79  int bits_per_pixel, int pass,
80  const uint8_t *src, int width)
81 {
82  int x, mask, dst_x, j, b, bpp;
83  uint8_t *d;
84  const uint8_t *s;
85  static const int masks[] = {0x80, 0x08, 0x88, 0x22, 0xaa, 0x55, 0xff};
86 
87  mask = masks[pass];
88  switch (bits_per_pixel) {
89  case 1:
90  memset(dst, 0, row_size);
91  dst_x = 0;
92  for (x = 0; x < width; x++) {
93  j = (x & 7);
94  if ((mask << j) & 0x80) {
95  b = (src[x >> 3] >> (7 - j)) & 1;
96  dst[dst_x >> 3] |= b << (7 - (dst_x & 7));
97  dst_x++;
98  }
99  }
100  break;
101  default:
102  bpp = bits_per_pixel >> 3;
103  d = dst;
104  s = src;
105  for (x = 0; x < width; x++) {
106  j = x & 7;
107  if ((mask << j) & 0x80) {
108  memcpy(d, s, bpp);
109  d += bpp;
110  }
111  s += bpp;
112  }
113  break;
114  }
115 }
116 
118  int w, int bpp)
119 {
120  int i;
121  for (i = 0; i < w; i++) {
122  int a, b, c, p, pa, pb, pc;
123 
124  a = src[i - bpp];
125  b = top[i];
126  c = top[i - bpp];
127 
128  p = b - c;
129  pc = a - c;
130 
131  pa = abs(p);
132  pb = abs(pc);
133  pc = abs(p + pc);
134 
135  if (pa <= pb && pa <= pc)
136  p = a;
137  else if (pb <= pc)
138  p = b;
139  else
140  p = c;
141  dst[i] = src[i] - p;
142  }
143 }
144 
145 static void sub_left_prediction(PNGEncContext *c, uint8_t *dst, const uint8_t *src, int bpp, int size)
146 {
147  const uint8_t *src1 = src + bpp;
148  const uint8_t *src2 = src;
149  int x, unaligned_w;
150 
151  memcpy(dst, src, bpp);
152  dst += bpp;
153  size -= bpp;
154  unaligned_w = FFMIN(32 - bpp, size);
155  for (x = 0; x < unaligned_w; x++)
156  *dst++ = *src1++ - *src2++;
157  size -= unaligned_w;
158  c->hdsp.diff_bytes(dst, src1, src2, size);
159 }
160 
161 static void png_filter_row(PNGEncContext *c, uint8_t *dst, int filter_type,
162  uint8_t *src, uint8_t *top, int size, int bpp)
163 {
164  int i;
165 
166  switch (filter_type) {
168  memcpy(dst, src, size);
169  break;
171  sub_left_prediction(c, dst, src, bpp, size);
172  break;
173  case PNG_FILTER_VALUE_UP:
174  c->hdsp.diff_bytes(dst, src, top, size);
175  break;
177  for (i = 0; i < bpp; i++)
178  dst[i] = src[i] - (top[i] >> 1);
179  for (; i < size; i++)
180  dst[i] = src[i] - ((src[i - bpp] + top[i]) >> 1);
181  break;
183  for (i = 0; i < bpp; i++)
184  dst[i] = src[i] - top[i];
185  sub_png_paeth_prediction(dst + i, src + i, top + i, size - i, bpp);
186  break;
187  }
188 }
189 
191  uint8_t *src, uint8_t *top, int size, int bpp)
192 {
193  int pred = s->filter_type;
194  av_assert0(bpp || !pred);
195  if (!top && pred)
196  pred = PNG_FILTER_VALUE_SUB;
197  if (pred == PNG_FILTER_VALUE_MIXED) {
198  int i;
199  int cost, bcost = INT_MAX;
200  uint8_t *buf1 = dst, *buf2 = dst + size + 16;
201  for (pred = 0; pred < 5; pred++) {
202  png_filter_row(s, buf1 + 1, pred, src, top, size, bpp);
203  buf1[0] = pred;
204  cost = 0;
205  for (i = 0; i <= size; i++)
206  cost += abs((int8_t) buf1[i]);
207  if (cost < bcost) {
208  bcost = cost;
209  FFSWAP(uint8_t *, buf1, buf2);
210  }
211  }
212  return buf2;
213  } else {
214  png_filter_row(s, dst + 1, pred, src, top, size, bpp);
215  dst[0] = pred;
216  return dst;
217  }
218 }
219 
220 static void png_write_chunk(uint8_t **f, uint32_t tag,
221  const uint8_t *buf, int length)
222 {
223  const AVCRC *crc_table = av_crc_get_table(AV_CRC_32_IEEE_LE);
224  uint32_t crc = ~0U;
225  uint8_t tagbuf[4];
226 
227  bytestream_put_be32(f, length);
228  AV_WL32(tagbuf, tag);
229  crc = av_crc(crc_table, crc, tagbuf, 4);
230  bytestream_put_be32(f, av_bswap32(tag));
231  if (length > 0) {
232  crc = av_crc(crc_table, crc, buf, length);
233  memcpy(*f, buf, length);
234  *f += length;
235  }
236  bytestream_put_be32(f, ~crc);
237 }
238 
240  const uint8_t *buf, int length)
241 {
242  PNGEncContext *s = avctx->priv_data;
243  const AVCRC *crc_table = av_crc_get_table(AV_CRC_32_IEEE_LE);
244  uint32_t crc = ~0U;
245 
246  if (avctx->codec_id == AV_CODEC_ID_PNG || avctx->frame_number == 0) {
247  png_write_chunk(&s->bytestream, MKTAG('I', 'D', 'A', 'T'), buf, length);
248  return;
249  }
250 
251  bytestream_put_be32(&s->bytestream, length + 4);
252 
253  bytestream_put_be32(&s->bytestream, MKBETAG('f', 'd', 'A', 'T'));
254  bytestream_put_be32(&s->bytestream, s->sequence_number);
255  crc = av_crc(crc_table, crc, s->bytestream - 8, 8);
256 
257  crc = av_crc(crc_table, crc, buf, length);
258  memcpy(s->bytestream, buf, length);
259  s->bytestream += length;
260 
261  bytestream_put_be32(&s->bytestream, ~crc);
262 
263  ++s->sequence_number;
264 }
265 
266 /* XXX: do filtering */
267 static int png_write_row(AVCodecContext *avctx, const uint8_t *data, int size)
268 {
269  PNGEncContext *s = avctx->priv_data;
270  int ret;
271 
272  s->zstream.avail_in = size;
273  s->zstream.next_in = data;
274  while (s->zstream.avail_in > 0) {
275  ret = deflate(&s->zstream, Z_NO_FLUSH);
276  if (ret != Z_OK)
277  return -1;
278  if (s->zstream.avail_out == 0) {
279  if (s->bytestream_end - s->bytestream > IOBUF_SIZE + 100)
280  png_write_image_data(avctx, s->buf, IOBUF_SIZE);
281  s->zstream.avail_out = IOBUF_SIZE;
282  s->zstream.next_out = s->buf;
283  }
284  }
285  return 0;
286 }
287 
288 #define AV_WB32_PNG(buf, n) AV_WB32(buf, lrint((n) * 100000))
289 static int png_get_chrm(enum AVColorPrimaries prim, uint8_t *buf)
290 {
291  double rx, ry, gx, gy, bx, by, wx = 0.3127, wy = 0.3290;
292  switch (prim) {
293  case AVCOL_PRI_BT709:
294  rx = 0.640; ry = 0.330;
295  gx = 0.300; gy = 0.600;
296  bx = 0.150; by = 0.060;
297  break;
298  case AVCOL_PRI_BT470M:
299  rx = 0.670; ry = 0.330;
300  gx = 0.210; gy = 0.710;
301  bx = 0.140; by = 0.080;
302  wx = 0.310; wy = 0.316;
303  break;
304  case AVCOL_PRI_BT470BG:
305  rx = 0.640; ry = 0.330;
306  gx = 0.290; gy = 0.600;
307  bx = 0.150; by = 0.060;
308  break;
309  case AVCOL_PRI_SMPTE170M:
310  case AVCOL_PRI_SMPTE240M:
311  rx = 0.630; ry = 0.340;
312  gx = 0.310; gy = 0.595;
313  bx = 0.155; by = 0.070;
314  break;
315  case AVCOL_PRI_BT2020:
316  rx = 0.708; ry = 0.292;
317  gx = 0.170; gy = 0.797;
318  bx = 0.131; by = 0.046;
319  break;
320  default:
321  return 0;
322  }
323 
324  AV_WB32_PNG(buf , wx); AV_WB32_PNG(buf + 4 , wy);
325  AV_WB32_PNG(buf + 8 , rx); AV_WB32_PNG(buf + 12, ry);
326  AV_WB32_PNG(buf + 16, gx); AV_WB32_PNG(buf + 20, gy);
327  AV_WB32_PNG(buf + 24, bx); AV_WB32_PNG(buf + 28, by);
328  return 1;
329 }
330 
332 {
333  double gamma = avpriv_get_gamma_from_trc(trc);
334  if (gamma <= 1e-6)
335  return 0;
336 
337  AV_WB32_PNG(buf, 1.0 / gamma);
338  return 1;
339 }
340 
341 static int encode_headers(AVCodecContext *avctx, const AVFrame *pict)
342 {
343  PNGEncContext *s = avctx->priv_data;
344 
345  /* write png header */
346  AV_WB32(s->buf, avctx->width);
347  AV_WB32(s->buf + 4, avctx->height);
348  s->buf[8] = s->bit_depth;
349  s->buf[9] = s->color_type;
350  s->buf[10] = 0; /* compression type */
351  s->buf[11] = 0; /* filter type */
352  s->buf[12] = s->is_progressive; /* interlace type */
353  png_write_chunk(&s->bytestream, MKTAG('I', 'H', 'D', 'R'), s->buf, 13);
354 
355  /* write physical information */
356  if (s->dpm) {
357  AV_WB32(s->buf, s->dpm);
358  AV_WB32(s->buf + 4, s->dpm);
359  s->buf[8] = 1; /* unit specifier is meter */
360  } else {
361  AV_WB32(s->buf, avctx->sample_aspect_ratio.num);
362  AV_WB32(s->buf + 4, avctx->sample_aspect_ratio.den);
363  s->buf[8] = 0; /* unit specifier is unknown */
364  }
365  png_write_chunk(&s->bytestream, MKTAG('p', 'H', 'Y', 's'), s->buf, 9);
366 
367  /* write colorspace information */
368  if (pict->color_primaries == AVCOL_PRI_BT709 &&
370  s->buf[0] = 1; /* rendering intent, relative colorimetric by default */
371  png_write_chunk(&s->bytestream, MKTAG('s', 'R', 'G', 'B'), s->buf, 1);
372  }
373 
374  if (png_get_chrm(pict->color_primaries, s->buf))
375  png_write_chunk(&s->bytestream, MKTAG('c', 'H', 'R', 'M'), s->buf, 32);
376  if (png_get_gama(pict->color_trc, s->buf))
377  png_write_chunk(&s->bytestream, MKTAG('g', 'A', 'M', 'A'), s->buf, 4);
378 
379  /* put the palette if needed */
381  int has_alpha, alpha, i;
382  unsigned int v;
383  uint32_t *palette;
384  uint8_t *ptr, *alpha_ptr;
385 
386  palette = (uint32_t *)pict->data[1];
387  ptr = s->buf;
388  alpha_ptr = s->buf + 256 * 3;
389  has_alpha = 0;
390  for (i = 0; i < 256; i++) {
391  v = palette[i];
392  alpha = v >> 24;
393  if (alpha != 0xff)
394  has_alpha = 1;
395  *alpha_ptr++ = alpha;
396  bytestream_put_be24(&ptr, v);
397  }
399  MKTAG('P', 'L', 'T', 'E'), s->buf, 256 * 3);
400  if (has_alpha) {
402  MKTAG('t', 'R', 'N', 'S'), s->buf + 256 * 3, 256);
403  }
404  }
405 
406  return 0;
407 }
408 
409 static int encode_frame(AVCodecContext *avctx, const AVFrame *pict)
410 {
411  PNGEncContext *s = avctx->priv_data;
412  const AVFrame *const p = pict;
413  int y, len, ret;
414  int row_size, pass_row_size;
415  uint8_t *ptr, *top, *crow_buf, *crow;
416  uint8_t *crow_base = NULL;
417  uint8_t *progressive_buf = NULL;
418  uint8_t *top_buf = NULL;
419 
420  row_size = (pict->width * s->bits_per_pixel + 7) >> 3;
421 
422  crow_base = av_malloc((row_size + 32) << (s->filter_type == PNG_FILTER_VALUE_MIXED));
423  if (!crow_base) {
424  ret = AVERROR(ENOMEM);
425  goto the_end;
426  }
427  // pixel data should be aligned, but there's a control byte before it
428  crow_buf = crow_base + 15;
429  if (s->is_progressive) {
430  progressive_buf = av_malloc(row_size + 1);
431  top_buf = av_malloc(row_size + 1);
432  if (!progressive_buf || !top_buf) {
433  ret = AVERROR(ENOMEM);
434  goto the_end;
435  }
436  }
437 
438  /* put each row */
439  s->zstream.avail_out = IOBUF_SIZE;
440  s->zstream.next_out = s->buf;
441  if (s->is_progressive) {
442  int pass;
443 
444  for (pass = 0; pass < NB_PASSES; pass++) {
445  /* NOTE: a pass is completely omitted if no pixels would be
446  * output */
447  pass_row_size = ff_png_pass_row_size(pass, s->bits_per_pixel, pict->width);
448  if (pass_row_size > 0) {
449  top = NULL;
450  for (y = 0; y < pict->height; y++)
451  if ((ff_png_pass_ymask[pass] << (y & 7)) & 0x80) {
452  ptr = p->data[0] + y * p->linesize[0];
453  FFSWAP(uint8_t *, progressive_buf, top_buf);
454  png_get_interlaced_row(progressive_buf, pass_row_size,
455  s->bits_per_pixel, pass,
456  ptr, pict->width);
457  crow = png_choose_filter(s, crow_buf, progressive_buf,
458  top, pass_row_size, s->bits_per_pixel >> 3);
459  png_write_row(avctx, crow, pass_row_size + 1);
460  top = progressive_buf;
461  }
462  }
463  }
464  } else {
465  top = NULL;
466  for (y = 0; y < pict->height; y++) {
467  ptr = p->data[0] + y * p->linesize[0];
468  crow = png_choose_filter(s, crow_buf, ptr, top,
469  row_size, s->bits_per_pixel >> 3);
470  png_write_row(avctx, crow, row_size + 1);
471  top = ptr;
472  }
473  }
474  /* compress last bytes */
475  for (;;) {
476  ret = deflate(&s->zstream, Z_FINISH);
477  if (ret == Z_OK || ret == Z_STREAM_END) {
478  len = IOBUF_SIZE - s->zstream.avail_out;
479  if (len > 0 && s->bytestream_end - s->bytestream > len + 100) {
480  png_write_image_data(avctx, s->buf, len);
481  }
482  s->zstream.avail_out = IOBUF_SIZE;
483  s->zstream.next_out = s->buf;
484  if (ret == Z_STREAM_END)
485  break;
486  } else {
487  ret = -1;
488  goto the_end;
489  }
490  }
491 
492  ret = 0;
493 
494 the_end:
495  av_freep(&crow_base);
496  av_freep(&progressive_buf);
497  av_freep(&top_buf);
498  deflateReset(&s->zstream);
499  return ret;
500 }
501 
502 static int encode_png(AVCodecContext *avctx, AVPacket *pkt,
503  const AVFrame *pict, int *got_packet)
504 {
505  PNGEncContext *s = avctx->priv_data;
506  int ret;
507  int enc_row_size;
508  size_t max_packet_size;
509 
510  enc_row_size = deflateBound(&s->zstream, (avctx->width * s->bits_per_pixel + 7) >> 3);
511  max_packet_size =
512  AV_INPUT_BUFFER_MIN_SIZE + // headers
513  avctx->height * (
514  enc_row_size +
515  12 * (((int64_t)enc_row_size + IOBUF_SIZE - 1) / IOBUF_SIZE) // IDAT * ceil(enc_row_size / IOBUF_SIZE)
516  );
517  if (max_packet_size > INT_MAX)
518  return AVERROR(ENOMEM);
519  ret = ff_alloc_packet2(avctx, pkt, max_packet_size, 0);
520  if (ret < 0)
521  return ret;
522 
523  s->bytestream_start =
524  s->bytestream = pkt->data;
525  s->bytestream_end = pkt->data + pkt->size;
526 
528  s->bytestream += 8;
529 
530  ret = encode_headers(avctx, pict);
531  if (ret < 0)
532  return ret;
533 
534  ret = encode_frame(avctx, pict);
535  if (ret < 0)
536  return ret;
537 
538  png_write_chunk(&s->bytestream, MKTAG('I', 'E', 'N', 'D'), NULL, 0);
539 
540  pkt->size = s->bytestream - s->bytestream_start;
541  pkt->flags |= AV_PKT_FLAG_KEY;
542  *got_packet = 1;
543 
544  return 0;
545 }
546 
547 static int apng_do_inverse_blend(AVFrame *output, const AVFrame *input,
548  APNGFctlChunk *fctl_chunk, uint8_t bpp)
549 {
550  // output: background, input: foreground
551  // output the image such that when blended with the background, will produce the foreground
552 
553  unsigned int x, y;
554  unsigned int leftmost_x = input->width;
555  unsigned int rightmost_x = 0;
556  unsigned int topmost_y = input->height;
557  unsigned int bottommost_y = 0;
558  const uint8_t *input_data = input->data[0];
559  uint8_t *output_data = output->data[0];
560  ptrdiff_t input_linesize = input->linesize[0];
561  ptrdiff_t output_linesize = output->linesize[0];
562 
563  // Find bounding box of changes
564  for (y = 0; y < input->height; ++y) {
565  for (x = 0; x < input->width; ++x) {
566  if (!memcmp(input_data + bpp * x, output_data + bpp * x, bpp))
567  continue;
568 
569  if (x < leftmost_x)
570  leftmost_x = x;
571  if (x >= rightmost_x)
572  rightmost_x = x + 1;
573  if (y < topmost_y)
574  topmost_y = y;
575  if (y >= bottommost_y)
576  bottommost_y = y + 1;
577  }
578 
579  input_data += input_linesize;
580  output_data += output_linesize;
581  }
582 
583  if (leftmost_x == input->width && rightmost_x == 0) {
584  // Empty frame
585  // APNG does not support empty frames, so we make it a 1x1 frame
586  leftmost_x = topmost_y = 0;
587  rightmost_x = bottommost_y = 1;
588  }
589 
590  // Do actual inverse blending
591  if (fctl_chunk->blend_op == APNG_BLEND_OP_SOURCE) {
592  output_data = output->data[0];
593  for (y = topmost_y; y < bottommost_y; ++y) {
594  memcpy(output_data,
595  input->data[0] + input_linesize * y + bpp * leftmost_x,
596  bpp * (rightmost_x - leftmost_x));
597  output_data += output_linesize;
598  }
599  } else { // APNG_BLEND_OP_OVER
600  size_t transparent_palette_index;
601  uint32_t *palette;
602 
603  switch (input->format) {
604  case AV_PIX_FMT_RGBA64BE:
605  case AV_PIX_FMT_YA16BE:
606  case AV_PIX_FMT_RGBA:
607  case AV_PIX_FMT_GRAY8A:
608  break;
609 
610  case AV_PIX_FMT_PAL8:
611  palette = (uint32_t*)input->data[1];
612  for (transparent_palette_index = 0; transparent_palette_index < 256; ++transparent_palette_index)
613  if (palette[transparent_palette_index] >> 24 == 0)
614  break;
615  break;
616 
617  default:
618  // No alpha, so blending not possible
619  return -1;
620  }
621 
622  for (y = topmost_y; y < bottommost_y; ++y) {
623  uint8_t *foreground = input->data[0] + input_linesize * y + bpp * leftmost_x;
624  uint8_t *background = output->data[0] + output_linesize * y + bpp * leftmost_x;
625  output_data = output->data[0] + output_linesize * (y - topmost_y);
626  for (x = leftmost_x; x < rightmost_x; ++x, foreground += bpp, background += bpp, output_data += bpp) {
627  if (!memcmp(foreground, background, bpp)) {
628  if (input->format == AV_PIX_FMT_PAL8) {
629  if (transparent_palette_index == 256) {
630  // Need fully transparent colour, but none exists
631  return -1;
632  }
633 
634  *output_data = transparent_palette_index;
635  } else {
636  memset(output_data, 0, bpp);
637  }
638  continue;
639  }
640 
641  // Check for special alpha values, since full inverse
642  // alpha-on-alpha blending is rarely possible, and when
643  // possible, doesn't compress much better than
644  // APNG_BLEND_OP_SOURCE blending
645  switch (input->format) {
646  case AV_PIX_FMT_RGBA64BE:
647  if (((uint16_t*)foreground)[3] == 0xffff ||
648  ((uint16_t*)background)[3] == 0)
649  break;
650  return -1;
651 
652  case AV_PIX_FMT_YA16BE:
653  if (((uint16_t*)foreground)[1] == 0xffff ||
654  ((uint16_t*)background)[1] == 0)
655  break;
656  return -1;
657 
658  case AV_PIX_FMT_RGBA:
659  if (foreground[3] == 0xff || background[3] == 0)
660  break;
661  return -1;
662 
663  case AV_PIX_FMT_GRAY8A:
664  if (foreground[1] == 0xff || background[1] == 0)
665  break;
666  return -1;
667 
668  case AV_PIX_FMT_PAL8:
669  if (palette[*foreground] >> 24 == 0xff ||
670  palette[*background] >> 24 == 0)
671  break;
672  return -1;
673  }
674 
675  memmove(output_data, foreground, bpp);
676  }
677  }
678  }
679 
680  output->width = rightmost_x - leftmost_x;
681  output->height = bottommost_y - topmost_y;
682  fctl_chunk->width = output->width;
683  fctl_chunk->height = output->height;
684  fctl_chunk->x_offset = leftmost_x;
685  fctl_chunk->y_offset = topmost_y;
686 
687  return 0;
688 }
689 
690 static int apng_encode_frame(AVCodecContext *avctx, const AVFrame *pict,
691  APNGFctlChunk *best_fctl_chunk, APNGFctlChunk *best_last_fctl_chunk)
692 {
693  PNGEncContext *s = avctx->priv_data;
694  int ret;
695  unsigned int y;
696  AVFrame* diffFrame;
697  uint8_t bpp = (s->bits_per_pixel + 7) >> 3;
698  uint8_t *original_bytestream, *original_bytestream_end;
699  uint8_t *temp_bytestream = 0, *temp_bytestream_end;
700  uint32_t best_sequence_number;
701  uint8_t *best_bytestream;
702  size_t best_bytestream_size = SIZE_MAX;
703  APNGFctlChunk last_fctl_chunk = *best_last_fctl_chunk;
704  APNGFctlChunk fctl_chunk = *best_fctl_chunk;
705 
706  if (avctx->frame_number == 0) {
707  best_fctl_chunk->width = pict->width;
708  best_fctl_chunk->height = pict->height;
709  best_fctl_chunk->x_offset = 0;
710  best_fctl_chunk->y_offset = 0;
711  best_fctl_chunk->blend_op = APNG_BLEND_OP_SOURCE;
712  return encode_frame(avctx, pict);
713  }
714 
715  diffFrame = av_frame_alloc();
716  if (!diffFrame)
717  return AVERROR(ENOMEM);
718 
719  diffFrame->format = pict->format;
720  diffFrame->width = pict->width;
721  diffFrame->height = pict->height;
722  if ((ret = av_frame_get_buffer(diffFrame, 32)) < 0)
723  goto fail;
724 
725  original_bytestream = s->bytestream;
726  original_bytestream_end = s->bytestream_end;
727 
728  temp_bytestream = av_malloc(original_bytestream_end - original_bytestream);
729  temp_bytestream_end = temp_bytestream + (original_bytestream_end - original_bytestream);
730  if (!temp_bytestream) {
731  ret = AVERROR(ENOMEM);
732  goto fail;
733  }
734 
735  for (last_fctl_chunk.dispose_op = 0; last_fctl_chunk.dispose_op < 3; ++last_fctl_chunk.dispose_op) {
736  // 0: APNG_DISPOSE_OP_NONE
737  // 1: APNG_DISPOSE_OP_BACKGROUND
738  // 2: APNG_DISPOSE_OP_PREVIOUS
739 
740  for (fctl_chunk.blend_op = 0; fctl_chunk.blend_op < 2; ++fctl_chunk.blend_op) {
741  // 0: APNG_BLEND_OP_SOURCE
742  // 1: APNG_BLEND_OP_OVER
743 
744  uint32_t original_sequence_number = s->sequence_number, sequence_number;
745  uint8_t *bytestream_start = s->bytestream;
746  size_t bytestream_size;
747 
748  // Do disposal
749  if (last_fctl_chunk.dispose_op != APNG_DISPOSE_OP_PREVIOUS) {
750  memcpy(diffFrame->data[0], s->last_frame->data[0],
751  s->last_frame->linesize[0] * s->last_frame->height);
752 
753  if (last_fctl_chunk.dispose_op == APNG_DISPOSE_OP_BACKGROUND) {
754  for (y = last_fctl_chunk.y_offset; y < last_fctl_chunk.y_offset + last_fctl_chunk.height; ++y) {
755  size_t row_start = s->last_frame->linesize[0] * y + bpp * last_fctl_chunk.x_offset;
756  memset(diffFrame->data[0] + row_start, 0, bpp * last_fctl_chunk.width);
757  }
758  }
759  } else {
760  if (!s->prev_frame)
761  continue;
762 
763  memcpy(diffFrame->data[0], s->prev_frame->data[0],
764  s->prev_frame->linesize[0] * s->prev_frame->height);
765  }
766 
767  // Do inverse blending
768  if (apng_do_inverse_blend(diffFrame, pict, &fctl_chunk, bpp) < 0)
769  continue;
770 
771  // Do encoding
772  ret = encode_frame(avctx, diffFrame);
773  sequence_number = s->sequence_number;
774  s->sequence_number = original_sequence_number;
775  bytestream_size = s->bytestream - bytestream_start;
776  s->bytestream = bytestream_start;
777  if (ret < 0)
778  goto fail;
779 
780  if (bytestream_size < best_bytestream_size) {
781  *best_fctl_chunk = fctl_chunk;
782  *best_last_fctl_chunk = last_fctl_chunk;
783 
784  best_sequence_number = sequence_number;
785  best_bytestream = s->bytestream;
786  best_bytestream_size = bytestream_size;
787 
788  if (best_bytestream == original_bytestream) {
789  s->bytestream = temp_bytestream;
790  s->bytestream_end = temp_bytestream_end;
791  } else {
792  s->bytestream = original_bytestream;
793  s->bytestream_end = original_bytestream_end;
794  }
795  }
796  }
797  }
798 
799  s->sequence_number = best_sequence_number;
800  s->bytestream = original_bytestream + best_bytestream_size;
801  s->bytestream_end = original_bytestream_end;
802  if (best_bytestream != original_bytestream)
803  memcpy(original_bytestream, best_bytestream, best_bytestream_size);
804 
805  ret = 0;
806 
807 fail:
808  av_freep(&temp_bytestream);
809  av_frame_free(&diffFrame);
810  return ret;
811 }
812 
814  const AVFrame *pict, int *got_packet)
815 {
816  PNGEncContext *s = avctx->priv_data;
817  int ret;
818  int enc_row_size;
819  size_t max_packet_size;
820  APNGFctlChunk fctl_chunk;
821 
822  if (pict && avctx->codec_id == AV_CODEC_ID_APNG && s->color_type == PNG_COLOR_TYPE_PALETTE) {
823  uint32_t checksum = ~av_crc(av_crc_get_table(AV_CRC_32_IEEE_LE), ~0U, pict->data[1], 256 * sizeof(uint32_t));
824 
825  if (avctx->frame_number == 0) {
826  s->palette_checksum = checksum;
827  } else if (checksum != s->palette_checksum) {
828  av_log(avctx, AV_LOG_ERROR,
829  "Input contains more than one unique palette. APNG does not support multiple palettes.\n");
830  return -1;
831  }
832  }
833 
834  enc_row_size = deflateBound(&s->zstream, (avctx->width * s->bits_per_pixel + 7) >> 3);
835  max_packet_size =
836  AV_INPUT_BUFFER_MIN_SIZE + // headers
837  avctx->height * (
838  enc_row_size +
839  (4 + 12) * (((int64_t)enc_row_size + IOBUF_SIZE - 1) / IOBUF_SIZE) // fdAT * ceil(enc_row_size / IOBUF_SIZE)
840  );
841  if (max_packet_size > INT_MAX)
842  return AVERROR(ENOMEM);
843 
844  if (avctx->frame_number == 0) {
846  if (!avctx->extradata)
847  return AVERROR(ENOMEM);
848 
849  ret = encode_headers(avctx, pict);
850  if (ret < 0)
851  return ret;
852 
853  avctx->extradata_size = s->bytestream - avctx->extradata;
854 
855  s->last_frame_packet = av_malloc(max_packet_size);
856  if (!s->last_frame_packet)
857  return AVERROR(ENOMEM);
858  } else if (s->last_frame) {
859  ret = ff_alloc_packet2(avctx, pkt, max_packet_size, 0);
860  if (ret < 0)
861  return ret;
862 
863  memcpy(pkt->data, s->last_frame_packet, s->last_frame_packet_size);
864  pkt->size = s->last_frame_packet_size;
865  pkt->pts = pkt->dts = s->last_frame->pts;
866  }
867 
868  if (pict) {
869  s->bytestream_start =
871  s->bytestream_end = s->bytestream + max_packet_size;
872 
873  // We're encoding the frame first, so we have to do a bit of shuffling around
874  // to have the image data write to the correct place in the buffer
875  fctl_chunk.sequence_number = s->sequence_number;
876  ++s->sequence_number;
877  s->bytestream += 26 + 12;
878 
879  ret = apng_encode_frame(avctx, pict, &fctl_chunk, &s->last_frame_fctl);
880  if (ret < 0)
881  return ret;
882 
883  fctl_chunk.delay_num = 0; // delay filled in during muxing
884  fctl_chunk.delay_den = 0;
885  } else {
887  }
888 
889  if (s->last_frame) {
890  uint8_t* last_fctl_chunk_start = pkt->data;
891  uint8_t buf[26];
892 
894  AV_WB32(buf + 4, s->last_frame_fctl.width);
895  AV_WB32(buf + 8, s->last_frame_fctl.height);
896  AV_WB32(buf + 12, s->last_frame_fctl.x_offset);
897  AV_WB32(buf + 16, s->last_frame_fctl.y_offset);
898  AV_WB16(buf + 20, s->last_frame_fctl.delay_num);
899  AV_WB16(buf + 22, s->last_frame_fctl.delay_den);
900  buf[24] = s->last_frame_fctl.dispose_op;
901  buf[25] = s->last_frame_fctl.blend_op;
902  png_write_chunk(&last_fctl_chunk_start, MKTAG('f', 'c', 'T', 'L'), buf, 26);
903 
904  *got_packet = 1;
905  }
906 
907  if (pict) {
908  if (!s->last_frame) {
909  s->last_frame = av_frame_alloc();
910  if (!s->last_frame)
911  return AVERROR(ENOMEM);
913  if (!s->prev_frame) {
914  s->prev_frame = av_frame_alloc();
915  if (!s->prev_frame)
916  return AVERROR(ENOMEM);
917 
918  s->prev_frame->format = pict->format;
919  s->prev_frame->width = pict->width;
920  s->prev_frame->height = pict->height;
921  if ((ret = av_frame_get_buffer(s->prev_frame, 32)) < 0)
922  return ret;
923  }
924 
925  // Do disposal, but not blending
926  memcpy(s->prev_frame->data[0], s->last_frame->data[0],
927  s->last_frame->linesize[0] * s->last_frame->height);
929  uint32_t y;
930  uint8_t bpp = (s->bits_per_pixel + 7) >> 3;
931  for (y = s->last_frame_fctl.y_offset; y < s->last_frame_fctl.y_offset + s->last_frame_fctl.height; ++y) {
932  size_t row_start = s->last_frame->linesize[0] * y + bpp * s->last_frame_fctl.x_offset;
933  memset(s->prev_frame->data[0] + row_start, 0, bpp * s->last_frame_fctl.width);
934  }
935  }
936  }
937 
939  ret = av_frame_ref(s->last_frame, (AVFrame*)pict);
940  if (ret < 0)
941  return ret;
942 
943  s->last_frame_fctl = fctl_chunk;
945  } else {
947  }
948 
949  return 0;
950 }
951 
953 {
954  PNGEncContext *s = avctx->priv_data;
955  int compression_level;
956 
957  switch (avctx->pix_fmt) {
958  case AV_PIX_FMT_RGBA:
959  avctx->bits_per_coded_sample = 32;
960  break;
961  case AV_PIX_FMT_RGB24:
962  avctx->bits_per_coded_sample = 24;
963  break;
964  case AV_PIX_FMT_GRAY8:
965  avctx->bits_per_coded_sample = 0x28;
966  break;
968  avctx->bits_per_coded_sample = 1;
969  break;
970  case AV_PIX_FMT_PAL8:
971  avctx->bits_per_coded_sample = 8;
972  }
973 
974 #if FF_API_CODED_FRAME
977  avctx->coded_frame->key_frame = 1;
979 #endif
980 
982 
983  s->filter_type = av_clip(avctx->prediction_method,
986  if (avctx->pix_fmt == AV_PIX_FMT_MONOBLACK)
988 
989  if (s->dpi && s->dpm) {
990  av_log(avctx, AV_LOG_ERROR, "Only one of 'dpi' or 'dpm' options should be set\n");
991  return AVERROR(EINVAL);
992  } else if (s->dpi) {
993  s->dpm = s->dpi * 10000 / 254;
994  }
995 
997  switch (avctx->pix_fmt) {
998  case AV_PIX_FMT_RGBA64BE:
999  s->bit_depth = 16;
1001  break;
1002  case AV_PIX_FMT_RGB48BE:
1003  s->bit_depth = 16;
1005  break;
1006  case AV_PIX_FMT_RGBA:
1007  s->bit_depth = 8;
1009  break;
1010  case AV_PIX_FMT_RGB24:
1011  s->bit_depth = 8;
1013  break;
1014  case AV_PIX_FMT_GRAY16BE:
1015  s->bit_depth = 16;
1017  break;
1018  case AV_PIX_FMT_GRAY8:
1019  s->bit_depth = 8;
1021  break;
1022  case AV_PIX_FMT_GRAY8A:
1023  s->bit_depth = 8;
1025  break;
1026  case AV_PIX_FMT_YA16BE:
1027  s->bit_depth = 16;
1029  break;
1030  case AV_PIX_FMT_MONOBLACK:
1031  s->bit_depth = 1;
1033  break;
1034  case AV_PIX_FMT_PAL8:
1035  s->bit_depth = 8;
1037  break;
1038  default:
1039  return -1;
1040  }
1042 
1043  s->zstream.zalloc = ff_png_zalloc;
1044  s->zstream.zfree = ff_png_zfree;
1045  s->zstream.opaque = NULL;
1046  compression_level = avctx->compression_level == FF_COMPRESSION_DEFAULT
1047  ? Z_DEFAULT_COMPRESSION
1048  : av_clip(avctx->compression_level, 0, 9);
1049  if (deflateInit2(&s->zstream, compression_level, Z_DEFLATED, 15, 8, Z_DEFAULT_STRATEGY) != Z_OK)
1050  return -1;
1051 
1052  return 0;
1053 }
1054 
1056 {
1057  PNGEncContext *s = avctx->priv_data;
1058 
1059  deflateEnd(&s->zstream);
1063  return 0;
1064 }
1065 
1066 #define OFFSET(x) offsetof(PNGEncContext, x)
1067 #define VE AV_OPT_FLAG_VIDEO_PARAM | AV_OPT_FLAG_ENCODING_PARAM
1068 static const AVOption options[] = {
1069  {"dpi", "Set image resolution (in dots per inch)", OFFSET(dpi), AV_OPT_TYPE_INT, {.i64 = 0}, 0, 0x10000, VE},
1070  {"dpm", "Set image resolution (in dots per meter)", OFFSET(dpm), AV_OPT_TYPE_INT, {.i64 = 0}, 0, 0x10000, VE},
1071  { NULL }
1072 };
1073 
1074 static const AVClass pngenc_class = {
1075  .class_name = "PNG encoder",
1076  .item_name = av_default_item_name,
1077  .option = options,
1078  .version = LIBAVUTIL_VERSION_INT,
1079 };
1080 
1081 static const AVClass apngenc_class = {
1082  .class_name = "APNG encoder",
1083  .item_name = av_default_item_name,
1084  .option = options,
1085  .version = LIBAVUTIL_VERSION_INT,
1086 };
1087 
1089  .name = "png",
1090  .long_name = NULL_IF_CONFIG_SMALL("PNG (Portable Network Graphics) image"),
1091  .type = AVMEDIA_TYPE_VIDEO,
1092  .id = AV_CODEC_ID_PNG,
1093  .priv_data_size = sizeof(PNGEncContext),
1094  .init = png_enc_init,
1095  .close = png_enc_close,
1096  .encode2 = encode_png,
1098  .pix_fmts = (const enum AVPixelFormat[]) {
1105  },
1106  .priv_class = &pngenc_class,
1107 };
1108 
1110  .name = "apng",
1111  .long_name = NULL_IF_CONFIG_SMALL("APNG (Animated Portable Network Graphics) image"),
1112  .type = AVMEDIA_TYPE_VIDEO,
1113  .id = AV_CODEC_ID_APNG,
1114  .priv_data_size = sizeof(PNGEncContext),
1115  .init = png_enc_init,
1116  .close = png_enc_close,
1117  .encode2 = encode_apng,
1118  .capabilities = CODEC_CAP_DELAY,
1119  .pix_fmts = (const enum AVPixelFormat[]) {
1126  },
1127  .priv_class = &apngenc_class,
1128 };
static void png_filter_row(PNGEncContext *c, uint8_t *dst, int filter_type, uint8_t *src, uint8_t *top, int size, int bpp)
Definition: pngenc.c:161
#define PNG_FILTER_VALUE_AVG
Definition: png.h:41
#define NULL
Definition: coverity.c:32
APNGFctlChunk last_frame_fctl
Definition: pngenc.c:73
float v
const char * s
Definition: avisynth_c.h:631
#define FF_COMPRESSION_DEFAULT
Definition: avcodec.h:1590
This structure describes decoded (raw) audio or video data.
Definition: frame.h:171
BYTE int const BYTE int int row_size
Definition: avisynth_c.h:676
AVOption.
Definition: opt.h:255
ptrdiff_t const GLvoid * data
Definition: opengl_enc.c:101
#define AV_CODEC_FLAG_INTERLACED_DCT
Use interlaced DCT.
Definition: avcodec.h:776
static uint8_t * png_choose_filter(PNGEncContext *s, uint8_t *dst, uint8_t *src, uint8_t *top, int size, int bpp)
Definition: pngenc.c:190
#define LIBAVUTIL_VERSION_INT
Definition: version.h:62
packed RGB 8:8:8, 24bpp, RGBRGB...
Definition: pixfmt.h:65
static av_cold int init(AVCodecContext *avctx)
Definition: avrndec.c:35
static const AVClass apngenc_class
Definition: pngenc.c:1081
uint8_t * bytestream
Definition: pngenc.c:51
int num
numerator
Definition: rational.h:44
int size
Definition: avcodec.h:1424
const char * b
Definition: vf_curves.c:109
uint32_t x_offset
Definition: pngenc.c:42
AVRational sample_aspect_ratio
sample aspect ratio (0 if unknown) That is the width of a pixel divided by the height of the pixel...
Definition: avcodec.h:1902
enum AVPixelFormat pix_fmt
Pixel format, see AV_PIX_FMT_xxx.
Definition: avcodec.h:1722
static int encode_png(AVCodecContext *avctx, AVPacket *pkt, const AVFrame *pict, int *got_packet)
Definition: pngenc.c:502
int color_type
Definition: pngenc.c:64
static AVPacket pkt
#define PNG_COLOR_TYPE_RGB
Definition: png.h:33
static const AVClass pngenc_class
Definition: pngenc.c:1074
int bit_depth
Definition: pngenc.c:63
#define PNG_COLOR_TYPE_GRAY_ALPHA
Definition: png.h:35
AVCodec.
Definition: avcodec.h:3472
#define PNG_COLOR_TYPE_PALETTE
Definition: png.h:32
AVColorTransferCharacteristic
Color Transfer Characteristic.
Definition: pixfmt.h:494
#define OFFSET(x)
Definition: pngenc.c:1066
av_cold void ff_huffyuvencdsp_init(HuffYUVEncDSPContext *c)
Definition: huffyuvencdsp.c:77
#define AV_CODEC_CAP_INTRA_ONLY
Codec is intra only.
Definition: avcodec.h:940
size_t last_frame_packet_size
Definition: pngenc.c:75
int filter_type
Definition: pngenc.c:55
#define PNG_FILTER_VALUE_PAETH
Definition: png.h:42
uint32_t y_offset
Definition: pngenc.c:42
const char * class_name
The name of the class; usually it is the same name as the context structure type to which the AVClass...
Definition: log.h:72
#define AV_WB64(p, v)
Definition: intreadwrite.h:433
#define av_assert0(cond)
assert() equivalent, that is always enabled.
Definition: avassert.h:37
double avpriv_get_gamma_from_trc(enum AVColorTransferCharacteristic trc)
Determine a suitable 'gamma' value to match the supplied AVColorTransferCharacteristic.
Definition: color_utils.c:24
int bits_per_pixel
Definition: pngenc.c:65
uint8_t
#define av_cold
Definition: attributes.h:74
#define av_malloc(s)
AVFrame * av_frame_alloc(void)
Allocate an AVFrame and set its fields to default values.
Definition: frame.c:135
#define PNG_COLOR_TYPE_RGB_ALPHA
Definition: png.h:34
8 bit with AV_PIX_FMT_RGB32 palette
Definition: pixfmt.h:74
AVOptions.
HuffYUVEncDSPContext hdsp
Definition: pngenc.c:49
static void sub_png_paeth_prediction(uint8_t *dst, uint8_t *src, uint8_t *top, int w, int bpp)
Definition: pngenc.c:117
static void deflate(uint8_t *dst, const uint8_t *p1, int width, int threshold, const uint8_t *coordinates[], int coord)
Definition: vf_neighbor.c:115
static int apng_encode_frame(AVCodecContext *avctx, const AVFrame *pict, APNGFctlChunk *best_fctl_chunk, APNGFctlChunk *best_last_fctl_chunk)
Definition: pngenc.c:690
packed RGBA 16:16:16:16, 64bpp, 16R, 16G, 16B, 16A, the 2-byte value for each R/G/B/A component is st...
Definition: pixfmt.h:271
int av_frame_ref(AVFrame *dst, const AVFrame *src)
Set up a new reference to the data described by the source frame.
Definition: frame.c:365
int64_t pts
Presentation timestamp in time_base units (time when frame should be shown to user).
Definition: frame.h:257
uint8_t * extradata
some codecs need / can use extradata like Huffman tables.
Definition: avcodec.h:1617
uint32_t sequence_number
Definition: pngenc.c:40
uint8_t blend_op
Definition: pngenc.c:44
uint8_t * data
Definition: avcodec.h:1423
uint32_t tag
Definition: movenc.c:1334
ptrdiff_t size
Definition: opengl_enc.c:101
int bits_per_coded_sample
bits per sample/pixel from the demuxer (needed for huffyuv).
Definition: avcodec.h:2996
AVColorPrimaries
Chromaticity coordinates of the source primaries.
Definition: pixfmt.h:476
#define AV_WB16(p, v)
Definition: intreadwrite.h:405
#define AV_INPUT_BUFFER_MIN_SIZE
minimum encoding buffer size Used to avoid some checks during header writing.
Definition: avcodec.h:643
#define av_log(a,...)
#define PNG_FILTER_VALUE_MIXED
Definition: png.h:43
int is_progressive
Definition: pngenc.c:62
AVCodec ff_apng_encoder
Definition: pngenc.c:1109
#define AV_PKT_FLAG_KEY
The packet contains a keyframe.
Definition: avcodec.h:1469
#define U(x)
Definition: vp56_arith.h:37
uint32_t palette_checksum
Definition: pngenc.c:68
also FCC Title 47 Code of Federal Regulations 73.682 (a)(20)
Definition: pixfmt.h:481
static double alpha(void *priv, double x, double y)
Definition: vf_geq.c:99
int width
width and height of the video frame
Definition: frame.h:220
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
Definition: log.h:176
uint32_t sequence_number
Definition: pngenc.c:69
16bit gray, 16bit alpha (big-endian)
Definition: pixfmt.h:246
static void png_get_interlaced_row(uint8_t *dst, int row_size, int bits_per_pixel, int pass, const uint8_t *src, int width)
Definition: pngenc.c:78
uint32_t width
Definition: pngenc.c:41
static const uint16_t mask[17]
Definition: lzw.c:38
z_stream zstream
Definition: pngenc.c:57
#define CODEC_CAP_DELAY
Encoder or decoder requires flushing with NULL input at the end in order to give the complete and cor...
Definition: avcodec.h:1064
av_default_item_name
#define AVERROR(e)
Definition: error.h:43
void av_frame_free(AVFrame **frame)
Free the frame and any dynamically allocated objects in it, e.g.
Definition: frame.c:148
void(* diff_bytes)(uint8_t *dst, const uint8_t *src1, const uint8_t *src2, int w)
Definition: huffyuvencdsp.h:25
#define NULL_IF_CONFIG_SMALL(x)
Return NULL if CONFIG_SMALL is true, otherwise the argument without modification. ...
Definition: internal.h:175
int dpm
Physical pixel density, in dots per meter, if set.
Definition: pngenc.c:60
int ff_png_get_nb_channels(int color_type)
Definition: png.c:49
#define AV_WB32_PNG(buf, n)
Definition: pngenc.c:288
int flags
AV_CODEC_FLAG_*.
Definition: avcodec.h:1597
#define PNGSIG
Definition: png.h:52
also ITU-R BT1361 / IEC 61966-2-4 / SMPTE RP177 Annex B
Definition: pixfmt.h:478
simple assert() macros that are a bit more flexible than ISO C assert().
static int encode_headers(AVCodecContext *avctx, const AVFrame *pict)
Definition: pngenc.c:341
GLsizei GLsizei * length
Definition: opengl_enc.c:115
const char * name
Name of the codec implementation.
Definition: avcodec.h:3479
Libavcodec external API header.
#define NB_PASSES
Definition: png.h:50
#define fail()
Definition: checkasm.h:57
#define AV_CODEC_CAP_FRAME_THREADS
Codec supports frame-level multithreading.
Definition: avcodec.h:920
packed RGBA 8:8:8:8, 32bpp, RGBARGBA...
Definition: pixfmt.h:95
int flags
A combination of AV_PKT_FLAG values.
Definition: avcodec.h:1429
#define pass
Definition: fft_template.c:509
uint8_t * bytestream_start
Definition: pngenc.c:52
enum AVPictureType pict_type
Picture type of the frame.
Definition: frame.h:242
alias for AV_PIX_FMT_YA8
Definition: pixfmt.h:158
#define FFMIN(a, b)
Definition: common.h:81
#define PNG_FILTER_VALUE_SUB
Definition: png.h:39
float y
static void png_write_chunk(uint8_t **f, uint32_t tag, const uint8_t *buf, int length)
Definition: pngenc.c:220
#define PNG_COLOR_TYPE_GRAY
Definition: png.h:31
int width
picture width / height.
Definition: avcodec.h:1681
uint16_t delay_num
Definition: pngenc.c:43
static const AVOption options[]
Definition: pngenc.c:1068
also ITU-R BT601-6 625 / ITU-R BT1358 625 / ITU-R BT1700 625 PAL & SECAM
Definition: pixfmt.h:483
uint32_t height
Definition: pngenc.c:41
uint32_t av_crc(const AVCRC *ctx, uint32_t crc, const uint8_t *buffer, size_t length)
Calculate the CRC of a block.
Definition: crc.c:356
uint8_t * last_frame_packet
Definition: pngenc.c:74
static int encode_apng(AVCodecContext *avctx, AVPacket *pkt, const AVFrame *pict, int *got_packet)
Definition: pngenc.c:813
static const float pred[4]
Definition: siprdata.h:259
int format
format of the frame, -1 if unknown or unset Values correspond to enum AVPixelFormat for video frames...
Definition: frame.h:232
static int png_get_gama(enum AVColorTransferCharacteristic trc, uint8_t *buf)
Definition: pngenc.c:331
#define IOBUF_SIZE
Definition: pngenc.c:37
#define src1
Definition: h264pred.c:139
#define av_bswap32
Definition: bswap.h:33
AVCodec ff_png_encoder
Definition: pngenc.c:1088
AVS_Value src
Definition: avisynth_c.h:482
functionally identical to above
Definition: pixfmt.h:485
enum AVCodecID codec_id
Definition: avcodec.h:1519
int compression_level
Definition: avcodec.h:1589
#define PNG_FILTER_VALUE_UP
Definition: png.h:40
int linesize[AV_NUM_DATA_POINTERS]
For video, size in bytes of each picture line.
Definition: frame.h:199
static void png_write_image_data(AVCodecContext *avctx, const uint8_t *buf, int length)
Definition: pngenc.c:239
main external API structure.
Definition: avcodec.h:1502
void * buf
Definition: avisynth_c.h:553
const uint8_t ff_png_pass_ymask[NB_PASSES]
Definition: png.c:25
int extradata_size
Definition: avcodec.h:1618
Replacements for frequently missing libm functions.
Describe the class of an AVClass context structure.
Definition: log.h:67
#define AV_WB32(p, v)
Definition: intreadwrite.h:419
Y , 16bpp, big-endian.
Definition: pixfmt.h:99
int dpi
Physical pixel density, in dots per inch, if set.
Definition: pngenc.c:59
#define VE
Definition: pngenc.c:1067
static av_cold int png_enc_init(AVCodecContext *avctx)
Definition: pngenc.c:952
uint8_t * bytestream_end
Definition: pngenc.c:53
int ff_alloc_packet2(AVCodecContext *avctx, AVPacket *avpkt, int64_t size, int64_t min_size)
Check AVPacket size and/or allocate data.
Definition: utils.c:1782
static int encode_frame(AVCodecContext *avctx, const AVFrame *pict)
Definition: pngenc.c:409
static enum AVPixelFormat pix_fmts[]
Definition: libkvazaar.c:209
uint8_t dispose_op
Definition: pngenc.c:44
int av_frame_get_buffer(AVFrame *frame, int align)
Allocate new buffer(s) for audio or video data.
Definition: frame.c:265
void av_frame_unref(AVFrame *frame)
Unreference all the buffers referenced by frame and reset the frame fields.
Definition: frame.c:464
uint8_t * data[AV_NUM_DATA_POINTERS]
pointer to the picture/channel planes.
Definition: frame.h:182
const AVCRC * av_crc_get_table(AVCRCId crc_id)
Get an initialized standard CRC table.
Definition: crc.c:342
uint8_t buf[IOBUF_SIZE]
Definition: pngenc.c:58
int palette
Definition: v4l.c:61
Y , 1bpp, 0 is black, 1 is white, in each byte pixels are ordered from the msb to the lsb...
Definition: pixfmt.h:73
static int png_write_row(AVCodecContext *avctx, const uint8_t *data, int size)
Definition: pngenc.c:267
Y , 8bpp.
Definition: pixfmt.h:71
IEC 61966-2-1 (sRGB or sYCC)
Definition: pixfmt.h:508
#define FF_DISABLE_DEPRECATION_WARNINGS
Definition: internal.h:79
common internal api header.
#define PNG_FILTER_VALUE_NONE
Definition: png.h:38
static double c[64]
packed RGB 16:16:16, 48bpp, 16R, 16G, 16B, the 2-byte value for each R/G/B component is stored as big...
Definition: pixfmt.h:111
int prediction_method
prediction method (needed for huffyuv)
Definition: avcodec.h:1883
attribute_deprecated AVFrame * coded_frame
the picture in the bitstream
Definition: avcodec.h:3024
int den
denominator
Definition: rational.h:45
void ff_png_zfree(void *opaque, void *ptr)
Definition: png.c:44
#define MKBETAG(a, b, c, d)
Definition: common.h:331
void * priv_data
Definition: avcodec.h:1544
static int output_data(MLPDecodeContext *m, unsigned int substr, AVFrame *frame, int *got_frame_ptr)
Write the audio data into the output buffer.
Definition: mlpdec.c:1043
#define FF_ENABLE_DEPRECATION_WARNINGS
Definition: internal.h:80
int len
int key_frame
1 -> keyframe, 0-> not
Definition: frame.h:237
APNG common header.
static int png_get_chrm(enum AVColorPrimaries prim, uint8_t *buf)
Definition: pngenc.c:289
enum AVColorPrimaries color_primaries
Definition: frame.h:493
int ff_png_pass_row_size(int pass, int bits_per_pixel, int width)
Definition: png.c:62
int64_t dts
Decompression timestamp in AVStream->time_base units; the time at which the packet is decompressed...
Definition: avcodec.h:1422
also ITU-R BT601-6 525 / ITU-R BT1358 525 / ITU-R BT1700 NTSC
Definition: pixfmt.h:484
int frame_number
Frame counter, set by libavcodec.
Definition: avcodec.h:2293
ITU-R BT2020.
Definition: pixfmt.h:487
int height
Definition: frame.h:220
#define av_freep(p)
enum AVColorTransferCharacteristic color_trc
Definition: frame.h:495
uint16_t delay_den
Definition: pngenc.c:43
static int apng_do_inverse_blend(AVFrame *output, const AVFrame *input, APNGFctlChunk *fctl_chunk, uint8_t bpp)
Definition: pngenc.c:547
AVFrame * last_frame
Definition: pngenc.c:72
static av_cold int png_enc_close(AVCodecContext *avctx)
Definition: pngenc.c:1055
#define FFSWAP(type, a, b)
Definition: common.h:84
#define MKTAG(a, b, c, d)
Definition: common.h:330
void * ff_png_zalloc(void *opaque, unsigned int items, unsigned int size)
Definition: png.c:39
AVPixelFormat
Pixel format.
Definition: pixfmt.h:61
This structure stores compressed data.
Definition: avcodec.h:1400
uint32_t AVCRC
Definition: crc.h:34
int64_t pts
Presentation timestamp in AVStream->time_base units; the time at which the decompressed packet will b...
Definition: avcodec.h:1416
for(j=16;j >0;--j)
AVFrame * prev_frame
Definition: pngenc.c:71
#define AV_WL32(p, v)
Definition: intreadwrite.h:426
#define FF_MIN_BUFFER_SIZE
Definition: avcodec.h:654
static void sub_left_prediction(PNGEncContext *c, uint8_t *dst, const uint8_t *src, int bpp, int size)
Definition: pngenc.c:145
static int width