demux: adaptive: remove redundant check of CRLF
[vlc.git] / src / misc / text_style.c
blob90de47a912415dec4c6620296f3379de10904531
1 /*****************************************************************************
2 * text_style.c
3 *****************************************************************************
4 * Copyright (C) 1999-2010 VLC authors and VideoLAN
5 * $Id$
7 * Author: basOS G <noxelia 4t gmail , com>
9 * This program is free software; you can redistribute it and/or modify it
10 * under the terms of the GNU Lesser General Public License as published by
11 * the Free Software Foundation; either version 2.1 of the License, or
12 * (at your option) any later version.
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU Lesser General Public License for more details.
19 * You should have received a copy of the GNU Lesser General Public License
20 * along with this program; if not, write to the Free Software Foundation,
21 * Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
22 *****************************************************************************/
24 #ifdef HAVE_CONFIG_H
25 # include "config.h"
26 #endif
28 #include <vlc_common.h>
29 #include <vlc_text_style.h>
31 #include <ctype.h>
33 /* */
34 text_style_t *text_style_New( void )
36 return text_style_Create( STYLE_FULLY_SET );
39 text_style_t *text_style_Create( int i_defaults )
41 text_style_t *p_style = calloc( 1, sizeof(*p_style) );
42 if( !p_style )
43 return NULL;
45 if( i_defaults == STYLE_NO_DEFAULTS )
46 return p_style;
48 /* initialize to default text style (FIXME: by flag) */
49 p_style->psz_fontname = NULL;
50 p_style->psz_monofontname = NULL;
51 p_style->i_features = STYLE_FULLY_SET;
52 p_style->i_style_flags = STYLE_OUTLINE;
53 p_style->f_font_relsize = STYLE_DEFAULT_REL_FONT_SIZE;
54 p_style->i_font_size = STYLE_DEFAULT_FONT_SIZE;
55 p_style->i_font_color = 0xffffff;
56 p_style->i_font_alpha = STYLE_ALPHA_OPAQUE;
57 p_style->i_outline_color = 0x000000;
58 p_style->i_outline_alpha = STYLE_ALPHA_OPAQUE;
59 p_style->i_shadow_color = 0x808080;
60 p_style->i_shadow_alpha = STYLE_ALPHA_OPAQUE;
61 p_style->i_background_color = 0x000000;
62 p_style->i_background_alpha = STYLE_ALPHA_OPAQUE;
63 p_style->i_karaoke_background_color = 0xffffff;
64 p_style->i_karaoke_background_alpha = STYLE_ALPHA_OPAQUE;
65 p_style->i_outline_width = 1;
66 p_style->i_shadow_width = 0;
67 p_style->i_spacing = -1;
68 p_style->e_wrapinfo = STYLE_WRAP_DEFAULT;
70 return p_style;
73 text_style_t *text_style_Copy( text_style_t *p_dst, const text_style_t *p_src )
75 if( !p_src )
76 return p_dst;
78 /* */
79 *p_dst = *p_src;
81 if( p_src->psz_fontname )
82 p_dst->psz_fontname = strdup( p_src->psz_fontname );
84 if( p_src->psz_monofontname )
85 p_dst->psz_monofontname = strdup( p_src->psz_monofontname );
87 return p_dst;
90 #define MERGE(var, fflag) \
91 if( (p_src->i_features & fflag) && (b_override || !(p_dst->i_features & fflag)) )\
92 p_dst->var = p_src->var
94 #define MERGE_SIZE(var) \
95 if( p_src->var > 0 && (b_override || p_dst->var <= 0) )\
96 p_dst->var = p_src->var
98 void text_style_Merge( text_style_t *p_dst, const text_style_t *p_src, bool b_override )
100 if( p_src->psz_fontname && (!p_dst->psz_fontname || b_override) )
102 free( p_dst->psz_fontname );
103 p_dst->psz_fontname = strdup( p_src->psz_fontname );
106 if( p_src->psz_monofontname && (!p_dst->psz_monofontname || b_override) )
108 free( p_dst->psz_monofontname );
109 p_dst->psz_monofontname = strdup( p_src->psz_monofontname );
112 if( p_src->i_features != STYLE_NO_DEFAULTS )
114 MERGE(i_font_color, STYLE_HAS_FONT_COLOR);
115 MERGE(i_font_alpha, STYLE_HAS_FONT_ALPHA);
116 MERGE(i_outline_color, STYLE_HAS_OUTLINE_COLOR);
117 MERGE(i_outline_alpha, STYLE_HAS_OUTLINE_ALPHA);
118 MERGE(i_shadow_color, STYLE_HAS_SHADOW_COLOR);
119 MERGE(i_shadow_alpha, STYLE_HAS_SHADOW_ALPHA);
120 MERGE(i_background_color, STYLE_HAS_BACKGROUND_COLOR);
121 MERGE(i_background_alpha, STYLE_HAS_BACKGROUND_ALPHA);
122 MERGE(i_karaoke_background_color, STYLE_HAS_K_BACKGROUND_COLOR);
123 MERGE(i_karaoke_background_alpha, STYLE_HAS_K_BACKGROUND_ALPHA);
124 MERGE(e_wrapinfo, STYLE_HAS_WRAP_INFO);
125 p_dst->i_features |= p_src->i_features;
126 p_dst->i_style_flags |= p_src->i_style_flags;
129 MERGE_SIZE(f_font_relsize);
130 MERGE_SIZE(i_font_size);
131 MERGE_SIZE(i_outline_width);
132 MERGE_SIZE(i_shadow_width);
133 MERGE_SIZE(i_spacing);
136 #undef MERGE
137 #undef MERGE_SIZE
139 text_style_t *text_style_Duplicate( const text_style_t *p_src )
141 if( !p_src )
142 return NULL;
144 text_style_t *p_dst = calloc( 1, sizeof(*p_dst) );
145 if( p_dst )
146 text_style_Copy( p_dst, p_src );
147 return p_dst;
150 void text_style_Delete( text_style_t *p_style )
152 if( p_style )
153 free( p_style->psz_fontname );
154 if( p_style )
155 free( p_style->psz_monofontname );
156 free( p_style );
159 text_segment_t *text_segment_New( const char *psz_text )
161 text_segment_t* segment = calloc( 1, sizeof(*segment) );
162 if( !segment )
163 return NULL;
165 if ( psz_text )
166 segment->psz_text = strdup( psz_text );
168 return segment;
171 text_segment_t *text_segment_NewInheritStyle( const text_style_t* p_style )
173 if ( !p_style )
174 return NULL; //FIXME: Allow this, even if it is an alias to text_segment_New( NULL ) ?
175 text_segment_t* p_segment = text_segment_New( NULL );
176 if ( unlikely( !p_segment ) )
177 return NULL;
178 p_segment->style = text_style_Duplicate( p_style );
179 if ( unlikely( !p_segment->style ) )
181 text_segment_Delete( p_segment );
182 return NULL;
184 return p_segment;
187 void text_segment_Delete( text_segment_t* segment )
189 if ( segment != NULL )
191 free( segment->psz_text );
192 text_style_Delete( segment->style );
193 free( segment );
197 void text_segment_ChainDelete( text_segment_t *segment )
199 while( segment != NULL )
201 text_segment_t *p_next = segment->p_next;
203 text_segment_Delete( segment );
205 segment = p_next;
209 text_segment_t *text_segment_Copy( text_segment_t *p_src )
211 text_segment_t *p_dst = NULL, *p_dst0 = NULL;
213 while( p_src ) {
214 text_segment_t *p_new = text_segment_New( p_src->psz_text );
216 if( unlikely( !p_new ) )
217 break;
219 p_new->style = text_style_Duplicate( p_src->style );
221 if( p_dst == NULL )
223 p_dst = p_dst0 = p_new;
225 else
227 p_dst->p_next = p_new;
228 p_dst = p_dst->p_next;
231 p_src = p_src->p_next;
234 return p_dst0;
237 unsigned int vlc_html_color( const char *psz_value, bool* ok )
239 unsigned int color = 0;
240 char* psz_end;
241 bool b_ret = false;
243 const char *psz_hex = (*psz_value == '#') ? psz_value + 1 : psz_value;
245 if( psz_hex != psz_value ||
246 (*psz_hex >= '0' && *psz_hex <= '9') ||
247 (*psz_hex >= 'A' && *psz_hex <= 'F') )
249 uint32_t i_value = strtol( psz_hex, &psz_end, 16 );
250 if( *psz_end == 0 || isspace( *psz_end ) )
252 switch( psz_end - psz_hex )
254 case 8:
255 color = (i_value << 24) | (i_value >> 8);
256 b_ret = true;
257 break;
258 case 6:
259 color = i_value | 0xFF000000;
260 b_ret = true;
261 break;
262 default:
263 break;
268 if( !b_ret && psz_hex == psz_value &&
269 !strncmp( "rgb", psz_value, 3 ) )
271 unsigned r,g,b,a = 0xFF;
272 if( psz_value[3] == 'a' )
273 b_ret = (sscanf( psz_value, "rgba(%3u,%3u,%3u,%3u)", &r, &g, &b, &a ) == 4);
274 else
275 b_ret = (sscanf( psz_value, "rgb(%3u,%3u,%3u)", &r, &g, &b ) == 3);
276 color = (a << 24) | (r << 16) | (g << 8) | b;
279 if( !b_ret && psz_hex == psz_value )
281 for( int i = 0; p_html_colors[i].psz_name != NULL; i++ )
283 if( !strcasecmp( psz_value, p_html_colors[i].psz_name ) )
285 // Assume opaque color since the table doesn't specify an alpha
286 color = p_html_colors[i].i_value | 0xFF000000;
287 b_ret = true;
288 break;
293 if ( ok != NULL )
294 *ok = b_ret;
296 return color;