mirror of https://github.com/freetype/freetype
[sfnt] Load variation store for 'COLR' v1.
* src/sfnt/ttcolr.c: Include `ttobjs.h` temporarily. (VARIABLE_COLRV1_ENABLED): New temporary macro to detect whether variable COLRv1 is enabled. (Colr): New fields `var_store` and `delta_set_idx_map`. (tt_face_load_colr, tt_face_free_colr) [VARIABLE_COLRV1_ENABLED]: Load and free variation store data using the functions from the Multiple Masters service.
This commit is contained in:
parent
1a242558be
commit
31b14fd4dc
|
@ -30,10 +30,15 @@
|
|||
#include <freetype/internal/ftcalc.h>
|
||||
#include <freetype/internal/ftdebug.h>
|
||||
#include <freetype/internal/ftstream.h>
|
||||
#include <freetype/internal/services/svmm.h>
|
||||
#include <freetype/tttags.h>
|
||||
#include <freetype/ftcolor.h>
|
||||
#include <freetype/config/integer-types.h>
|
||||
|
||||
/* the next code line is a temporary hack, to be removed together with */
|
||||
/* `VARIABLE_COLRV1_ENABLED` and related code */
|
||||
#include "../truetype/ttobjs.h"
|
||||
|
||||
|
||||
#ifdef TT_CONFIG_OPTION_COLOR_LAYERS
|
||||
|
||||
|
@ -50,6 +55,10 @@
|
|||
#define COLR_HEADER_SIZE 14U
|
||||
|
||||
|
||||
#define VARIABLE_COLRV1_ENABLED \
|
||||
( ((TT_Driver)FT_FACE_DRIVER( face ))->enable_variable_colrv1 )
|
||||
|
||||
|
||||
typedef enum FT_PaintFormat_Internal_
|
||||
{
|
||||
FT_COLR_PAINTFORMAT_INTERNAL_SCALE_CENTER = 18,
|
||||
|
@ -104,6 +113,10 @@
|
|||
*/
|
||||
FT_Byte* paints_start_v1;
|
||||
|
||||
/* Item Variation Store for variable 'COLR' v1. */
|
||||
GX_ItemVarStoreRec var_store;
|
||||
GX_DeltaSetIdxMapRec delta_set_idx_map;
|
||||
|
||||
/* The memory that backs up the `COLR' table. */
|
||||
void* table;
|
||||
FT_ULong table_size;
|
||||
|
@ -138,7 +151,9 @@
|
|||
FT_ULong base_glyph_offset, layer_offset;
|
||||
FT_ULong base_glyphs_offset_v1, num_base_glyphs_v1;
|
||||
FT_ULong layer_offset_v1, num_layers_v1, clip_list_offset;
|
||||
FT_ULong var_idx_map_offset, var_store_offset;
|
||||
FT_ULong table_size;
|
||||
FT_ULong colr_offset_in_stream;
|
||||
|
||||
|
||||
/* `COLR' always needs `CPAL' */
|
||||
|
@ -149,6 +164,8 @@
|
|||
if ( error )
|
||||
goto NoColr;
|
||||
|
||||
colr_offset_in_stream = FT_STREAM_POS();
|
||||
|
||||
if ( table_size < COLR_HEADER_SIZE )
|
||||
goto InvalidTable;
|
||||
|
||||
|
@ -239,6 +256,64 @@
|
|||
colr->clip_list = (FT_Byte*)( table + clip_list_offset );
|
||||
else
|
||||
colr->clip_list = 0;
|
||||
|
||||
colr->var_store.dataCount = 0;
|
||||
colr->var_store.varData = NULL;
|
||||
colr->var_store.axisCount = 0;
|
||||
colr->var_store.regionCount = 0;
|
||||
colr->var_store.varRegionList = 0;
|
||||
|
||||
colr->delta_set_idx_map.mapCount = 0;
|
||||
colr->delta_set_idx_map.outerIndex = NULL;
|
||||
colr->delta_set_idx_map.innerIndex = NULL;
|
||||
|
||||
#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT
|
||||
if ( face->variation_support & TT_FACE_FLAG_VAR_FVAR &&
|
||||
VARIABLE_COLRV1_ENABLED )
|
||||
{
|
||||
FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm;
|
||||
|
||||
|
||||
var_idx_map_offset = FT_NEXT_ULONG( p );
|
||||
|
||||
if ( var_idx_map_offset >= table_size )
|
||||
goto InvalidTable;
|
||||
|
||||
var_store_offset = FT_NEXT_ULONG( p );
|
||||
if ( var_store_offset >= table_size )
|
||||
goto InvalidTable;
|
||||
|
||||
if ( var_store_offset )
|
||||
{
|
||||
/* If variation info has not been initialized yet, try doing so, */
|
||||
/* otherwise loading the variation store will fail as it */
|
||||
/* requires access to `blend` for checking the number of axes. */
|
||||
if ( !face->blend )
|
||||
if ( mm->get_mm_var( FT_FACE( face ), NULL ) )
|
||||
goto InvalidTable;
|
||||
|
||||
/* Try loading `VarIdxMap` and `VarStore`. */
|
||||
error = mm->load_item_var_store(
|
||||
FT_FACE( face ),
|
||||
colr_offset_in_stream + var_store_offset,
|
||||
&colr->var_store );
|
||||
if ( error != FT_Err_Ok )
|
||||
goto InvalidTable;
|
||||
}
|
||||
|
||||
if ( colr->var_store.axisCount && var_idx_map_offset )
|
||||
{
|
||||
error = mm->load_delta_set_idx_map(
|
||||
FT_FACE( face ),
|
||||
colr_offset_in_stream + var_idx_map_offset,
|
||||
&colr->delta_set_idx_map,
|
||||
&colr->var_store,
|
||||
table_size );
|
||||
if ( error != FT_Err_Ok )
|
||||
goto InvalidTable;
|
||||
}
|
||||
}
|
||||
#endif /* TT_CONFIG_OPTION_GX_VAR_SUPPORT */
|
||||
}
|
||||
|
||||
colr->base_glyphs = (FT_Byte*)( table + base_glyph_offset );
|
||||
|
@ -251,6 +326,19 @@
|
|||
return FT_Err_Ok;
|
||||
|
||||
InvalidTable:
|
||||
#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT
|
||||
if ( VARIABLE_COLRV1_ENABLED )
|
||||
{
|
||||
FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm;
|
||||
|
||||
|
||||
mm->done_delta_set_idx_map( FT_FACE( face ),
|
||||
&colr->delta_set_idx_map );
|
||||
mm->done_item_var_store( FT_FACE( face ),
|
||||
&colr->var_store );
|
||||
}
|
||||
#endif
|
||||
|
||||
error = FT_THROW( Invalid_Table );
|
||||
|
||||
NoColr:
|
||||
|
@ -272,6 +360,18 @@
|
|||
|
||||
if ( colr )
|
||||
{
|
||||
#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT
|
||||
if ( VARIABLE_COLRV1_ENABLED )
|
||||
{
|
||||
FT_Service_MultiMasters mm = (FT_Service_MultiMasters)face->mm;
|
||||
|
||||
|
||||
mm->done_delta_set_idx_map( FT_FACE( face ),
|
||||
&colr->delta_set_idx_map );
|
||||
mm->done_item_var_store( FT_FACE( face ),
|
||||
&colr->var_store );
|
||||
}
|
||||
#endif
|
||||
FT_FRAME_RELEASE( colr->table );
|
||||
FT_FREE( colr );
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue