mirror of
https://github.com/mpv-player/mpv
synced 2025-01-01 04:36:24 +01:00
Libass interface reworked:
- ass_instance_t renamed to ass_renderer_t - ass_library_t introduced - use of mplayer-specific global variables limited to ass_mp.c git-svn-id: svn://svn.mplayerhq.hu/mplayer/trunk@20493 b3059339-0415-0410-9bf9-f77b7e298cf2
This commit is contained in:
parent
a383ad29ea
commit
efea99c2c9
@ -5,7 +5,7 @@ LIBNAME=libass.a
|
||||
|
||||
LIBS=$(LIBNAME)
|
||||
|
||||
SRCS=ass.c ass_cache.c ass_fontconfig.c ass_render.c ass_utils.c ass_mp.c ass_bitmap.c
|
||||
SRCS=ass.c ass_cache.c ass_fontconfig.c ass_render.c ass_utils.c ass_mp.c ass_bitmap.c ass_library.c
|
||||
|
||||
OBJS=$(SRCS:.c=.o)
|
||||
|
||||
|
53
libass/ass.c
53
libass/ass.c
@ -36,18 +36,14 @@
|
||||
|
||||
#ifdef USE_ICONV
|
||||
#include <iconv.h>
|
||||
extern char *sub_cp;
|
||||
#endif
|
||||
extern int extract_embedded_fonts;
|
||||
extern char** ass_force_style_list;
|
||||
|
||||
#include "mp_msg.h"
|
||||
#include "ass.h"
|
||||
#include "ass_utils.h"
|
||||
#include "ass_library.h"
|
||||
#include "libvo/sub.h" // for utf8_get_char
|
||||
|
||||
char *get_path(char *);
|
||||
|
||||
typedef enum {PST_UNKNOWN = 0, PST_INFO, PST_STYLES, PST_EVENTS, PST_FONTS} parser_state_t;
|
||||
|
||||
struct parser_priv_s {
|
||||
@ -327,10 +323,11 @@ void process_force_style(ass_track_t* track) {
|
||||
char **fs, *eq, *dt, *style, *tname, *token;
|
||||
ass_style_t* target;
|
||||
int sid;
|
||||
char** list = track->library->style_overrides;
|
||||
|
||||
if (!ass_force_style_list) return;
|
||||
if (!list) return;
|
||||
|
||||
for (fs = ass_force_style_list; *fs; ++fs) {
|
||||
for (fs = list; *fs; ++fs) {
|
||||
eq = strchr(*fs, '=');
|
||||
if (!eq)
|
||||
continue;
|
||||
@ -577,8 +574,8 @@ static int decode_font(ass_track_t* track)
|
||||
dsize = q - buf;
|
||||
assert(dsize <= size / 4 * 3 + 2);
|
||||
|
||||
if (extract_embedded_fonts)
|
||||
ass_process_font(track->parser_priv->fontname, (char*)buf, dsize);
|
||||
if (track->library->extract_fonts)
|
||||
ass_process_font(track->library, track->parser_priv->fontname, (char*)buf, dsize);
|
||||
|
||||
error_decode_font:
|
||||
if (buf) free(buf);
|
||||
@ -795,24 +792,24 @@ void ass_process_chunk(ass_track_t* track, char *data, int size, long long timec
|
||||
|
||||
#ifdef USE_ICONV
|
||||
/** \brief recode buffer to utf-8
|
||||
* constraint: sub_cp != 0
|
||||
* constraint: codepage != 0
|
||||
* \param data pointer to text buffer
|
||||
* \param size buffer size
|
||||
* \return a pointer to recoded buffer, caller is responsible for freeing it
|
||||
**/
|
||||
static char* sub_recode(char* data, size_t size)
|
||||
static char* sub_recode(char* data, size_t size, char* codepage)
|
||||
{
|
||||
static iconv_t icdsc = (iconv_t)(-1);
|
||||
char* tocp = "UTF-8";
|
||||
char* outbuf;
|
||||
assert(sub_cp);
|
||||
assert(codepage);
|
||||
|
||||
{
|
||||
char* cp_tmp = sub_cp;
|
||||
char* cp_tmp = codepage;
|
||||
#ifdef HAVE_ENCA
|
||||
char enca_lang[3], enca_fallback[100];
|
||||
if (sscanf(sub_cp, "enca:%2s:%99s", enca_lang, enca_fallback) == 2
|
||||
|| sscanf(sub_cp, "ENCA:%2s:%99s", enca_lang, enca_fallback) == 2) {
|
||||
if (sscanf(codepage, "enca:%2s:%99s", enca_lang, enca_fallback) == 2
|
||||
|| sscanf(codepage, "ENCA:%2s:%99s", enca_lang, enca_fallback) == 2) {
|
||||
cp_tmp = guess_buffer_cp((unsigned char*)data, size, enca_lang, enca_fallback);
|
||||
}
|
||||
#endif
|
||||
@ -868,7 +865,7 @@ static char* sub_recode(char* data, size_t size)
|
||||
/**
|
||||
* \brief read file contents into newly allocated buffer, recoding to utf-8
|
||||
*/
|
||||
static char* read_file(char* fname)
|
||||
static char* read_file(char* fname, char* codepage)
|
||||
{
|
||||
int res;
|
||||
long sz;
|
||||
@ -915,8 +912,8 @@ static char* read_file(char* fname)
|
||||
fclose(fp);
|
||||
|
||||
#ifdef USE_ICONV
|
||||
if (sub_cp) {
|
||||
char* tmpbuf = sub_recode(buf, sz);
|
||||
if (codepage) {
|
||||
char* tmpbuf = sub_recode(buf, sz, codepage);
|
||||
free(buf);
|
||||
buf = tmpbuf;
|
||||
}
|
||||
@ -929,17 +926,17 @@ static char* read_file(char* fname)
|
||||
* \param fname file name
|
||||
* \return newly allocated track
|
||||
*/
|
||||
ass_track_t* ass_read_file(char* fname)
|
||||
ass_track_t* ass_read_file(ass_library_t* library, char* fname, char* codepage)
|
||||
{
|
||||
char* buf;
|
||||
ass_track_t* track;
|
||||
int i;
|
||||
|
||||
buf = read_file(fname);
|
||||
buf = read_file(fname, codepage);
|
||||
if (!buf)
|
||||
return 0;
|
||||
|
||||
track = ass_new_track();
|
||||
track = ass_new_track(library);
|
||||
track->name = strdup(fname);
|
||||
|
||||
// process header
|
||||
@ -971,12 +968,12 @@ ass_track_t* ass_read_file(char* fname)
|
||||
/**
|
||||
* \brief read styles from file into already initialized track
|
||||
*/
|
||||
int ass_read_styles(ass_track_t* track, char* fname)
|
||||
int ass_read_styles(ass_track_t* track, char* fname, char* codepage)
|
||||
{
|
||||
char* buf;
|
||||
parser_state_t old_state;
|
||||
|
||||
buf = read_file(fname);
|
||||
buf = read_file(fname, codepage);
|
||||
if (!buf)
|
||||
return 1;
|
||||
|
||||
@ -1030,15 +1027,17 @@ static char* validate_fname(char* name)
|
||||
* \param data binary font data
|
||||
* \param data_size data size
|
||||
*/
|
||||
void ass_process_font(const char* name, char* data, int data_size)
|
||||
void ass_process_font(ass_library_t* library, const char* name, char* data, int data_size)
|
||||
{
|
||||
char buf[1000];
|
||||
FILE* fp = 0;
|
||||
int rc;
|
||||
struct stat st;
|
||||
char* fname;
|
||||
const char* fonts_dir = library->fonts_dir;
|
||||
|
||||
char* fonts_dir = get_path("fonts");
|
||||
if (!fonts_dir)
|
||||
return;
|
||||
rc = stat(fonts_dir, &st);
|
||||
if (rc) {
|
||||
int res;
|
||||
@ -1058,7 +1057,6 @@ void ass_process_font(const char* name, char* data, int data_size)
|
||||
|
||||
snprintf(buf, 1000, "%s/%s", fonts_dir, fname);
|
||||
free(fname);
|
||||
free(fonts_dir);
|
||||
|
||||
fp = fopen(buf, "wb");
|
||||
if (!fp) return;
|
||||
@ -1086,8 +1084,9 @@ long long ass_step_sub(ass_track_t* track, long long now, int movement) {
|
||||
return ((long long)track->events[i].Start) - now;
|
||||
}
|
||||
|
||||
ass_track_t* ass_new_track(void) {
|
||||
ass_track_t* ass_new_track(ass_library_t* library) {
|
||||
ass_track_t* track = calloc(1, sizeof(ass_track_t));
|
||||
track->library = library;
|
||||
track->parser_priv = calloc(1, sizeof(parser_priv_t));
|
||||
return track;
|
||||
}
|
||||
|
59
libass/ass.h
59
libass/ass.h
@ -23,8 +23,8 @@
|
||||
|
||||
#include "ass_types.h"
|
||||
|
||||
/// Libass "library object". Contents are private.
|
||||
typedef struct ass_instance_s ass_instance_t;
|
||||
/// Libass renderer object. Contents are private.
|
||||
typedef struct ass_renderer_s ass_renderer_t;
|
||||
|
||||
/// a linked list of images produced by ass renderer
|
||||
typedef struct ass_image_s {
|
||||
@ -41,20 +41,47 @@ typedef struct ass_image_s {
|
||||
* \brief initialize the library
|
||||
* \return library handle or NULL if failed
|
||||
*/
|
||||
ass_instance_t* ass_init(void);
|
||||
ass_library_t* ass_library_init(void);
|
||||
|
||||
/**
|
||||
* \brief finalize the library
|
||||
* \param priv library handle
|
||||
*/
|
||||
void ass_done(ass_instance_t* priv);
|
||||
void ass_library_done(ass_library_t*);
|
||||
|
||||
void ass_set_frame_size(ass_instance_t* priv, int w, int h);
|
||||
void ass_set_margins(ass_instance_t* priv, int t, int b, int l, int r);
|
||||
void ass_set_use_margins(ass_instance_t* priv, int use);
|
||||
void ass_set_aspect_ratio(ass_instance_t* priv, double ar);
|
||||
void ass_set_font_scale(ass_instance_t* priv, double font_scale);
|
||||
int ass_set_fonts(ass_instance_t* priv, const char* fonts_dir, const char* default_font, const char* default_family);
|
||||
/**
|
||||
* \brief set private font directory
|
||||
* It is used for saving embedded fonts and also in font lookup.
|
||||
*/
|
||||
void ass_set_fonts_dir(ass_library_t* priv, const char* fonts_dir);
|
||||
|
||||
void ass_set_extract_fonts(ass_library_t* priv, int extract);
|
||||
|
||||
void ass_set_style_overrides(ass_library_t* priv, char** list);
|
||||
|
||||
/**
|
||||
* \brief initialize the renderer
|
||||
* \param priv library handle
|
||||
* \return renderer handle or NULL if failed
|
||||
*/
|
||||
ass_renderer_t* ass_renderer_init(ass_library_t*);
|
||||
|
||||
/**
|
||||
* \brief finalize the renderer
|
||||
* \param priv renderer handle
|
||||
*/
|
||||
void ass_renderer_done(ass_renderer_t* priv);
|
||||
|
||||
void ass_set_frame_size(ass_renderer_t* priv, int w, int h);
|
||||
void ass_set_margins(ass_renderer_t* priv, int t, int b, int l, int r);
|
||||
void ass_set_use_margins(ass_renderer_t* priv, int use);
|
||||
void ass_set_aspect_ratio(ass_renderer_t* priv, double ar);
|
||||
void ass_set_font_scale(ass_renderer_t* priv, double font_scale);
|
||||
|
||||
/**
|
||||
* \brief set font lookup defaults
|
||||
*/
|
||||
int ass_set_fonts(ass_renderer_t* priv, const char* default_font, const char* default_family);
|
||||
|
||||
/**
|
||||
* \brief render a frame, producing a list of ass_image_t
|
||||
@ -62,16 +89,16 @@ int ass_set_fonts(ass_instance_t* priv, const char* fonts_dir, const char* defa
|
||||
* \param track subtitle track
|
||||
* \param now video timestamp in milliseconds
|
||||
*/
|
||||
ass_image_t* ass_render_frame(ass_instance_t *priv, ass_track_t* track, long long now);
|
||||
ass_image_t* ass_render_frame(ass_renderer_t *priv, ass_track_t* track, long long now);
|
||||
|
||||
|
||||
// The following functions operate on track objects and do not need an ass_instance //
|
||||
// The following functions operate on track objects and do not need an ass_renderer //
|
||||
|
||||
/**
|
||||
* \brief allocate a new empty track object
|
||||
* \return pointer to empty track
|
||||
*/
|
||||
ass_track_t* ass_new_track(void);
|
||||
ass_track_t* ass_new_track(ass_library_t*);
|
||||
|
||||
/**
|
||||
* \brief deallocate track and all its child objects (styles and events)
|
||||
@ -132,13 +159,13 @@ void ass_process_chunk(ass_track_t* track, char *data, int size, long long timec
|
||||
* \param fname file name
|
||||
* \return newly allocated track
|
||||
*/
|
||||
ass_track_t* ass_read_file(char* fname);
|
||||
ass_track_t* ass_read_file(ass_library_t* library, char* fname, char* codepage);
|
||||
|
||||
/**
|
||||
* \brief read styles from file into already initialized track
|
||||
* \return 0 on success
|
||||
*/
|
||||
int ass_read_styles(ass_track_t* track, char* fname);
|
||||
int ass_read_styles(ass_track_t* track, char* fname, char* codepage);
|
||||
|
||||
/**
|
||||
* \brief Process embedded matroska font. Saves it to ~/.mplayer/fonts.
|
||||
@ -146,7 +173,7 @@ int ass_read_styles(ass_track_t* track, char* fname);
|
||||
* \param data binary font data
|
||||
* \param data_size data size
|
||||
*/
|
||||
void ass_process_font(const char* name, char* data, int data_size);
|
||||
void ass_process_font(ass_library_t* library, const char* name, char* data, int data_size);
|
||||
|
||||
/**
|
||||
* \brief Calculates timeshift from now to the start of some other subtitle event, depending on movement parameter
|
||||
|
72
libass/ass_library.c
Normal file
72
libass/ass_library.c
Normal file
@ -0,0 +1,72 @@
|
||||
// -*- c-basic-offset: 8; indent-tabs-mode: t -*-
|
||||
// vim:ts=8:sw=8:noet:ai:
|
||||
/*
|
||||
Copyright (C) 2006 Evgeniy Stepanov <eugeni.stepanov@gmail.com>
|
||||
|
||||
This program 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.
|
||||
|
||||
This program 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 St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <inttypes.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "ass.h"
|
||||
#include "ass_library.h"
|
||||
|
||||
|
||||
ass_library_t* ass_library_init(void)
|
||||
{
|
||||
return calloc(1, sizeof(ass_library_t));
|
||||
}
|
||||
|
||||
void ass_library_done(ass_library_t* priv)
|
||||
{
|
||||
if (priv) free(priv);
|
||||
}
|
||||
|
||||
void ass_set_fonts_dir(ass_library_t* priv, const char* fonts_dir)
|
||||
{
|
||||
if (priv->fonts_dir)
|
||||
free(priv->fonts_dir);
|
||||
|
||||
priv->fonts_dir = fonts_dir ? strdup(fonts_dir) : 0;
|
||||
}
|
||||
|
||||
void ass_set_extract_fonts(ass_library_t* priv, int extract)
|
||||
{
|
||||
priv->extract_fonts = !!extract;
|
||||
}
|
||||
|
||||
void ass_set_style_overrides(ass_library_t* priv, char** list)
|
||||
{
|
||||
char** p;
|
||||
char** q;
|
||||
int cnt;
|
||||
|
||||
if (priv->style_overrides) {
|
||||
for (p = priv->style_overrides; *p; ++p)
|
||||
free(*p);
|
||||
free(priv->style_overrides);
|
||||
}
|
||||
|
||||
if (!list) return;
|
||||
|
||||
for (p = list, cnt = 0; *p; ++p, ++cnt) {}
|
||||
|
||||
priv->style_overrides = malloc(cnt * sizeof(char*));
|
||||
for (p = list, q = priv->style_overrides; *p; ++p, ++q)
|
||||
*q = strdup(*p);
|
||||
}
|
31
libass/ass_library.h
Normal file
31
libass/ass_library.h
Normal file
@ -0,0 +1,31 @@
|
||||
// -*- c-basic-offset: 8; indent-tabs-mode: t -*-
|
||||
// vim:ts=8:sw=8:noet:ai:
|
||||
/*
|
||||
Copyright (C) 2006 Evgeniy Stepanov <eugeni.stepanov@gmail.com>
|
||||
|
||||
This program 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.
|
||||
|
||||
This program 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 St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef __ASS_LIBRARY_H__
|
||||
#define __ASS_LIBRARY_H__
|
||||
|
||||
struct ass_library_s {
|
||||
char* fonts_dir;
|
||||
int extract_fonts;
|
||||
char** style_overrides;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -27,8 +27,10 @@
|
||||
#include "ass.h"
|
||||
#include "ass_utils.h"
|
||||
#include "ass_mp.h"
|
||||
#include "ass_library.h"
|
||||
|
||||
// libass-related command line options
|
||||
ass_library_t* ass_library;
|
||||
int ass_enabled = 0;
|
||||
float ass_font_scale = 1.;
|
||||
float ass_line_spacing = 0.;
|
||||
@ -50,11 +52,17 @@ extern char* font_name;
|
||||
extern float text_font_scale_factor;
|
||||
extern int subtitle_autoscale;
|
||||
|
||||
#ifdef USE_ICONV
|
||||
extern char* sub_cp;
|
||||
#else
|
||||
static char* sub_cp = 0;
|
||||
#endif
|
||||
|
||||
extern double ass_internal_font_size_coeff;
|
||||
extern void process_force_style(ass_track_t* track);
|
||||
|
||||
ass_track_t* ass_default_track() {
|
||||
ass_track_t* track = ass_new_track();
|
||||
ass_track_t* ass_default_track(ass_library_t* library) {
|
||||
ass_track_t* track = ass_new_track(library);
|
||||
|
||||
track->track_type = TRACK_TYPE_ASS;
|
||||
track->Timer = 100.;
|
||||
@ -63,7 +71,7 @@ ass_track_t* ass_default_track() {
|
||||
track->WrapStyle = 0;
|
||||
|
||||
if (ass_styles_file)
|
||||
ass_read_styles(track, ass_styles_file);
|
||||
ass_read_styles(track, ass_styles_file, sub_cp);
|
||||
|
||||
if (track->n_styles == 0) {
|
||||
ass_style_t* style;
|
||||
@ -182,11 +190,11 @@ int ass_process_subtitle(ass_track_t* track, subtitle* sub)
|
||||
* \param fps video framerate
|
||||
* \return newly allocated ass_track, filled with subtitles from subdata
|
||||
*/
|
||||
ass_track_t* ass_read_subdata(sub_data* subdata, double fps) {
|
||||
ass_track_t* ass_read_subdata(ass_library_t* library, sub_data* subdata, double fps) {
|
||||
ass_track_t* track;
|
||||
int i;
|
||||
|
||||
track = ass_default_track();
|
||||
track = ass_default_track(library);
|
||||
track->name = subdata->filename ? strdup(subdata->filename) : 0;
|
||||
|
||||
for (i = 0; i < subdata->sub_num; ++i) {
|
||||
@ -203,9 +211,7 @@ ass_track_t* ass_read_subdata(sub_data* subdata, double fps) {
|
||||
|
||||
char *get_path(char *);
|
||||
|
||||
extern char *font_name;
|
||||
|
||||
void ass_configure(ass_instance_t* priv, int w, int h) {
|
||||
void ass_configure(ass_renderer_t* priv, int w, int h) {
|
||||
char *dir, *path, *family;
|
||||
ass_set_frame_size(priv, w, h);
|
||||
ass_set_margins(priv, ass_top_margin, ass_bottom_margin, 0, 0);
|
||||
@ -218,7 +224,7 @@ void ass_configure(ass_instance_t* priv, int w, int h) {
|
||||
if (font_fontconfig && font_name) family = strdup(font_name);
|
||||
else family = 0;
|
||||
|
||||
ass_set_fonts(priv, dir, path, family);
|
||||
ass_set_fonts(priv, path, family);
|
||||
|
||||
free(dir);
|
||||
free(path);
|
||||
|
@ -23,6 +23,7 @@
|
||||
|
||||
#include "subreader.h"
|
||||
|
||||
extern ass_library_t* ass_library;
|
||||
extern int ass_enabled;
|
||||
extern float ass_font_scale;
|
||||
extern float ass_line_spacing;
|
||||
@ -35,11 +36,11 @@ extern char* ass_color;
|
||||
extern char* ass_border_color;
|
||||
extern char* ass_styles_file;
|
||||
|
||||
ass_track_t* ass_default_track();
|
||||
ass_track_t* ass_default_track(ass_library_t* library);
|
||||
int ass_process_subtitle(ass_track_t* track, subtitle* sub);
|
||||
ass_track_t* ass_read_subdata(sub_data* subdata, double fps);
|
||||
ass_track_t* ass_read_subdata(ass_library_t* library, sub_data* subdata, double fps);
|
||||
|
||||
void ass_configure(ass_instance_t* priv, int w, int h);
|
||||
void ass_configure(ass_renderer_t* priv, int w, int h);
|
||||
|
||||
#endif
|
||||
|
||||
|
@ -36,6 +36,7 @@
|
||||
#include "ass_cache.h"
|
||||
#include "ass_utils.h"
|
||||
#include "ass_fontconfig.h"
|
||||
#include "ass_library.h"
|
||||
|
||||
#include "libvo/sub.h" // for utf8_get_char
|
||||
|
||||
@ -56,13 +57,14 @@ typedef struct ass_settings_s {
|
||||
int use_margins; // 0 - place all subtitles inside original frame
|
||||
// 1 - use margins for placing toptitles and subtitles
|
||||
double aspect; // frame aspect ratio, d_width / d_height.
|
||||
char* fonts_dir;
|
||||
|
||||
char* default_font;
|
||||
char* default_family;
|
||||
} ass_settings_t;
|
||||
|
||||
struct ass_instance_s {
|
||||
FT_Library library;
|
||||
struct ass_renderer_s {
|
||||
ass_library_t* library;
|
||||
FT_Library ftlibrary;
|
||||
fc_instance_t* fontconfig_priv;
|
||||
ass_settings_t settings;
|
||||
int render_id;
|
||||
@ -166,7 +168,7 @@ typedef struct render_context_s {
|
||||
|
||||
// frame-global data
|
||||
typedef struct frame_context_s {
|
||||
ass_instance_t* ass_priv;
|
||||
ass_renderer_t* ass_priv;
|
||||
int width, height; // screen dimensions
|
||||
int orig_height; // frame height ( = screen height - margins )
|
||||
int orig_width; // frame width ( = screen width - margins )
|
||||
@ -177,7 +179,7 @@ typedef struct frame_context_s {
|
||||
double border_scale;
|
||||
} frame_context_t;
|
||||
|
||||
static ass_instance_t* ass_instance;
|
||||
static ass_renderer_t* ass_renderer;
|
||||
static ass_settings_t* global_settings;
|
||||
static text_info_t text_info;
|
||||
static render_context_t render_context;
|
||||
@ -219,11 +221,11 @@ static void ass_lazy_track_init(void)
|
||||
}
|
||||
}
|
||||
|
||||
ass_instance_t* ass_init(void)
|
||||
ass_renderer_t* ass_renderer_init(ass_library_t* library)
|
||||
{
|
||||
int error;
|
||||
FT_Library ft;
|
||||
ass_instance_t* priv = 0;
|
||||
ass_renderer_t* priv = 0;
|
||||
|
||||
memset(&render_context, 0, sizeof(render_context));
|
||||
memset(&frame_context, 0, sizeof(frame_context));
|
||||
@ -235,7 +237,7 @@ ass_instance_t* ass_init(void)
|
||||
goto ass_init_exit;
|
||||
}
|
||||
|
||||
priv = calloc(1, sizeof(ass_instance_t));
|
||||
priv = calloc(1, sizeof(ass_renderer_t));
|
||||
if (!priv) {
|
||||
FT_Done_FreeType(ft);
|
||||
goto ass_init_exit;
|
||||
@ -243,7 +245,8 @@ ass_instance_t* ass_init(void)
|
||||
|
||||
priv->synth_priv = ass_synth_init();
|
||||
|
||||
priv->library = ft;
|
||||
priv->library = library;
|
||||
priv->ftlibrary = ft;
|
||||
// images_root and related stuff is zero-filled in calloc
|
||||
|
||||
ass_face_cache_init();
|
||||
@ -258,7 +261,7 @@ ass_init_exit:
|
||||
return priv;
|
||||
}
|
||||
|
||||
void ass_done(ass_instance_t* priv)
|
||||
void ass_renderer_done(ass_renderer_t* priv)
|
||||
{
|
||||
ass_face_cache_done();
|
||||
ass_glyph_cache_done();
|
||||
@ -266,7 +269,7 @@ void ass_done(ass_instance_t* priv)
|
||||
FT_Stroker_Done(render_context.stroker);
|
||||
render_context.stroker = 0;
|
||||
}
|
||||
if (priv && priv->library) FT_Done_FreeType(priv->library);
|
||||
if (priv && priv->ftlibrary) FT_Done_FreeType(priv->ftlibrary);
|
||||
if (priv && priv->fontconfig_priv) fontconfig_done(priv->fontconfig_priv);
|
||||
if (priv && priv->synth_priv) ass_synth_done(priv->synth_priv);
|
||||
if (priv) free(priv);
|
||||
@ -388,7 +391,7 @@ static ass_image_t* render_text(text_info_t* text_info, int dst_x, int dst_y)
|
||||
if (text_info->glyphs[i].glyph) {
|
||||
if ((text_info->glyphs[i].symbol == '\n') || (text_info->glyphs[i].symbol == 0))
|
||||
continue;
|
||||
error = glyph_to_bitmap(ass_instance->synth_priv,
|
||||
error = glyph_to_bitmap(ass_renderer->synth_priv,
|
||||
text_info->glyphs[i].glyph, text_info->glyphs[i].outline_glyph,
|
||||
&text_info->glyphs[i].bm, &text_info->glyphs[i].bm_o,
|
||||
&text_info->glyphs[i].bm_s, text_info->glyphs[i].be);
|
||||
@ -566,7 +569,7 @@ static void update_font(void)
|
||||
{
|
||||
int error;
|
||||
unsigned val;
|
||||
ass_instance_t* priv = frame_context.ass_priv;
|
||||
ass_renderer_t* priv = frame_context.ass_priv;
|
||||
face_desc_t desc;
|
||||
desc.family = strdup(render_context.family);
|
||||
|
||||
@ -581,7 +584,7 @@ static void update_font(void)
|
||||
else if (val == 1) val = 110; //italic
|
||||
desc.italic = val;
|
||||
|
||||
error = ass_new_face(priv->library, priv->fontconfig_priv, &desc, &(render_context.face));
|
||||
error = ass_new_face(priv->ftlibrary, priv->fontconfig_priv, &desc, &(render_context.face));
|
||||
if (error) {
|
||||
render_context.face = 0;
|
||||
}
|
||||
@ -615,7 +618,7 @@ static void change_border(double border)
|
||||
if (!render_context.stroker) {
|
||||
int error;
|
||||
#if (FREETYPE_MAJOR > 2) || ((FREETYPE_MAJOR == 2) && (FREETYPE_MINOR > 1))
|
||||
error = FT_Stroker_New( ass_instance->library, &render_context.stroker );
|
||||
error = FT_Stroker_New( ass_renderer->ftlibrary, &render_context.stroker );
|
||||
#else // < 2.2
|
||||
error = FT_Stroker_New( render_context.face->memory, &render_context.stroker );
|
||||
#endif
|
||||
@ -1903,13 +1906,13 @@ static int ass_render_event(ass_event_t* event, event_images_t* event_images)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void ass_reconfigure(ass_instance_t* priv)
|
||||
static void ass_reconfigure(ass_renderer_t* priv)
|
||||
{
|
||||
priv->render_id = ++last_render_id;
|
||||
ass_glyph_cache_reset();
|
||||
}
|
||||
|
||||
void ass_set_frame_size(ass_instance_t* priv, int w, int h)
|
||||
void ass_set_frame_size(ass_renderer_t* priv, int w, int h)
|
||||
{
|
||||
if (priv->settings.frame_width != w || priv->settings.frame_height != h) {
|
||||
priv->settings.frame_width = w;
|
||||
@ -1920,7 +1923,7 @@ void ass_set_frame_size(ass_instance_t* priv, int w, int h)
|
||||
}
|
||||
}
|
||||
|
||||
void ass_set_margins(ass_instance_t* priv, int t, int b, int l, int r)
|
||||
void ass_set_margins(ass_renderer_t* priv, int t, int b, int l, int r)
|
||||
{
|
||||
if (priv->settings.left_margin != l ||
|
||||
priv->settings.right_margin != r ||
|
||||
@ -1934,12 +1937,12 @@ void ass_set_margins(ass_instance_t* priv, int t, int b, int l, int r)
|
||||
}
|
||||
}
|
||||
|
||||
void ass_set_use_margins(ass_instance_t* priv, int use)
|
||||
void ass_set_use_margins(ass_renderer_t* priv, int use)
|
||||
{
|
||||
priv->settings.use_margins = use;
|
||||
}
|
||||
|
||||
void ass_set_aspect_ratio(ass_instance_t* priv, double ar)
|
||||
void ass_set_aspect_ratio(ass_renderer_t* priv, double ar)
|
||||
{
|
||||
if (priv->settings.aspect != ar) {
|
||||
priv->settings.aspect = ar;
|
||||
@ -1947,7 +1950,7 @@ void ass_set_aspect_ratio(ass_instance_t* priv, double ar)
|
||||
}
|
||||
}
|
||||
|
||||
void ass_set_font_scale(ass_instance_t* priv, double font_scale)
|
||||
void ass_set_font_scale(ass_renderer_t* priv, double font_scale)
|
||||
{
|
||||
if (priv->settings.font_size_coeff != font_scale) {
|
||||
priv->settings.font_size_coeff = font_scale;
|
||||
@ -1955,22 +1958,19 @@ void ass_set_font_scale(ass_instance_t* priv, double font_scale)
|
||||
}
|
||||
}
|
||||
|
||||
int ass_set_fonts(ass_instance_t* priv, const char* fonts_dir, const char* default_font, const char* default_family)
|
||||
int ass_set_fonts(ass_renderer_t* priv, const char* default_font, const char* default_family)
|
||||
{
|
||||
if (priv->settings.fonts_dir)
|
||||
free(priv->settings.fonts_dir);
|
||||
if (priv->settings.default_font)
|
||||
free(priv->settings.default_font);
|
||||
if (priv->settings.default_family)
|
||||
free(priv->settings.default_family);
|
||||
|
||||
priv->settings.fonts_dir = fonts_dir ? strdup(fonts_dir) : 0;
|
||||
priv->settings.default_font = default_font ? strdup(default_font) : 0;
|
||||
priv->settings.default_family = default_family ? strdup(default_family) : 0;
|
||||
|
||||
if (priv->fontconfig_priv)
|
||||
fontconfig_done(priv->fontconfig_priv);
|
||||
priv->fontconfig_priv = fontconfig_init(fonts_dir, default_family, default_font);
|
||||
priv->fontconfig_priv = fontconfig_init(priv->library->fonts_dir, default_family, default_font);
|
||||
|
||||
return !!priv->fontconfig_priv;
|
||||
}
|
||||
@ -1978,11 +1978,11 @@ int ass_set_fonts(ass_instance_t* priv, const char* fonts_dir, const char* defau
|
||||
/**
|
||||
* \brief Start a new frame
|
||||
*/
|
||||
static int ass_start_frame(ass_instance_t *priv, ass_track_t* track, long long now)
|
||||
static int ass_start_frame(ass_renderer_t *priv, ass_track_t* track, long long now)
|
||||
{
|
||||
ass_image_t* img;
|
||||
|
||||
ass_instance = priv;
|
||||
ass_renderer = priv;
|
||||
global_settings = &priv->settings;
|
||||
|
||||
if (!priv->settings.frame_width && !priv->settings.frame_height)
|
||||
@ -2044,9 +2044,9 @@ static render_priv_t* get_render_priv(ass_event_t* event)
|
||||
if (!event->render_priv)
|
||||
event->render_priv = calloc(1, sizeof(render_priv_t));
|
||||
// FIXME: check render_id
|
||||
if (ass_instance->render_id != event->render_priv->render_id) {
|
||||
if (ass_renderer->render_id != event->render_priv->render_id) {
|
||||
memset(event->render_priv, 0, sizeof(render_priv_t));
|
||||
event->render_priv->render_id = ass_instance->render_id;
|
||||
event->render_priv->render_id = ass_renderer->render_id;
|
||||
}
|
||||
return event->render_priv;
|
||||
}
|
||||
@ -2191,7 +2191,7 @@ static void fix_collisions(event_images_t* imgs, int cnt)
|
||||
* \param track track
|
||||
* \param now current video timestamp (ms)
|
||||
*/
|
||||
ass_image_t* ass_render_frame(ass_instance_t *priv, ass_track_t* track, long long now)
|
||||
ass_image_t* ass_render_frame(ass_renderer_t *priv, ass_track_t* track, long long now)
|
||||
{
|
||||
int i, cnt, rc;
|
||||
event_images_t eimg[MAX_EVENTS];
|
||||
@ -2232,7 +2232,7 @@ ass_image_t* ass_render_frame(ass_instance_t *priv, ass_track_t* track, long lon
|
||||
fix_collisions(last, eimg + cnt - last);
|
||||
|
||||
// concat lists
|
||||
tail = &ass_instance->images_root;
|
||||
tail = &ass_renderer->images_root;
|
||||
for (i = 0; i < cnt; ++i) {
|
||||
ass_image_t* cur = eimg[i].imgs;
|
||||
while (cur) {
|
||||
@ -2242,6 +2242,6 @@ ass_image_t* ass_render_frame(ass_instance_t *priv, ass_track_t* track, long lon
|
||||
}
|
||||
}
|
||||
|
||||
return ass_instance->images_root;
|
||||
return ass_renderer->images_root;
|
||||
}
|
||||
|
||||
|
@ -79,6 +79,8 @@ typedef struct ass_event_s {
|
||||
|
||||
typedef struct parser_priv_s parser_priv_t;
|
||||
|
||||
typedef struct ass_library_s ass_library_t;
|
||||
|
||||
/// ass track represent either an external script or a matroska subtitle stream (no real difference between them)
|
||||
/// it can be used in rendering after the headers are parsed (i.e. events format line read)
|
||||
typedef struct ass_track_s {
|
||||
@ -104,6 +106,7 @@ typedef struct ass_track_s {
|
||||
int default_style; // index of default style
|
||||
char* name; // file name in case of external subs, 0 for streams
|
||||
|
||||
ass_library_t* library;
|
||||
parser_priv_t* parser_priv;
|
||||
} ass_track_t;
|
||||
|
||||
|
@ -60,7 +60,7 @@ static struct vf_priv_s {
|
||||
// 0 = insert always
|
||||
int auto_insert;
|
||||
|
||||
ass_instance_t* ass_priv;
|
||||
ass_renderer_t* ass_priv;
|
||||
|
||||
unsigned char* planes[3];
|
||||
unsigned char* dirty_rows;
|
||||
@ -349,7 +349,7 @@ static int control(vf_instance_t *vf, int request, void *data)
|
||||
{
|
||||
switch (request) {
|
||||
case VFCTRL_INIT_EOSD:
|
||||
vf->priv->ass_priv = ass_init();
|
||||
vf->priv->ass_priv = ass_renderer_init((ass_library_t*)data);
|
||||
return vf->priv->ass_priv ? CONTROL_TRUE : CONTROL_FALSE;
|
||||
case VFCTRL_DRAW_EOSD:
|
||||
if (vf->priv->ass_priv) return CONTROL_TRUE;
|
||||
@ -361,7 +361,7 @@ static int control(vf_instance_t *vf, int request, void *data)
|
||||
static void uninit(struct vf_instance_s* vf)
|
||||
{
|
||||
if (vf->priv->ass_priv)
|
||||
ass_done(vf->priv->ass_priv);
|
||||
ass_renderer_done(vf->priv->ass_priv);
|
||||
if (vf->priv->planes[1])
|
||||
free(vf->priv->planes[1]);
|
||||
if (vf->priv->planes[2])
|
||||
|
@ -29,7 +29,7 @@ typedef struct vf_vo_data_s {
|
||||
struct vf_priv_s {
|
||||
vf_vo_data_t* vf_vo_data;
|
||||
#ifdef USE_ASS
|
||||
ass_instance_t* ass_priv;
|
||||
ass_renderer_t* ass_priv;
|
||||
#endif
|
||||
};
|
||||
#define video_out (vf->priv->vf_vo_data->vo)
|
||||
@ -107,7 +107,7 @@ static int control(struct vf_instance_s* vf, int request, void* data)
|
||||
#ifdef USE_ASS
|
||||
case VFCTRL_INIT_EOSD:
|
||||
{
|
||||
vf->priv->ass_priv = ass_init();
|
||||
vf->priv->ass_priv = ass_renderer_init((ass_library_t*)data);
|
||||
if (!vf->priv->ass_priv) return CONTROL_FALSE;
|
||||
return CONTROL_TRUE;
|
||||
}
|
||||
@ -185,7 +185,7 @@ static void uninit(struct vf_instance_s* vf)
|
||||
if (vf->priv) {
|
||||
#ifdef USE_ASS
|
||||
if (vf->priv->ass_priv)
|
||||
ass_done(vf->priv->ass_priv);
|
||||
ass_renderer_done(vf->priv->ass_priv);
|
||||
#endif
|
||||
free(vf->priv);
|
||||
}
|
||||
|
@ -1624,7 +1624,7 @@ demux_mkv_read_attachments (demuxer_t *demuxer)
|
||||
if (extract_embedded_fonts && name && data && data_size &&
|
||||
mime && (strcmp(mime, "application/x-truetype-font") == 0 ||
|
||||
strcmp(mime, "application/x-font") == 0))
|
||||
ass_process_font(name, data, data_size);
|
||||
ass_process_font(ass_library, name, data, data_size);
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
@ -2385,7 +2385,7 @@ demux_mkv_parse_ass_data (demuxer_t *demuxer)
|
||||
|
||||
if (track->subtitle_type == MATROSKA_SUBTYPE_SSA)
|
||||
{
|
||||
track->sh_sub.ass_track = ass_new_track();
|
||||
track->sh_sub.ass_track = ass_new_track(ass_library);
|
||||
size = track->private_size;
|
||||
m = demux_mkv_decode (track,track->private_data,&buffer,&size,2);
|
||||
if (buffer && m)
|
||||
@ -2398,7 +2398,7 @@ demux_mkv_parse_ass_data (demuxer_t *demuxer)
|
||||
}
|
||||
else
|
||||
{
|
||||
track->sh_sub.ass_track = ass_default_track();
|
||||
track->sh_sub.ass_track = ass_default_track(ass_library);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
27
mplayer.c
27
mplayer.c
@ -705,6 +705,12 @@ static void exit_player_with_rc(const char* how, int rc){
|
||||
#endif
|
||||
free_osd_list();
|
||||
|
||||
#ifdef USE_ASS
|
||||
if(ass_enabled) {
|
||||
ass_library_done(ass_library);
|
||||
}
|
||||
#endif
|
||||
|
||||
current_module="exit_player";
|
||||
|
||||
// free mplayer config
|
||||
@ -978,9 +984,13 @@ void add_subtitles(char *filename, float fps, int silent)
|
||||
subd = sub_read_file(filename, fps);
|
||||
#ifdef USE_ASS
|
||||
if (ass_enabled)
|
||||
asst = ass_read_file(filename);
|
||||
#ifdef USE_ICONV
|
||||
asst = ass_read_file(ass_library, filename, sub_cp);
|
||||
#else
|
||||
asst = ass_read_file(ass_library, filename, 0);
|
||||
#endif
|
||||
if (ass_enabled && subd && !asst)
|
||||
asst = ass_read_subdata(subd, fps);
|
||||
asst = ass_read_subdata(ass_library, subd, fps);
|
||||
|
||||
if (!asst && !subd && !silent)
|
||||
#else
|
||||
@ -3099,6 +3109,17 @@ if(!codecs_file || !parse_codec_cfg(codecs_file)){
|
||||
#endif /* USE_OSD */
|
||||
vo_init_osd();
|
||||
|
||||
#ifdef USE_ASS
|
||||
if(ass_enabled) {
|
||||
char* path = get_path("fonts");
|
||||
ass_library = ass_library_init();
|
||||
ass_set_fonts_dir(ass_library, path);
|
||||
ass_set_extract_fonts(ass_library, extract_embedded_fonts);
|
||||
ass_set_style_overrides(ass_library, ass_force_style_list);
|
||||
free(path);
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_RTC
|
||||
if(!nortc)
|
||||
{
|
||||
@ -3882,7 +3903,7 @@ sh_video->vfilter=(void*)append_filters(sh_video->vfilter);
|
||||
|
||||
#ifdef USE_ASS
|
||||
if (ass_enabled)
|
||||
((vf_instance_t *)sh_video->vfilter)->control(sh_video->vfilter, VFCTRL_INIT_EOSD, 0);
|
||||
((vf_instance_t *)sh_video->vfilter)->control(sh_video->vfilter, VFCTRL_INIT_EOSD, ass_library);
|
||||
#endif
|
||||
|
||||
current_module="init_video_codec";
|
||||
|
Loading…
Reference in New Issue
Block a user