1 /*
2 * DVB subtitle encoding
3 * Copyright (c) 2005 Fabrice Bellard
4 *
5 * This file is part of FFmpeg.
6 *
7 * FFmpeg is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
11 *
12 * FFmpeg is distributed in the hope that it will be useful,
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
18 * License along with FFmpeg; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20 */
26
32
33 #define PUTBITS2(val)\
34 {\
35 bitbuf |= (val) << bitcnt;\
36 bitcnt -= 2;\
37 if (bitcnt < 0) {\
38 bitcnt = 6;\
39 *q++ = bitbuf;\
40 bitbuf = 0;\
41 }\
42 }
43
45 const uint8_t *bitmap, int linesize,
47 {
48 uint8_t *q, *line_begin;
49 unsigned int bitbuf;
50 int bitcnt;
52
53 q = *pq;
54
55 for(y = 0; y <
h; y++) {
56 // Worst case line is 3 bits per value + 4 bytes overhead
57 if (buf_size * 8 <
w * 3 + 32)
59 line_begin = q;
60 *q++ = 0x10;
61 bitbuf = 0;
62 bitcnt = 6;
63
64 x = 0;
66 x1 = x;
68 while (x1 <
w && bitmap[x1] ==
color)
69 x1++;
75 }
else if (
len >= 3 &&
len <= 10) {
81 }
else if (
len >= 12 &&
len <= 27) {
89 }
else if (
len >= 29) {
90 /* length = 29 ... 284 */
102 } else {
106 }
108 }
110 }
111 /* end of line */
115 if (bitcnt != 6) {
116 *q++ = bitbuf;
117 }
118 *q++ = 0xf0;
119 bitmap += linesize;
120 buf_size -= q - line_begin;
121 }
123 *pq = q;
125 }
126
127 #define PUTBITS4(val)\
128 {\
129 bitbuf |= (val) << bitcnt;\
130 bitcnt -= 4;\
131 if (bitcnt < 0) {\
132 bitcnt = 4;\
133 *q++ = bitbuf;\
134 bitbuf = 0;\
135 }\
136 }
137
138 /* some DVB decoders only implement 4 bits/pixel */
140 const uint8_t *bitmap, int linesize,
142 {
143 uint8_t *q, *line_begin;
144 unsigned int bitbuf;
145 int bitcnt;
147
148 q = *pq;
149
150 for(y = 0; y <
h; y++) {
151 // Worst case line is 6 bits per value, + 4 bytes overhead
152 if (buf_size * 8 <
w * 6 + 32)
154 line_begin = q;
155 *q++ = 0x11;
156 bitbuf = 0;
157 bitcnt = 4;
158
159 x = 0;
161 x1 = x;
162 color = bitmap[x1++];
163 while (x1 <
w && bitmap[x1] ==
color)
164 x1++;
172 }
else if (
len >= 4 &&
len <= 7) {
176 }
else if (
len >= 9 &&
len <= 24) {
181 }
else if (
len >= 25) {
190 } else {
194 }
196 }
198 }
199 /* end of line */
202 if (bitcnt != 4) {
203 *q++ = bitbuf;
204 }
205 *q++ = 0xf0;
206 bitmap += linesize;
207 buf_size -= q - line_begin;
208 }
210 *pq = q;
212 }
213
215 const uint8_t *bitmap, int linesize,
217 {
218 uint8_t *q, *line_begin;
220
221 q = *pq;
222
223 for (y = 0; y <
h; y++) {
224 // Worst case line is 12 bits per value, + 3 bytes overhead
225 if (buf_size * 8 <
w * 12 + 24)
227 line_begin = q;
228 *q++ = 0x12;
229
230 x = 0;
232 x1 = x;
233 color = bitmap[x1++];
234 while (x1 <
w && bitmap[x1] ==
color)
235 x1++;
238 // 00000001 to 11111111 1 pixel in colour x
240 } else {
242 // 00000000 0LLLLLLL L pixels (1-127) in colour 0 (L > 0)
244 *q++ = 0x00;
246 }
else if (
len > 2) {
247 // 00000000 1LLLLLLL CCCCCCCC L pixels (3-127) in colour C (L > 2)
249 *q++ = 0x00;
252 }
256 } else {
259 }
260 }
262 }
263 /* end of line */
264 // 00000000 00000000 end of 8-bit/pixel_code_string
265 *q++ = 0x00;
266 *q++ = 0x00;
267 *q++ = 0xf0;
268 bitmap += linesize;
269 buf_size -= q - line_begin;
270 }
272 *pq = q;
274 }
275
278 {
280 uint8_t *q, *pseg_len;
281 int page_id, region_id, clut_id, object_id,
i, bpp_index, page_state, min_colors;
282
283
284 q = outbuf;
285
286 page_id = 1;
287
289 case 2:
290 case 4:
291 case 8:
292 min_colors = 1 <<
s->min_bpp;
293 break;
294 default:
297 }
298
299 if (
h->num_rects && !
h->rects)
301
302 if (
h->num_rects >= 256)
304
306 if (buf_size < 11)
308 /* display definition segment */
309 *q++ = 0x0f; /* sync_byte */
310 *q++ = 0x14; /* segment_type */
311 bytestream_put_be16(&q, page_id);
312 pseg_len = q;
313 q += 2; /* segment length */
314 *q++ = 0x00; /* dds version number & display window flag */
315 bytestream_put_be16(&q, avctx->
width - 1);
/* display width */
316 bytestream_put_be16(&q, avctx->
height - 1);
/* display height */
317 bytestream_put_be16(&pseg_len, q - pseg_len - 2);
318 buf_size -= 11;
319 }
320
321 /* page composition segment */
322
323 if (buf_size < 8 + h->num_rects * 6)
325 *q++ = 0x0f; /* sync_byte */
326 *q++ = 0x10; /* segment_type */
327 bytestream_put_be16(&q, page_id);
328 pseg_len = q;
329 q += 2; /* segment length */
330 *q++ = 30; /* page_timeout (seconds) */
331 page_state = 2; /* mode change */
332 /* page_version = 0 + page_state */
333 *q++ = (
s->object_version << 4) | (page_state << 2) | 3;
334
335 for (region_id = 0; region_id <
h->num_rects; region_id++) {
336 *q++ = region_id;
337 *q++ = 0xff; /* reserved */
338 bytestream_put_be16(&q,
h->rects[region_id]->x);
/* left pos */
339 bytestream_put_be16(&q,
h->rects[region_id]->y);
/* top pos */
340 }
341
342 bytestream_put_be16(&pseg_len, q - pseg_len - 2);
343 buf_size -= 8 +
h->num_rects * 6;
344
346 for (clut_id = 0; clut_id <
h->num_rects; clut_id++) {
347 /* CLUT segment */
348 int nb_colors =
FFMAX(min_colors,
h->rects[clut_id]->nb_colors);
349
350 if (nb_colors <= 4
U) {
351 /* 2 bpp, some decoders do not support it correctly */
352 bpp_index = 0;
353 }
else if (nb_colors <= 16
U) {
354 /* 4 bpp, standard encoding */
355 bpp_index = 1;
356 }
else if (nb_colors <= 256
U) {
357 /* 8 bpp, standard encoding */
358 bpp_index = 2;
359 } else {
361 }
362
363 if (buf_size < 6 + h->rects[clut_id]->nb_colors * 6)
365
366 /* CLUT segment */
367 *q++ = 0x0f; /* sync byte */
368 *q++ = 0x12; /* CLUT definition segment */
369 bytestream_put_be16(&q, page_id);
370 pseg_len = q;
371 q += 2; /* segment length */
372 *q++ = clut_id;
373 *q++ = (0 << 4) | 0
xf;
/* version = 0 */
374
375 for(
i = 0;
i <
h->rects[clut_id]->nb_colors;
i++) {
376 *q++ =
i;
/* clut_entry_id */
377 *q++ = (1 << (7 - bpp_index)) | (0xf << 1) | 1; /* 2 bits/pixel full range */
378 {
380 uint32_t x= ((uint32_t*)
h->rects[clut_id]->data[1])[
i];
381 a = (x >> 24) & 0xff;
382 r = (x >> 16) & 0xff;
385
390 }
391 }
392
393 bytestream_put_be16(&pseg_len, q - pseg_len - 2);
394 buf_size -= 6 +
h->rects[clut_id]->nb_colors * 6;
395 }
396
397 if (buf_size < h->num_rects * 22)
399 for (region_id = 0; region_id <
h->num_rects; region_id++) {
400
401 /* region composition segment */
402 int nb_colors =
FFMAX(min_colors,
h->rects[region_id]->nb_colors);
403
404 if (nb_colors <= 4) {
405 /* 2 bpp, some decoders do not support it correctly */
406 bpp_index = 0;
407 } else if (nb_colors <= 16) {
408 /* 4 bpp, standard encoding */
409 bpp_index = 1;
410 } else if (nb_colors <= 256) {
411 /* 8 bpp, standard encoding */
412 bpp_index = 2;
413 } else {
415 }
416
417 *q++ = 0x0f; /* sync_byte */
418 *q++ = 0x11; /* segment_type */
419 bytestream_put_be16(&q, page_id);
420 pseg_len = q;
421 q += 2; /* segment length */
422 *q++ = region_id;
423 *q++ = (
s->object_version << 4) | (0 << 3) | 0x07;
/* version , no fill */
424 bytestream_put_be16(&q,
h->rects[region_id]->w);
/* region width */
425 bytestream_put_be16(&q,
h->rects[region_id]->h);
/* region height */
426 *q++ = ((1 + bpp_index) << 5) | ((1 + bpp_index) << 2) | 0x03;
427 *q++ = region_id; /* clut_id == region_id */
428 *q++ = 0; /* 8 bit fill colors */
429 *q++ = 0x03; /* 4 bit and 2 bit fill colors */
430
431 bytestream_put_be16(&q, region_id); /* object_id == region_id */
432 *q++ = (0 << 6) | (0 << 4);
433 *q++ = 0;
434 *q++ = 0xf0;
435 *q++ = 0;
436
437 bytestream_put_be16(&pseg_len, q - pseg_len - 2);
438 }
439 buf_size -=
h->num_rects * 22;
440
441 for (object_id = 0; object_id <
h->num_rects; object_id++) {
442 int (*dvb_encode_rle)(uint8_t **pq, int buf_size,
443 const uint8_t *bitmap, int linesize,
445
446 int nb_colors =
FFMAX(min_colors,
h->rects[object_id]->nb_colors);
447
448 if (buf_size < 13)
450
451 /* bpp_index maths */
452 if (nb_colors <= 4) {
453 /* 2 bpp, some decoders do not support it correctly */
455 } else if (nb_colors <= 16) {
456 /* 4 bpp, standard encoding */
458 } else if (nb_colors <= 256) {
459 /* 8 bpp, standard encoding */
461 } else {
463 }
464
465 /* Object Data segment */
466 *q++ = 0x0f; /* sync byte */
467 *q++ = 0x13;
468 bytestream_put_be16(&q, page_id);
469 pseg_len = q;
470 q += 2; /* segment length */
471
472 bytestream_put_be16(&q, object_id);
473 *q++ = (
s->object_version << 4) | (0 << 2) | (0 << 1) | 1;
/* version = 0,
474 object_coding_method,
475 non_modifying_color_flag */
476 {
477 uint8_t *ptop_field_len, *pbottom_field_len, *top_ptr, *bottom_ptr;
479
480 ptop_field_len = q;
481 q += 2;
482 pbottom_field_len = q;
483 q += 2;
484 buf_size -= 13;
485
486 top_ptr = q;
487 ret = dvb_encode_rle(&q, buf_size,
488 h->rects[object_id]->data[0],
489 h->rects[object_id]->w * 2,
490 h->rects[object_id]->w,
491 h->rects[object_id]->h >> 1);
495 bottom_ptr = q;
496 ret = dvb_encode_rle(&q, buf_size,
497 h->rects[object_id]->data[0] +
h->rects[object_id]->w,
498 h->rects[object_id]->w * 2,
499 h->rects[object_id]->w,
500 h->rects[object_id]->h >> 1);
504
505 bytestream_put_be16(&ptop_field_len, bottom_ptr - top_ptr);
506 bytestream_put_be16(&pbottom_field_len, q - bottom_ptr);
507 }
508
509 bytestream_put_be16(&pseg_len, q - pseg_len - 2);
510 }
511 }
512
513 /* end of display set segment */
514
515 if (buf_size < 6)
517 *q++ = 0x0f; /* sync_byte */
518 *q++ = 0x80; /* segment_type */
519 bytestream_put_be16(&q, page_id);
520 pseg_len = q;
521 q += 2; /* segment length */
522
523 bytestream_put_be16(&pseg_len, q - pseg_len - 2);
524 buf_size -= 6;
525
526 s->object_version = (
s->object_version + 1) & 0
xf;
527 return q - outbuf;
528 }
529
530 #define OFFSET(x) offsetof(DVBSubtitleContext, x)
531 #define SE AV_OPT_FLAG_SUBTITLE_PARAM | AV_OPT_FLAG_ENCODING_PARAM
533 {
"min_bpp",
"minimum bits-per-pixel for subtitle colors (2, 4 or 8)",
OFFSET(min_bpp),
AV_OPT_TYPE_INT, {.i64 = 4}, 2, 8,
SE},
535 };
536
542 };
543
552 };