~ubuntu-branches/ubuntu/intrepid/gstreamer0.10-ffmpeg/intrepid

« back to all changes in this revision

Viewing changes to gst-libs/ext/ffmpeg/libavformat/png.c

  • Committer: Bazaar Package Importer
  • Author(s): Sebastian Dröge
  • Date: 2006-04-01 16:13:43 UTC
  • mto: (1.2.2 lenny)
  • mto: This revision was merged to the branch mainline in revision 5.
  • Revision ID: james.westby@ubuntu.com-20060401161343-n621cgjlujio0otg
Tags: upstream-0.10.1
Import upstream version 0.10.1

Show diffs side-by-side

added added

removed removed

Lines of Context:
14
14
 *
15
15
 * You should have received a copy of the GNU Lesser General Public
16
16
 * License along with this library; if not, write to the Free Software
17
 
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 
17
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18
18
 */
19
19
#include "avformat.h"
20
20
 
64
64
    int channels;
65
65
    int bits_per_pixel;
66
66
    int bpp;
67
 
    
 
67
 
68
68
    uint8_t *image_buf;
69
69
    int image_linesize;
70
70
    uint32_t palette[256];
107
107
};
108
108
 
109
109
/* Mask to determine which pixels to overwrite while displaying */
110
 
static const uint8_t png_pass_dsp_mask[NB_PASSES] = { 
 
110
static const uint8_t png_pass_dsp_mask[NB_PASSES] = {
111
111
    0xff, 0x0f, 0xff, 0x33, 0xff, 0x55, 0xff
112
112
};
113
113
 
158
158
/* NOTE: we try to construct a good looking image at each pass. width
159
159
   is the original image width. We also do pixel format convertion at
160
160
   this stage */
161
 
static void png_put_interlaced_row(uint8_t *dst, int width, 
162
 
                                   int bits_per_pixel, int pass, 
 
161
static void png_put_interlaced_row(uint8_t *dst, int width,
 
162
                                   int bits_per_pixel, int pass,
163
163
                                   int color_type, const uint8_t *src)
164
164
{
165
165
    int x, mask, dsp_mask, j, src_x, b, bpp;
166
166
    uint8_t *d;
167
167
    const uint8_t *s;
168
 
    
 
168
 
169
169
    mask = png_pass_mask[pass];
170
170
    dsp_mask = png_pass_dsp_mask[pass];
171
171
    switch(bits_per_pixel) {
213
213
    }
214
214
}
215
215
 
216
 
static void png_get_interlaced_row(uint8_t *dst, int row_size, 
217
 
                                   int bits_per_pixel, int pass, 
 
216
static void png_get_interlaced_row(uint8_t *dst, int row_size,
 
217
                                   int bits_per_pixel, int pass,
218
218
                                   const uint8_t *src, int width)
219
219
{
220
220
    int x, mask, dst_x, j, b, bpp;
253
253
 
254
254
/* XXX: optimize */
255
255
/* NOTE: 'dst' can be equal to 'last' */
256
 
static void png_filter_row(uint8_t *dst, int filter_type, 
 
256
static void png_filter_row(uint8_t *dst, int filter_type,
257
257
                           uint8_t *src, uint8_t *last, int size, int bpp)
258
258
{
259
259
    int i, p;
323
323
    uint8_t *d;
324
324
    int j;
325
325
    unsigned int v;
326
 
    
 
326
 
327
327
    d = dst;
328
328
    for(j = 0; j < width; j++) {
329
329
        v = ((uint32_t *)src)[j];
356
356
{
357
357
    uint8_t *ptr, *last_row;
358
358
    int got_line;
359
 
    
 
359
 
360
360
    if (!s->interlace_type) {
361
361
        ptr = s->image_buf + s->image_linesize * s->y;
362
362
        /* need to swap bytes correctly for RGB_ALPHA */
363
363
        if (s->color_type == PNG_COLOR_TYPE_RGB_ALPHA) {
364
 
            png_filter_row(s->tmp_row, s->crow_buf[0], s->crow_buf + 1, 
 
364
            png_filter_row(s->tmp_row, s->crow_buf[0], s->crow_buf + 1,
365
365
                           s->last_row, s->row_size, s->bpp);
366
366
            memcpy(s->last_row, s->tmp_row, s->row_size);
367
367
            convert_to_rgba32(ptr, s->tmp_row, s->width);
371
371
                last_row = s->last_row;
372
372
            else
373
373
                last_row = ptr - s->image_linesize;
374
 
            
375
 
            png_filter_row(ptr, s->crow_buf[0], s->crow_buf + 1, 
 
374
 
 
375
            png_filter_row(ptr, s->crow_buf[0], s->crow_buf + 1,
376
376
                           last_row, s->row_size, s->bpp);
377
377
        }
378
378
        s->y++;
388
388
                   wait for the next one */
389
389
                if (got_line)
390
390
                    break;
391
 
                png_filter_row(s->tmp_row, s->crow_buf[0], s->crow_buf + 1, 
 
391
                png_filter_row(s->tmp_row, s->crow_buf[0], s->crow_buf + 1,
392
392
                               s->last_row, s->pass_row_size, s->bpp);
393
393
                memcpy(s->last_row, s->tmp_row, s->pass_row_size);
394
394
                got_line = 1;
395
395
            }
396
396
            if ((png_pass_dsp_ymask[s->pass] << (s->y & 7)) & 0x80) {
397
397
                /* NOTE: rgba32 is handled directly in png_put_interlaced_row */
398
 
                png_put_interlaced_row(ptr, s->width, s->bits_per_pixel, s->pass, 
 
398
                png_put_interlaced_row(ptr, s->width, s->bits_per_pixel, s->pass,
399
399
                                       s->color_type, s->last_row);
400
400
            }
401
401
            s->y++;
407
407
                    } else {
408
408
                        s->pass++;
409
409
                        s->y = 0;
410
 
                        s->pass_row_size = png_pass_row_size(s->pass, 
411
 
                                                             s->bits_per_pixel, 
 
410
                        s->pass_row_size = png_pass_row_size(s->pass,
 
411
                                                             s->bits_per_pixel,
412
412
                                                             s->width);
413
413
                        s->crow_size = s->pass_row_size + 1;
414
414
                        if (s->pass_row_size != 0)
456
456
    return 0;
457
457
}
458
458
 
459
 
static int png_read(ByteIOContext *f, 
 
459
static int png_read(ByteIOContext *f,
460
460
                    int (*alloc_cb)(void *opaque, AVImageInfo *info), void *opaque)
461
461
{
462
462
    AVImageInfo info1, *info = &info1;
487
487
            goto fail;
488
488
        tag = get_le32(f);
489
489
#ifdef DEBUG
490
 
        printf("png: tag=%c%c%c%c length=%u\n", 
 
490
        printf("png: tag=%c%c%c%c length=%u\n",
491
491
               (tag & 0xff),
492
492
               ((tag >> 8) & 0xff),
493
493
               ((tag >> 16) & 0xff),
507
507
            crc = get_be32(f);
508
508
            s->state |= PNG_IHDR;
509
509
#ifdef DEBUG
510
 
            printf("width=%d height=%d depth=%d color_type=%d compression_type=%d filter_type=%d interlace_type=%d\n", 
511
 
                   s->width, s->height, s->bit_depth, s->color_type, 
 
510
            printf("width=%d height=%d depth=%d color_type=%d compression_type=%d filter_type=%d interlace_type=%d\n",
 
511
                   s->width, s->height, s->bit_depth, s->color_type,
512
512
                   s->compression_type, s->filter_type, s->interlace_type);
513
513
#endif
514
514
            break;
526
526
                s->bpp = (s->bits_per_pixel + 7) >> 3;
527
527
                s->row_size = (info->width * s->bits_per_pixel + 7) >> 3;
528
528
 
529
 
                if (s->bit_depth == 8 && 
 
529
                if (s->bit_depth == 8 &&
530
530
                    s->color_type == PNG_COLOR_TYPE_RGB) {
531
531
                    info->pix_fmt = PIX_FMT_RGB24;
532
 
                } else if (s->bit_depth == 8 && 
 
532
                } else if (s->bit_depth == 8 &&
533
533
                           s->color_type == PNG_COLOR_TYPE_RGB_ALPHA) {
534
534
                    info->pix_fmt = PIX_FMT_RGBA32;
535
 
                } else if (s->bit_depth == 8 && 
 
535
                } else if (s->bit_depth == 8 &&
536
536
                           s->color_type == PNG_COLOR_TYPE_GRAY) {
537
537
                    info->pix_fmt = PIX_FMT_GRAY8;
538
 
                } else if (s->bit_depth == 1 && 
 
538
                } else if (s->bit_depth == 1 &&
539
539
                           s->color_type == PNG_COLOR_TYPE_GRAY) {
540
540
                    info->pix_fmt = PIX_FMT_MONOBLACK;
541
541
                } else if (s->color_type == PNG_COLOR_TYPE_PALETTE) {
544
544
                    goto fail;
545
545
                }
546
546
                ret = alloc_cb(opaque, info);
547
 
                if (ret) 
 
547
                if (ret)
548
548
                    goto the_end;
549
549
 
550
550
                /* compute the compressed row size */
552
552
                    s->crow_size = s->row_size + 1;
553
553
                } else {
554
554
                    s->pass = 0;
555
 
                    s->pass_row_size = png_pass_row_size(s->pass, 
556
 
                                                         s->bits_per_pixel, 
 
555
                    s->pass_row_size = png_pass_row_size(s->pass,
 
556
                                                         s->bits_per_pixel,
557
557
                                                         s->width);
558
558
                    s->crow_size = s->pass_row_size + 1;
559
559
                }
560
560
#ifdef DEBUG
561
 
                printf("row_size=%d crow_size =%d\n", 
 
561
                printf("row_size=%d crow_size =%d\n",
562
562
                       s->row_size, s->crow_size);
563
563
#endif
564
564
                s->image_buf = info->pict.data[0];
592
592
        case MKTAG('P', 'L', 'T', 'E'):
593
593
            {
594
594
                int n, i, r, g, b;
595
 
                
 
595
 
596
596
                if ((length % 3) != 0 || length > 256 * 3)
597
597
                    goto skip_tag;
598
598
                /* read the palette */
716
716
    uint8_t *ptr;
717
717
    uint8_t *crow_buf = NULL;
718
718
    uint8_t *tmp_buf = NULL;
719
 
    
 
719
 
720
720
    s->f = f;
721
721
    is_progressive = info->interleaved;
722
722
    switch(info->pix_fmt) {
764
764
 
765
765
    /* write png header */
766
766
    put_buffer(f, pngsig, 8);
767
 
    
 
767
 
768
768
    to_be32(s->buf, info->width);
769
769
    to_be32(s->buf + 4, info->height);
770
770
    s->buf[8] = bit_depth;
772
772
    s->buf[10] = 0; /* compression type */
773
773
    s->buf[11] = 0; /* filter type */
774
774
    s->buf[12] = is_progressive; /* interlace type */
775
 
    
 
775
 
776
776
    png_write_chunk(f, MKTAG('I', 'H', 'D', 'R'), s->buf, 13);
777
777
 
778
778
    /* put the palette if needed */
781
781
        unsigned int v;
782
782
        uint32_t *palette;
783
783
        uint8_t *alpha_ptr;
784
 
        
 
784
 
785
785
        palette = (uint32_t *)info->pict.data[1];
786
786
        ptr = s->buf;
787
787
        alpha_ptr = s->buf + 256 * 3;
824
824
                        } else {
825
825
                            ptr1 = ptr;
826
826
                        }
827
 
                        png_get_interlaced_row(crow_buf + 1, pass_row_size, 
828
 
                                               bits_per_pixel, pass, 
 
827
                        png_get_interlaced_row(crow_buf + 1, pass_row_size,
 
828
                                               bits_per_pixel, pass,
829
829
                                               ptr1, info->width);
830
830
                        crow_buf[0] = PNG_FILTER_VALUE_NONE;
831
831
                        png_write_row(s, crow_buf, pass_row_size + 1);
879
879
    "png",
880
880
    png_probe,
881
881
    png_read,
882
 
    (1 << PIX_FMT_RGBA32) | (1 << PIX_FMT_RGB24) | (1 << PIX_FMT_GRAY8) | 
 
882
    (1 << PIX_FMT_RGBA32) | (1 << PIX_FMT_RGB24) | (1 << PIX_FMT_GRAY8) |
883
883
    (1 << PIX_FMT_MONOBLACK) | (1 << PIX_FMT_PAL8),
884
884
    png_write,
885
885
    AVIMAGE_INTERLEAVED,