[subset] Implement subsetting of SingleSubst
This commit is contained in:
parent
3f00d0b0df
commit
0d160d5ff5
|
@ -452,6 +452,8 @@ struct hb_serialize_context_t
|
|||
this->debug_depth = 0;
|
||||
}
|
||||
|
||||
inline bool err (bool e) { return this->ran_out_of_room = this->ran_out_of_room || e; }
|
||||
|
||||
/* To be called around main operation. */
|
||||
template <typename Type>
|
||||
inline Type *start_serialize (void)
|
||||
|
|
|
@ -51,27 +51,40 @@ static inline Type const & Null (void) {
|
|||
|
||||
/* Specializaitons for arbitrary-content Null objects expressed in bytes. */
|
||||
#define DECLARE_NULL_NAMESPACE_BYTES(Namespace, Type) \
|
||||
} /* Close namespace. */ \
|
||||
extern HB_INTERNAL const unsigned char _hb_Null_##Namespace##_##Type[Namespace::Type::min_size]; \
|
||||
template <> \
|
||||
/*static*/ inline const Namespace::Type& Null<Namespace::Type> (void) { \
|
||||
return *reinterpret_cast<const Namespace::Type *> (_hb_Null_##Namespace##_##Type); \
|
||||
} \
|
||||
namespace Namespace { \
|
||||
static_assert (true, "Just so we take semicolon after.")
|
||||
} /* Close namespace. */ \
|
||||
extern HB_INTERNAL const unsigned char _hb_Null_##Namespace##_##Type[Namespace::Type::min_size]; \
|
||||
template <> \
|
||||
/*static*/ inline const Namespace::Type& Null<Namespace::Type> (void) { \
|
||||
return *reinterpret_cast<const Namespace::Type *> (_hb_Null_##Namespace##_##Type); \
|
||||
} \
|
||||
namespace Namespace { \
|
||||
static_assert (true, "Just so we take semicolon after.")
|
||||
#define DEFINE_NULL_NAMESPACE_BYTES(Namespace, Type) \
|
||||
const unsigned char _hb_Null_##Namespace##_##Type[Namespace::Type::min_size]
|
||||
const unsigned char _hb_Null_##Namespace##_##Type[Namespace::Type::min_size]
|
||||
|
||||
/* Specializaitons for arbitrary-content Null objects expressed as struct initializer. */
|
||||
#define DECLARE_NULL_INSTANCE(Type) \
|
||||
extern HB_INTERNAL const Type _hb_Null_##Type; \
|
||||
template <> \
|
||||
/*static*/ inline const Type& Null<Type> (void) { \
|
||||
return _hb_Null_##Type; \
|
||||
} \
|
||||
extern HB_INTERNAL const Type _hb_Null_##Type; \
|
||||
template <> \
|
||||
/*static*/ inline const Type& Null<Type> (void) { \
|
||||
return _hb_Null_##Type; \
|
||||
} \
|
||||
static_assert (true, "Just so we take semicolon after.")
|
||||
#define DEFINE_NULL_INSTANCE(Type) \
|
||||
const Type _hb_Null_##Type
|
||||
const Type _hb_Null_##Type
|
||||
|
||||
/* Specializaiton to disallow Null objects. */
|
||||
#define DECLARE_NULL_DISALLOW(Type) \
|
||||
template <> inline const Type& Null<Type> (void)
|
||||
#define DECLARE_NULL_NAMSPACE_DISALLOW(Namespace, Type) \
|
||||
} /* Close namespace. */ \
|
||||
template <> \
|
||||
/*static*/ inline const Namespace::Type& Null<Namespace::Type> (void) { \
|
||||
extern void *_hb_undefined; \
|
||||
return *reinterpret_cast<const Namespace::Type *> (_hb_undefined); \
|
||||
} \
|
||||
namespace Namespace { \
|
||||
static_assert (true, "Just so we take semicolon after.")
|
||||
|
||||
/* Global writable pool. Enlarge as necessary. */
|
||||
|
||||
|
|
|
@ -35,6 +35,11 @@
|
|||
namespace OT {
|
||||
|
||||
|
||||
static inline void SingleSubst_serialize (hb_serialize_context_t *c,
|
||||
Supplier<GlyphID> &glyphs,
|
||||
Supplier<GlyphID> &substitutes,
|
||||
unsigned int num_glyphs);
|
||||
|
||||
struct SingleSubstFormat1
|
||||
{
|
||||
inline bool intersects (const hb_set_t *glyphs) const
|
||||
|
@ -104,19 +109,26 @@ struct SingleSubstFormat1
|
|||
|
||||
inline bool subset (hb_subset_context_t *c) const
|
||||
{
|
||||
return false;
|
||||
TRACE_SUBSET (this);
|
||||
hb_auto_t<hb_vector_t<hb_codepoint_t>> from;
|
||||
hb_auto_t<hb_vector_t<hb_codepoint_t>> to;
|
||||
hb_auto_t<hb_vector_t<GlyphID>> from;
|
||||
hb_auto_t<hb_vector_t<GlyphID>> to;
|
||||
hb_codepoint_t delta = deltaGlyphID;
|
||||
for (hb_auto_t<Coverage::Iter> iter (this+coverage); iter.more (); iter.next ())
|
||||
{
|
||||
//if (!c->plan->glyphs->has (iter.get_glyph ()))
|
||||
// continue;
|
||||
from.push (iter.get_glyph ());
|
||||
to.push ((iter.get_glyph () + delta) & 0xFFFF);
|
||||
if (!c->plan->glyphset->has (iter.get_glyph ()))
|
||||
continue;
|
||||
from.push ()->set (iter.get_glyph ());
|
||||
to.push ()->set ((iter.get_glyph () + delta) & 0xFFFF);
|
||||
}
|
||||
return_trace (false);
|
||||
c->serializer->err (from.in_error () || to.in_error ());
|
||||
|
||||
Supplier<GlyphID> from_supplier (&from);
|
||||
Supplier<GlyphID> to_supplier (&to);
|
||||
SingleSubst_serialize (c->serializer,
|
||||
from_supplier,
|
||||
to_supplier,
|
||||
from.len);
|
||||
return_trace (from.len);
|
||||
}
|
||||
|
||||
inline bool sanitize (hb_sanitize_context_t *c) const
|
||||
|
@ -204,8 +216,24 @@ struct SingleSubstFormat2
|
|||
inline bool subset (hb_subset_context_t *c) const
|
||||
{
|
||||
TRACE_SUBSET (this);
|
||||
// TODO(subset)
|
||||
return_trace (false);
|
||||
hb_auto_t<hb_vector_t<GlyphID>> from;
|
||||
hb_auto_t<hb_vector_t<GlyphID>> to;
|
||||
for (hb_auto_t<Coverage::Iter> iter (this+coverage); iter.more (); iter.next ())
|
||||
{
|
||||
if (!c->plan->glyphset->has (iter.get_glyph ()))
|
||||
continue;
|
||||
from.push ()->set (iter.get_glyph ());
|
||||
to.push ()->set (substitute[iter.get_coverage ()]);
|
||||
}
|
||||
c->serializer->err (from.in_error () || to.in_error ());
|
||||
|
||||
Supplier<GlyphID> from_supplier (&from);
|
||||
Supplier<GlyphID> to_supplier (&to);
|
||||
SingleSubst_serialize (c->serializer,
|
||||
from_supplier,
|
||||
to_supplier,
|
||||
from.len);
|
||||
return_trace (from.len);
|
||||
}
|
||||
|
||||
inline bool sanitize (hb_sanitize_context_t *c) const
|
||||
|
@ -275,6 +303,17 @@ struct SingleSubst
|
|||
} u;
|
||||
};
|
||||
|
||||
static inline void
|
||||
SingleSubst_serialize (hb_serialize_context_t *c,
|
||||
Supplier<GlyphID> &glyphs,
|
||||
Supplier<GlyphID> &substitutes,
|
||||
unsigned int num_glyphs)
|
||||
{
|
||||
c->start_embed<SingleSubst> ()->serialize (c,
|
||||
glyphs,
|
||||
substitutes,
|
||||
num_glyphs);
|
||||
}
|
||||
|
||||
struct Sequence
|
||||
{
|
||||
|
|
|
@ -72,6 +72,8 @@ struct hb_vector_t
|
|||
return p;
|
||||
}
|
||||
|
||||
inline bool in_error (void) const { return allocated == 0; }
|
||||
|
||||
/* Allocate for size but don't adjust len. */
|
||||
inline bool alloc (unsigned int size)
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue