annotate dvdsub.c @ 2918:13dcd22f0816 libavcodec

Add DTS_INC to the CFLAGS for DTS. This is only set by external configure programs (such as the MPlayer one) and thus somewhat hackish. We already do this for things like MLIB_INC and IPP_INC so it should be acceptable.
author diego
date Sun, 23 Oct 2005 18:16:53 +0000
parents 1f117208d20f
children ef2149182f1c
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
1 /*
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
2 * DVD subtitle decoding for ffmpeg
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
3 * Copyright (c) 2005 Fabrice Bellard.
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
4 *
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
5 * This library is free software; you can redistribute it and/or
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
6 * modify it under the terms of the GNU Lesser General Public
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
7 * License as published by the Free Software Foundation; either
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
8 * version 2 of the License, or (at your option) any later version.
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
9 *
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
10 * This library is distributed in the hope that it will be useful,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
13 * Lesser General Public License for more details.
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
14 *
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
15 * You should have received a copy of the GNU Lesser General Public
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
16 * License along with this library; if not, write to the Free Software
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
18 */
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
19 #include "avcodec.h"
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
20
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
21 //#define DEBUG
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
22
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
23 typedef struct DVDSubContext {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
24 } DVDSubContext;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
25
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
26 static int dvdsub_init_decoder(AVCodecContext *avctx)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
27 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
28 return 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
29 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
30
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
31 uint16_t getbe16(const uint8_t *p)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
32 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
33 return (p[0] << 8) | p[1];
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
34 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
35
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
36 int get_nibble(const uint8_t *buf, int nibble_offset)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
37 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
38 return (buf[nibble_offset >> 1] >> ((1 - (nibble_offset & 1)) << 2)) & 0xf;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
39 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
40
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
41 static int decode_rle(uint8_t *bitmap, int linesize, int w, int h,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
42 const uint8_t *buf, int nibble_offset, int buf_size)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
43 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
44 unsigned int v;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
45 int x, y, len, color, nibble_end;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
46 uint8_t *d;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
47
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
48 nibble_end = buf_size * 2;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
49 x = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
50 y = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
51 d = bitmap;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
52 for(;;) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
53 if (nibble_offset >= nibble_end)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
54 return -1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
55 v = get_nibble(buf, nibble_offset++);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
56 if (v < 0x4) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
57 v = (v << 4) | get_nibble(buf, nibble_offset++);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
58 if (v < 0x10) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
59 v = (v << 4) | get_nibble(buf, nibble_offset++);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
60 if (v < 0x040) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
61 v = (v << 4) | get_nibble(buf, nibble_offset++);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
62 if (v < 4) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
63 v |= (w - x) << 2;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
64 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
65 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
66 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
67 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
68 len = v >> 2;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
69 if (len > (w - x))
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
70 len = (w - x);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
71 color = v & 0x03;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
72 memset(d + x, color, len);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
73 x += len;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
74 if (x >= w) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
75 y++;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
76 if (y >= h)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
77 break;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
78 d += linesize;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
79 x = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
80 /* byte align */
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
81 nibble_offset += (nibble_offset & 1);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
82 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
83 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
84 return 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
85 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
86
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
87 static void guess_palette(uint32_t *rgba_palette,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
88 uint8_t *palette,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
89 uint8_t *alpha,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
90 uint32_t subtitle_color)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
91 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
92 uint8_t color_used[16];
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
93 int nb_opaque_colors, i, level, j, r, g, b;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
94
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
95 for(i = 0; i < 4; i++)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
96 rgba_palette[i] = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
97
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
98 memset(color_used, 0, 16);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
99 nb_opaque_colors = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
100 for(i = 0; i < 4; i++) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
101 if (alpha[i] != 0 && !color_used[palette[i]]) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
102 color_used[palette[i]] = 1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
103 nb_opaque_colors++;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
104 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
105 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
106
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
107 if (nb_opaque_colors == 0)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
108 return;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
109
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
110 j = nb_opaque_colors;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
111 memset(color_used, 0, 16);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
112 for(i = 0; i < 4; i++) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
113 if (alpha[i] != 0) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
114 if (!color_used[palette[i]]) {
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
115 level = (0xff * j) / nb_opaque_colors;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
116 r = (((subtitle_color >> 16) & 0xff) * level) >> 8;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
117 g = (((subtitle_color >> 8) & 0xff) * level) >> 8;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
118 b = (((subtitle_color >> 0) & 0xff) * level) >> 8;
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
119 rgba_palette[i] = b | (g << 8) | (r << 16) | ((alpha[i] * 17) << 24);
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
120 color_used[palette[i]] = (i + 1);
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
121 j--;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
122 } else {
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
123 rgba_palette[i] = (rgba_palette[color_used[palette[i]] - 1] & 0x00ffffff) |
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
124 ((alpha[i] * 17) << 24);
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
125 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
126 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
127 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
128 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
129
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
130 static int decode_dvd_subtitles(AVSubtitle *sub_header,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
131 const uint8_t *buf, int buf_size)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
132 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
133 int cmd_pos, pos, cmd, x1, y1, x2, y2, offset1, offset2, next_cmd_pos;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
134 uint8_t palette[4], alpha[4];
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
135 int date;
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
136 int i;
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
137 int is_menu = 0;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
138
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
139 if (buf_size < 4)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
140 return -1;
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
141 sub_header->rects = NULL;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
142 sub_header->num_rects = 0;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
143 sub_header->start_display_time = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
144 sub_header->end_display_time = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
145
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
146 cmd_pos = getbe16(buf + 2);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
147 while ((cmd_pos + 4) < buf_size) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
148 date = getbe16(buf + cmd_pos);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
149 next_cmd_pos = getbe16(buf + cmd_pos + 2);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
150 #ifdef DEBUG
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
151 av_log(NULL, AV_LOG_INFO, "cmd_pos=0x%04x next=0x%04x date=%d\n",
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
152 cmd_pos, next_cmd_pos, date);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
153 #endif
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
154 pos = cmd_pos + 4;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
155 offset1 = -1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
156 offset2 = -1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
157 x1 = y1 = x2 = y2 = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
158 while (pos < buf_size) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
159 cmd = buf[pos++];
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
160 #ifdef DEBUG
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
161 av_log(NULL, AV_LOG_INFO, "cmd=%02x\n", cmd);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
162 #endif
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
163 switch(cmd) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
164 case 0x00:
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
165 /* menu subpicture */
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
166 is_menu = 1;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
167 break;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
168 case 0x01:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
169 /* set start date */
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
170 sub_header->start_display_time = (date << 10) / 90;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
171 break;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
172 case 0x02:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
173 /* set end date */
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
174 sub_header->end_display_time = (date << 10) / 90;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
175 break;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
176 case 0x03:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
177 /* set palette */
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
178 if ((buf_size - pos) < 2)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
179 goto fail;
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
180 palette[3] = buf[pos] >> 4;
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
181 palette[2] = buf[pos] & 0x0f;
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
182 palette[1] = buf[pos + 1] >> 4;
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
183 palette[0] = buf[pos + 1] & 0x0f;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
184 pos += 2;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
185 break;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
186 case 0x04:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
187 /* set alpha */
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
188 if ((buf_size - pos) < 2)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
189 goto fail;
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
190 alpha[3] = buf[pos] >> 4;
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
191 alpha[2] = buf[pos] & 0x0f;
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
192 alpha[1] = buf[pos + 1] >> 4;
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
193 alpha[0] = buf[pos + 1] & 0x0f;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
194 pos += 2;
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
195 #ifdef DEBUG
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
196 av_log(NULL, AV_LOG_INFO, "alpha=%x%x%x%x\n", alpha[0],alpha[1],alpha[2],alpha[3]);
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
197 #endif
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
198 break;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
199 case 0x05:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
200 if ((buf_size - pos) < 6)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
201 goto fail;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
202 x1 = (buf[pos] << 4) | (buf[pos + 1] >> 4);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
203 x2 = ((buf[pos + 1] & 0x0f) << 8) | buf[pos + 2];
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
204 y1 = (buf[pos + 3] << 4) | (buf[pos + 4] >> 4);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
205 y2 = ((buf[pos + 4] & 0x0f) << 8) | buf[pos + 5];
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
206 #ifdef DEBUG
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
207 av_log(NULL, AV_LOG_INFO, "x1=%d x2=%d y1=%d y2=%d\n",
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
208 x1, x2, y1, y2);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
209 #endif
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
210 pos += 6;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
211 break;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
212 case 0x06:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
213 if ((buf_size - pos) < 4)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
214 goto fail;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
215 offset1 = getbe16(buf + pos);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
216 offset2 = getbe16(buf + pos + 2);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
217 #ifdef DEBUG
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
218 av_log(NULL, AV_LOG_INFO, "offset1=0x%04x offset2=0x%04x\n", offset1, offset2);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
219 #endif
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
220 pos += 4;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
221 break;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
222 case 0xff:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
223 default:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
224 goto the_end;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
225 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
226 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
227 the_end:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
228 if (offset1 >= 0) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
229 int w, h;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
230 uint8_t *bitmap;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
231
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
232 /* decode the bitmap */
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
233 w = x2 - x1 + 1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
234 if (w < 0)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
235 w = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
236 h = y2 - y1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
237 if (h < 0)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
238 h = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
239 if (w > 0 && h > 0) {
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
240 if (sub_header->rects != NULL) {
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
241 for (i = 0; i < sub_header->num_rects; i++) {
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
242 av_free(sub_header->rects[i].bitmap);
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
243 av_free(sub_header->rects[i].rgba_palette);
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
244 }
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
245 av_freep(&sub_header->rects);
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
246 sub_header->num_rects = 0;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
247 }
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
248
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
249 bitmap = av_malloc(w * h);
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
250 sub_header->rects = av_mallocz(sizeof(AVSubtitleRect));
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
251 sub_header->num_rects = 1;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
252 sub_header->rects[0].rgba_palette = av_malloc(4 * 4);
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
253 decode_rle(bitmap, w * 2, w, h / 2,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
254 buf, offset1 * 2, buf_size);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
255 decode_rle(bitmap + w, w * 2, w, h / 2,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
256 buf, offset2 * 2, buf_size);
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
257 guess_palette(sub_header->rects[0].rgba_palette,
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
258 palette, alpha, 0xffff00);
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
259 sub_header->rects[0].x = x1;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
260 sub_header->rects[0].y = y1;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
261 sub_header->rects[0].w = w;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
262 sub_header->rects[0].h = h;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
263 sub_header->rects[0].nb_colors = 4;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
264 sub_header->rects[0].linesize = w;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
265 sub_header->rects[0].bitmap = bitmap;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
266 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
267 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
268 if (next_cmd_pos == cmd_pos)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
269 break;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
270 cmd_pos = next_cmd_pos;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
271 }
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
272 if (sub_header->num_rects > 0)
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
273 return is_menu;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
274 fail:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
275 return -1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
276 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
277
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
278 static int is_transp(const uint8_t *buf, int pitch, int n,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
279 const uint8_t *transp_color)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
280 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
281 int i;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
282 for(i = 0; i < n; i++) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
283 if (!transp_color[*buf])
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
284 return 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
285 buf += pitch;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
286 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
287 return 1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
288 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
289
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
290 /* return 0 if empty rectangle, 1 if non empty */
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
291 static int find_smallest_bounding_rectangle(AVSubtitle *s)
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
292 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
293 uint8_t transp_color[256];
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
294 int y1, y2, x1, x2, y, w, h, i;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
295 uint8_t *bitmap;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
296
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
297 if (s->num_rects == 0 || s->rects == NULL || s->rects[0].w <= 0 || s->rects[0].h <= 0)
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
298 return 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
299
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
300 memset(transp_color, 0, 256);
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
301 for(i = 0; i < s->rects[0].nb_colors; i++) {
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
302 if ((s->rects[0].rgba_palette[i] >> 24) == 0)
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
303 transp_color[i] = 1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
304 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
305 y1 = 0;
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
306 while (y1 < s->rects[0].h && is_transp(s->rects[0].bitmap + y1 * s->rects[0].linesize,
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
307 1, s->rects[0].w, transp_color))
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
308 y1++;
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
309 if (y1 == s->rects[0].h) {
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
310 av_freep(&s->rects[0].bitmap);
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
311 s->rects[0].w = s->rects[0].h = 0;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
312 return 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
313 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
314
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
315 y2 = s->rects[0].h - 1;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
316 while (y2 > 0 && is_transp(s->rects[0].bitmap + y2 * s->rects[0].linesize, 1,
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
317 s->rects[0].w, transp_color))
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
318 y2--;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
319 x1 = 0;
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
320 while (x1 < (s->rects[0].w - 1) && is_transp(s->rects[0].bitmap + x1, s->rects[0].linesize,
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
321 s->rects[0].h, transp_color))
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
322 x1++;
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
323 x2 = s->rects[0].w - 1;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
324 while (x2 > 0 && is_transp(s->rects[0].bitmap + x2, s->rects[0].linesize, s->rects[0].h,
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
325 transp_color))
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
326 x2--;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
327 w = x2 - x1 + 1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
328 h = y2 - y1 + 1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
329 bitmap = av_malloc(w * h);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
330 if (!bitmap)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
331 return 1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
332 for(y = 0; y < h; y++) {
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
333 memcpy(bitmap + w * y, s->rects[0].bitmap + x1 + (y1 + y) * s->rects[0].linesize, w);
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
334 }
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
335 av_freep(&s->rects[0].bitmap);
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
336 s->rects[0].bitmap = bitmap;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
337 s->rects[0].linesize = w;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
338 s->rects[0].w = w;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
339 s->rects[0].h = h;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
340 s->rects[0].x += x1;
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
341 s->rects[0].y += y1;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
342 return 1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
343 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
344
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
345 static int dvdsub_close_decoder(AVCodecContext *avctx)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
346 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
347 return 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
348 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
349
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
350 #ifdef DEBUG
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
351 #undef fprintf
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
352 static void ppm_save(const char *filename, uint8_t *bitmap, int w, int h,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
353 uint32_t *rgba_palette)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
354 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
355 int x, y, v;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
356 FILE *f;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
357
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
358 f = fopen(filename, "w");
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
359 if (!f) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
360 perror(filename);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
361 exit(1);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
362 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
363 fprintf(f, "P6\n"
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
364 "%d %d\n"
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
365 "%d\n",
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
366 w, h, 255);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
367 for(y = 0; y < h; y++) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
368 for(x = 0; x < w; x++) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
369 v = rgba_palette[bitmap[y * w + x]];
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
370 putc((v >> 16) & 0xff, f);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
371 putc((v >> 8) & 0xff, f);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
372 putc((v >> 0) & 0xff, f);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
373 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
374 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
375 fclose(f);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
376 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
377 #endif
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
378
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
379 static int dvdsub_decode(AVCodecContext *avctx,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
380 void *data, int *data_size,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
381 uint8_t *buf, int buf_size)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
382 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
383 AVSubtitle *sub = (void *)data;
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
384 int is_menu;
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
385
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
386 is_menu = decode_dvd_subtitles(sub, buf, buf_size);
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
387
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
388 if (is_menu < 0) {
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
389 no_subtitle:
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
390 *data_size = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
391
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
392 return buf_size;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
393 }
2833
1f117208d20f subs.diff fixes a couple of minor bugs in my DVB subtitle decoder, and also fixes a few
michael
parents: 2797
diff changeset
394 if (!is_menu && find_smallest_bounding_rectangle(sub) == 0)
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
395 goto no_subtitle;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
396
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
397 #if defined(DEBUG)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
398 av_log(NULL, AV_LOG_INFO, "start=%d ms end =%d ms\n",
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
399 sub->start_display_time,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
400 sub->end_display_time);
2797
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
401 ppm_save("/tmp/a.ppm", sub->rects[0].bitmap,
217844bd1fa1 10l (forgot to commit this yesterday)
michael
parents: 2756
diff changeset
402 sub->rects[0].w, sub->rects[0].h, sub->rects[0].rgba_palette);
2756
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
403 #endif
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
404
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
405 *data_size = 1;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
406 return buf_size;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
407 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
408
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
409 AVCodec dvdsub_decoder = {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
410 "dvdsub",
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
411 CODEC_TYPE_SUBTITLE,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
412 CODEC_ID_DVD_SUBTITLE,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
413 sizeof(DVDSubContext),
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
414 dvdsub_init_decoder,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
415 NULL,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
416 dvdsub_close_decoder,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
417 dvdsub_decode,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
418 };
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
419
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
420 /* parser definition */
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
421 typedef struct DVDSubParseContext {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
422 uint8_t *packet;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
423 int packet_len;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
424 int packet_index;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
425 } DVDSubParseContext;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
426
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
427 static int dvdsub_parse_init(AVCodecParserContext *s)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
428 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
429 return 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
430 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
431
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
432 static int dvdsub_parse(AVCodecParserContext *s,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
433 AVCodecContext *avctx,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
434 uint8_t **poutbuf, int *poutbuf_size,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
435 const uint8_t *buf, int buf_size)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
436 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
437 DVDSubParseContext *pc = s->priv_data;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
438
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
439 if (pc->packet_index == 0) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
440 if (buf_size < 2)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
441 return 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
442 pc->packet_len = (buf[0] << 8) | buf[1];
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
443 av_freep(&pc->packet);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
444 pc->packet = av_malloc(pc->packet_len);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
445 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
446 if (pc->packet) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
447 if (pc->packet_index + buf_size <= pc->packet_len) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
448 memcpy(pc->packet + pc->packet_index, buf, buf_size);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
449 pc->packet_index += buf_size;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
450 if (pc->packet_index >= pc->packet_len) {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
451 *poutbuf = pc->packet;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
452 *poutbuf_size = pc->packet_len;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
453 pc->packet_index = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
454 return buf_size;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
455 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
456 } else {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
457 /* erroneous size */
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
458 pc->packet_index = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
459 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
460 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
461 *poutbuf = NULL;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
462 *poutbuf_size = 0;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
463 return buf_size;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
464 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
465
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
466 static void dvdsub_parse_close(AVCodecParserContext *s)
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
467 {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
468 DVDSubParseContext *pc = s->priv_data;
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
469 av_freep(&pc->packet);
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
470 }
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
471
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
472 AVCodecParser dvdsub_parser = {
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
473 { CODEC_ID_DVD_SUBTITLE },
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
474 sizeof(DVDSubParseContext),
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
475 dvdsub_parse_init,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
476 dvdsub_parse,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
477 dvdsub_parse_close,
d8874c8749ec subtitle codec type support
bellard
parents:
diff changeset
478 };