1 #include "colormodels.h"
2 #include "funcprotos.h"
6 static void delete_vcodec_stub(quicktime_video_map_t *vtrack)
8 printf("delete_vcodec_stub called\n");
11 static void delete_acodec_stub(quicktime_audio_map_t *atrack)
13 printf("delete_acodec_stub called\n");
16 static int decode_video_stub(quicktime_t *file,
17 unsigned char **row_pointers,
20 printf("decode_video_stub called\n");
24 static int encode_video_stub(quicktime_t *file,
25 unsigned char **row_pointers,
28 printf("encode_video_stub called\n");
32 static int decode_audio_stub(quicktime_t *file,
39 printf("decode_audio_stub called\n");
43 static int encode_audio_stub(quicktime_t *file,
49 printf("encode_audio_stub called\n");
54 static int reads_colormodel_stub(quicktime_t *file,
58 return (colormodel == BC_RGB888);
61 static int writes_colormodel_stub(quicktime_t *file,
65 return (colormodel == BC_RGB888);
68 static void flush_codec_stub(quicktime_t *file, int track)
72 /* Convert Microsoft audio id to codec */
73 void quicktime_id_to_codec(char *result, int id)
78 memcpy(result, QUICKTIME_MP3, 4);
81 memcpy(result, QUICKTIME_WMA, 4);
84 printf("quicktime_id_to_codec: unknown audio id: 0x%06x\n", id);
89 int quicktime_codec_to_id(char *codec)
91 if(quicktime_match_32(codec, QUICKTIME_MP3))
94 if(quicktime_match_32(codec, QUICKTIME_WMA))
97 printf("quicktime_codec_to_id: unknown codec %c%c%c%c\n",
98 codec[0], codec[1], codec[2], codec[3]);
103 quicktime_codec_t* quicktime_new_codec()
105 quicktime_codec_t *codec = malloc(sizeof(*codec));
106 if( !codec ) return 0;
107 memset(codec, 0, sizeof(*codec));
108 codec->delete_vcodec = delete_vcodec_stub;
109 codec->delete_acodec = delete_acodec_stub;
110 codec->decode_video = decode_video_stub;
111 codec->encode_video = encode_video_stub;
112 codec->decode_audio = decode_audio_stub;
113 codec->encode_audio = encode_audio_stub;
114 codec->reads_colormodel = reads_colormodel_stub;
115 codec->writes_colormodel = writes_colormodel_stub;
116 codec->flush = flush_codec_stub;
120 void quicktime_del_codec(quicktime_codec_t *codec)
122 if( codec ) free(codec);
125 int new_vcodec(quicktime_video_map_t *vtrack)
127 int result = quicktime_find_vcodec(vtrack);
129 char *compressor = vtrack->track->mdia.minf.stbl.stsd.table[0].format;
131 "new_vcodec: couldn't find codec for \"%c%c%c%c\"\n",
132 compressor[0], compressor[1], compressor[2], compressor[3]);
139 int new_acodec(quicktime_audio_map_t *atrack)
141 int result = quicktime_find_acodec(atrack);
143 char *compressor = atrack->track->mdia.minf.stbl.stsd.table[0].format;
145 "new_acodec: couldn't find codec for \"%c%c%c%c\"\n",
146 compressor[0], compressor[1], compressor[2], compressor[3]);
153 int quicktime_init_vcodec(quicktime_video_map_t *vtrack)
155 int result = new_vcodec(vtrack);
159 int quicktime_init_acodec(quicktime_audio_map_t *atrack)
161 int result = new_acodec(atrack);
166 int quicktime_delete_vcodec(quicktime_video_map_t *vtrack)
170 quicktime_codec_t *codec_base = vtrack->codec;
172 codec_base->delete_vcodec(vtrack);
179 int quicktime_delete_acodec(quicktime_audio_map_t *atrack)
183 quicktime_codec_t *codec_base = atrack->codec;
185 codec_base->delete_acodec(atrack);
192 int quicktime_supported_video(quicktime_t *file, int track)
194 if(track < file->total_vtracks)
196 quicktime_video_map_t *video_map = &file->vtracks[track];
206 int quicktime_supported_audio(quicktime_t *file, int track)
208 if(track < file->total_atracks)
210 quicktime_audio_map_t *audio_map = &file->atracks[track];
221 long quicktime_decode_video(quicktime_t *file,
222 unsigned char **row_pointers,
227 if(track < 0 || track >= file->total_vtracks)
229 fprintf(stderr, "quicktime_decode_video: track %d out of range %d - %d\n",
232 file->total_vtracks);
236 /* Get dimensions from first video track */
237 if(!file->do_scaling)
239 quicktime_video_map_t *video_map = &file->vtracks[track];
240 quicktime_trak_t *trak = video_map->track;
241 int track_width = trak->tkhd.track_width;
242 int track_height = trak->tkhd.track_height;
246 file->in_w = track_width;
247 file->in_h = track_height;
248 file->out_w = track_width;
249 file->out_h = track_height;
252 result = ((quicktime_codec_t*)file->vtracks[track].codec)->decode_video(file,
255 file->vtracks[track].current_position++;
259 void quicktime_set_parameter(quicktime_t *file, const char *key, void *value)
262 for(i = 0; i < file->total_vtracks; i++)
264 quicktime_codec_t *codec = (quicktime_codec_t*)file->vtracks[i].codec;
266 if(codec->set_parameter) codec->set_parameter(file, i,(char*)key, value);
269 for(i = 0; i < file->total_atracks; i++)
271 quicktime_codec_t *codec = (quicktime_codec_t*)file->atracks[i].codec;
273 if(codec->set_parameter) codec->set_parameter(file, i,(char*)key, value);
277 int quicktime_encode_video(quicktime_t *file,
278 unsigned char **row_pointers,
282 result = ((quicktime_codec_t*)file->vtracks[track].codec)->encode_video(file, row_pointers, track);
283 file->vtracks[track].current_position++;
288 int quicktime_decode_audio(quicktime_t *file,
294 int quicktime_track, quicktime_channel;
297 quicktime_channel_location(file, &quicktime_track, &quicktime_channel, channel);
298 result = ((quicktime_codec_t*)file->atracks[quicktime_track].codec)->decode_audio(file,
304 file->atracks[quicktime_track].current_position += samples;
309 /* Since all channels are written at the same time: */
310 /* Encode using the compressor for the first audio track. */
311 /* Which means all the audio channels must be on the same track. */
313 int quicktime_encode_audio(quicktime_t *file, int16_t **input_i, float **input_f, long samples)
316 //char *compressor = quicktime_audio_compressor(file, 0);
318 result = ((quicktime_codec_t*)file->atracks[0].codec)->encode_audio(file,
323 file->atracks[0].current_position += samples;
328 int quicktime_reads_cmodel(quicktime_t *file,
332 int result = ((quicktime_codec_t*)file->vtracks[track].codec)->reads_colormodel(file, colormodel, track);
336 int quicktime_writes_cmodel(quicktime_t *file,
340 return ((quicktime_codec_t*)file->vtracks[track].codec)->writes_colormodel(file, colormodel, track);
343 /* Compressors that can only encode a window at a time */
344 /* need to flush extra data here. */
346 int quicktime_flush_acodec(quicktime_t *file, int track)
348 ((quicktime_codec_t*)file->atracks[track].codec)->flush(file, track);
352 void quicktime_flush_vcodec(quicktime_t *file, int track)
354 ((quicktime_codec_t*)file->vtracks[track].codec)->flush(file, track);
357 int64_t quicktime_samples_to_bytes(quicktime_trak_t *track, long samples)
359 char *compressor = track->mdia.minf.stbl.stsd.table[0].format;
360 int channels = track->mdia.minf.stbl.stsd.table[0].channels;
362 if(quicktime_match_32(compressor, QUICKTIME_DV))
363 return (int64_t)samples * track->mdia.minf.stbl.stsz.sample_size;
365 if(quicktime_match_32(compressor, QUICKTIME_IMA4))
366 return samples * channels;
368 if(quicktime_match_32(compressor, QUICKTIME_ULAW))
369 return samples * channels;
371 /* Default use the sample size specification for TWOS and RAW */
372 return samples * channels * track->mdia.minf.stbl.stsd.table[0].sample_size / 8;
375 int quicktime_codecs_flush(quicktime_t *file)
379 if(!file->wr) return result;
381 if(file->total_atracks)
383 for(i = 0; i < file->total_atracks && !result; i++)
385 quicktime_flush_acodec(file, i);
389 if(file->total_vtracks)
391 for(i = 0; i < file->total_vtracks && !result; i++)
393 quicktime_flush_vcodec(file, i);