Mercurial > libavcodec.hg
comparison dvdsub.c @ 2797:217844bd1fa1 libavcodec
10l (forgot to commit this yesterday)
DVB subtitle decoder by (Ian Caulfield: imc25, cam ac uk)
author | michael |
---|---|
date | Sun, 17 Jul 2005 09:22:51 +0000 |
parents | d8874c8749ec |
children | 1f117208d20f |
comparison
equal
deleted
inserted
replaced
2796:95c35706acbb | 2797:217844bd1fa1 |
---|---|
130 const uint8_t *buf, int buf_size) | 130 const uint8_t *buf, int buf_size) |
131 { | 131 { |
132 int cmd_pos, pos, cmd, x1, y1, x2, y2, offset1, offset2, next_cmd_pos; | 132 int cmd_pos, pos, cmd, x1, y1, x2, y2, offset1, offset2, next_cmd_pos; |
133 uint8_t palette[4], alpha[4]; | 133 uint8_t palette[4], alpha[4]; |
134 int date; | 134 int date; |
135 int i; | |
135 | 136 |
136 if (buf_size < 4) | 137 if (buf_size < 4) |
137 return -1; | 138 return -1; |
138 sub_header->bitmap = NULL; | 139 sub_header->rects = NULL; |
139 sub_header->rgba_palette = NULL; | 140 sub_header->num_rects = 0; |
140 sub_header->start_display_time = 0; | 141 sub_header->start_display_time = 0; |
141 sub_header->end_display_time = 0; | 142 sub_header->end_display_time = 0; |
142 | 143 |
143 cmd_pos = getbe16(buf + 2); | 144 cmd_pos = getbe16(buf + 2); |
144 while ((cmd_pos + 4) < buf_size) { | 145 while ((cmd_pos + 4) < buf_size) { |
228 w = 0; | 229 w = 0; |
229 h = y2 - y1; | 230 h = y2 - y1; |
230 if (h < 0) | 231 if (h < 0) |
231 h = 0; | 232 h = 0; |
232 if (w > 0 && h > 0) { | 233 if (w > 0 && h > 0) { |
233 av_freep(&sub_header->bitmap); | 234 if (sub_header->rects != NULL) { |
234 av_freep(&sub_header->rgba_palette); | 235 for (i = 0; i < sub_header->num_rects; i++) { |
236 av_free(sub_header->rects[i].bitmap); | |
237 av_free(sub_header->rects[i].rgba_palette); | |
238 } | |
239 av_freep(&sub_header->rects); | |
240 sub_header->num_rects = 0; | |
241 } | |
242 | |
235 bitmap = av_malloc(w * h); | 243 bitmap = av_malloc(w * h); |
236 sub_header->rgba_palette = av_malloc(4 * 4); | 244 sub_header->rects = av_mallocz(sizeof(AVSubtitleRect)); |
245 sub_header->num_rects = 1; | |
246 sub_header->rects[0].rgba_palette = av_malloc(4 * 4); | |
237 decode_rle(bitmap, w * 2, w, h / 2, | 247 decode_rle(bitmap, w * 2, w, h / 2, |
238 buf, offset1 * 2, buf_size); | 248 buf, offset1 * 2, buf_size); |
239 decode_rle(bitmap + w, w * 2, w, h / 2, | 249 decode_rle(bitmap + w, w * 2, w, h / 2, |
240 buf, offset2 * 2, buf_size); | 250 buf, offset2 * 2, buf_size); |
241 guess_palette(sub_header->rgba_palette, | 251 guess_palette(sub_header->rects[0].rgba_palette, |
242 palette, alpha, 0xffff00); | 252 palette, alpha, 0xffff00); |
243 sub_header->x = x1; | 253 sub_header->rects[0].x = x1; |
244 sub_header->y = y1; | 254 sub_header->rects[0].y = y1; |
245 sub_header->w = w; | 255 sub_header->rects[0].w = w; |
246 sub_header->h = h; | 256 sub_header->rects[0].h = h; |
247 sub_header->nb_colors = 4; | 257 sub_header->rects[0].nb_colors = 4; |
248 sub_header->linesize = w; | 258 sub_header->rects[0].linesize = w; |
249 sub_header->bitmap = bitmap; | 259 sub_header->rects[0].bitmap = bitmap; |
250 } | 260 } |
251 } | 261 } |
252 if (next_cmd_pos == cmd_pos) | 262 if (next_cmd_pos == cmd_pos) |
253 break; | 263 break; |
254 cmd_pos = next_cmd_pos; | 264 cmd_pos = next_cmd_pos; |
255 } | 265 } |
256 if (sub_header->bitmap) | 266 if (sub_header->num_rects > 0) |
257 return 0; | 267 return 0; |
258 fail: | 268 fail: |
259 return -1; | 269 return -1; |
260 } | 270 } |
261 | 271 |
276 { | 286 { |
277 uint8_t transp_color[256]; | 287 uint8_t transp_color[256]; |
278 int y1, y2, x1, x2, y, w, h, i; | 288 int y1, y2, x1, x2, y, w, h, i; |
279 uint8_t *bitmap; | 289 uint8_t *bitmap; |
280 | 290 |
281 if (s->w <= 0 || s->h <= 0) | 291 if (s->num_rects == 0 || s->rects == NULL || s->rects[0].w <= 0 || s->rects[0].h <= 0) |
282 return 0; | 292 return 0; |
283 | 293 |
284 memset(transp_color, 0, 256); | 294 memset(transp_color, 0, 256); |
285 for(i = 0; i < s->nb_colors; i++) { | 295 for(i = 0; i < s->rects[0].nb_colors; i++) { |
286 if ((s->rgba_palette[i] >> 24) == 0) | 296 if ((s->rects[0].rgba_palette[i] >> 24) == 0) |
287 transp_color[i] = 1; | 297 transp_color[i] = 1; |
288 } | 298 } |
289 y1 = 0; | 299 y1 = 0; |
290 while (y1 < s->h && is_transp(s->bitmap + y1 * s->linesize, 1, s->w, | 300 while (y1 < s->rects[0].h && is_transp(s->rects[0].bitmap + y1 * s->rects[0].linesize, |
291 transp_color)) | 301 1, s->rects[0].w, transp_color)) |
292 y1++; | 302 y1++; |
293 if (y1 == s->h) { | 303 if (y1 == s->rects[0].h) { |
294 av_freep(&s->bitmap); | 304 av_freep(&s->rects[0].bitmap); |
295 s->w = s->h = 0; | 305 s->rects[0].w = s->rects[0].h = 0; |
296 return 0; | 306 return 0; |
297 } | 307 } |
298 | 308 |
299 y2 = s->h - 1; | 309 y2 = s->rects[0].h - 1; |
300 while (y2 > 0 && is_transp(s->bitmap + y2 * s->linesize, 1, s->w, | 310 while (y2 > 0 && is_transp(s->rects[0].bitmap + y2 * s->rects[0].linesize, 1, |
301 transp_color)) | 311 s->rects[0].w, transp_color)) |
302 y2--; | 312 y2--; |
303 x1 = 0; | 313 x1 = 0; |
304 while (x1 < (s->w - 1) && is_transp(s->bitmap + x1, s->linesize, s->h, | 314 while (x1 < (s->rects[0].w - 1) && is_transp(s->rects[0].bitmap + x1, s->rects[0].linesize, |
305 transp_color)) | 315 s->rects[0].h, transp_color)) |
306 x1++; | 316 x1++; |
307 x2 = s->w - 1; | 317 x2 = s->rects[0].w - 1; |
308 while (x2 > 0 && is_transp(s->bitmap + x2, s->linesize, s->h, | 318 while (x2 > 0 && is_transp(s->rects[0].bitmap + x2, s->rects[0].linesize, s->rects[0].h, |
309 transp_color)) | 319 transp_color)) |
310 x2--; | 320 x2--; |
311 w = x2 - x1 + 1; | 321 w = x2 - x1 + 1; |
312 h = y2 - y1 + 1; | 322 h = y2 - y1 + 1; |
313 bitmap = av_malloc(w * h); | 323 bitmap = av_malloc(w * h); |
314 if (!bitmap) | 324 if (!bitmap) |
315 return 1; | 325 return 1; |
316 for(y = 0; y < h; y++) { | 326 for(y = 0; y < h; y++) { |
317 memcpy(bitmap + w * y, s->bitmap + x1 + (y1 + y) * s->linesize, w); | 327 memcpy(bitmap + w * y, s->rects[0].bitmap + x1 + (y1 + y) * s->rects[0].linesize, w); |
318 } | 328 } |
319 av_freep(&s->bitmap); | 329 av_freep(&s->rects[0].bitmap); |
320 s->bitmap = bitmap; | 330 s->rects[0].bitmap = bitmap; |
321 s->linesize = w; | 331 s->rects[0].linesize = w; |
322 s->w = w; | 332 s->rects[0].w = w; |
323 s->h = h; | 333 s->rects[0].h = h; |
324 s->x += x1; | 334 s->rects[0].x += x1; |
325 s->y += y1; | 335 s->rects[0].y += y1; |
326 return 1; | 336 return 1; |
327 } | 337 } |
328 | 338 |
329 static int dvdsub_close_decoder(AVCodecContext *avctx) | 339 static int dvdsub_close_decoder(AVCodecContext *avctx) |
330 { | 340 { |
377 | 387 |
378 #if defined(DEBUG) | 388 #if defined(DEBUG) |
379 av_log(NULL, AV_LOG_INFO, "start=%d ms end =%d ms\n", | 389 av_log(NULL, AV_LOG_INFO, "start=%d ms end =%d ms\n", |
380 sub->start_display_time, | 390 sub->start_display_time, |
381 sub->end_display_time); | 391 sub->end_display_time); |
382 ppm_save("/tmp/a.ppm", sub->bitmap, | 392 ppm_save("/tmp/a.ppm", sub->rects[0].bitmap, |
383 sub->w, sub->h, sub->rgba_palette); | 393 sub->rects[0].w, sub->rects[0].h, sub->rects[0].rgba_palette); |
384 #endif | 394 #endif |
385 | 395 |
386 *data_size = 1; | 396 *data_size = 1; |
387 return buf_size; | 397 return buf_size; |
388 } | 398 } |