mirror of https://github.com/mpv-player/mpv
add new -subfont option, that allows having a different font for OSD (controls and menu) and subtitles
git-svn-id: svn://svn.mplayerhq.hu/mplayer/trunk@23356 b3059339-0415-0410-9bf9-f77b7e298cf2
This commit is contained in:
parent
b0615f0024
commit
194fc1b15b
|
@ -292,6 +292,7 @@
|
||||||
{"sub-no-text-pp", &sub_no_text_pp, CONF_TYPE_FLAG, 0, 0, 1, NULL},
|
{"sub-no-text-pp", &sub_no_text_pp, CONF_TYPE_FLAG, 0, 0, 1, NULL},
|
||||||
{"sub-fuzziness", &sub_match_fuzziness, CONF_TYPE_INT, CONF_RANGE, 0, 2, NULL},
|
{"sub-fuzziness", &sub_match_fuzziness, CONF_TYPE_INT, CONF_RANGE, 0, 2, NULL},
|
||||||
{"font", &font_name, CONF_TYPE_STRING, 0, 0, 0, NULL},
|
{"font", &font_name, CONF_TYPE_STRING, 0, 0, 0, NULL},
|
||||||
|
{"subfont", &sub_font_name, CONF_TYPE_STRING, 0, 0, 0, NULL},
|
||||||
{"ffactor", &font_factor, CONF_TYPE_FLOAT, CONF_RANGE, 0.0, 10.0, NULL},
|
{"ffactor", &font_factor, CONF_TYPE_FLOAT, CONF_RANGE, 0.0, 10.0, NULL},
|
||||||
{"subpos", &sub_pos, CONF_TYPE_INT, CONF_RANGE, 0, 100, NULL},
|
{"subpos", &sub_pos, CONF_TYPE_INT, CONF_RANGE, 0, 100, NULL},
|
||||||
{"subalign", &sub_alignment, CONF_TYPE_INT, CONF_RANGE, 0, 2, NULL},
|
{"subalign", &sub_alignment, CONF_TYPE_INT, CONF_RANGE, 0, 2, NULL},
|
||||||
|
|
|
@ -11,6 +11,7 @@
|
||||||
#include <malloc.h>
|
#include <malloc.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#include "mplayer.h"
|
||||||
#include "mp_msg.h"
|
#include "mp_msg.h"
|
||||||
|
|
||||||
#include "libmpcodecs/img_format.h"
|
#include "libmpcodecs/img_format.h"
|
||||||
|
@ -267,7 +268,7 @@ static int config(struct vf_instance_s* vf, int width, int height, int d_width,
|
||||||
// here is the right place to get screen dimensions
|
// here is the right place to get screen dimensions
|
||||||
if (force_load_font) {
|
if (force_load_font) {
|
||||||
force_load_font = 0;
|
force_load_font = 0;
|
||||||
load_font_ft(width,height);
|
load_font_ft(width,height,&vo_font,font_name);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
if(outfmt == IMGFMT_MPEGPES)
|
if(outfmt == IMGFMT_MPEGPES)
|
||||||
|
|
|
@ -62,6 +62,7 @@ typedef struct {
|
||||||
} font_desc_t;
|
} font_desc_t;
|
||||||
|
|
||||||
extern font_desc_t* vo_font;
|
extern font_desc_t* vo_font;
|
||||||
|
extern font_desc_t* sub_font;
|
||||||
|
|
||||||
#ifdef HAVE_FREETYPE
|
#ifdef HAVE_FREETYPE
|
||||||
|
|
||||||
|
@ -86,7 +87,7 @@ void free_font_desc(font_desc_t *desc);
|
||||||
void render_one_glyph(font_desc_t *desc, int c);
|
void render_one_glyph(font_desc_t *desc, int c);
|
||||||
int kerning(font_desc_t *desc, int prevc, int c);
|
int kerning(font_desc_t *desc, int prevc, int c);
|
||||||
|
|
||||||
void load_font_ft(int width, int height);
|
void load_font_ft(int width, int height, font_desc_t **desc, const char *name);
|
||||||
|
|
||||||
void blur(unsigned char *buffer, unsigned short *tmp2, int width, int height,
|
void blur(unsigned char *buffer, unsigned short *tmp2, int width, int height,
|
||||||
int stride, int *m2, int r, int mwidth);
|
int stride, int *m2, int r, int mwidth);
|
||||||
|
|
|
@ -942,7 +942,7 @@ int kerning(font_desc_t *desc, int prevc, int c)
|
||||||
{
|
{
|
||||||
FT_Vector kern;
|
FT_Vector kern;
|
||||||
|
|
||||||
if (!vo_font->dynamic) return 0;
|
if (!desc->dynamic) return 0;
|
||||||
if (prevc < 0 || c < 0) return 0;
|
if (prevc < 0 || c < 0) return 0;
|
||||||
if (desc->font[prevc] != desc->font[c]) return 0;
|
if (desc->font[prevc] != desc->font[c]) return 0;
|
||||||
if (desc->font[prevc] == -1 || desc->font[c] == -1) return 0;
|
if (desc->font[prevc] == -1 || desc->font[c] == -1) return 0;
|
||||||
|
@ -1137,7 +1137,7 @@ int done_freetype(void)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void load_font_ft(int width, int height)
|
void load_font_ft(int width, int height, font_desc_t** fontp, const char *font_name)
|
||||||
{
|
{
|
||||||
#ifdef HAVE_FONTCONFIG
|
#ifdef HAVE_FONTCONFIG
|
||||||
FcPattern *fc_pattern;
|
FcPattern *fc_pattern;
|
||||||
|
@ -1145,6 +1145,7 @@ void load_font_ft(int width, int height)
|
||||||
FcChar8 *s;
|
FcChar8 *s;
|
||||||
FcBool scalable;
|
FcBool scalable;
|
||||||
#endif
|
#endif
|
||||||
|
font_desc_t *vo_font = *fontp;
|
||||||
vo_image_width = width;
|
vo_image_width = width;
|
||||||
vo_image_height = height;
|
vo_image_height = height;
|
||||||
|
|
||||||
|
@ -1177,10 +1178,10 @@ void load_font_ft(int width, int height)
|
||||||
}
|
}
|
||||||
// s doesn't need to be freed according to fontconfig docs
|
// s doesn't need to be freed according to fontconfig docs
|
||||||
FcPatternGetString(fc_pattern, FC_FILE, 0, &s);
|
FcPatternGetString(fc_pattern, FC_FILE, 0, &s);
|
||||||
vo_font=read_font_desc_ft(s, width, height);
|
*fontp=read_font_desc_ft(s, width, height);
|
||||||
FcPatternDestroy(fc_pattern);
|
FcPatternDestroy(fc_pattern);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
#endif
|
#endif
|
||||||
vo_font=read_font_desc_ft(font_name, width, height);
|
*fontp=read_font_desc_ft(font_name, width, height);
|
||||||
}
|
}
|
||||||
|
|
64
libvo/sub.c
64
libvo/sub.c
|
@ -14,6 +14,7 @@
|
||||||
#define OSD_NAV_BOX_ALPHA 0x7f
|
#define OSD_NAV_BOX_ALPHA 0x7f
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#include "mplayer.h"
|
||||||
#include "mp_msg.h"
|
#include "mp_msg.h"
|
||||||
#include "help_mp.h"
|
#include "help_mp.h"
|
||||||
#include "video_out.h"
|
#include "video_out.h"
|
||||||
|
@ -63,6 +64,7 @@ char * __sub_osd_names_short[] ={ "", "|>", "||", "[]", "<<" , ">>", "", "", "",
|
||||||
|
|
||||||
//static int vo_font_loaded=-1;
|
//static int vo_font_loaded=-1;
|
||||||
font_desc_t* vo_font=NULL;
|
font_desc_t* vo_font=NULL;
|
||||||
|
font_desc_t* sub_font=NULL;
|
||||||
|
|
||||||
unsigned char* vo_osd_text=NULL;
|
unsigned char* vo_osd_text=NULL;
|
||||||
int sub_unicode=0;
|
int sub_unicode=0;
|
||||||
|
@ -392,7 +394,7 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
|
|
||||||
obj->flags|=OSDFLAG_CHANGED|OSDFLAG_VISIBLE;
|
obj->flags|=OSDFLAG_CHANGED|OSDFLAG_VISIBLE;
|
||||||
|
|
||||||
if(!vo_sub || !vo_font || !sub_visibility || (vo_font->font[40]<0)){
|
if(!vo_sub || !sub_font || !sub_visibility || (sub_font->font[40]<0)){
|
||||||
obj->flags&=~OSDFLAG_VISIBLE;
|
obj->flags&=~OSDFLAG_VISIBLE;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -402,7 +404,7 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
|
|
||||||
// too long lines divide into a smaller ones
|
// too long lines divide into a smaller ones
|
||||||
i=k=lasth=0;
|
i=k=lasth=0;
|
||||||
h=vo_font->height;
|
h=sub_font->height;
|
||||||
lastStripPosition=-1;
|
lastStripPosition=-1;
|
||||||
l=vo_sub->lines;
|
l=vo_sub->lines;
|
||||||
|
|
||||||
|
@ -413,7 +415,7 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
int *char_seq, char_position, xlimit = dxs * sub_width_p / 100, counter;
|
int *char_seq, char_position, xlimit = dxs * sub_width_p / 100, counter;
|
||||||
|
|
||||||
while (l) {
|
while (l) {
|
||||||
xsize = -vo_font->charspace;
|
xsize = -sub_font->charspace;
|
||||||
l--;
|
l--;
|
||||||
t=vo_sub->text[i++];
|
t=vo_sub->text[i++];
|
||||||
char_position = 0;
|
char_position = 0;
|
||||||
|
@ -436,7 +438,7 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
mp_msg(MSGT_OSD,MSGL_WARN,"\nMAX_UCS exceeded!\n");
|
mp_msg(MSGT_OSD,MSGL_WARN,"\nMAX_UCS exceeded!\n");
|
||||||
}
|
}
|
||||||
if (!c) c++; // avoid UCS 0
|
if (!c) c++; // avoid UCS 0
|
||||||
render_one_glyph(vo_font, c);
|
render_one_glyph(sub_font, c);
|
||||||
|
|
||||||
if (c == ' ') {
|
if (c == ' ') {
|
||||||
struct osd_text_t *tmp_ott = (struct osd_text_t *) calloc(1, sizeof(struct osd_text_t));
|
struct osd_text_t *tmp_ott = (struct osd_text_t *) calloc(1, sizeof(struct osd_text_t));
|
||||||
|
@ -447,7 +449,7 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
tmp_ott->prev = cp_ott;
|
tmp_ott->prev = cp_ott;
|
||||||
cp_ott->next = tmp_ott;
|
cp_ott->next = tmp_ott;
|
||||||
tmp_ott->osd_kerning =
|
tmp_ott->osd_kerning =
|
||||||
vo_font->charspace + vo_font->width[' '];
|
sub_font->charspace + sub_font->width[' '];
|
||||||
cp_ott = tmp_ott;
|
cp_ott = tmp_ott;
|
||||||
}
|
}
|
||||||
tmp_ott->osd_length = xsize;
|
tmp_ott->osd_length = xsize;
|
||||||
|
@ -459,16 +461,16 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
xsize = 0;
|
xsize = 0;
|
||||||
prevc = c;
|
prevc = c;
|
||||||
} else {
|
} else {
|
||||||
int delta_xsize = vo_font->width[c] + vo_font->charspace + kerning(vo_font, prevc, c);
|
int delta_xsize = sub_font->width[c] + sub_font->charspace + kerning(sub_font, prevc, c);
|
||||||
|
|
||||||
if (xsize + delta_xsize <= dxs) {
|
if (xsize + delta_xsize <= dxs) {
|
||||||
if (!x) x = 1;
|
if (!x) x = 1;
|
||||||
prevc = c;
|
prevc = c;
|
||||||
char_seq[char_position++] = c;
|
char_seq[char_position++] = c;
|
||||||
xsize += delta_xsize;
|
xsize += delta_xsize;
|
||||||
if ((!suboverlap_enabled) && ((font = vo_font->font[c]) >= 0)) {
|
if ((!suboverlap_enabled) && ((font = sub_font->font[c]) >= 0)) {
|
||||||
if (vo_font->pic_a[font]->h > h) {
|
if (sub_font->pic_a[font]->h > h) {
|
||||||
h = vo_font->pic_a[font]->h;
|
h = sub_font->pic_a[font]->h;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
@ -490,7 +492,7 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
tmp_ott->prev = cp_ott;
|
tmp_ott->prev = cp_ott;
|
||||||
cp_ott->next = tmp_ott;
|
cp_ott->next = tmp_ott;
|
||||||
tmp_ott->osd_kerning =
|
tmp_ott->osd_kerning =
|
||||||
vo_font->charspace + vo_font->width[' '];
|
sub_font->charspace + sub_font->width[' '];
|
||||||
cp_ott = tmp_ott;
|
cp_ott = tmp_ott;
|
||||||
}
|
}
|
||||||
tmp_ott->osd_length = xsize;
|
tmp_ott->osd_length = xsize;
|
||||||
|
@ -499,7 +501,7 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
for (counter = 0; counter < char_position; ++counter)
|
for (counter = 0; counter < char_position; ++counter)
|
||||||
tmp_ott->text[counter] = char_seq[counter];
|
tmp_ott->text[counter] = char_seq[counter];
|
||||||
char_position = 0;
|
char_position = 0;
|
||||||
xsize = -vo_font->charspace;
|
xsize = -sub_font->charspace;
|
||||||
}
|
}
|
||||||
free(char_seq);
|
free(char_seq);
|
||||||
|
|
||||||
|
@ -522,7 +524,7 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
tmp->prev = tmp_otp;
|
tmp->prev = tmp_otp;
|
||||||
tmp_otp = tmp;
|
tmp_otp = tmp;
|
||||||
tmp_otp->ott = tmp_ott;
|
tmp_otp->ott = tmp_ott;
|
||||||
value = -2 * vo_font->charspace - vo_font->width[' '];
|
value = -2 * sub_font->charspace - sub_font->width[' '];
|
||||||
} else {
|
} else {
|
||||||
tmp_otp->value = value;
|
tmp_otp->value = value;
|
||||||
exit = 1;
|
exit = 1;
|
||||||
|
@ -623,7 +625,7 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
break;
|
break;
|
||||||
|
|
||||||
if (h > obj->y) { // out of the screen so end parsing
|
if (h > obj->y) { // out of the screen so end parsing
|
||||||
obj->y -= lasth - vo_font->height; // correct the y position
|
obj->y -= lasth - sub_font->height; // correct the y position
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
xsize = tmp_otp->value;
|
xsize = tmp_otp->value;
|
||||||
|
@ -640,17 +642,17 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
c = tmp_ott->text[counter];
|
c = tmp_ott->text[counter];
|
||||||
render_one_glyph(vo_font, c);
|
render_one_glyph(sub_font, c);
|
||||||
obj->params.subtitle.utbl[utblc++] = c;
|
obj->params.subtitle.utbl[utblc++] = c;
|
||||||
k++;
|
k++;
|
||||||
}
|
}
|
||||||
obj->params.subtitle.utbl[utblc++] = ' ';
|
obj->params.subtitle.utbl[utblc++] = ' ';
|
||||||
}
|
}
|
||||||
obj->params.subtitle.utbl[utblc - 1] = 0;
|
obj->params.subtitle.utbl[utblc - 1] = 0;
|
||||||
obj->y -= vo_font->height;
|
obj->y -= sub_font->height;
|
||||||
}
|
}
|
||||||
if(obj->params.subtitle.lines)
|
if(obj->params.subtitle.lines)
|
||||||
obj->y = dys - ((obj->params.subtitle.lines - 1) * vo_font->height + vo_font->pic_a[vo_font->font[40]]->h);
|
obj->y = dys - ((obj->params.subtitle.lines - 1) * sub_font->height + sub_font->pic_a[sub_font->font[40]]->h);
|
||||||
|
|
||||||
// free memory
|
// free memory
|
||||||
if (otp_sub != NULL) {
|
if (otp_sub != NULL) {
|
||||||
|
@ -689,7 +691,7 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
obj->bbox.x1=xmin;
|
obj->bbox.x1=xmin;
|
||||||
obj->bbox.x2=xmax;
|
obj->bbox.x2=xmax;
|
||||||
obj->bbox.y1=obj->y;
|
obj->bbox.y1=obj->y;
|
||||||
// obj->bbox.y2=obj->y+obj->params.subtitle.lines*vo_font->height;
|
// obj->bbox.y2=obj->y+obj->params.subtitle.lines*sub_font->height;
|
||||||
obj->flags|=OSDFLAG_BBOX;
|
obj->flags|=OSDFLAG_BBOX;
|
||||||
|
|
||||||
alloc_buf(obj);
|
alloc_buf(obj);
|
||||||
|
@ -735,18 +737,18 @@ inline static void vo_update_text_sub(mp_osd_obj_t* obj,int dxs,int dys){
|
||||||
}
|
}
|
||||||
prevc = -1;
|
prevc = -1;
|
||||||
while ((c=obj->params.subtitle.utbl[j++])){
|
while ((c=obj->params.subtitle.utbl[j++])){
|
||||||
x += kerning(vo_font,prevc,c);
|
x += kerning(sub_font,prevc,c);
|
||||||
if ((font=vo_font->font[c])>=0)
|
if ((font=sub_font->font[c])>=0)
|
||||||
draw_alpha_buf(obj,x,y,
|
draw_alpha_buf(obj,x,y,
|
||||||
vo_font->width[c],
|
sub_font->width[c],
|
||||||
vo_font->pic_a[font]->h+y<obj->dys ? vo_font->pic_a[font]->h : obj->dys-y,
|
sub_font->pic_a[font]->h+y<obj->dys ? sub_font->pic_a[font]->h : obj->dys-y,
|
||||||
vo_font->pic_b[font]->bmp+vo_font->start[c],
|
sub_font->pic_b[font]->bmp+sub_font->start[c],
|
||||||
vo_font->pic_a[font]->bmp+vo_font->start[c],
|
sub_font->pic_a[font]->bmp+sub_font->start[c],
|
||||||
vo_font->pic_a[font]->w);
|
sub_font->pic_a[font]->w);
|
||||||
x+=vo_font->width[c]+vo_font->charspace;
|
x+=sub_font->width[c]+sub_font->charspace;
|
||||||
prevc = c;
|
prevc = c;
|
||||||
}
|
}
|
||||||
y+=vo_font->height;
|
y+=sub_font->height;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -829,12 +831,18 @@ int vo_update_osd(int dxs,int dys){
|
||||||
if (defer_counter >= FONT_LOAD_DEFER) force_load_font = 1;
|
if (defer_counter >= FONT_LOAD_DEFER) force_load_font = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!vo_font || force_load_font) {
|
if (force_load_font) {
|
||||||
force_load_font = 0;
|
force_load_font = 0;
|
||||||
load_font_ft(dxs, dys);
|
load_font_ft(dxs, dys, &vo_font, font_name);
|
||||||
|
load_font_ft(dxs, dys, &sub_font, sub_font_name);
|
||||||
prev_dxs = dxs;
|
prev_dxs = dxs;
|
||||||
prev_dys = dys;
|
prev_dys = dys;
|
||||||
defer_counter = 0;
|
defer_counter = 0;
|
||||||
|
} else {
|
||||||
|
if (!vo_font)
|
||||||
|
load_font_ft(dxs, dys, &vo_font, font_name);
|
||||||
|
if (!sub_font)
|
||||||
|
load_font_ft(dxs, dys, &sub_font, sub_font_name);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
|
@ -186,6 +186,7 @@ static int play_n_frames_mf=-1;
|
||||||
|
|
||||||
// sub:
|
// sub:
|
||||||
char *font_name=NULL;
|
char *font_name=NULL;
|
||||||
|
char *sub_font_name=NULL;
|
||||||
#ifdef HAVE_FONTCONFIG
|
#ifdef HAVE_FONTCONFIG
|
||||||
extern int font_fontconfig;
|
extern int font_fontconfig;
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -322,6 +322,7 @@ extern int vo_flags;
|
||||||
|
|
||||||
// sub:
|
// sub:
|
||||||
char *font_name=NULL;
|
char *font_name=NULL;
|
||||||
|
char *sub_font_name=NULL;
|
||||||
#ifdef HAVE_FONTCONFIG
|
#ifdef HAVE_FONTCONFIG
|
||||||
extern int font_fontconfig;
|
extern int font_fontconfig;
|
||||||
#endif
|
#endif
|
||||||
|
@ -2533,6 +2534,10 @@ if(!codecs_file || !parse_codec_cfg(codecs_file)){
|
||||||
if(!vo_font)
|
if(!vo_font)
|
||||||
vo_font=read_font_desc(MPLAYER_DATADIR "/font/font.desc",font_factor,verbose>1);
|
vo_font=read_font_desc(MPLAYER_DATADIR "/font/font.desc",font_factor,verbose>1);
|
||||||
}
|
}
|
||||||
|
if (sub_font_name)
|
||||||
|
sub_font = read_font_desc(sub_font_name, font_factor, verbose>1);
|
||||||
|
else
|
||||||
|
sub_font = vo_font;
|
||||||
#endif
|
#endif
|
||||||
#ifdef HAVE_FONTCONFIG
|
#ifdef HAVE_FONTCONFIG
|
||||||
}
|
}
|
||||||
|
|
|
@ -19,6 +19,7 @@ extern int osd_level;
|
||||||
extern unsigned int osd_visible;
|
extern unsigned int osd_visible;
|
||||||
|
|
||||||
extern char * font_name;
|
extern char * font_name;
|
||||||
|
extern char * sub_font_name;
|
||||||
extern float font_factor;
|
extern float font_factor;
|
||||||
extern float movie_aspect;
|
extern float movie_aspect;
|
||||||
extern float force_fps;
|
extern float force_fps;
|
||||||
|
|
Loading…
Reference in New Issue