Mercurial > libavformat.hg
annotate wc3movie.c @ 1960:c0289552590f libavformat
Change the vhook code to send real timestamps to the filters instead of the
current time of day, which is useless, and which the filters could just as
easily query for themselves.
patch by Bobby Bingham, uhmmmm gmail com
author | diego |
---|---|
date | Thu, 29 Mar 2007 05:24:35 +0000 |
parents | a782462e2497 |
children | 2f0154760e5f |
rev | line source |
---|---|
225 | 1 /* |
2 * Wing Commander III Movie (.mve) File Demuxer | |
3 * Copyright (c) 2003 The ffmpeg Project | |
4 * | |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
5 * This file is part of FFmpeg. |
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
6 * |
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
7 * FFmpeg is free software; you can redistribute it and/or |
225 | 8 * modify it under the terms of the GNU Lesser General Public |
9 * License as published by the Free Software Foundation; either | |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
10 * version 2.1 of the License, or (at your option) any later version. |
225 | 11 * |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
12 * FFmpeg is distributed in the hope that it will be useful, |
225 | 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 | |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
18 * License along with FFmpeg; if not, write to the Free Software |
896
edbe5c3717f9
Update licensing information: The FSF changed postal address.
diego
parents:
887
diff
changeset
|
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
225 | 20 */ |
21 | |
22 /** | |
23 * @file wc3movie.c | |
24 * Wing Commander III Movie file demuxer | |
25 * by Mike Melanson (melanson@pcisys.net) | |
26 * for more information on the WC3 .mve file format, visit: | |
27 * http://www.pcisys.net/~melanson/codecs/ | |
28 */ | |
29 | |
30 #include "avformat.h" | |
31 | |
32 #define WC3_PREAMBLE_SIZE 8 | |
33 | |
386
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
34 #define FORM_TAG MKTAG('F', 'O', 'R', 'M') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
35 #define MOVE_TAG MKTAG('M', 'O', 'V', 'E') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
36 #define _PC__TAG MKTAG('_', 'P', 'C', '_') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
37 #define SOND_TAG MKTAG('S', 'O', 'N', 'D') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
38 #define BNAM_TAG MKTAG('B', 'N', 'A', 'M') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
39 #define SIZE_TAG MKTAG('S', 'I', 'Z', 'E') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
40 #define PALT_TAG MKTAG('P', 'A', 'L', 'T') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
41 #define INDX_TAG MKTAG('I', 'N', 'D', 'X') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
42 #define BRCH_TAG MKTAG('B', 'R', 'C', 'H') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
43 #define SHOT_TAG MKTAG('S', 'H', 'O', 'T') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
44 #define VGA__TAG MKTAG('V', 'G', 'A', ' ') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
45 #define TEXT_TAG MKTAG('T', 'E', 'X', 'T') |
c152849ee643
remove numerous definitions of BE_*/LE_* macros; convert FOURCC_TAG ->
melanson
parents:
370
diff
changeset
|
46 #define AUDI_TAG MKTAG('A', 'U', 'D', 'I') |
225 | 47 |
48 /* video resolution unless otherwise specified */ | |
49 #define WC3_DEFAULT_WIDTH 320 | |
50 #define WC3_DEFAULT_HEIGHT 165 | |
51 | |
52 /* always use the same PCM audio parameters */ | |
53 #define WC3_SAMPLE_RATE 22050 | |
54 #define WC3_AUDIO_CHANNELS 1 | |
55 #define WC3_AUDIO_BITS 16 | |
56 | |
57 /* nice, constant framerate */ | |
58 #define WC3_FRAME_PTS_INC (90000 / 15) | |
59 | |
60 #define PALETTE_SIZE (256 * 3) | |
61 #define PALETTE_COUNT 256 | |
62 | |
63 typedef struct Wc3DemuxContext { | |
64 int width; | |
65 int height; | |
66 unsigned char *palettes; | |
67 int palette_count; | |
68 int64_t pts; | |
69 int video_stream_index; | |
70 int audio_stream_index; | |
71 | |
245 | 72 AVPaletteControl palette_control; |
225 | 73 |
74 } Wc3DemuxContext; | |
75 | |
76 /* bizarre palette lookup table */ | |
243 | 77 static const unsigned char wc3_pal_lookup[] = { |
885 | 78 0x00, 0x03, 0x05, 0x07, 0x09, 0x0B, 0x0D, 0x0E, |
225 | 79 0x10, 0x12, 0x13, 0x15, 0x16, 0x18, 0x19, 0x1A, |
885 | 80 0x1C, 0x1D, 0x1F, 0x20, 0x21, 0x23, 0x24, 0x25, |
225 | 81 0x27, 0x28, 0x29, 0x2A, 0x2C, 0x2D, 0x2E, 0x2F, |
885 | 82 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x38, 0x39, |
225 | 83 0x3A, 0x3B, 0x3C, 0x3D, 0x3F, 0x40, 0x41, 0x42, |
885 | 84 0x43, 0x44, 0x45, 0x46, 0x48, 0x49, 0x4A, 0x4B, |
225 | 85 0x4C, 0x4D, 0x4E, 0x4F, 0x50, 0x51, 0x52, 0x53, |
885 | 86 0x54, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x5B, 0x5C, |
225 | 87 0x5D, 0x5E, 0x5F, 0x60, 0x61, 0x62, 0x63, 0x64, |
885 | 88 0x65, 0x66, 0x67, 0x68, 0x69, 0x6A, 0x6B, 0x6C, |
225 | 89 0x6D, 0x6E, 0x6F, 0x70, 0x71, 0x72, 0x73, 0x74, |
885 | 90 0x75, 0x76, 0x77, 0x78, 0x79, 0x7A, 0x7B, 0x7C, |
225 | 91 0x7D, 0x7D, 0x7E, 0x7F, 0x80, 0x81, 0x82, 0x83, |
885 | 92 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8A, 0x8B, |
225 | 93 0x8C, 0x8D, 0x8D, 0x8E, 0x8F, 0x90, 0x91, 0x92, |
885 | 94 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, 0x99, |
225 | 95 0x9A, 0x9B, 0x9C, 0x9D, 0x9E, 0x9F, 0xA0, 0xA1, |
885 | 96 0xA2, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, 0xA8, |
225 | 97 0xA9, 0xAA, 0xAA, 0xAB, 0xAC, 0xAD, 0xAE, 0xAF, |
885 | 98 0xB0, 0xB1, 0xB2, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, |
225 | 99 0xB7, 0xB8, 0xB9, 0xB9, 0xBA, 0xBB, 0xBC, 0xBD, |
885 | 100 0xBE, 0xBF, 0xBF, 0xC0, 0xC1, 0xC2, 0xC3, 0xC4, |
225 | 101 0xC5, 0xC5, 0xC6, 0xC7, 0xC8, 0xC9, 0xCA, 0xCB, |
885 | 102 0xCB, 0xCC, 0xCD, 0xCE, 0xCF, 0xD0, 0xD0, 0xD1, |
225 | 103 0xD2, 0xD3, 0xD4, 0xD5, 0xD5, 0xD6, 0xD7, 0xD8, |
104 0xD9, 0xDA, 0xDA, 0xDB, 0xDC, 0xDD, 0xDE, 0xDF, | |
105 0xDF, 0xE0, 0xE1, 0xE2, 0xE3, 0xE4, 0xE4, 0xE5, | |
885 | 106 0xE6, 0xE7, 0xE8, 0xE9, 0xE9, 0xEA, 0xEB, 0xEC, |
225 | 107 0xED, 0xED, 0xEE, 0xEF, 0xF0, 0xF1, 0xF1, 0xF2, |
885 | 108 0xF3, 0xF4, 0xF5, 0xF6, 0xF6, 0xF7, 0xF8, 0xF9, |
225 | 109 0xFA, 0xFA, 0xFB, 0xFC, 0xFD, 0xFD, 0xFD, 0xFD |
110 }; | |
111 | |
112 | |
113 static int wc3_probe(AVProbeData *p) | |
114 { | |
115 if (p->buf_size < 12) | |
116 return 0; | |
117 | |
1673 | 118 if ((AV_RL32(&p->buf[0]) != FORM_TAG) || |
119 (AV_RL32(&p->buf[8]) != MOVE_TAG)) | |
225 | 120 return 0; |
121 | |
122 return AVPROBE_SCORE_MAX; | |
123 } | |
124 | |
125 static int wc3_read_header(AVFormatContext *s, | |
126 AVFormatParameters *ap) | |
127 { | |
128 Wc3DemuxContext *wc3 = (Wc3DemuxContext *)s->priv_data; | |
129 ByteIOContext *pb = &s->pb; | |
130 unsigned int fourcc_tag; | |
131 unsigned int size; | |
132 AVStream *st; | |
133 unsigned char preamble[WC3_PREAMBLE_SIZE]; | |
134 int ret = 0; | |
135 int current_palette = 0; | |
136 int bytes_to_read; | |
137 int i; | |
243 | 138 unsigned char rotate; |
225 | 139 |
140 /* default context members */ | |
141 wc3->width = WC3_DEFAULT_WIDTH; | |
142 wc3->height = WC3_DEFAULT_HEIGHT; | |
143 wc3->palettes = NULL; | |
144 wc3->palette_count = 0; | |
145 wc3->pts = 0; | |
146 wc3->video_stream_index = wc3->audio_stream_index = 0; | |
147 | |
148 /* skip the first 3 32-bit numbers */ | |
149 url_fseek(pb, 12, SEEK_CUR); | |
150 | |
151 /* traverse through the chunks and load the header information before | |
152 * the first BRCH tag */ | |
885 | 153 if ((ret = get_buffer(pb, preamble, WC3_PREAMBLE_SIZE)) != |
225 | 154 WC3_PREAMBLE_SIZE) |
482 | 155 return AVERROR_IO; |
1673 | 156 fourcc_tag = AV_RL32(&preamble[0]); |
157 size = (AV_RB32(&preamble[4]) + 1) & (~1); | |
225 | 158 |
159 do { | |
160 switch (fourcc_tag) { | |
161 | |
162 case SOND_TAG: | |
163 case INDX_TAG: | |
164 /* SOND unknown, INDX unnecessary; ignore both */ | |
165 url_fseek(pb, size, SEEK_CUR); | |
166 break; | |
167 | |
168 case _PC__TAG: | |
169 /* need the number of palettes */ | |
170 url_fseek(pb, 8, SEEK_CUR); | |
171 if ((ret = get_buffer(pb, preamble, 4)) != 4) | |
482 | 172 return AVERROR_IO; |
1673 | 173 wc3->palette_count = AV_RL32(&preamble[0]); |
643 | 174 if((unsigned)wc3->palette_count >= UINT_MAX / PALETTE_SIZE){ |
175 wc3->palette_count= 0; | |
639 | 176 return -1; |
643 | 177 } |
225 | 178 wc3->palettes = av_malloc(wc3->palette_count * PALETTE_SIZE); |
179 break; | |
180 | |
181 case BNAM_TAG: | |
182 /* load up the name */ | |
643 | 183 if ((unsigned)size < 512) |
225 | 184 bytes_to_read = size; |
185 else | |
186 bytes_to_read = 512; | |
187 if ((ret = get_buffer(pb, s->title, bytes_to_read)) != bytes_to_read) | |
482 | 188 return AVERROR_IO; |
225 | 189 break; |
190 | |
191 case SIZE_TAG: | |
192 /* video resolution override */ | |
885 | 193 if ((ret = get_buffer(pb, preamble, WC3_PREAMBLE_SIZE)) != |
225 | 194 WC3_PREAMBLE_SIZE) |
482 | 195 return AVERROR_IO; |
1673 | 196 wc3->width = AV_RL32(&preamble[0]); |
197 wc3->height = AV_RL32(&preamble[4]); | |
225 | 198 break; |
199 | |
200 case PALT_TAG: | |
201 /* one of several palettes */ | |
643 | 202 if ((unsigned)current_palette >= wc3->palette_count) |
225 | 203 return AVERROR_INVALIDDATA; |
885 | 204 if ((ret = get_buffer(pb, |
205 &wc3->palettes[current_palette * PALETTE_SIZE], | |
225 | 206 PALETTE_SIZE)) != PALETTE_SIZE) |
482 | 207 return AVERROR_IO; |
225 | 208 |
209 /* transform the current palette in place */ | |
210 for (i = current_palette * PALETTE_SIZE; | |
211 i < (current_palette + 1) * PALETTE_SIZE; i++) { | |
243 | 212 /* rotate each palette component left by 2 and use the result |
213 * as an index into the color component table */ | |
885 | 214 rotate = ((wc3->palettes[i] << 2) & 0xFF) | |
243 | 215 ((wc3->palettes[i] >> 6) & 0xFF); |
216 wc3->palettes[i] = wc3_pal_lookup[rotate]; | |
225 | 217 } |
218 current_palette++; | |
219 break; | |
220 | |
221 default: | |
370
845f9de2c883
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
295
diff
changeset
|
222 av_log(s, AV_LOG_ERROR, " unrecognized WC3 chunk: %c%c%c%c (0x%02X%02X%02X%02X)\n", |
225 | 223 preamble[0], preamble[1], preamble[2], preamble[3], |
224 preamble[0], preamble[1], preamble[2], preamble[3]); | |
225 return AVERROR_INVALIDDATA; | |
226 break; | |
227 } | |
228 | |
885 | 229 if ((ret = get_buffer(pb, preamble, WC3_PREAMBLE_SIZE)) != |
225 | 230 WC3_PREAMBLE_SIZE) |
482 | 231 return AVERROR_IO; |
1673 | 232 fourcc_tag = AV_RL32(&preamble[0]); |
225 | 233 /* chunk sizes are 16-bit aligned */ |
1673 | 234 size = (AV_RB32(&preamble[4]) + 1) & (~1); |
225 | 235 |
236 } while (fourcc_tag != BRCH_TAG); | |
237 | |
238 /* initialize the decoder streams */ | |
239 st = av_new_stream(s, 0); | |
240 if (!st) | |
241 return AVERROR_NOMEM; | |
462
b69898ffc92a
move time_base (pts_num/pts_den) from AVFormatContext -> AVStream
michael
parents:
386
diff
changeset
|
242 av_set_pts_info(st, 33, 1, 90000); |
225 | 243 wc3->video_stream_index = st->index; |
820
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
244 st->codec->codec_type = CODEC_TYPE_VIDEO; |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
245 st->codec->codec_id = CODEC_ID_XAN_WC3; |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
246 st->codec->codec_tag = 0; /* no fourcc */ |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
247 st->codec->width = wc3->width; |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
248 st->codec->height = wc3->height; |
225 | 249 |
250 /* palette considerations */ | |
820
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
251 st->codec->palctrl = &wc3->palette_control; |
225 | 252 |
253 st = av_new_stream(s, 0); | |
254 if (!st) | |
255 return AVERROR_NOMEM; | |
462
b69898ffc92a
move time_base (pts_num/pts_den) from AVFormatContext -> AVStream
michael
parents:
386
diff
changeset
|
256 av_set_pts_info(st, 33, 1, 90000); |
225 | 257 wc3->audio_stream_index = st->index; |
820
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
258 st->codec->codec_type = CODEC_TYPE_AUDIO; |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
259 st->codec->codec_id = CODEC_ID_PCM_S16LE; |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
260 st->codec->codec_tag = 1; |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
261 st->codec->channels = WC3_AUDIO_CHANNELS; |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
262 st->codec->bits_per_sample = WC3_AUDIO_BITS; |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
263 st->codec->sample_rate = WC3_SAMPLE_RATE; |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
264 st->codec->bit_rate = st->codec->channels * st->codec->sample_rate * |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
265 st->codec->bits_per_sample; |
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
775
diff
changeset
|
266 st->codec->block_align = WC3_AUDIO_BITS * WC3_AUDIO_CHANNELS; |
225 | 267 |
268 return 0; | |
269 } | |
270 | |
271 static int wc3_read_packet(AVFormatContext *s, | |
272 AVPacket *pkt) | |
273 { | |
274 Wc3DemuxContext *wc3 = (Wc3DemuxContext *)s->priv_data; | |
275 ByteIOContext *pb = &s->pb; | |
276 unsigned int fourcc_tag; | |
277 unsigned int size; | |
278 int packet_read = 0; | |
279 int ret = 0; | |
280 unsigned char preamble[WC3_PREAMBLE_SIZE]; | |
281 unsigned char text[1024]; | |
282 unsigned int palette_number; | |
295
bff1a372ae38
revised palette API, courtesy of Roberto Togni (rtogni at freemail.it)
melanson
parents:
245
diff
changeset
|
283 int i; |
bff1a372ae38
revised palette API, courtesy of Roberto Togni (rtogni at freemail.it)
melanson
parents:
245
diff
changeset
|
284 unsigned char r, g, b; |
bff1a372ae38
revised palette API, courtesy of Roberto Togni (rtogni at freemail.it)
melanson
parents:
245
diff
changeset
|
285 int base_palette_index; |
225 | 286 |
287 while (!packet_read) { | |
288 | |
289 /* get the next chunk preamble */ | |
290 if ((ret = get_buffer(pb, preamble, WC3_PREAMBLE_SIZE)) != | |
291 WC3_PREAMBLE_SIZE) | |
482 | 292 ret = AVERROR_IO; |
225 | 293 |
1673 | 294 fourcc_tag = AV_RL32(&preamble[0]); |
225 | 295 /* chunk sizes are 16-bit aligned */ |
1673 | 296 size = (AV_RB32(&preamble[4]) + 1) & (~1); |
225 | 297 |
298 switch (fourcc_tag) { | |
299 | |
300 case BRCH_TAG: | |
301 /* no-op */ | |
302 break; | |
303 | |
304 case SHOT_TAG: | |
305 /* load up new palette */ | |
306 if ((ret = get_buffer(pb, preamble, 4)) != 4) | |
482 | 307 return AVERROR_IO; |
1673 | 308 palette_number = AV_RL32(&preamble[0]); |
225 | 309 if (palette_number >= wc3->palette_count) |
310 return AVERROR_INVALIDDATA; | |
295
bff1a372ae38
revised palette API, courtesy of Roberto Togni (rtogni at freemail.it)
melanson
parents:
245
diff
changeset
|
311 base_palette_index = palette_number * PALETTE_COUNT * 3; |
bff1a372ae38
revised palette API, courtesy of Roberto Togni (rtogni at freemail.it)
melanson
parents:
245
diff
changeset
|
312 for (i = 0; i < PALETTE_COUNT; i++) { |
bff1a372ae38
revised palette API, courtesy of Roberto Togni (rtogni at freemail.it)
melanson
parents:
245
diff
changeset
|
313 r = wc3->palettes[base_palette_index + i * 3 + 0]; |
bff1a372ae38
revised palette API, courtesy of Roberto Togni (rtogni at freemail.it)
melanson
parents:
245
diff
changeset
|
314 g = wc3->palettes[base_palette_index + i * 3 + 1]; |
bff1a372ae38
revised palette API, courtesy of Roberto Togni (rtogni at freemail.it)
melanson
parents:
245
diff
changeset
|
315 b = wc3->palettes[base_palette_index + i * 3 + 2]; |
bff1a372ae38
revised palette API, courtesy of Roberto Togni (rtogni at freemail.it)
melanson
parents:
245
diff
changeset
|
316 wc3->palette_control.palette[i] = (r << 16) | (g << 8) | (b); |
bff1a372ae38
revised palette API, courtesy of Roberto Togni (rtogni at freemail.it)
melanson
parents:
245
diff
changeset
|
317 } |
245 | 318 wc3->palette_control.palette_changed = 1; |
225 | 319 break; |
320 | |
321 case VGA__TAG: | |
322 /* send out video chunk */ | |
775 | 323 ret= av_get_packet(pb, pkt, size); |
225 | 324 pkt->stream_index = wc3->video_stream_index; |
325 pkt->pts = wc3->pts; | |
326 if (ret != size) | |
482 | 327 ret = AVERROR_IO; |
225 | 328 packet_read = 1; |
329 break; | |
330 | |
331 case TEXT_TAG: | |
332 /* subtitle chunk */ | |
333 #if 0 | |
334 url_fseek(pb, size, SEEK_CUR); | |
335 #else | |
643 | 336 if ((unsigned)size > sizeof(text) || (ret = get_buffer(pb, text, size)) != size) |
482 | 337 ret = AVERROR_IO; |
225 | 338 else { |
339 int i = 0; | |
370
845f9de2c883
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
295
diff
changeset
|
340 av_log (s, AV_LOG_DEBUG, "Subtitle time!\n"); |
845f9de2c883
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
295
diff
changeset
|
341 av_log (s, AV_LOG_DEBUG, " inglish: %s\n", &text[i + 1]); |
225 | 342 i += text[i] + 1; |
370
845f9de2c883
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
295
diff
changeset
|
343 av_log (s, AV_LOG_DEBUG, " doytsch: %s\n", &text[i + 1]); |
225 | 344 i += text[i] + 1; |
370
845f9de2c883
av_log() patch by (Michel Bardiaux <mbardiaux at peaktime dot be>)
michael
parents:
295
diff
changeset
|
345 av_log (s, AV_LOG_DEBUG, " fronsay: %s\n", &text[i + 1]); |
225 | 346 } |
347 #endif | |
348 break; | |
349 | |
350 case AUDI_TAG: | |
351 /* send out audio chunk */ | |
775 | 352 ret= av_get_packet(pb, pkt, size); |
225 | 353 pkt->stream_index = wc3->audio_stream_index; |
354 pkt->pts = wc3->pts; | |
355 if (ret != size) | |
482 | 356 ret = AVERROR_IO; |
225 | 357 |
358 /* time to advance pts */ | |
359 wc3->pts += WC3_FRAME_PTS_INC; | |
360 | |
361 packet_read = 1; | |
362 break; | |
363 | |
364 default: | |
887 | 365 av_log (s, AV_LOG_ERROR, " unrecognized WC3 chunk: %c%c%c%c (0x%02X%02X%02X%02X)\n", |
225 | 366 preamble[0], preamble[1], preamble[2], preamble[3], |
367 preamble[0], preamble[1], preamble[2], preamble[3]); | |
368 ret = AVERROR_INVALIDDATA; | |
369 packet_read = 1; | |
370 break; | |
371 } | |
372 } | |
373 | |
374 return ret; | |
375 } | |
376 | |
377 static int wc3_read_close(AVFormatContext *s) | |
378 { | |
379 Wc3DemuxContext *wc3 = (Wc3DemuxContext *)s->priv_data; | |
380 | |
381 av_free(wc3->palettes); | |
382 | |
383 return 0; | |
384 } | |
385 | |
1169 | 386 AVInputFormat wc3_demuxer = { |
225 | 387 "wc3movie", |
388 "Wing Commander III movie format", | |
389 sizeof(Wc3DemuxContext), | |
390 wc3_probe, | |
391 wc3_read_header, | |
392 wc3_read_packet, | |
393 wc3_read_close, | |
394 }; |