diff options
-rw-r--r-- | ChangeLog | 1 | ||||
-rw-r--r-- | src/libspudvb/xine_spudvb_decoder.c | 40 | ||||
-rw-r--r-- | src/xine-engine/Makefile.am | 4 | ||||
-rw-r--r-- | src/xine-engine/spu.c | 62 | ||||
-rw-r--r-- | src/xine-engine/spu.h | 44 | ||||
-rw-r--r-- | src/xine-engine/xine.c | 6 |
6 files changed, 146 insertions, 11 deletions
@@ -39,6 +39,7 @@ xine-lib (1.1.90) (Unreleased) compatibility reasons, though they must appear before it. * The XML parser handles CDATA elements. * Text handling within XML is improved. + * DVB subtitles' opacity is now controllable. xine-lib (1.1.9) (unreleased) * Fix dvd://.../title[.chapter] handling (somewhat broken in 1.1.8). diff --git a/src/libspudvb/xine_spudvb_decoder.c b/src/libspudvb/xine_spudvb_decoder.c index 7fe972be6..f5bb49b33 100644 --- a/src/libspudvb/xine_spudvb_decoder.c +++ b/src/libspudvb/xine_spudvb_decoder.c @@ -30,6 +30,7 @@ #include "pthread.h" #include <errno.h> #include "xine_internal.h" +#include "spu.h" #include "osd.h" #define MAX_REGIONS 7 @@ -292,6 +293,24 @@ static void decode_4bit_pixel_code_string (dvb_spu_decoder_t * this, int r, int } } +static void recalculate_trans (dvb_spu_decoder_t *this) +{ + dvbsub_func_t *const dvbsub = this->dvbsub; + xine_spu_opacity_t opacity; + int i; + + _x_spu_get_opacity (this->stream->xine, &opacity); + for (i = 0; i < MAX_REGIONS * 256; ++i) { + /* ETSI-300-743 says "full transparency if Y == 0". */ + if (dvbsub->colours[i].y == 0) + dvbsub->trans[i] = 0; + else { + int v = _x_spu_calculate_opacity (&dvbsub->colours[i], dvbsub->colours[i].foo, &opacity); + dvbsub->trans[i] = v * 14 / 255 + 1; + } + } + +} static void set_clut(dvb_spu_decoder_t *this,int CLUT_id,int CLUT_entry_id,int Y_value, int Cr_value, int Cb_value, int T_value) { @@ -304,13 +323,7 @@ static void set_clut(dvb_spu_decoder_t *this,int CLUT_id,int CLUT_entry_id,int Y dvbsub->colours[(CLUT_id*256)+CLUT_entry_id].y=Y_value; dvbsub->colours[(CLUT_id*256)+CLUT_entry_id].cr=Cr_value; dvbsub->colours[(CLUT_id*256)+CLUT_entry_id].cb=Cb_value; - - if (Y_value==0) { - dvbsub->trans[(CLUT_id*256)+CLUT_entry_id]=T_value; - } else { - dvbsub->trans[(CLUT_id*256)+CLUT_entry_id]=255; - } - + dvbsub->colours[(CLUT_id*256)+CLUT_entry_id].foo = T_value; } static void process_CLUT_definition_segment(dvb_spu_decoder_t *this) { @@ -816,6 +829,7 @@ static void spudec_decode_data (spu_decoder_t * this_gen, buf_element_t * buf) process_object_data_segment (this); break; case 0x80: /* Page is now completely rendered */ + recalculate_trans(this); draw_subtitles( this ); break; default: @@ -911,6 +925,18 @@ static spu_decoder_t *dvb_spu_class_open_plugin (spu_decoder_class_t * class_gen this->dvbsub->regions[i].CLUT_id = 0; } + { + xine_spu_opacity_t opacity; + static const clut_t black = { 0, 0, 0, 0 }; + int t; + + _x_spu_get_opacity (this->stream->xine, &opacity); + t = _x_spu_calculate_opacity (&black, 0, &opacity); + + for (i = 0; i < MAX_REGIONS * 256; i++) + this->dvbsub->colours[i].foo = t; + } + pthread_mutex_init(&this->dvbsub_osd_mutex, NULL); pthread_cond_init(&this->dvbsub_restart_timeout, NULL); this->dvbsub_hide_timeout.tv_nsec = 0; diff --git a/src/xine-engine/Makefile.am b/src/xine-engine/Makefile.am index 082b06be9..36c48a3c9 100644 --- a/src/xine-engine/Makefile.am +++ b/src/xine-engine/Makefile.am @@ -18,7 +18,7 @@ noinst_HEADERS = bswap.h ffmpeg_bswap.h xineinclude_HEADERS = buffer.h metronom.h configfile.h vo_scale.h \ audio_out.h resample.h video_out.h xine_internal.h spu_decoder.h \ - video_overlay.h osd.h scratch.h xine_plugin.h xineintl.h \ + video_overlay.h osd.h spu.h scratch.h xine_plugin.h xineintl.h \ plugin_catalog.h audio_decoder.h video_decoder.h post.h \ io_helper.h broadcaster.h info_helper.h refcounter.h alphablend.h @@ -27,7 +27,7 @@ lib_LTLIBRARIES = libxine.la libxine_la_SOURCES = xine.c metronom.c configfile.c buffer.c \ load_plugins.c video_decoder.c buffer_types.c \ audio_decoder.c video_out.c audio_out.c resample.c events.c \ - video_overlay.c osd.c scratch.c demux.c vo_scale.c \ + video_overlay.c osd.c spu.c scratch.c demux.c vo_scale.c \ xine_interface.c post.c tvmode.c broadcaster.c io_helper.c \ input_rip.c input_cache.c info_helper.c refcounter.c \ alphablend.c diff --git a/src/xine-engine/spu.c b/src/xine-engine/spu.c new file mode 100644 index 000000000..813300fb0 --- /dev/null +++ b/src/xine-engine/spu.c @@ -0,0 +1,62 @@ +/* + * Copyright (C) 2007 the xine project + * + * This file is part of xine, a free video player. + * + * xine is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * xine is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +#include "xine_internal.h" +#include "spu.h" + +#define BLACK_OPACITY 67 +#define COLOUR_OPACITY 100 + +static void no_op (void *user_data, xine_cfg_entry_t *entry) +{ +} + +void _x_spu_misc_init (xine_t *this) +{ + this->config->register_range (this->config, "subtitles.bitmap.black_opacity", + BLACK_OPACITY, 0, 100, + _("opacity for the black parts of bitmapped subtitles"), + NULL, + 10, no_op, NULL); + this->config->register_range (this->config, "subtitles.bitmap.colour_opacity", + COLOUR_OPACITY, 0, 100, + _("opacity for the colour parts of bitmapped subtitles"), + NULL, + 10, no_op, NULL); +} + +void _x_spu_get_opacity (xine_t *this, xine_spu_opacity_t *opacity) +{ + cfg_entry_t *entry; + + entry = this->config->lookup_entry (this->config, "subtitles.bitmap.black_opacity"); + opacity->black = entry ? entry->num_value : BLACK_OPACITY; + entry = this->config->lookup_entry (this->config, "subtitles.bitmap.colour_opacity"); + opacity->colour = entry ? entry->num_value : COLOUR_OPACITY; +} + +int _x_spu_calculate_opacity (const clut_t *clut, uint8_t trans, const xine_spu_opacity_t *opacity) +{ + int value = (clut->y == 0 || (clut->y == 16 && clut->cb == 128 && clut->cr == 128)) + ? opacity->black + : opacity->colour; + return value * (255 - trans) / 100; +} diff --git a/src/xine-engine/spu.h b/src/xine-engine/spu.h new file mode 100644 index 000000000..daba7866b --- /dev/null +++ b/src/xine-engine/spu.h @@ -0,0 +1,44 @@ +/* + * Copyright (C) 2007 the xine project + * + * This file is part of xine, a free video player. + * + * xine is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * xine is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +#ifndef XINE_UTILS_SPU_H +#define XINE_UTILS_SPU_H + +#ifndef XINE_PROTECTED +#define XINE_PROTECTED +#endif + +typedef struct xine_spu_opacity_s xine_spu_opacity_t; + +struct xine_spu_opacity_s { + uint8_t black, colour; +}; + +void _x_spu_misc_init (xine_t *); + +void _x_spu_get_opacity (xine_t *, xine_spu_opacity_t *) XINE_PROTECTED; + +/* in: trans = 0..255, 0=opaque + * out: 0..255, 0=transparent + */ +int _x_spu_calculate_opacity (const clut_t *, uint8_t trans, const xine_spu_opacity_t *) XINE_PROTECTED; + +#endif diff --git a/src/xine-engine/xine.c b/src/xine-engine/xine.c index 96f97d94c..2d3b32176 100644 --- a/src/xine-engine/xine.c +++ b/src/xine-engine/xine.c @@ -70,6 +70,7 @@ #include "metronom.h" #include "configfile.h" #include "osd.h" +#include "spu.h" #include "xineutils.h" #include "compat.h" @@ -730,9 +731,10 @@ xine_stream_t *xine_stream_new (xine_t *this, /* * osd */ - if (vo) + if (vo) { + _x_spu_misc_init (this); stream->osd_renderer = _x_osd_renderer_init(stream); - else + } else stream->osd_renderer = NULL; /* |