[HarfBuzz] harfbuzz-ng: Branch 'master' - 13 commits
Behdad Esfahbod
behdad at kemper.freedesktop.org
Thu May 13 10:34:54 PDT 2010
src/Makefile.am | 19 -
src/check-internal-symbols.sh | 28 +
src/hb-blob-private.h | 2
src/hb-buffer-private.h | 156 --------
src/hb-buffer-private.hh | 175 +++++++++
src/hb-buffer.c | 650 -----------------------------------
src/hb-buffer.cc | 637 ++++++++++++++++++++++++++++++++++
src/hb-common.h | 9
src/hb-font-private.h | 92 ----
src/hb-font-private.hh | 92 ++++
src/hb-font.cc | 4
src/hb-ft.c | 240 ------------
src/hb-ft.cc | 240 ++++++++++++
src/hb-open-type-private.hh | 11
src/hb-ot-layout-common-private.hh | 2
src/hb-ot-layout-gdef-private.hh | 2
src/hb-ot-layout-gsub-private.hh | 34 -
src/hb-ot-layout-gsubgpos-private.hh | 6
src/hb-ot-layout-private.h | 121 ------
src/hb-ot-layout-private.hh | 121 ++++++
src/hb-ot-layout.cc | 2
src/hb-ot-shape-private.h | 53 --
src/hb-ot-shape-private.hh | 53 ++
src/hb-ot-shape.c | 164 --------
src/hb-ot-shape.cc | 164 ++++++++
src/hb-private.h | 8
src/hb-shape.c | 258 -------------
src/hb-shape.cc | 258 +++++++++++++
src/hb-unicode-private.h | 3
src/hb-unicode.c | 2
30 files changed, 1824 insertions(+), 1782 deletions(-)
New commits:
commit f679635893eebc13402c5ee51a6f106eed0c76be
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Thu May 13 13:34:17 2010 -0400
Don't use variable-length-arrays
diff --git a/src/hb-open-type-private.hh b/src/hb-open-type-private.hh
index adbd4c7..a57bef5 100644
--- a/src/hb-open-type-private.hh
+++ b/src/hb-open-type-private.hh
@@ -77,9 +77,14 @@ inline Type& StructAfter(TObject &X)
* Size checking
*/
+/* Check _assertion in a method environment */
#define _DEFINE_SIZE_ASSERTION(_assertion) \
inline void _size_assertion (void) const \
{ ASSERT_STATIC (_assertion); }
+/* Check that _code compiles in a method environment */
+#define _DEFINE_COMPILES_ASSERTION(_code) \
+ inline void _compiles_assertion (void) const \
+ { _code; }
#define DEFINE_SIZE_STATIC(size) \
@@ -99,11 +104,13 @@ inline Type& StructAfter(TObject &X)
static const unsigned int min_size = (size)
#define DEFINE_SIZE_ARRAY(size, array) \
- _DEFINE_SIZE_ASSERTION (sizeof (*this) == (size) + array[0].static_size); \
+ _DEFINE_SIZE_ASSERTION (sizeof (*this) == (size) + sizeof (array[0])); \
+ _DEFINE_COMPILES_ASSERTION ((void) array[0].static_size) \
static const unsigned int min_size = (size)
#define DEFINE_SIZE_ARRAY2(size, array1, array2) \
- _DEFINE_SIZE_ASSERTION (sizeof (*this) == (size) + this->array1[0].static_size + this->array2[0].static_size); \
+ _DEFINE_SIZE_ASSERTION (sizeof (*this) == (size) + sizeof (this->array1[0]) + sizeof (this->array2[0])); \
+ _DEFINE_COMPILES_ASSERTION ((void) array1[0].static_size; (void) array2[0].static_size) \
static const unsigned int min_size = (size)
commit 72071a8afaba2952fe42be093024ae9dbd37f233
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Thu May 13 13:22:24 2010 -0400
Add a few more buffer convenience methods
diff --git a/src/hb-buffer-private.hh b/src/hb-buffer-private.hh
index 73bae80..db67f81 100644
--- a/src/hb-buffer-private.hh
+++ b/src/hb-buffer-private.hh
@@ -130,6 +130,18 @@ struct _hb_buffer_t {
inline void swap (void) { _hb_buffer_swap (this); }
inline void clear_output (void) { _hb_buffer_clear_output (this); }
inline void next_glyph (void) { _hb_buffer_next_glyph (this); }
+ inline void add_output_glyphs (unsigned int num_in,
+ unsigned int num_out,
+ const hb_codepoint_t *glyph_data,
+ unsigned short component,
+ unsigned short ligID)
+ { _hb_buffer_add_output_glyphs (this, num_in, num_out, glyph_data, component, ligID); }
+ inline void add_output_glyphs_be16 (unsigned int num_in,
+ unsigned int num_out,
+ const uint16_t *glyph_data_be,
+ unsigned short component,
+ unsigned short ligID)
+ { _hb_buffer_add_output_glyphs_be16 (this, num_in, num_out, glyph_data_be, component, ligID); }
inline void add_output_glyph (hb_codepoint_t glyph_index,
unsigned short component = 0xFFFF,
unsigned short ligID = 0xFFFF)
diff --git a/src/hb-ot-layout-gsub-private.hh b/src/hb-ot-layout-gsub-private.hh
index 9a4b2e8..2b5919e 100644
--- a/src/hb-ot-layout-gsub-private.hh
+++ b/src/hb-ot-layout-gsub-private.hh
@@ -166,9 +166,9 @@ struct Sequence
if (unlikely (!substitute.len))
return false;
- _hb_buffer_add_output_glyphs_be16 (context->buffer, 1,
- substitute.len, (const uint16_t *) substitute.array,
- 0xFFFF, 0xFFFF);
+ context->buffer->add_output_glyphs_be16 (1,
+ substitute.len, (const uint16_t *) substitute.array,
+ 0xFFFF, 0xFFFF);
/* This is a guess only ... */
if (_hb_ot_layout_has_new_glyph_classes (context->layout->face))
@@ -400,15 +400,15 @@ struct Ligature
if (j == context->buffer->in_pos + i) /* No input glyphs skipped */
/* We don't use a new ligature ID if there are no skipped
glyphs and the ligature already has an ID. */
- _hb_buffer_add_output_glyphs_be16 (context->buffer, i,
- 1, (const uint16_t *) &ligGlyph,
- 0,
- IN_LIGID (context->buffer->in_pos) && !IN_COMPONENT (context->buffer->in_pos) ?
- 0xFFFF : context->buffer->allocate_lig_id ());
+ context->buffer->add_output_glyphs_be16 (i,
+ 1, (const uint16_t *) &ligGlyph,
+ 0,
+ IN_LIGID (context->buffer->in_pos) && !IN_COMPONENT (context->buffer->in_pos) ?
+ 0xFFFF : context->buffer->allocate_lig_id ());
else
{
unsigned int lig_id = context->buffer->allocate_lig_id ();
- _hb_buffer_add_output_glyph (context->buffer, ligGlyph, 0xFFFF, lig_id);
+ context->buffer->add_output_glyph (ligGlyph, 0xFFFF, lig_id);
/* Now we must do a second loop to copy the skipped glyphs to
`out' and assign component values to it. We start with the
@@ -420,7 +420,7 @@ struct Ligature
for ( i = 1; i < count; i++ )
{
while (_hb_ot_layout_skip_mark (context->layout->face, IN_CURINFO (), context->lookup_flag, NULL))
- _hb_buffer_add_output_glyph (context->buffer, IN_CURGLYPH (), i, lig_id);
+ context->buffer->add_output_glyph (IN_CURGLYPH (), i, lig_id);
(context->buffer->in_pos)++;
}
commit 11a81612e51c598e857507c268312206423cbfca
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Thu May 13 00:01:40 2010 -0400
Minor
diff --git a/src/hb-unicode.c b/src/hb-unicode.c
index fce79e6..7970a79 100644
--- a/src/hb-unicode.c
+++ b/src/hb-unicode.c
@@ -291,7 +291,7 @@ const hb_direction_t horiz_dir[] =
#undef LTR
#undef RTL
-HB_INTERNAL hb_direction_t
+hb_direction_t
_hb_script_get_horizontal_direction (hb_script_t script)
{
if (unlikely ((unsigned int) script >= ARRAY_LENGTH (horiz_dir)))
commit 3f93518a634cb1852bf050877db23b9b9203ad03
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Wed May 12 23:48:40 2010 -0400
Improve check for internal symbols
diff --git a/src/check-internal-symbols.sh b/src/check-internal-symbols.sh
index 7558518..124a7b0 100755
--- a/src/check-internal-symbols.sh
+++ b/src/check-internal-symbols.sh
@@ -17,7 +17,7 @@ stat=0
so=.libs/libharfbuzz.so
if test -f "$so"; then
echo "Checking that we are exposing internal symbols"
- if nm $so | grep ' T _hb'; then
+ if nm $so | grep ' T ' | grep -v ' T _fini\>\| T _init\>\| T hb_'; then
echo "Ouch, internal symbols exposed"
stat=1
fi
commit 357d0f29c431b842179ee4b56c21bcc402178ce7
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Wed May 12 23:46:16 2010 -0400
Make HB_PRIVATE more useful
So we can apply it to class methods also. Not sure if that works!
diff --git a/src/hb-blob-private.h b/src/hb-blob-private.h
index 26cad0a..c91af65 100644
--- a/src/hb-blob-private.h
+++ b/src/hb-blob-private.h
@@ -50,7 +50,7 @@ struct _hb_blob_t {
void *user_data;
};
-HB_INTERNAL hb_blob_t _hb_blob_nil;
+extern HB_INTERNAL hb_blob_t _hb_blob_nil;
HB_END_DECLS
diff --git a/src/hb-font-private.hh b/src/hb-font-private.hh
index ec07931..0d82850 100644
--- a/src/hb-font-private.hh
+++ b/src/hb-font-private.hh
@@ -50,8 +50,8 @@ struct _hb_font_funcs_t {
hb_font_get_kerning_func_t get_kerning;
};
-HB_INTERNAL hb_font_funcs_t
-_hb_font_funcs_nil;
+extern HB_INTERNAL hb_font_funcs_t _hb_font_funcs_nil;
+
/*
* hb_face_t
diff --git a/src/hb-private.h b/src/hb-private.h
index 03c53fb..6108d40 100644
--- a/src/hb-private.h
+++ b/src/hb-private.h
@@ -108,7 +108,7 @@
#endif
#ifndef HB_INTERNAL
-# define HB_INTERNAL extern __attribute__((__visibility__("hidden")))
+# define HB_INTERNAL __attribute__((__visibility__("hidden")))
#endif
diff --git a/src/hb-unicode-private.h b/src/hb-unicode-private.h
index ba530d2..01272da 100644
--- a/src/hb-unicode-private.h
+++ b/src/hb-unicode-private.h
@@ -49,8 +49,7 @@ struct _hb_unicode_funcs_t {
hb_unicode_get_eastasian_width_func_t get_eastasian_width;
};
-HB_INTERNAL hb_unicode_funcs_t
-_hb_unicode_funcs_nil;
+extern HB_INTERNAL hb_unicode_funcs_t _hb_unicode_funcs_nil;
HB_INTERNAL hb_direction_t
commit 1d5e78013696b10751d8a35027619e81978e1312
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Wed May 12 23:43:00 2010 -0400
Add a few other buffer methods
diff --git a/src/hb-buffer-private.hh b/src/hb-buffer-private.hh
index b5e4550..73bae80 100644
--- a/src/hb-buffer-private.hh
+++ b/src/hb-buffer-private.hh
@@ -94,10 +94,6 @@ _hb_buffer_add_output_glyph (hb_buffer_t *buffer,
HB_INTERNAL void
_hb_buffer_next_glyph (hb_buffer_t *buffer);
-HB_INTERNAL void
-_hb_buffer_replace_glyph (hb_buffer_t *buffer,
- hb_codepoint_t glyph_index);
-
struct _hb_buffer_t {
@@ -132,6 +128,13 @@ struct _hb_buffer_t {
/* Methods */
inline unsigned int allocate_lig_id (void) { return max_lig_id++; }
inline void swap (void) { _hb_buffer_swap (this); }
+ inline void clear_output (void) { _hb_buffer_clear_output (this); }
+ inline void next_glyph (void) { _hb_buffer_next_glyph (this); }
+ inline void add_output_glyph (hb_codepoint_t glyph_index,
+ unsigned short component = 0xFFFF,
+ unsigned short ligID = 0xFFFF)
+ { _hb_buffer_add_output_glyph (this, glyph_index, component, ligID); }
+ inline void replace_glyph (hb_codepoint_t glyph_index) { add_output_glyph (glyph_index); }
};
diff --git a/src/hb-buffer.cc b/src/hb-buffer.cc
index de7a2eb..bad5dcd 100644
--- a/src/hb-buffer.cc
+++ b/src/hb-buffer.cc
@@ -443,13 +443,6 @@ _hb_buffer_next_glyph (hb_buffer_t *buffer)
buffer->in_pos++;
}
-void
-_hb_buffer_replace_glyph (hb_buffer_t *buffer,
- hb_codepoint_t glyph_index)
-{
- _hb_buffer_add_output_glyph (buffer, glyph_index, 0xFFFF, 0xFFFF);
-}
-
unsigned int
hb_buffer_get_length (hb_buffer_t *buffer)
diff --git a/src/hb-ot-layout-gsub-private.hh b/src/hb-ot-layout-gsub-private.hh
index 0101c4f..9a4b2e8 100644
--- a/src/hb-ot-layout-gsub-private.hh
+++ b/src/hb-ot-layout-gsub-private.hh
@@ -49,7 +49,7 @@ struct SingleSubstFormat1
return false;
glyph_id += deltaGlyphID;
- _hb_buffer_replace_glyph (context->buffer, glyph_id);
+ context->buffer->replace_glyph (glyph_id);
/* We inherit the old glyph class to the substituted glyph */
if (_hb_ot_layout_has_new_glyph_classes (context->layout->face))
@@ -93,7 +93,7 @@ struct SingleSubstFormat2
return false;
glyph_id = substitute[index];
- _hb_buffer_replace_glyph (context->buffer, glyph_id);
+ context->buffer->replace_glyph (glyph_id);
/* We inherit the old glyph class to the substituted glyph */
if (_hb_ot_layout_has_new_glyph_classes (context->layout->face))
@@ -302,7 +302,7 @@ struct AlternateSubstFormat1
glyph_id = alt_set[alt_index];
- _hb_buffer_replace_glyph (context->buffer, glyph_id);
+ context->buffer->replace_glyph (glyph_id);
/* We inherit the old glyph class to the substituted glyph */
if (_hb_ot_layout_has_new_glyph_classes (context->layout->face))
@@ -832,7 +832,7 @@ struct SubstLookup : Lookup
if (likely (!is_reverse ()))
{
/* in/out forward substitution */
- _hb_buffer_clear_output (buffer);
+ buffer->clear_output ();
buffer->in_pos = 0;
while (buffer->in_pos < buffer->in_length)
{
@@ -840,7 +840,7 @@ struct SubstLookup : Lookup
apply_once (layout, buffer, NO_CONTEXT, MAX_NESTING_LEVEL))
ret = true;
else
- _hb_buffer_next_glyph (buffer);
+ buffer->next_glyph ();
}
if (ret)
diff --git a/src/hb-ot-layout-gsubgpos-private.hh b/src/hb-ot-layout-gsubgpos-private.hh
index 066abbd..cefde13 100644
--- a/src/hb-ot-layout-gsubgpos-private.hh
+++ b/src/hb-ot-layout-gsubgpos-private.hh
@@ -208,7 +208,7 @@ static inline bool apply_lookup (hb_apply_context_t *context,
if (unlikely (context->buffer->in_pos == end))
return true;
/* No lookup applied for this index */
- _hb_buffer_next_glyph (context->buffer);
+ context->buffer->next_glyph ();
}
if (lookupCount && i == lookupRecord->sequenceIndex)
@@ -232,7 +232,7 @@ static inline bool apply_lookup (hb_apply_context_t *context,
{
not_applied:
/* No lookup applied for this index */
- _hb_buffer_next_glyph (context->buffer);
+ context->buffer->next_glyph ();
i++;
}
}
commit d0316a81f59a4e814b0af78797d915d7ce04d119
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Wed May 12 23:34:52 2010 -0400
Add buffer->swap()
diff --git a/src/hb-buffer-private.hh b/src/hb-buffer-private.hh
index c8859c8..b5e4550 100644
--- a/src/hb-buffer-private.hh
+++ b/src/hb-buffer-private.hh
@@ -62,37 +62,6 @@ ASSERT_STATIC (sizeof (hb_glyph_position_t) == sizeof (hb_internal_glyph_positio
ASSERT_STATIC (sizeof (hb_glyph_info_t) == sizeof (hb_glyph_position_t));
-struct _hb_buffer_t {
- hb_reference_count_t ref_count;
-
- /* Information about how the text in the buffer should be treated */
- hb_unicode_funcs_t *unicode;
- hb_direction_t direction;
- hb_script_t script;
- hb_language_t language;
-
- /* Buffer contents */
-
- unsigned int allocated;
-
- hb_bool_t have_output; /* whether we have an output buffer going on */
- hb_bool_t have_positions; /* whether we have positions */
- unsigned int in_length;
- unsigned int out_length;
- unsigned int in_pos;
- unsigned int out_pos; /* out_length and out_pos are actually always the same */
-
- hb_internal_glyph_info_t *in_string;
- hb_internal_glyph_info_t *out_string;
- hb_internal_glyph_position_t *positions;
-
- /* Other stuff */
-
- unsigned int max_lig_id;
-
- inline unsigned int allocate_lig_id (void) { return max_lig_id++; }
-};
-
HB_INTERNAL void
_hb_buffer_swap (hb_buffer_t *buffer);
@@ -130,6 +99,43 @@ _hb_buffer_replace_glyph (hb_buffer_t *buffer,
hb_codepoint_t glyph_index);
+
+struct _hb_buffer_t {
+ hb_reference_count_t ref_count;
+
+ /* Information about how the text in the buffer should be treated */
+ hb_unicode_funcs_t *unicode;
+ hb_direction_t direction;
+ hb_script_t script;
+ hb_language_t language;
+
+ /* Buffer contents */
+
+ unsigned int allocated;
+
+ hb_bool_t have_output; /* whether we have an output buffer going on */
+ hb_bool_t have_positions; /* whether we have positions */
+ unsigned int in_length;
+ unsigned int out_length;
+ unsigned int in_pos;
+ unsigned int out_pos; /* out_length and out_pos are actually always the same */
+
+ hb_internal_glyph_info_t *in_string;
+ hb_internal_glyph_info_t *out_string;
+ hb_internal_glyph_position_t *positions;
+
+ /* Other stuff */
+
+ unsigned int max_lig_id;
+
+
+ /* Methods */
+ inline unsigned int allocate_lig_id (void) { return max_lig_id++; }
+ inline void swap (void) { _hb_buffer_swap (this); }
+};
+
+
+
#ifndef BUFFER
#define BUFFER buffer
#endif
diff --git a/src/hb-ot-layout-gsub-private.hh b/src/hb-ot-layout-gsub-private.hh
index 38364a5..0101c4f 100644
--- a/src/hb-ot-layout-gsub-private.hh
+++ b/src/hb-ot-layout-gsub-private.hh
@@ -844,7 +844,7 @@ struct SubstLookup : Lookup
}
if (ret)
- _hb_buffer_swap (buffer);
+ buffer->swap ();
}
else
{
commit 3b649a38b5772dd7aba7f07ff7698a7f427f421f
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Wed May 12 23:28:38 2010 -0400
Add check for internal symbols
diff --git a/src/Makefile.am b/src/Makefile.am
index 9c534a6..f52ea49 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -99,7 +99,8 @@ main_SOURCES = main.cc
main_CPPFLAGS = $(HBCFLAGS)
main_LDADD = libharfbuzz.la $(HBLIBS)
-TESTS =
+TESTS = \
+ check-internal-symbols.sh
if HAVE_ICU
else
diff --git a/src/check-internal-symbols.sh b/src/check-internal-symbols.sh
new file mode 100755
index 0000000..7558518
--- /dev/null
+++ b/src/check-internal-symbols.sh
@@ -0,0 +1,28 @@
+#!/bin/sh
+
+LC_ALL=C
+export LC_ALL
+
+if which nm 2>/dev/null >/dev/null; then
+ :
+else
+ echo "check-internal-symbols.sh: 'nm' not found; skipping test"
+ exit 0
+fi
+
+test -z "$srcdir" && srcdir=.
+test -z "$MAKE" && MAKE=make
+stat=0
+
+so=.libs/libharfbuzz.so
+if test -f "$so"; then
+ echo "Checking that we are exposing internal symbols"
+ if nm $so | grep ' T _hb'; then
+ echo "Ouch, internal symbols exposed"
+ stat=1
+ fi
+else
+ echo "check-internal-symbols.sh: libharfbuzz.so not found; skipping test"
+fi
+
+exit $stat
commit eee8598d75d3af692d9ececf7e8ac458e892ba9e
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Wed May 12 23:22:55 2010 -0400
Hide internal symbols
diff --git a/src/hb-ot-layout-private.hh b/src/hb-ot-layout-private.hh
index e18222b..e25f7ac 100644
--- a/src/hb-ot-layout-private.hh
+++ b/src/hb-ot-layout-private.hh
@@ -80,10 +80,10 @@ struct _hb_ot_layout_context_t
};
-void
+HB_INTERNAL void
_hb_ot_layout_init (hb_face_t *face);
-void
+HB_INTERNAL void
_hb_ot_layout_fini (hb_face_t *face);
diff --git a/src/hb-private.h b/src/hb-private.h
index 7e292dc..03c53fb 100644
--- a/src/hb-private.h
+++ b/src/hb-private.h
@@ -66,10 +66,6 @@
#undef MAX
#define MAX(a,b) ((a) > (b) ? (a) : (b))
-#ifndef HB_INTERNAL
-# define HB_INTERNAL extern
-#endif
-
#undef ARRAY_LENGTH
#define ARRAY_LENGTH(__array) ((signed int) (sizeof (__array) / sizeof (__array[0])))
@@ -111,6 +107,10 @@
#define HB_UNUSED
#endif
+#ifndef HB_INTERNAL
+# define HB_INTERNAL extern __attribute__((__visibility__("hidden")))
+#endif
+
#if (defined(__WIN32__) && !defined(__WINE__)) || defined(_MSC_VER)
#define snprintf _snprintf
commit 8951fc2c82f2db4865da6d9e303fce419b6363bb
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Wed May 12 23:13:39 2010 -0400
Add buffer->allocate_lig_id()
diff --git a/src/hb-buffer-private.hh b/src/hb-buffer-private.hh
index 1a3ac70..c8859c8 100644
--- a/src/hb-buffer-private.hh
+++ b/src/hb-buffer-private.hh
@@ -89,6 +89,8 @@ struct _hb_buffer_t {
/* Other stuff */
unsigned int max_lig_id;
+
+ inline unsigned int allocate_lig_id (void) { return max_lig_id++; }
};
@@ -127,9 +129,6 @@ HB_INTERNAL void
_hb_buffer_replace_glyph (hb_buffer_t *buffer,
hb_codepoint_t glyph_index);
-HB_INTERNAL unsigned short
-_hb_buffer_allocate_lig_id (hb_buffer_t *buffer);
-
#ifndef BUFFER
#define BUFFER buffer
diff --git a/src/hb-buffer.cc b/src/hb-buffer.cc
index 9588d5e..de7a2eb 100644
--- a/src/hb-buffer.cc
+++ b/src/hb-buffer.cc
@@ -450,12 +450,6 @@ _hb_buffer_replace_glyph (hb_buffer_t *buffer,
_hb_buffer_add_output_glyph (buffer, glyph_index, 0xFFFF, 0xFFFF);
}
-unsigned short
-_hb_buffer_allocate_lig_id (hb_buffer_t *buffer)
-{
- return ++buffer->max_lig_id;
-}
-
unsigned int
hb_buffer_get_length (hb_buffer_t *buffer)
diff --git a/src/hb-ot-layout-gsub-private.hh b/src/hb-ot-layout-gsub-private.hh
index 849a20c..38364a5 100644
--- a/src/hb-ot-layout-gsub-private.hh
+++ b/src/hb-ot-layout-gsub-private.hh
@@ -404,10 +404,10 @@ struct Ligature
1, (const uint16_t *) &ligGlyph,
0,
IN_LIGID (context->buffer->in_pos) && !IN_COMPONENT (context->buffer->in_pos) ?
- 0xFFFF : _hb_buffer_allocate_lig_id (context->buffer));
+ 0xFFFF : context->buffer->allocate_lig_id ());
else
{
- unsigned int lig_id = _hb_buffer_allocate_lig_id (context->buffer);
+ unsigned int lig_id = context->buffer->allocate_lig_id ();
_hb_buffer_add_output_glyph (context->buffer, ligGlyph, 0xFFFF, lig_id);
/* Now we must do a second loop to copy the skipped glyphs to
commit 1ce4dc95dbb28842085342aea4f9d12cbe9671a9
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Wed May 12 18:29:25 2010 -0400
Use bit tricks for HB_DIRECTION_IS_*
We already depend on the exact values of the direction enum
in HB_DIRECTION_REVERSE(), so we may as well use that.
diff --git a/src/hb-common.h b/src/hb-common.h
index cc673ad..f64d6cc 100644
--- a/src/hb-common.h
+++ b/src/hb-common.h
@@ -79,10 +79,10 @@ typedef enum _hb_direction_t {
HB_DIRECTION_BTT
} hb_direction_t;
-#define HB_DIRECTION_IS_HORIZONTAL(dir) ((dir) == HB_DIRECTION_LTR || (dir) == HB_DIRECTION_RTL)
-#define HB_DIRECTION_IS_VERTICAL(dir) ((dir) == HB_DIRECTION_TTB || (dir) == HB_DIRECTION_BTT)
-#define HB_DIRECTION_IS_FORWARD(dir) ((dir) == HB_DIRECTION_LTR || (dir) == HB_DIRECTION_TTB)
-#define HB_DIRECTION_IS_BACKWARD(dir) ((dir) == HB_DIRECTION_RTL || (dir) == HB_DIRECTION_BTT)
+#define HB_DIRECTION_IS_HORIZONTAL(dir) ((((unsigned int) (dir)) & ~1U) == 0)
+#define HB_DIRECTION_IS_VERTICAL(dir) ((((unsigned int) (dir)) & ~1U) == 2)
+#define HB_DIRECTION_IS_FORWARD(dir) ((((unsigned int) (dir)) & ~2U) == 0)
+#define HB_DIRECTION_IS_BACKWARD(dir) ((((unsigned int) (dir)) & ~2U) == 1)
#define HB_DIRECTION_REVERSE(dir) ((hb_direction_t) (((unsigned int) (dir)) ^ 1))
commit 22da7fd94d6318c52df69d70470a85464ffc533d
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Wed May 12 18:23:21 2010 -0400
Rename a few files to be C++ sources
In anticipation for buffer revamp coming.
diff --git a/src/Makefile.am b/src/Makefile.am
index 7b10fe2..9c534a6 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -12,16 +12,16 @@ HBLIBS =
HBSOURCES = \
hb-blob.c \
hb-blob-private.h \
- hb-buffer.c \
- hb-buffer-private.h \
+ hb-buffer.cc \
+ hb-buffer-private.hh \
hb-font.cc \
- hb-font-private.h \
+ hb-font-private.hh \
hb-object-private.h \
hb-open-file-private.hh \
hb-open-type-private.hh \
hb-language.c \
hb-private.h \
- hb-shape.c \
+ hb-shape.cc \
hb-unicode.c \
hb-unicode-private.h \
$(NULL)
@@ -43,9 +43,9 @@ HBSOURCES += \
hb-ot-layout-gpos-private.hh \
hb-ot-layout-gsubgpos-private.hh \
hb-ot-layout-gsub-private.hh \
- hb-ot-layout-private.h \
- hb-ot-shape.c \
- hb-ot-shape-private.h \
+ hb-ot-layout-private.hh \
+ hb-ot-shape.cc \
+ hb-ot-shape-private.hh \
hb-ot-tag.c \
$(NULL)
HBHEADERS += \
@@ -80,7 +80,7 @@ if HAVE_FREETYPE
HBCFLAGS += $(FREETYPE_CFLAGS)
HBLIBS += $(FREETYPE_LIBS)
HBSOURCES += \
- hb-ft.c \
+ hb-ft.cc \
$(NULL)
HBHEADERS += \
hb-ft.h \
diff --git a/src/hb-buffer-private.h b/src/hb-buffer-private.h
deleted file mode 100644
index bc562ba..0000000
--- a/src/hb-buffer-private.h
+++ /dev/null
@@ -1,155 +0,0 @@
-/*
- * Copyright (C) 1998-2004 David Turner and Werner Lemberg
- * Copyright (C) 2004,2007,2009 Red Hat, Inc.
- *
- * This is part of HarfBuzz, a text shaping library.
- *
- * Permission is hereby granted, without written agreement and without
- * license or royalty fees, to use, copy, modify, and distribute this
- * software and its documentation for any purpose, provided that the
- * above copyright notice and the following two paragraphs appear in
- * all copies of this software.
- *
- * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
- * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
- * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
- * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
- * DAMAGE.
- *
- * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
- * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
- * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
- * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
- * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
- *
- * Red Hat Author(s): Owen Taylor, Behdad Esfahbod
- */
-
-#ifndef HB_BUFFER_PRIVATE_H
-#define HB_BUFFER_PRIVATE_H
-
-#include "hb-private.h"
-#include "hb-buffer.h"
-#include "hb-unicode-private.h"
-
-HB_BEGIN_DECLS
-
-#define HB_BUFFER_GLYPH_PROPERTIES_UNKNOWN 0xFFFF
-
-
-typedef struct _hb_internal_glyph_info_t {
- hb_codepoint_t codepoint;
- hb_mask_t mask;
- uint32_t cluster;
- uint16_t component;
- uint16_t lig_id;
- uint32_t gproperty;
-} hb_internal_glyph_info_t;
-
-typedef struct _hb_internal_glyph_position_t {
- hb_position_t x_advance;
- hb_position_t y_advance;
- hb_position_t x_offset;
- hb_position_t y_offset;
- uint32_t back : 16; /* number of glyphs to go back
- for drawing current glyph */
- int32_t cursive_chain : 16; /* character to which this connects,
- may be positive or negative */
-} hb_internal_glyph_position_t;
-
-ASSERT_STATIC (sizeof (hb_glyph_info_t) == sizeof (hb_internal_glyph_info_t));
-ASSERT_STATIC (sizeof (hb_glyph_position_t) == sizeof (hb_internal_glyph_position_t));
-ASSERT_STATIC (sizeof (hb_glyph_info_t) == sizeof (hb_glyph_position_t));
-
-
-struct _hb_buffer_t {
- hb_reference_count_t ref_count;
-
- /* Information about how the text in the buffer should be treated */
- hb_unicode_funcs_t *unicode;
- hb_direction_t direction;
- hb_script_t script;
- hb_language_t language;
-
- /* Buffer contents */
-
- unsigned int allocated;
-
- hb_bool_t have_output; /* whether we have an output buffer going on */
- hb_bool_t have_positions; /* whether we have positions */
- unsigned int in_length;
- unsigned int out_length;
- unsigned int in_pos;
- unsigned int out_pos; /* out_length and out_pos are actually always the same */
-
- hb_internal_glyph_info_t *in_string;
- hb_internal_glyph_info_t *out_string;
- hb_internal_glyph_position_t *positions;
-
- /* Other stuff */
-
- unsigned int max_lig_id;
-};
-
-
-HB_INTERNAL void
-_hb_buffer_swap (hb_buffer_t *buffer);
-
-HB_INTERNAL void
-_hb_buffer_clear_output (hb_buffer_t *buffer);
-
-HB_INTERNAL void
-_hb_buffer_add_output_glyphs (hb_buffer_t *buffer,
- unsigned int num_in,
- unsigned int num_out,
- const hb_codepoint_t *glyph_data,
- unsigned short component,
- unsigned short ligID);
-
-HB_INTERNAL void
-_hb_buffer_add_output_glyphs_be16 (hb_buffer_t *buffer,
- unsigned int num_in,
- unsigned int num_out,
- const uint16_t *glyph_data_be,
- unsigned short component,
- unsigned short ligID);
-
-HB_INTERNAL void
-_hb_buffer_add_output_glyph (hb_buffer_t *buffer,
- hb_codepoint_t glyph_index,
- unsigned short component,
- unsigned short ligID);
-
-HB_INTERNAL void
-_hb_buffer_next_glyph (hb_buffer_t *buffer);
-
-HB_INTERNAL void
-_hb_buffer_replace_glyph (hb_buffer_t *buffer,
- hb_codepoint_t glyph_index);
-
-HB_INTERNAL unsigned short
-_hb_buffer_allocate_lig_id (hb_buffer_t *buffer);
-
-
-#ifndef BUFFER
-#define BUFFER buffer
-#endif
-
-/* convenience macros */
-#define IN_GLYPH(pos) (BUFFER->in_string[(pos)].codepoint)
-#define IN_INFO(pos) (&BUFFER->in_string[(pos)])
-#define IN_CURGLYPH() (BUFFER->in_string[BUFFER->in_pos].codepoint)
-#define IN_NEXTGLYPH() (BUFFER->in_string[BUFFER->in_pos + 1].codepoint)
-#define IN_CURINFO() (&BUFFER->in_string[BUFFER->in_pos])
-#define IN_MASK(pos) (BUFFER->in_string[(pos)].mask)
-#define IN_CLUSTER(pos) (BUFFER->in_string[(pos)].cluster)
-#define IN_LIGID(pos) (BUFFER->in_string[(pos)].lig_id)
-#define IN_COMPONENT(pos) (BUFFER->in_string[(pos)].component)
-#define POSITION(pos) (&BUFFER->positions[(pos)])
-#define CURPOSITION() (&BUFFER->positions[BUFFER->in_pos])
-#define OUT_GLYPH(pos) (BUFFER->out_string[(pos)].codepoint)
-#define OUT_INFO(pos) (&BUFFER->out_string[(pos)])
-
-HB_END_DECLS
-
-#endif /* HB_BUFFER_PRIVATE_H */
diff --git a/src/hb-buffer-private.hh b/src/hb-buffer-private.hh
new file mode 100644
index 0000000..1a3ac70
--- /dev/null
+++ b/src/hb-buffer-private.hh
@@ -0,0 +1,155 @@
+/*
+ * Copyright (C) 1998-2004 David Turner and Werner Lemberg
+ * Copyright (C) 2004,2007,2009,2010 Red Hat, Inc.
+ *
+ * This is part of HarfBuzz, a text shaping library.
+ *
+ * Permission is hereby granted, without written agreement and without
+ * license or royalty fees, to use, copy, modify, and distribute this
+ * software and its documentation for any purpose, provided that the
+ * above copyright notice and the following two paragraphs appear in
+ * all copies of this software.
+ *
+ * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
+ * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
+ * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
+ * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
+ * DAMAGE.
+ *
+ * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
+ * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
+ * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
+ * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
+ *
+ * Red Hat Author(s): Owen Taylor, Behdad Esfahbod
+ */
+
+#ifndef HB_BUFFER_PRIVATE_H
+#define HB_BUFFER_PRIVATE_H
+
+#include "hb-private.h"
+#include "hb-buffer.h"
+#include "hb-unicode-private.h"
+
+HB_BEGIN_DECLS
+
+#define HB_BUFFER_GLYPH_PROPERTIES_UNKNOWN 0xFFFF
+
+
+typedef struct _hb_internal_glyph_info_t {
+ hb_codepoint_t codepoint;
+ hb_mask_t mask;
+ uint32_t cluster;
+ uint16_t component;
+ uint16_t lig_id;
+ uint32_t gproperty;
+} hb_internal_glyph_info_t;
+
+typedef struct _hb_internal_glyph_position_t {
+ hb_position_t x_advance;
+ hb_position_t y_advance;
+ hb_position_t x_offset;
+ hb_position_t y_offset;
+ uint32_t back : 16; /* number of glyphs to go back
+ for drawing current glyph */
+ int32_t cursive_chain : 16; /* character to which this connects,
+ may be positive or negative */
+} hb_internal_glyph_position_t;
+
+ASSERT_STATIC (sizeof (hb_glyph_info_t) == sizeof (hb_internal_glyph_info_t));
+ASSERT_STATIC (sizeof (hb_glyph_position_t) == sizeof (hb_internal_glyph_position_t));
+ASSERT_STATIC (sizeof (hb_glyph_info_t) == sizeof (hb_glyph_position_t));
+
+
+struct _hb_buffer_t {
+ hb_reference_count_t ref_count;
+
+ /* Information about how the text in the buffer should be treated */
+ hb_unicode_funcs_t *unicode;
+ hb_direction_t direction;
+ hb_script_t script;
+ hb_language_t language;
+
+ /* Buffer contents */
+
+ unsigned int allocated;
+
+ hb_bool_t have_output; /* whether we have an output buffer going on */
+ hb_bool_t have_positions; /* whether we have positions */
+ unsigned int in_length;
+ unsigned int out_length;
+ unsigned int in_pos;
+ unsigned int out_pos; /* out_length and out_pos are actually always the same */
+
+ hb_internal_glyph_info_t *in_string;
+ hb_internal_glyph_info_t *out_string;
+ hb_internal_glyph_position_t *positions;
+
+ /* Other stuff */
+
+ unsigned int max_lig_id;
+};
+
+
+HB_INTERNAL void
+_hb_buffer_swap (hb_buffer_t *buffer);
+
+HB_INTERNAL void
+_hb_buffer_clear_output (hb_buffer_t *buffer);
+
+HB_INTERNAL void
+_hb_buffer_add_output_glyphs (hb_buffer_t *buffer,
+ unsigned int num_in,
+ unsigned int num_out,
+ const hb_codepoint_t *glyph_data,
+ unsigned short component,
+ unsigned short ligID);
+
+HB_INTERNAL void
+_hb_buffer_add_output_glyphs_be16 (hb_buffer_t *buffer,
+ unsigned int num_in,
+ unsigned int num_out,
+ const uint16_t *glyph_data_be,
+ unsigned short component,
+ unsigned short ligID);
+
+HB_INTERNAL void
+_hb_buffer_add_output_glyph (hb_buffer_t *buffer,
+ hb_codepoint_t glyph_index,
+ unsigned short component,
+ unsigned short ligID);
+
+HB_INTERNAL void
+_hb_buffer_next_glyph (hb_buffer_t *buffer);
+
+HB_INTERNAL void
+_hb_buffer_replace_glyph (hb_buffer_t *buffer,
+ hb_codepoint_t glyph_index);
+
+HB_INTERNAL unsigned short
+_hb_buffer_allocate_lig_id (hb_buffer_t *buffer);
+
+
+#ifndef BUFFER
+#define BUFFER buffer
+#endif
+
+/* convenience macros */
+#define IN_GLYPH(pos) (BUFFER->in_string[(pos)].codepoint)
+#define IN_INFO(pos) (&BUFFER->in_string[(pos)])
+#define IN_CURGLYPH() (BUFFER->in_string[BUFFER->in_pos].codepoint)
+#define IN_NEXTGLYPH() (BUFFER->in_string[BUFFER->in_pos + 1].codepoint)
+#define IN_CURINFO() (&BUFFER->in_string[BUFFER->in_pos])
+#define IN_MASK(pos) (BUFFER->in_string[(pos)].mask)
+#define IN_CLUSTER(pos) (BUFFER->in_string[(pos)].cluster)
+#define IN_LIGID(pos) (BUFFER->in_string[(pos)].lig_id)
+#define IN_COMPONENT(pos) (BUFFER->in_string[(pos)].component)
+#define POSITION(pos) (&BUFFER->positions[(pos)])
+#define CURPOSITION() (&BUFFER->positions[BUFFER->in_pos])
+#define OUT_GLYPH(pos) (BUFFER->out_string[(pos)].codepoint)
+#define OUT_INFO(pos) (&BUFFER->out_string[(pos)])
+
+HB_END_DECLS
+
+#endif /* HB_BUFFER_PRIVATE_H */
diff --git a/src/hb-buffer.c b/src/hb-buffer.c
deleted file mode 100644
index adec7c1..0000000
--- a/src/hb-buffer.c
+++ /dev/null
@@ -1,650 +0,0 @@
-/*
- * Copyright (C) 1998-2004 David Turner and Werner Lemberg
- * Copyright (C) 2004,2007 Red Hat, Inc.
- *
- * This is part of HarfBuzz, a text shaping library.
- *
- * Permission is hereby granted, without written agreement and without
- * license or royalty fees, to use, copy, modify, and distribute this
- * software and its documentation for any purpose, provided that the
- * above copyright notice and the following two paragraphs appear in
- * all copies of this software.
- *
- * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
- * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
- * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
- * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
- * DAMAGE.
- *
- * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
- * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
- * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
- * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
- * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
- *
- * Red Hat Author(s): Owen Taylor, Behdad Esfahbod
- */
-
-#include "hb-buffer-private.h"
-
-#include <string.h>
-
-
-static hb_buffer_t _hb_buffer_nil = {
- HB_REFERENCE_COUNT_INVALID, /* ref_count */
-
- &_hb_unicode_funcs_nil /* unicode */
-};
-
-/* Here is how the buffer works internally:
- *
- * There are two string pointers: in_string and out_string. They
- * always have same allocated size, but different length and positions.
- *
- * As an optimization, both in_string and out_string may point to the
- * same piece of memory, which is owned by in_string. This remains the
- * case as long as out_length doesn't exceed in_length at any time.
- * In that case, swap() is no-op and the glyph operations operate mostly
- * in-place.
- *
- * As soon as out_string gets longer than in_string, out_string is moved over
- * to an alternate buffer (which we reuse the positions buffer for!), and its
- * current contents (out_length entries) are copied to the alt buffer.
- * This should all remain transparent to the user. swap() then switches
- * in_string and out_string.
- */
-
-/* XXX err handling */
-
-/* Internal API */
-
-static void
-hb_buffer_ensure_separate (hb_buffer_t *buffer, unsigned int size)
-{
- hb_buffer_ensure (buffer, size);
- if (buffer->out_string == buffer->in_string)
- {
- assert (buffer->have_output);
- if (!buffer->positions)
- buffer->positions = calloc (buffer->allocated, sizeof (buffer->positions[0]));
-
- buffer->out_string = (hb_internal_glyph_info_t *) buffer->positions;
- memcpy (buffer->out_string, buffer->in_string, buffer->out_length * sizeof (buffer->out_string[0]));
- }
-}
-
-/* Public API */
-
-hb_buffer_t *
-hb_buffer_create (unsigned int pre_alloc_size)
-{
- hb_buffer_t *buffer;
-
- if (!HB_OBJECT_DO_CREATE (hb_buffer_t, buffer))
- return &_hb_buffer_nil;
-
- if (pre_alloc_size)
- hb_buffer_ensure(buffer, pre_alloc_size);
-
- buffer->unicode = &_hb_unicode_funcs_nil;
-
- return buffer;
-}
-
-hb_buffer_t *
-hb_buffer_reference (hb_buffer_t *buffer)
-{
- HB_OBJECT_DO_REFERENCE (buffer);
-}
-
-unsigned int
-hb_buffer_get_reference_count (hb_buffer_t *buffer)
-{
- HB_OBJECT_DO_GET_REFERENCE_COUNT (buffer);
-}
-
-void
-hb_buffer_destroy (hb_buffer_t *buffer)
-{
- HB_OBJECT_DO_DESTROY (buffer);
-
- hb_unicode_funcs_destroy (buffer->unicode);
-
- free (buffer->in_string);
- free (buffer->positions);
-
- free (buffer);
-}
-
-
-void
-hb_buffer_set_unicode_funcs (hb_buffer_t *buffer,
- hb_unicode_funcs_t *unicode)
-{
- if (!unicode)
- unicode = &_hb_unicode_funcs_nil;
-
- hb_unicode_funcs_reference (unicode);
- hb_unicode_funcs_destroy (buffer->unicode);
- buffer->unicode = unicode;
-}
-
-hb_unicode_funcs_t *
-hb_buffer_get_unicode_funcs (hb_buffer_t *buffer)
-{
- return buffer->unicode;
-}
-
-void
-hb_buffer_set_direction (hb_buffer_t *buffer,
- hb_direction_t direction)
-
-{
- buffer->direction = direction;
-}
-
-hb_direction_t
-hb_buffer_get_direction (hb_buffer_t *buffer)
-{
- return buffer->direction;
-}
-
-void
-hb_buffer_set_script (hb_buffer_t *buffer,
- hb_script_t script)
-{
- buffer->script = script;
-}
-
-hb_script_t
-hb_buffer_get_script (hb_buffer_t *buffer)
-{
- return buffer->script;
-}
-
-void
-hb_buffer_set_language (hb_buffer_t *buffer,
- hb_language_t language)
-{
- buffer->language = language;
-}
-
-hb_language_t
-hb_buffer_get_language (hb_buffer_t *buffer)
-{
- return buffer->language;
-}
-
-
-void
-hb_buffer_clear (hb_buffer_t *buffer)
-{
- buffer->have_output = FALSE;
- buffer->have_positions = FALSE;
- buffer->in_length = 0;
- buffer->out_length = 0;
- buffer->in_pos = 0;
- buffer->out_pos = 0;
- buffer->out_string = buffer->in_string;
- buffer->max_lig_id = 0;
-}
-
-void
-hb_buffer_ensure (hb_buffer_t *buffer, unsigned int size)
-{
- unsigned int new_allocated = buffer->allocated;
-
- if (size > new_allocated)
- {
- while (size > new_allocated)
- new_allocated += (new_allocated >> 1) + 8;
-
- if (buffer->positions)
- buffer->positions = realloc (buffer->positions, new_allocated * sizeof (buffer->positions[0]));
-
- if (buffer->out_string != buffer->in_string)
- {
- buffer->in_string = realloc (buffer->in_string, new_allocated * sizeof (buffer->in_string[0]));
- buffer->out_string = (hb_internal_glyph_info_t *) buffer->positions;
- }
- else
- {
- buffer->in_string = realloc (buffer->in_string, new_allocated * sizeof (buffer->in_string[0]));
- buffer->out_string = buffer->in_string;
- }
-
- buffer->allocated = new_allocated;
- }
-}
-
-void
-hb_buffer_add_glyph (hb_buffer_t *buffer,
- hb_codepoint_t codepoint,
- hb_mask_t mask,
- unsigned int cluster)
-{
- hb_internal_glyph_info_t *glyph;
-
- hb_buffer_ensure (buffer, buffer->in_length + 1);
-
- glyph = &buffer->in_string[buffer->in_length];
- glyph->codepoint = codepoint;
- glyph->mask = mask;
- glyph->cluster = cluster;
- glyph->component = 0;
- glyph->lig_id = 0;
- glyph->gproperty = HB_BUFFER_GLYPH_PROPERTIES_UNKNOWN;
-
- buffer->in_length++;
-}
-
-
-/* HarfBuzz-Internal API */
-
-void
-_hb_buffer_clear_output (hb_buffer_t *buffer)
-{
- buffer->have_output = TRUE;
- buffer->have_positions = FALSE;
- buffer->out_length = 0;
- buffer->out_pos = 0;
- buffer->out_string = buffer->in_string;
-}
-
-void
-hb_buffer_clear_positions (hb_buffer_t *buffer)
-{
- _hb_buffer_clear_output (buffer);
- buffer->have_output = FALSE;
- buffer->have_positions = TRUE;
-
- if (unlikely (!buffer->positions))
- {
- buffer->positions = calloc (buffer->allocated, sizeof (buffer->positions[0]));
- return;
- }
-
- memset (buffer->positions, 0, sizeof (buffer->positions[0]) * buffer->in_length);
-}
-
-void
-_hb_buffer_swap (hb_buffer_t *buffer)
-{
- unsigned int tmp;
-
- assert (buffer->have_output);
-
- if (buffer->out_string != buffer->in_string)
- {
- hb_internal_glyph_info_t *tmp_string;
- tmp_string = buffer->in_string;
- buffer->in_string = buffer->out_string;
- buffer->out_string = tmp_string;
- buffer->positions = (hb_internal_glyph_position_t *) buffer->out_string;
- }
-
- tmp = buffer->in_length;
- buffer->in_length = buffer->out_length;
- buffer->out_length = tmp;
-
- tmp = buffer->in_pos;
- buffer->in_pos = buffer->out_pos;
- buffer->out_pos = tmp;
-}
-
-/* The following function copies `num_out' elements from `glyph_data'
- to `buffer->out_string', advancing the in array pointer in the structure
- by `num_in' elements, and the out array pointer by `num_out' elements.
- Finally, it sets the `length' field of `out' equal to
- `pos' of the `out' structure.
-
- If `component' is 0xFFFF, the component value from buffer->in_pos
- will copied `num_out' times, otherwise `component' itself will
- be used to fill the `component' fields.
-
- If `lig_id' is 0xFFFF, the lig_id value from buffer->in_pos
- will copied `num_out' times, otherwise `lig_id' itself will
- be used to fill the `lig_id' fields.
-
- The mask for all replacement glyphs are taken
- from the glyph at position `buffer->in_pos'.
-
- The cluster value for the glyph at position buffer->in_pos is used
- for all replacement glyphs */
-
-void
-_hb_buffer_add_output_glyphs (hb_buffer_t *buffer,
- unsigned int num_in,
- unsigned int num_out,
- const hb_codepoint_t *glyph_data,
- unsigned short component,
- unsigned short lig_id)
-{
- unsigned int i;
- unsigned int mask;
- unsigned int cluster;
-
- if (buffer->out_string != buffer->in_string ||
- buffer->out_pos + num_out > buffer->in_pos + num_in)
- {
- hb_buffer_ensure_separate (buffer, buffer->out_pos + num_out);
- }
-
- mask = buffer->in_string[buffer->in_pos].mask;
- cluster = buffer->in_string[buffer->in_pos].cluster;
- if (component == 0xFFFF)
- component = buffer->in_string[buffer->in_pos].component;
- if (lig_id == 0xFFFF)
- lig_id = buffer->in_string[buffer->in_pos].lig_id;
-
- for (i = 0; i < num_out; i++)
- {
- hb_internal_glyph_info_t *info = &buffer->out_string[buffer->out_pos + i];
- info->codepoint = glyph_data[i];
- info->mask = mask;
- info->cluster = cluster;
- info->component = component;
- info->lig_id = lig_id;
- info->gproperty = HB_BUFFER_GLYPH_PROPERTIES_UNKNOWN;
- }
-
- buffer->in_pos += num_in;
- buffer->out_pos += num_out;
- buffer->out_length = buffer->out_pos;
-}
-
-void
-_hb_buffer_add_output_glyphs_be16 (hb_buffer_t *buffer,
- unsigned int num_in,
- unsigned int num_out,
- const uint16_t *glyph_data_be,
- unsigned short component,
- unsigned short lig_id)
-{
- unsigned int i;
- unsigned int mask;
- unsigned int cluster;
-
- if (buffer->out_string != buffer->in_string ||
- buffer->out_pos + num_out > buffer->in_pos + num_in)
- {
- hb_buffer_ensure_separate (buffer, buffer->out_pos + num_out);
- }
-
- mask = buffer->in_string[buffer->in_pos].mask;
- cluster = buffer->in_string[buffer->in_pos].cluster;
- if (component == 0xFFFF)
- component = buffer->in_string[buffer->in_pos].component;
- if (lig_id == 0xFFFF)
- lig_id = buffer->in_string[buffer->in_pos].lig_id;
-
- for (i = 0; i < num_out; i++)
- {
- hb_internal_glyph_info_t *info = &buffer->out_string[buffer->out_pos + i];
- info->codepoint = hb_be_uint16 (glyph_data_be[i]);
- info->mask = mask;
- info->cluster = cluster;
- info->component = component;
- info->lig_id = lig_id;
- info->gproperty = HB_BUFFER_GLYPH_PROPERTIES_UNKNOWN;
- }
-
- buffer->in_pos += num_in;
- buffer->out_pos += num_out;
- buffer->out_length = buffer->out_pos;
-}
-
-void
-_hb_buffer_add_output_glyph (hb_buffer_t *buffer,
- hb_codepoint_t glyph_index,
- unsigned short component,
- unsigned short lig_id)
-{
- hb_internal_glyph_info_t *info;
-
- if (buffer->out_string != buffer->in_string)
- {
- hb_buffer_ensure (buffer, buffer->out_pos + 1);
- buffer->out_string[buffer->out_pos] = buffer->in_string[buffer->in_pos];
- }
- else if (buffer->out_pos != buffer->in_pos)
- buffer->out_string[buffer->out_pos] = buffer->in_string[buffer->in_pos];
-
- info = &buffer->out_string[buffer->out_pos];
- info->codepoint = glyph_index;
- if (component != 0xFFFF)
- info->component = component;
- if (lig_id != 0xFFFF)
- info->lig_id = lig_id;
- info->gproperty = HB_BUFFER_GLYPH_PROPERTIES_UNKNOWN;
-
- buffer->in_pos++;
- buffer->out_pos++;
- buffer->out_length = buffer->out_pos;
-}
-
-void
-_hb_buffer_next_glyph (hb_buffer_t *buffer)
-{
- if (buffer->have_output)
- {
- if (buffer->out_string != buffer->in_string)
- {
- hb_buffer_ensure (buffer, buffer->out_pos + 1);
- buffer->out_string[buffer->out_pos] = buffer->in_string[buffer->in_pos];
- }
- else if (buffer->out_pos != buffer->in_pos)
- buffer->out_string[buffer->out_pos] = buffer->in_string[buffer->in_pos];
-
- buffer->out_pos++;
- buffer->out_length = buffer->out_pos;
- }
-
- buffer->in_pos++;
-}
-
-void
-_hb_buffer_replace_glyph (hb_buffer_t *buffer,
- hb_codepoint_t glyph_index)
-{
- _hb_buffer_add_output_glyph (buffer, glyph_index, 0xFFFF, 0xFFFF);
-}
-
-unsigned short
-_hb_buffer_allocate_lig_id (hb_buffer_t *buffer)
-{
- return ++buffer->max_lig_id;
-}
-
-
-unsigned int
-hb_buffer_get_length (hb_buffer_t *buffer)
-{
- return buffer->in_length;
-}
-
-/* Return value valid as long as buffer not modified */
-hb_glyph_info_t *
-hb_buffer_get_glyph_infos (hb_buffer_t *buffer)
-{
- return (hb_glyph_info_t *) buffer->in_string;
-}
-
-/* Return value valid as long as buffer not modified */
-hb_glyph_position_t *
-hb_buffer_get_glyph_positions (hb_buffer_t *buffer)
-{
- if (!buffer->have_positions)
- hb_buffer_clear_positions (buffer);
-
- return (hb_glyph_position_t *) buffer->positions;
-}
-
-
-static void
-reverse_range (hb_buffer_t *buffer,
- unsigned int start,
- unsigned int end)
-{
- unsigned int i, j;
-
- for (i = start, j = end - 1; i < j; i++, j--) {
- hb_internal_glyph_info_t t;
-
- t = buffer->in_string[i];
- buffer->in_string[i] = buffer->in_string[j];
- buffer->in_string[j] = t;
- }
-
- if (buffer->positions) {
- for (i = 0, j = end - 1; i < j; i++, j--) {
- hb_internal_glyph_position_t t;
-
- t = buffer->positions[i];
- buffer->positions[i] = buffer->positions[j];
- buffer->positions[j] = t;
- }
- }
-}
-
-void
-hb_buffer_reverse (hb_buffer_t *buffer)
-{
- if (unlikely (!buffer->in_length))
- return;
-
- reverse_range (buffer, 0, buffer->in_length);
-}
-
-void
-hb_buffer_reverse_clusters (hb_buffer_t *buffer)
-{
- unsigned int i, start, count, last_cluster;
-
- if (unlikely (!buffer->in_length))
- return;
-
- hb_buffer_reverse (buffer);
-
- count = buffer->in_length;
- start = 0;
- last_cluster = buffer->in_string[0].cluster;
- for (i = 1; i < count; i++) {
- if (last_cluster != buffer->in_string[i].cluster) {
- reverse_range (buffer, start, i);
- start = i;
- last_cluster = buffer->in_string[i].cluster;
- }
- }
- reverse_range (buffer, start, i);
-}
-
-
-#define ADD_UTF(T) \
- HB_STMT_START { \
- const T *next = (const T *) text + item_offset; \
- const T *end = next + item_length; \
- while (next < end) { \
- hb_codepoint_t u; \
- const T *old_next = next; \
- next = UTF_NEXT (next, end, u); \
- hb_buffer_add_glyph (buffer, u, 0, old_next - (const T *) text); \
- } \
- } HB_STMT_END
-
-
-#define UTF8_COMPUTE(Char, Mask, Len) \
- if (Char < 128) { Len = 1; Mask = 0x7f; } \
- else if ((Char & 0xe0) == 0xc0) { Len = 2; Mask = 0x1f; } \
- else if ((Char & 0xf0) == 0xe0) { Len = 3; Mask = 0x0f; } \
- else if ((Char & 0xf8) == 0xf0) { Len = 4; Mask = 0x07; } \
- else Len = 0;
-
-static inline const uint8_t *
-hb_utf8_next (const uint8_t *text,
- const uint8_t *end,
- hb_codepoint_t *unicode)
-{
- uint8_t c = *text;
- unsigned int mask, len;
-
- UTF8_COMPUTE (c, mask, len);
- if (unlikely (!len || (unsigned int) (end - text) < len)) {
- *unicode = -1;
- return text + 1;
- } else {
- hb_codepoint_t result;
- unsigned int i;
- result = c & mask;
- for (i = 1; i < len; i++)
- {
- if (unlikely ((text[i] & 0xc0) != 0x80))
- {
- *unicode = -1;
- return text + 1;
- }
- result <<= 6;
- result |= (text[i] & 0x3f);
- }
- *unicode = result;
- return text + len;
- }
-}
-
-void
-hb_buffer_add_utf8 (hb_buffer_t *buffer,
- const char *text,
- unsigned int text_length HB_UNUSED,
- unsigned int item_offset,
- unsigned int item_length)
-{
-#define UTF_NEXT(S, E, U) hb_utf8_next (S, E, &(U))
- ADD_UTF (uint8_t);
-#undef UTF_NEXT
-}
-
-static inline const uint16_t *
-hb_utf16_next (const uint16_t *text,
- const uint16_t *end,
- hb_codepoint_t *unicode)
-{
- uint16_t c = *text++;
-
- if (unlikely (c >= 0xd800 && c < 0xdc00)) {
- /* high surrogate */
- uint16_t l;
- if (text < end && ((l = *text), unlikely (l >= 0xdc00 && l < 0xe000))) {
- /* low surrogate */
- *unicode = ((hb_codepoint_t) ((c) - 0xd800) * 0x400 + (l) - 0xdc00 + 0x10000);
- text++;
- } else
- *unicode = -1;
- } else
- *unicode = c;
-
- return text;
-}
-
-void
-hb_buffer_add_utf16 (hb_buffer_t *buffer,
- const uint16_t *text,
- unsigned int text_length HB_UNUSED,
- unsigned int item_offset,
- unsigned int item_length)
-{
-#define UTF_NEXT(S, E, U) hb_utf16_next (S, E, &(U))
- ADD_UTF (uint16_t);
-#undef UTF_NEXT
-}
-
-void
-hb_buffer_add_utf32 (hb_buffer_t *buffer,
- const uint32_t *text,
- unsigned int text_length HB_UNUSED,
- unsigned int item_offset,
- unsigned int item_length)
-{
-#define UTF_NEXT(S, E, U) ((U) = *(S), (S)+1)
- ADD_UTF (uint32_t);
-#undef UTF_NEXT
-}
diff --git a/src/hb-buffer.cc b/src/hb-buffer.cc
new file mode 100644
index 0000000..9588d5e
--- /dev/null
+++ b/src/hb-buffer.cc
@@ -0,0 +1,650 @@
+/*
+ * Copyright (C) 1998-2004 David Turner and Werner Lemberg
+ * Copyright (C) 2004,2007,2009,2010 Red Hat, Inc.
+ *
+ * This is part of HarfBuzz, a text shaping library.
+ *
+ * Permission is hereby granted, without written agreement and without
+ * license or royalty fees, to use, copy, modify, and distribute this
+ * software and its documentation for any purpose, provided that the
+ * above copyright notice and the following two paragraphs appear in
+ * all copies of this software.
+ *
+ * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
+ * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
+ * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
+ * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
+ * DAMAGE.
+ *
+ * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
+ * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
+ * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
+ * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
+ *
+ * Red Hat Author(s): Owen Taylor, Behdad Esfahbod
+ */
+
+#include "hb-buffer-private.hh"
+
+#include <string.h>
+
+
+static hb_buffer_t _hb_buffer_nil = {
+ HB_REFERENCE_COUNT_INVALID, /* ref_count */
+
+ &_hb_unicode_funcs_nil /* unicode */
+};
+
+/* Here is how the buffer works internally:
+ *
+ * There are two string pointers: in_string and out_string. They
+ * always have same allocated size, but different length and positions.
+ *
+ * As an optimization, both in_string and out_string may point to the
+ * same piece of memory, which is owned by in_string. This remains the
+ * case as long as out_length doesn't exceed in_length at any time.
+ * In that case, swap() is no-op and the glyph operations operate mostly
+ * in-place.
+ *
+ * As soon as out_string gets longer than in_string, out_string is moved over
+ * to an alternate buffer (which we reuse the positions buffer for!), and its
+ * current contents (out_length entries) are copied to the alt buffer.
+ * This should all remain transparent to the user. swap() then switches
+ * in_string and out_string.
+ */
+
+/* XXX err handling */
+
+/* Internal API */
+
+static void
+hb_buffer_ensure_separate (hb_buffer_t *buffer, unsigned int size)
+{
+ hb_buffer_ensure (buffer, size);
+ if (buffer->out_string == buffer->in_string)
+ {
+ assert (buffer->have_output);
+ if (!buffer->positions)
+ buffer->positions = (hb_internal_glyph_position_t *) calloc (buffer->allocated, sizeof (buffer->positions[0]));
+
+ buffer->out_string = (hb_internal_glyph_info_t *) buffer->positions;
+ memcpy (buffer->out_string, buffer->in_string, buffer->out_length * sizeof (buffer->out_string[0]));
+ }
+}
+
+/* Public API */
+
+hb_buffer_t *
+hb_buffer_create (unsigned int pre_alloc_size)
+{
+ hb_buffer_t *buffer;
+
+ if (!HB_OBJECT_DO_CREATE (hb_buffer_t, buffer))
+ return &_hb_buffer_nil;
+
+ if (pre_alloc_size)
+ hb_buffer_ensure(buffer, pre_alloc_size);
+
+ buffer->unicode = &_hb_unicode_funcs_nil;
+
+ return buffer;
+}
+
+hb_buffer_t *
+hb_buffer_reference (hb_buffer_t *buffer)
+{
+ HB_OBJECT_DO_REFERENCE (buffer);
+}
+
+unsigned int
+hb_buffer_get_reference_count (hb_buffer_t *buffer)
+{
+ HB_OBJECT_DO_GET_REFERENCE_COUNT (buffer);
+}
+
+void
+hb_buffer_destroy (hb_buffer_t *buffer)
+{
+ HB_OBJECT_DO_DESTROY (buffer);
+
+ hb_unicode_funcs_destroy (buffer->unicode);
+
+ free (buffer->in_string);
+ free (buffer->positions);
+
+ free (buffer);
+}
+
+
+void
+hb_buffer_set_unicode_funcs (hb_buffer_t *buffer,
+ hb_unicode_funcs_t *unicode)
+{
+ if (!unicode)
+ unicode = &_hb_unicode_funcs_nil;
+
+ hb_unicode_funcs_reference (unicode);
+ hb_unicode_funcs_destroy (buffer->unicode);
+ buffer->unicode = unicode;
+}
+
+hb_unicode_funcs_t *
+hb_buffer_get_unicode_funcs (hb_buffer_t *buffer)
+{
+ return buffer->unicode;
+}
+
+void
+hb_buffer_set_direction (hb_buffer_t *buffer,
+ hb_direction_t direction)
+
+{
+ buffer->direction = direction;
+}
+
+hb_direction_t
+hb_buffer_get_direction (hb_buffer_t *buffer)
+{
+ return buffer->direction;
+}
+
+void
+hb_buffer_set_script (hb_buffer_t *buffer,
+ hb_script_t script)
+{
+ buffer->script = script;
+}
+
+hb_script_t
+hb_buffer_get_script (hb_buffer_t *buffer)
+{
+ return buffer->script;
+}
+
+void
+hb_buffer_set_language (hb_buffer_t *buffer,
+ hb_language_t language)
+{
+ buffer->language = language;
+}
+
+hb_language_t
+hb_buffer_get_language (hb_buffer_t *buffer)
+{
+ return buffer->language;
+}
+
+
+void
+hb_buffer_clear (hb_buffer_t *buffer)
+{
+ buffer->have_output = FALSE;
+ buffer->have_positions = FALSE;
+ buffer->in_length = 0;
+ buffer->out_length = 0;
+ buffer->in_pos = 0;
+ buffer->out_pos = 0;
+ buffer->out_string = buffer->in_string;
+ buffer->max_lig_id = 0;
+}
+
+void
+hb_buffer_ensure (hb_buffer_t *buffer, unsigned int size)
+{
+ unsigned int new_allocated = buffer->allocated;
+
+ if (size > new_allocated)
+ {
+ while (size > new_allocated)
+ new_allocated += (new_allocated >> 1) + 8;
+
+ if (buffer->positions)
+ buffer->positions = (hb_internal_glyph_position_t *) realloc (buffer->positions, new_allocated * sizeof (buffer->positions[0]));
+
+ if (buffer->out_string != buffer->in_string)
+ {
+ buffer->in_string = (hb_internal_glyph_info_t *) realloc (buffer->in_string, new_allocated * sizeof (buffer->in_string[0]));
+ buffer->out_string = (hb_internal_glyph_info_t *) buffer->positions;
+ }
+ else
+ {
+ buffer->in_string = (hb_internal_glyph_info_t *) realloc (buffer->in_string, new_allocated * sizeof (buffer->in_string[0]));
+ buffer->out_string = buffer->in_string;
+ }
+
+ buffer->allocated = new_allocated;
+ }
+}
+
+void
+hb_buffer_add_glyph (hb_buffer_t *buffer,
+ hb_codepoint_t codepoint,
+ hb_mask_t mask,
+ unsigned int cluster)
+{
+ hb_internal_glyph_info_t *glyph;
+
+ hb_buffer_ensure (buffer, buffer->in_length + 1);
+
+ glyph = &buffer->in_string[buffer->in_length];
+ glyph->codepoint = codepoint;
+ glyph->mask = mask;
+ glyph->cluster = cluster;
+ glyph->component = 0;
+ glyph->lig_id = 0;
+ glyph->gproperty = HB_BUFFER_GLYPH_PROPERTIES_UNKNOWN;
+
+ buffer->in_length++;
+}
+
+
+/* HarfBuzz-Internal API */
+
+void
+_hb_buffer_clear_output (hb_buffer_t *buffer)
+{
+ buffer->have_output = TRUE;
+ buffer->have_positions = FALSE;
+ buffer->out_length = 0;
+ buffer->out_pos = 0;
+ buffer->out_string = buffer->in_string;
+}
+
+void
+hb_buffer_clear_positions (hb_buffer_t *buffer)
+{
+ _hb_buffer_clear_output (buffer);
+ buffer->have_output = FALSE;
+ buffer->have_positions = TRUE;
+
+ if (unlikely (!buffer->positions))
+ {
+ buffer->positions = (hb_internal_glyph_position_t *) calloc (buffer->allocated, sizeof (buffer->positions[0]));
+ return;
+ }
+
+ memset (buffer->positions, 0, sizeof (buffer->positions[0]) * buffer->in_length);
+}
+
+void
+_hb_buffer_swap (hb_buffer_t *buffer)
+{
+ unsigned int tmp;
+
+ assert (buffer->have_output);
+
+ if (buffer->out_string != buffer->in_string)
+ {
+ hb_internal_glyph_info_t *tmp_string;
+ tmp_string = buffer->in_string;
+ buffer->in_string = buffer->out_string;
+ buffer->out_string = tmp_string;
+ buffer->positions = (hb_internal_glyph_position_t *) buffer->out_string;
+ }
+
+ tmp = buffer->in_length;
+ buffer->in_length = buffer->out_length;
+ buffer->out_length = tmp;
+
+ tmp = buffer->in_pos;
+ buffer->in_pos = buffer->out_pos;
+ buffer->out_pos = tmp;
+}
+
+/* The following function copies `num_out' elements from `glyph_data'
+ to `buffer->out_string', advancing the in array pointer in the structure
+ by `num_in' elements, and the out array pointer by `num_out' elements.
+ Finally, it sets the `length' field of `out' equal to
+ `pos' of the `out' structure.
+
+ If `component' is 0xFFFF, the component value from buffer->in_pos
+ will copied `num_out' times, otherwise `component' itself will
+ be used to fill the `component' fields.
+
+ If `lig_id' is 0xFFFF, the lig_id value from buffer->in_pos
+ will copied `num_out' times, otherwise `lig_id' itself will
+ be used to fill the `lig_id' fields.
+
+ The mask for all replacement glyphs are taken
+ from the glyph at position `buffer->in_pos'.
+
+ The cluster value for the glyph at position buffer->in_pos is used
+ for all replacement glyphs */
+
+void
+_hb_buffer_add_output_glyphs (hb_buffer_t *buffer,
+ unsigned int num_in,
+ unsigned int num_out,
+ const hb_codepoint_t *glyph_data,
+ unsigned short component,
+ unsigned short lig_id)
+{
+ unsigned int i;
+ unsigned int mask;
+ unsigned int cluster;
+
+ if (buffer->out_string != buffer->in_string ||
+ buffer->out_pos + num_out > buffer->in_pos + num_in)
+ {
+ hb_buffer_ensure_separate (buffer, buffer->out_pos + num_out);
+ }
+
+ mask = buffer->in_string[buffer->in_pos].mask;
+ cluster = buffer->in_string[buffer->in_pos].cluster;
+ if (component == 0xFFFF)
+ component = buffer->in_string[buffer->in_pos].component;
+ if (lig_id == 0xFFFF)
+ lig_id = buffer->in_string[buffer->in_pos].lig_id;
+
+ for (i = 0; i < num_out; i++)
+ {
+ hb_internal_glyph_info_t *info = &buffer->out_string[buffer->out_pos + i];
+ info->codepoint = glyph_data[i];
+ info->mask = mask;
+ info->cluster = cluster;
+ info->component = component;
+ info->lig_id = lig_id;
+ info->gproperty = HB_BUFFER_GLYPH_PROPERTIES_UNKNOWN;
+ }
+
+ buffer->in_pos += num_in;
+ buffer->out_pos += num_out;
+ buffer->out_length = buffer->out_pos;
+}
+
+void
+_hb_buffer_add_output_glyphs_be16 (hb_buffer_t *buffer,
+ unsigned int num_in,
+ unsigned int num_out,
+ const uint16_t *glyph_data_be,
+ unsigned short component,
+ unsigned short lig_id)
+{
+ unsigned int i;
+ unsigned int mask;
+ unsigned int cluster;
+
+ if (buffer->out_string != buffer->in_string ||
+ buffer->out_pos + num_out > buffer->in_pos + num_in)
+ {
+ hb_buffer_ensure_separate (buffer, buffer->out_pos + num_out);
+ }
+
+ mask = buffer->in_string[buffer->in_pos].mask;
+ cluster = buffer->in_string[buffer->in_pos].cluster;
+ if (component == 0xFFFF)
+ component = buffer->in_string[buffer->in_pos].component;
+ if (lig_id == 0xFFFF)
+ lig_id = buffer->in_string[buffer->in_pos].lig_id;
+
+ for (i = 0; i < num_out; i++)
+ {
+ hb_internal_glyph_info_t *info = &buffer->out_string[buffer->out_pos + i];
+ info->codepoint = hb_be_uint16 (glyph_data_be[i]);
+ info->mask = mask;
+ info->cluster = cluster;
+ info->component = component;
+ info->lig_id = lig_id;
+ info->gproperty = HB_BUFFER_GLYPH_PROPERTIES_UNKNOWN;
+ }
+
+ buffer->in_pos += num_in;
+ buffer->out_pos += num_out;
+ buffer->out_length = buffer->out_pos;
+}
+
+void
+_hb_buffer_add_output_glyph (hb_buffer_t *buffer,
+ hb_codepoint_t glyph_index,
+ unsigned short component,
+ unsigned short lig_id)
+{
+ hb_internal_glyph_info_t *info;
+
+ if (buffer->out_string != buffer->in_string)
+ {
+ hb_buffer_ensure (buffer, buffer->out_pos + 1);
+ buffer->out_string[buffer->out_pos] = buffer->in_string[buffer->in_pos];
+ }
+ else if (buffer->out_pos != buffer->in_pos)
+ buffer->out_string[buffer->out_pos] = buffer->in_string[buffer->in_pos];
+
+ info = &buffer->out_string[buffer->out_pos];
+ info->codepoint = glyph_index;
+ if (component != 0xFFFF)
+ info->component = component;
+ if (lig_id != 0xFFFF)
+ info->lig_id = lig_id;
+ info->gproperty = HB_BUFFER_GLYPH_PROPERTIES_UNKNOWN;
+
+ buffer->in_pos++;
+ buffer->out_pos++;
+ buffer->out_length = buffer->out_pos;
+}
+
+void
+_hb_buffer_next_glyph (hb_buffer_t *buffer)
+{
+ if (buffer->have_output)
+ {
+ if (buffer->out_string != buffer->in_string)
+ {
+ hb_buffer_ensure (buffer, buffer->out_pos + 1);
+ buffer->out_string[buffer->out_pos] = buffer->in_string[buffer->in_pos];
+ }
+ else if (buffer->out_pos != buffer->in_pos)
+ buffer->out_string[buffer->out_pos] = buffer->in_string[buffer->in_pos];
+
+ buffer->out_pos++;
+ buffer->out_length = buffer->out_pos;
+ }
+
+ buffer->in_pos++;
+}
+
+void
+_hb_buffer_replace_glyph (hb_buffer_t *buffer,
+ hb_codepoint_t glyph_index)
+{
+ _hb_buffer_add_output_glyph (buffer, glyph_index, 0xFFFF, 0xFFFF);
+}
+
+unsigned short
+_hb_buffer_allocate_lig_id (hb_buffer_t *buffer)
+{
+ return ++buffer->max_lig_id;
+}
+
+
+unsigned int
+hb_buffer_get_length (hb_buffer_t *buffer)
+{
+ return buffer->in_length;
+}
+
+/* Return value valid as long as buffer not modified */
+hb_glyph_info_t *
+hb_buffer_get_glyph_infos (hb_buffer_t *buffer)
+{
+ return (hb_glyph_info_t *) buffer->in_string;
+}
+
+/* Return value valid as long as buffer not modified */
+hb_glyph_position_t *
+hb_buffer_get_glyph_positions (hb_buffer_t *buffer)
+{
+ if (!buffer->have_positions)
+ hb_buffer_clear_positions (buffer);
+
+ return (hb_glyph_position_t *) buffer->positions;
+}
+
+
+static void
+reverse_range (hb_buffer_t *buffer,
+ unsigned int start,
+ unsigned int end)
+{
+ unsigned int i, j;
+
+ for (i = start, j = end - 1; i < j; i++, j--) {
+ hb_internal_glyph_info_t t;
+
+ t = buffer->in_string[i];
+ buffer->in_string[i] = buffer->in_string[j];
+ buffer->in_string[j] = t;
+ }
+
+ if (buffer->positions) {
+ for (i = 0, j = end - 1; i < j; i++, j--) {
+ hb_internal_glyph_position_t t;
+
+ t = buffer->positions[i];
+ buffer->positions[i] = buffer->positions[j];
+ buffer->positions[j] = t;
+ }
+ }
+}
+
+void
+hb_buffer_reverse (hb_buffer_t *buffer)
+{
+ if (unlikely (!buffer->in_length))
+ return;
+
+ reverse_range (buffer, 0, buffer->in_length);
+}
+
+void
+hb_buffer_reverse_clusters (hb_buffer_t *buffer)
+{
+ unsigned int i, start, count, last_cluster;
+
+ if (unlikely (!buffer->in_length))
+ return;
+
+ hb_buffer_reverse (buffer);
+
+ count = buffer->in_length;
+ start = 0;
+ last_cluster = buffer->in_string[0].cluster;
+ for (i = 1; i < count; i++) {
+ if (last_cluster != buffer->in_string[i].cluster) {
+ reverse_range (buffer, start, i);
+ start = i;
+ last_cluster = buffer->in_string[i].cluster;
+ }
+ }
+ reverse_range (buffer, start, i);
+}
+
+
+#define ADD_UTF(T) \
+ HB_STMT_START { \
+ const T *next = (const T *) text + item_offset; \
+ const T *end = next + item_length; \
+ while (next < end) { \
+ hb_codepoint_t u; \
+ const T *old_next = next; \
+ next = UTF_NEXT (next, end, u); \
+ hb_buffer_add_glyph (buffer, u, 0, old_next - (const T *) text); \
+ } \
+ } HB_STMT_END
+
+
+#define UTF8_COMPUTE(Char, Mask, Len) \
+ if (Char < 128) { Len = 1; Mask = 0x7f; } \
+ else if ((Char & 0xe0) == 0xc0) { Len = 2; Mask = 0x1f; } \
+ else if ((Char & 0xf0) == 0xe0) { Len = 3; Mask = 0x0f; } \
+ else if ((Char & 0xf8) == 0xf0) { Len = 4; Mask = 0x07; } \
+ else Len = 0;
+
+static inline const uint8_t *
+hb_utf8_next (const uint8_t *text,
+ const uint8_t *end,
+ hb_codepoint_t *unicode)
+{
+ uint8_t c = *text;
+ unsigned int mask, len;
+
+ UTF8_COMPUTE (c, mask, len);
+ if (unlikely (!len || (unsigned int) (end - text) < len)) {
+ *unicode = -1;
+ return text + 1;
+ } else {
+ hb_codepoint_t result;
+ unsigned int i;
+ result = c & mask;
+ for (i = 1; i < len; i++)
+ {
+ if (unlikely ((text[i] & 0xc0) != 0x80))
+ {
+ *unicode = -1;
+ return text + 1;
+ }
+ result <<= 6;
+ result |= (text[i] & 0x3f);
+ }
+ *unicode = result;
+ return text + len;
+ }
+}
+
+void
+hb_buffer_add_utf8 (hb_buffer_t *buffer,
+ const char *text,
+ unsigned int text_length HB_UNUSED,
+ unsigned int item_offset,
+ unsigned int item_length)
+{
+#define UTF_NEXT(S, E, U) hb_utf8_next (S, E, &(U))
+ ADD_UTF (uint8_t);
+#undef UTF_NEXT
+}
+
+static inline const uint16_t *
+hb_utf16_next (const uint16_t *text,
+ const uint16_t *end,
+ hb_codepoint_t *unicode)
+{
+ uint16_t c = *text++;
+
+ if (unlikely (c >= 0xd800 && c < 0xdc00)) {
+ /* high surrogate */
+ uint16_t l;
+ if (text < end && ((l = *text), unlikely (l >= 0xdc00 && l < 0xe000))) {
+ /* low surrogate */
+ *unicode = ((hb_codepoint_t) ((c) - 0xd800) * 0x400 + (l) - 0xdc00 + 0x10000);
+ text++;
+ } else
+ *unicode = -1;
+ } else
+ *unicode = c;
+
+ return text;
+}
+
+void
+hb_buffer_add_utf16 (hb_buffer_t *buffer,
+ const uint16_t *text,
+ unsigned int text_length HB_UNUSED,
+ unsigned int item_offset,
+ unsigned int item_length)
+{
+#define UTF_NEXT(S, E, U) hb_utf16_next (S, E, &(U))
+ ADD_UTF (uint16_t);
+#undef UTF_NEXT
+}
+
+void
+hb_buffer_add_utf32 (hb_buffer_t *buffer,
+ const uint32_t *text,
+ unsigned int text_length HB_UNUSED,
+ unsigned int item_offset,
+ unsigned int item_length)
+{
+#define UTF_NEXT(S, E, U) ((U) = *(S), (S)+1)
+ ADD_UTF (uint32_t);
+#undef UTF_NEXT
+}
diff --git a/src/hb-common.h b/src/hb-common.h
index a2bc114..cc673ad 100644
--- a/src/hb-common.h
+++ b/src/hb-common.h
@@ -83,6 +83,7 @@ typedef enum _hb_direction_t {
#define HB_DIRECTION_IS_VERTICAL(dir) ((dir) == HB_DIRECTION_TTB || (dir) == HB_DIRECTION_BTT)
#define HB_DIRECTION_IS_FORWARD(dir) ((dir) == HB_DIRECTION_LTR || (dir) == HB_DIRECTION_TTB)
#define HB_DIRECTION_IS_BACKWARD(dir) ((dir) == HB_DIRECTION_RTL || (dir) == HB_DIRECTION_BTT)
+#define HB_DIRECTION_REVERSE(dir) ((hb_direction_t) (((unsigned int) (dir)) ^ 1))
#endif /* HB_COMMON_H */
diff --git a/src/hb-font-private.h b/src/hb-font-private.h
deleted file mode 100644
index 2b024cc..0000000
--- a/src/hb-font-private.h
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * Copyright (C) 2009 Red Hat, Inc.
- *
- * This is part of HarfBuzz, a text shaping library.
- *
- * Permission is hereby granted, without written agreement and without
- * license or royalty fees, to use, copy, modify, and distribute this
- * software and its documentation for any purpose, provided that the
- * above copyright notice and the following two paragraphs appear in
- * all copies of this software.
- *
- * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
- * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
- * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
- * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
- * DAMAGE.
- *
- * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
- * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
- * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
- * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
- * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
- *
- * Red Hat Author(s): Behdad Esfahbod
- */
-
-#ifndef HB_FONT_PRIVATE_H
-#define HB_FONT_PRIVATE_H
-
-#include "hb-private.h"
-
-#include "hb-font.h"
-
-#include "hb-ot-layout-private.h"
-
-HB_BEGIN_DECLS
-
-/*
- * hb_font_funcs_t
- */
-
-struct _hb_font_funcs_t {
- hb_reference_count_t ref_count;
-
- hb_bool_t immutable;
-
- hb_font_get_glyph_func_t get_glyph;
- hb_font_get_contour_point_func_t get_contour_point;
- hb_font_get_glyph_metrics_func_t get_glyph_metrics;
- hb_font_get_kerning_func_t get_kerning;
-};
-
-HB_INTERNAL hb_font_funcs_t
-_hb_font_funcs_nil;
-
-/*
- * hb_face_t
- */
-
-struct _hb_face_t {
- hb_reference_count_t ref_count;
-
- hb_get_table_func_t get_table;
- hb_destroy_func_t destroy;
- void *user_data;
-
- hb_ot_layout_t ot_layout;
-};
-
-
-/*
- * hb_font_t
- */
-
-struct _hb_font_t {
- hb_reference_count_t ref_count;
-
- hb_16dot16_t x_scale;
- hb_16dot16_t y_scale;
-
- unsigned int x_ppem;
- unsigned int y_ppem;
-
- hb_font_funcs_t *klass;
- hb_destroy_func_t destroy;
- void *user_data;
-};
-
-
-HB_END_DECLS
-
-#endif /* HB_FONT_PRIVATE_H */
diff --git a/src/hb-font-private.hh b/src/hb-font-private.hh
new file mode 100644
index 0000000..ec07931
--- /dev/null
+++ b/src/hb-font-private.hh
@@ -0,0 +1,92 @@
+/*
+ * Copyright (C) 2009 Red Hat, Inc.
+ *
+ * This is part of HarfBuzz, a text shaping library.
+ *
+ * Permission is hereby granted, without written agreement and without
+ * license or royalty fees, to use, copy, modify, and distribute this
+ * software and its documentation for any purpose, provided that the
+ * above copyright notice and the following two paragraphs appear in
+ * all copies of this software.
+ *
+ * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
+ * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
+ * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
+ * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
+ * DAMAGE.
+ *
+ * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
+ * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
+ * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
+ * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
+ *
+ * Red Hat Author(s): Behdad Esfahbod
+ */
+
+#ifndef HB_FONT_PRIVATE_H
+#define HB_FONT_PRIVATE_H
+
+#include "hb-private.h"
+
+#include "hb-font.h"
+
+#include "hb-ot-layout-private.hh"
+
+HB_BEGIN_DECLS
+
+/*
+ * hb_font_funcs_t
+ */
+
+struct _hb_font_funcs_t {
+ hb_reference_count_t ref_count;
+
+ hb_bool_t immutable;
+
+ hb_font_get_glyph_func_t get_glyph;
+ hb_font_get_contour_point_func_t get_contour_point;
+ hb_font_get_glyph_metrics_func_t get_glyph_metrics;
+ hb_font_get_kerning_func_t get_kerning;
+};
+
+HB_INTERNAL hb_font_funcs_t
+_hb_font_funcs_nil;
+
+/*
+ * hb_face_t
+ */
+
+struct _hb_face_t {
+ hb_reference_count_t ref_count;
+
+ hb_get_table_func_t get_table;
+ hb_destroy_func_t destroy;
+ void *user_data;
+
+ hb_ot_layout_t ot_layout;
+};
+
+
+/*
+ * hb_font_t
+ */
+
+struct _hb_font_t {
+ hb_reference_count_t ref_count;
+
+ hb_16dot16_t x_scale;
+ hb_16dot16_t y_scale;
+
+ unsigned int x_ppem;
+ unsigned int y_ppem;
+
+ hb_font_funcs_t *klass;
+ hb_destroy_func_t destroy;
+ void *user_data;
+};
+
+
+HB_END_DECLS
+
+#endif /* HB_FONT_PRIVATE_H */
diff --git a/src/hb-font.cc b/src/hb-font.cc
index 20aeb16..46b63a4 100644
--- a/src/hb-font.cc
+++ b/src/hb-font.cc
@@ -26,11 +26,11 @@
#include "hb-private.h"
-#include "hb-font-private.h"
+#include "hb-font-private.hh"
#include "hb-blob-private.h"
#include "hb-open-file-private.hh"
-#include "hb-ot-layout-private.h"
+#include "hb-ot-layout-private.hh"
#include <string.h>
diff --git a/src/hb-ft.c b/src/hb-ft.c
deleted file mode 100644
index e6f3e84..0000000
--- a/src/hb-ft.c
+++ /dev/null
@@ -1,240 +0,0 @@
-/*
- * Copyright (C) 2009 Red Hat, Inc.
- * Copyright (C) 2009 Keith Stribley <devel at thanlwinsoft.org>
- *
- * This is part of HarfBuzz, a text shaping library.
- *
- * Permission is hereby granted, without written agreement and without
- * license or royalty fees, to use, copy, modify, and distribute this
- * software and its documentation for any purpose, provided that the
- * above copyright notice and the following two paragraphs appear in
- * all copies of this software.
- *
- * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
- * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
- * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
- * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
- * DAMAGE.
- *
- * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
- * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
- * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
- * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
- * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
- *
- * Red Hat Author(s): Behdad Esfahbod
- */
-
-#include "hb-private.h"
-
-#include "hb-ft.h"
-
-#include "hb-font-private.h"
-
-#include FT_TRUETYPE_TABLES_H
-
-static hb_codepoint_t
-hb_ft_get_glyph (hb_font_t *font HB_UNUSED,
- hb_face_t *face HB_UNUSED,
- const void *user_data,
- hb_codepoint_t unicode,
- hb_codepoint_t variation_selector)
-{
- FT_Face ft_face = (FT_Face) user_data;
-
-#ifdef HAVE_FT_FACE_GETCHARVARIANTINDEX
- if (unlikely (variation_selector)) {
- hb_codepoint_t glyph = FT_Face_GetCharVariantIndex (ft_face, unicode, variation_selector);
- if (glyph)
- return glyph;
- }
-#endif
-
- return FT_Get_Char_Index (ft_face, unicode);
-}
-
-static hb_bool_t
-hb_ft_get_contour_point (hb_font_t *font HB_UNUSED,
- hb_face_t *face HB_UNUSED,
- const void *user_data,
- unsigned int point_index,
- hb_codepoint_t glyph,
- hb_position_t *x,
- hb_position_t *y)
-{
- FT_Face ft_face = (FT_Face) user_data;
- int load_flags = FT_LOAD_DEFAULT;
-
- /* TODO: load_flags, embolden, etc */
-
- if (unlikely (FT_Load_Glyph (ft_face, glyph, load_flags)))
- return FALSE;
-
- if (unlikely (ft_face->glyph->format != FT_GLYPH_FORMAT_OUTLINE))
- return FALSE;
-
- if (unlikely (point_index >= (unsigned int) ft_face->glyph->outline.n_points))
- return FALSE;
-
- *x = ft_face->glyph->outline.points[point_index].x;
- *y = ft_face->glyph->outline.points[point_index].y;
-
- return TRUE;
-}
-
-static void
-hb_ft_get_glyph_metrics (hb_font_t *font HB_UNUSED,
- hb_face_t *face HB_UNUSED,
- const void *user_data,
- hb_codepoint_t glyph,
- hb_glyph_metrics_t *metrics)
-{
- FT_Face ft_face = (FT_Face) user_data;
- int load_flags = FT_LOAD_DEFAULT;
-
- /* TODO: load_flags, embolden, etc */
-
- metrics->x_advance = metrics->y_advance = 0;
- metrics->x_offset = metrics->y_offset = 0;
- metrics->width = metrics->height = 0;
- if (likely (!FT_Load_Glyph (ft_face, glyph, load_flags)))
- {
- /* TODO: A few negations should be in order here, not sure. */
- metrics->x_advance = ft_face->glyph->advance.x;
- metrics->y_advance = ft_face->glyph->advance.y;
- metrics->x_offset = ft_face->glyph->metrics.horiBearingX;
- metrics->y_offset = ft_face->glyph->metrics.horiBearingY;
- metrics->width = ft_face->glyph->metrics.width;
- metrics->height = ft_face->glyph->metrics.height;
- }
-}
-
-static hb_position_t
-hb_ft_get_kerning (hb_font_t *font HB_UNUSED,
- hb_face_t *face HB_UNUSED,
- const void *user_data,
- hb_codepoint_t first_glyph,
- hb_codepoint_t second_glyph)
-{
- FT_Face ft_face = (FT_Face) user_data;
- FT_Vector kerning;
-
- /* TODO: Kern type? */
- if (FT_Get_Kerning (ft_face, first_glyph, second_glyph, FT_KERNING_DEFAULT, &kerning))
- return 0;
-
- return kerning.x;
-}
-
-static hb_font_funcs_t ft_ffuncs = {
- HB_REFERENCE_COUNT_INVALID, /* ref_count */
-
- TRUE, /* immutable */
-
- hb_ft_get_glyph,
- hb_ft_get_contour_point,
- hb_ft_get_glyph_metrics,
- hb_ft_get_kerning
-};
-
-hb_font_funcs_t *
-hb_ft_get_font_funcs (void)
-{
- return &ft_ffuncs;
-}
-
-
-static hb_blob_t *
-_get_table (hb_tag_t tag, void *user_data)
-{
- FT_Face ft_face = (FT_Face) user_data;
- FT_Byte *buffer;
- FT_ULong length = 0;
- FT_Error error;
-
- if (unlikely (tag == HB_TAG_NONE))
- return hb_blob_create_empty ();
-
- error = FT_Load_Sfnt_Table (ft_face, tag, 0, NULL, &length);
- if (error)
- return hb_blob_create_empty ();
-
- /* TODO Use FT_Memory? */
- buffer = malloc (length);
- if (buffer == NULL)
- return NULL;
-
- error = FT_Load_Sfnt_Table (ft_face, tag, 0, buffer, &length);
- if (error)
- return hb_blob_create_empty ();
-
- return hb_blob_create ((const char *) buffer, length,
- HB_MEMORY_MODE_WRITABLE,
- free, buffer);
-}
-
-
-hb_face_t *
-hb_ft_face_create (FT_Face ft_face,
- hb_destroy_func_t destroy)
-{
- hb_face_t *face;
-
- if (ft_face->stream->read == NULL) {
- hb_blob_t *blob;
-
- blob = hb_blob_create ((const char *) ft_face->stream->base,
- (unsigned int) ft_face->stream->size,
- /* TODO: Check FT_FACE_FLAG_EXTERNAL_STREAM? */
- HB_MEMORY_MODE_READONLY_MAY_MAKE_WRITABLE,
- destroy, ft_face);
- face = hb_face_create_for_data (blob, ft_face->face_index);
- hb_blob_destroy (blob);
- } else {
- face = hb_face_create_for_tables (_get_table, destroy, ft_face);
- }
-
- return face;
-}
-
-static void
-hb_ft_face_finalize (FT_Face ft_face)
-{
- hb_face_destroy (ft_face->generic.data);
-}
-
-hb_face_t *
-hb_ft_face_create_cached (FT_Face ft_face)
-{
- if (unlikely (!ft_face->generic.data || ft_face->generic.finalizer != (FT_Generic_Finalizer) hb_ft_face_finalize))
- {
- if (ft_face->generic.finalizer)
- ft_face->generic.finalizer (ft_face);
-
- ft_face->generic.data = hb_ft_face_create (ft_face, NULL);
- ft_face->generic.finalizer = (FT_Generic_Finalizer) hb_ft_face_finalize;
- }
-
- return hb_face_reference (ft_face->generic.data);
-}
-
-
-hb_font_t *
-hb_ft_font_create (FT_Face ft_face,
- hb_destroy_func_t destroy)
-{
- hb_font_t *font;
-
- font = hb_font_create ();
- hb_font_set_funcs (font,
- hb_ft_get_font_funcs (),
- destroy, ft_face);
- hb_font_set_scale (font,
- ft_face->size->metrics.x_scale,
- ft_face->size->metrics.y_scale);
- hb_font_set_ppem (font,
- ft_face->size->metrics.x_ppem,
- ft_face->size->metrics.y_ppem);
-
- return font;
-}
diff --git a/src/hb-ft.cc b/src/hb-ft.cc
new file mode 100644
index 0000000..5b911bc
--- /dev/null
+++ b/src/hb-ft.cc
@@ -0,0 +1,240 @@
+/*
+ * Copyright (C) 2009 Red Hat, Inc.
+ * Copyright (C) 2009 Keith Stribley <devel at thanlwinsoft.org>
+ *
+ * This is part of HarfBuzz, a text shaping library.
+ *
+ * Permission is hereby granted, without written agreement and without
+ * license or royalty fees, to use, copy, modify, and distribute this
+ * software and its documentation for any purpose, provided that the
+ * above copyright notice and the following two paragraphs appear in
+ * all copies of this software.
+ *
+ * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
+ * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
+ * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
+ * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
+ * DAMAGE.
+ *
+ * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
+ * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
+ * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
+ * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
+ *
+ * Red Hat Author(s): Behdad Esfahbod
+ */
+
+#include "hb-private.h"
+
+#include "hb-ft.h"
+
+#include "hb-font-private.hh"
+
+#include FT_TRUETYPE_TABLES_H
+
+static hb_codepoint_t
+hb_ft_get_glyph (hb_font_t *font HB_UNUSED,
+ hb_face_t *face HB_UNUSED,
+ const void *user_data,
+ hb_codepoint_t unicode,
+ hb_codepoint_t variation_selector)
+{
+ FT_Face ft_face = (FT_Face) user_data;
+
+#ifdef HAVE_FT_FACE_GETCHARVARIANTINDEX
+ if (unlikely (variation_selector)) {
+ hb_codepoint_t glyph = FT_Face_GetCharVariantIndex (ft_face, unicode, variation_selector);
+ if (glyph)
+ return glyph;
+ }
+#endif
+
+ return FT_Get_Char_Index (ft_face, unicode);
+}
+
+static hb_bool_t
+hb_ft_get_contour_point (hb_font_t *font HB_UNUSED,
+ hb_face_t *face HB_UNUSED,
+ const void *user_data,
+ unsigned int point_index,
+ hb_codepoint_t glyph,
+ hb_position_t *x,
+ hb_position_t *y)
+{
+ FT_Face ft_face = (FT_Face) user_data;
+ int load_flags = FT_LOAD_DEFAULT;
+
+ /* TODO: load_flags, embolden, etc */
+
+ if (unlikely (FT_Load_Glyph (ft_face, glyph, load_flags)))
+ return FALSE;
+
+ if (unlikely (ft_face->glyph->format != FT_GLYPH_FORMAT_OUTLINE))
+ return FALSE;
+
+ if (unlikely (point_index >= (unsigned int) ft_face->glyph->outline.n_points))
+ return FALSE;
+
+ *x = ft_face->glyph->outline.points[point_index].x;
+ *y = ft_face->glyph->outline.points[point_index].y;
+
+ return TRUE;
+}
+
+static void
+hb_ft_get_glyph_metrics (hb_font_t *font HB_UNUSED,
+ hb_face_t *face HB_UNUSED,
+ const void *user_data,
+ hb_codepoint_t glyph,
+ hb_glyph_metrics_t *metrics)
+{
+ FT_Face ft_face = (FT_Face) user_data;
+ int load_flags = FT_LOAD_DEFAULT;
+
+ /* TODO: load_flags, embolden, etc */
+
+ metrics->x_advance = metrics->y_advance = 0;
+ metrics->x_offset = metrics->y_offset = 0;
+ metrics->width = metrics->height = 0;
+ if (likely (!FT_Load_Glyph (ft_face, glyph, load_flags)))
+ {
+ /* TODO: A few negations should be in order here, not sure. */
+ metrics->x_advance = ft_face->glyph->advance.x;
+ metrics->y_advance = ft_face->glyph->advance.y;
+ metrics->x_offset = ft_face->glyph->metrics.horiBearingX;
+ metrics->y_offset = ft_face->glyph->metrics.horiBearingY;
+ metrics->width = ft_face->glyph->metrics.width;
+ metrics->height = ft_face->glyph->metrics.height;
+ }
+}
+
+static hb_position_t
+hb_ft_get_kerning (hb_font_t *font HB_UNUSED,
+ hb_face_t *face HB_UNUSED,
+ const void *user_data,
+ hb_codepoint_t first_glyph,
+ hb_codepoint_t second_glyph)
+{
+ FT_Face ft_face = (FT_Face) user_data;
+ FT_Vector kerning;
+
+ /* TODO: Kern type? */
+ if (FT_Get_Kerning (ft_face, first_glyph, second_glyph, FT_KERNING_DEFAULT, &kerning))
+ return 0;
+
+ return kerning.x;
+}
+
+static hb_font_funcs_t ft_ffuncs = {
+ HB_REFERENCE_COUNT_INVALID, /* ref_count */
+
+ TRUE, /* immutable */
+
+ hb_ft_get_glyph,
+ hb_ft_get_contour_point,
+ hb_ft_get_glyph_metrics,
+ hb_ft_get_kerning
+};
+
+hb_font_funcs_t *
+hb_ft_get_font_funcs (void)
+{
+ return &ft_ffuncs;
+}
+
+
+static hb_blob_t *
+_get_table (hb_tag_t tag, void *user_data)
+{
+ FT_Face ft_face = (FT_Face) user_data;
+ FT_Byte *buffer;
+ FT_ULong length = 0;
+ FT_Error error;
+
+ if (unlikely (tag == HB_TAG_NONE))
+ return hb_blob_create_empty ();
+
+ error = FT_Load_Sfnt_Table (ft_face, tag, 0, NULL, &length);
+ if (error)
+ return hb_blob_create_empty ();
+
+ /* TODO Use FT_Memory? */
+ buffer = (FT_Byte *) malloc (length);
+ if (buffer == NULL)
+ return NULL;
+
+ error = FT_Load_Sfnt_Table (ft_face, tag, 0, buffer, &length);
+ if (error)
+ return hb_blob_create_empty ();
+
+ return hb_blob_create ((const char *) buffer, length,
+ HB_MEMORY_MODE_WRITABLE,
+ free, buffer);
+}
+
+
+hb_face_t *
+hb_ft_face_create (FT_Face ft_face,
+ hb_destroy_func_t destroy)
+{
+ hb_face_t *face;
+
+ if (ft_face->stream->read == NULL) {
+ hb_blob_t *blob;
+
+ blob = hb_blob_create ((const char *) ft_face->stream->base,
+ (unsigned int) ft_face->stream->size,
+ /* TODO: Check FT_FACE_FLAG_EXTERNAL_STREAM? */
+ HB_MEMORY_MODE_READONLY_MAY_MAKE_WRITABLE,
+ destroy, ft_face);
+ face = hb_face_create_for_data (blob, ft_face->face_index);
+ hb_blob_destroy (blob);
+ } else {
+ face = hb_face_create_for_tables (_get_table, destroy, ft_face);
+ }
+
+ return face;
+}
+
+static void
+hb_ft_face_finalize (FT_Face ft_face)
+{
+ hb_face_destroy ((hb_face_t *) ft_face->generic.data);
+}
+
+hb_face_t *
+hb_ft_face_create_cached (FT_Face ft_face)
+{
+ if (unlikely (!ft_face->generic.data || ft_face->generic.finalizer != (FT_Generic_Finalizer) hb_ft_face_finalize))
+ {
+ if (ft_face->generic.finalizer)
+ ft_face->generic.finalizer (ft_face);
+
+ ft_face->generic.data = hb_ft_face_create (ft_face, NULL);
+ ft_face->generic.finalizer = (FT_Generic_Finalizer) hb_ft_face_finalize;
+ }
+
+ return hb_face_reference ((hb_face_t *) ft_face->generic.data);
+}
+
+
+hb_font_t *
+hb_ft_font_create (FT_Face ft_face,
+ hb_destroy_func_t destroy)
+{
+ hb_font_t *font;
+
+ font = hb_font_create ();
+ hb_font_set_funcs (font,
+ hb_ft_get_font_funcs (),
+ destroy, ft_face);
+ hb_font_set_scale (font,
+ ft_face->size->metrics.x_scale,
+ ft_face->size->metrics.y_scale);
+ hb_font_set_ppem (font,
+ ft_face->size->metrics.x_ppem,
+ ft_face->size->metrics.y_ppem);
+
+ return font;
+}
diff --git a/src/hb-ot-layout-common-private.hh b/src/hb-ot-layout-common-private.hh
index 75cbc64..8c04150 100644
--- a/src/hb-ot-layout-common-private.hh
+++ b/src/hb-ot-layout-common-private.hh
@@ -27,7 +27,7 @@
#ifndef HB_OT_LAYOUT_COMMON_PRIVATE_HH
#define HB_OT_LAYOUT_COMMON_PRIVATE_HH
-#include "hb-ot-layout-private.h"
+#include "hb-ot-layout-private.hh"
#include "hb-open-type-private.hh"
diff --git a/src/hb-ot-layout-gdef-private.hh b/src/hb-ot-layout-gdef-private.hh
index 517f9ef..d43a4c2 100644
--- a/src/hb-ot-layout-gdef-private.hh
+++ b/src/hb-ot-layout-gdef-private.hh
@@ -29,7 +29,7 @@
#include "hb-ot-layout-common-private.hh"
-#include "hb-font-private.h"
+#include "hb-font-private.hh"
/*
diff --git a/src/hb-ot-layout-gsubgpos-private.hh b/src/hb-ot-layout-gsubgpos-private.hh
index 09c817d..066abbd 100644
--- a/src/hb-ot-layout-gsubgpos-private.hh
+++ b/src/hb-ot-layout-gsubgpos-private.hh
@@ -27,7 +27,7 @@
#ifndef HB_OT_LAYOUT_GSUBGPOS_PRIVATE_HH
#define HB_OT_LAYOUT_GSUBGPOS_PRIVATE_HH
-#include "hb-buffer-private.h"
+#include "hb-buffer-private.hh"
#include "hb-ot-layout-gdef-private.hh"
diff --git a/src/hb-ot-layout-private.h b/src/hb-ot-layout-private.h
deleted file mode 100644
index a9d4c57..0000000
--- a/src/hb-ot-layout-private.h
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright (C) 2007,2008,2009 Red Hat, Inc.
- *
- * This is part of HarfBuzz, a text shaping library.
- *
- * Permission is hereby granted, without written agreement and without
- * license or royalty fees, to use, copy, modify, and distribute this
- * software and its documentation for any purpose, provided that the
- * above copyright notice and the following two paragraphs appear in
- * all copies of this software.
- *
- * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
- * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
- * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
- * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
- * DAMAGE.
- *
- * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
- * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
- * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
- * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
- * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
- *
- * Red Hat Author(s): Behdad Esfahbod
- */
-
-#ifndef HB_OT_LAYOUT_PRIVATE_H
-#define HB_OT_LAYOUT_PRIVATE_H
-
-#include "hb-private.h"
-
-#include "hb-ot-layout.h"
-
-#include "hb-font.h"
-#include "hb-buffer-private.h"
-
-
-HB_BEGIN_DECLS
-
-typedef unsigned int hb_ot_layout_class_t;
-
-/*
- * hb_ot_layout_t
- */
-
-typedef struct _hb_ot_layout_t hb_ot_layout_t;
-
-struct _hb_ot_layout_t
-{
- hb_blob_t *gdef_blob;
- hb_blob_t *gsub_blob;
- hb_blob_t *gpos_blob;
-
- const struct GDEF *gdef;
- const struct GSUB *gsub;
- const struct GPOS *gpos;
-
- struct
- {
- unsigned char *klasses;
- unsigned int len;
- } new_gdef;
-};
-
-typedef struct _hb_ot_layout_context_t hb_ot_layout_context_t;
-struct _hb_ot_layout_context_t
-{
- hb_face_t *face;
- hb_font_t *font;
-
- union info_t
- {
- struct gpos_t
- {
- unsigned int last; /* the last valid glyph--used with cursive positioning */
- hb_position_t anchor_x; /* the coordinates of the anchor point */
- hb_position_t anchor_y; /* of the last valid glyph */
- } gpos;
- } info;
-};
-
-
-void
-_hb_ot_layout_init (hb_face_t *face);
-
-void
-_hb_ot_layout_fini (hb_face_t *face);
-
-
-/*
- * GDEF
- */
-
-HB_INTERNAL hb_bool_t
-_hb_ot_layout_has_new_glyph_classes (hb_face_t *face);
-
-HB_INTERNAL void
-_hb_ot_layout_set_glyph_property (hb_face_t *face,
- hb_codepoint_t glyph,
- unsigned int property);
-
-HB_INTERNAL void
-_hb_ot_layout_set_glyph_class (hb_face_t *face,
- hb_codepoint_t glyph,
- hb_ot_layout_glyph_class_t klass);
-
-HB_INTERNAL hb_bool_t
-_hb_ot_layout_check_glyph_property (hb_face_t *face,
- hb_internal_glyph_info_t *ginfo,
- unsigned int lookup_flags,
- unsigned int *property);
-
-HB_INTERNAL hb_bool_t
-_hb_ot_layout_skip_mark (hb_face_t *face,
- hb_internal_glyph_info_t *ginfo,
- unsigned int lookup_flags,
- unsigned int *property);
-
-HB_END_DECLS
-
-#endif /* HB_OT_LAYOUT_PRIVATE_H */
diff --git a/src/hb-ot-layout-private.hh b/src/hb-ot-layout-private.hh
new file mode 100644
index 0000000..e18222b
--- /dev/null
+++ b/src/hb-ot-layout-private.hh
@@ -0,0 +1,121 @@
+/*
+ * Copyright (C) 2007,2008,2009 Red Hat, Inc.
+ *
+ * This is part of HarfBuzz, a text shaping library.
+ *
+ * Permission is hereby granted, without written agreement and without
+ * license or royalty fees, to use, copy, modify, and distribute this
+ * software and its documentation for any purpose, provided that the
+ * above copyright notice and the following two paragraphs appear in
+ * all copies of this software.
+ *
+ * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
+ * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
+ * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
+ * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
+ * DAMAGE.
+ *
+ * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
+ * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
+ * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
+ * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
+ *
+ * Red Hat Author(s): Behdad Esfahbod
+ */
+
+#ifndef HB_OT_LAYOUT_PRIVATE_H
+#define HB_OT_LAYOUT_PRIVATE_H
+
+#include "hb-private.h"
+
+#include "hb-ot-layout.h"
+
+#include "hb-font.h"
+#include "hb-buffer-private.hh"
+
+
+HB_BEGIN_DECLS
+
+typedef unsigned int hb_ot_layout_class_t;
+
+/*
+ * hb_ot_layout_t
+ */
+
+typedef struct _hb_ot_layout_t hb_ot_layout_t;
+
+struct _hb_ot_layout_t
+{
+ hb_blob_t *gdef_blob;
+ hb_blob_t *gsub_blob;
+ hb_blob_t *gpos_blob;
+
+ const struct GDEF *gdef;
+ const struct GSUB *gsub;
+ const struct GPOS *gpos;
+
+ struct
+ {
+ unsigned char *klasses;
+ unsigned int len;
+ } new_gdef;
+};
+
+typedef struct _hb_ot_layout_context_t hb_ot_layout_context_t;
+struct _hb_ot_layout_context_t
+{
+ hb_face_t *face;
+ hb_font_t *font;
+
+ union info_t
+ {
+ struct gpos_t
+ {
+ unsigned int last; /* the last valid glyph--used with cursive positioning */
+ hb_position_t anchor_x; /* the coordinates of the anchor point */
+ hb_position_t anchor_y; /* of the last valid glyph */
+ } gpos;
+ } info;
+};
+
+
+void
+_hb_ot_layout_init (hb_face_t *face);
+
+void
+_hb_ot_layout_fini (hb_face_t *face);
+
+
+/*
+ * GDEF
+ */
+
+HB_INTERNAL hb_bool_t
+_hb_ot_layout_has_new_glyph_classes (hb_face_t *face);
+
+HB_INTERNAL void
+_hb_ot_layout_set_glyph_property (hb_face_t *face,
+ hb_codepoint_t glyph,
+ unsigned int property);
+
+HB_INTERNAL void
+_hb_ot_layout_set_glyph_class (hb_face_t *face,
+ hb_codepoint_t glyph,
+ hb_ot_layout_glyph_class_t klass);
+
+HB_INTERNAL hb_bool_t
+_hb_ot_layout_check_glyph_property (hb_face_t *face,
+ hb_internal_glyph_info_t *ginfo,
+ unsigned int lookup_flags,
+ unsigned int *property);
+
+HB_INTERNAL hb_bool_t
+_hb_ot_layout_skip_mark (hb_face_t *face,
+ hb_internal_glyph_info_t *ginfo,
+ unsigned int lookup_flags,
+ unsigned int *property);
+
+HB_END_DECLS
+
+#endif /* HB_OT_LAYOUT_PRIVATE_H */
diff --git a/src/hb-ot-layout.cc b/src/hb-ot-layout.cc
index 5908cdd..63186a3 100644
--- a/src/hb-ot-layout.cc
+++ b/src/hb-ot-layout.cc
@@ -28,7 +28,7 @@
#define HB_OT_LAYOUT_CC
-#include "hb-ot-layout-private.h"
+#include "hb-ot-layout-private.hh"
#include "hb-ot-layout-gdef-private.hh"
#include "hb-ot-layout-gsub-private.hh"
diff --git a/src/hb-ot-shape-private.h b/src/hb-ot-shape-private.h
deleted file mode 100644
index 1183a63..0000000
--- a/src/hb-ot-shape-private.h
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2009 Red Hat, Inc.
- *
- * This is part of HarfBuzz, a text shaping library.
- *
- * Permission is hereby granted, without written agreement and without
- * license or royalty fees, to use, copy, modify, and distribute this
- * software and its documentation for any purpose, provided that the
- * above copyright notice and the following two paragraphs appear in
- * all copies of this software.
- *
- * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
- * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
- * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
- * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
- * DAMAGE.
- *
- * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
- * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
- * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
- * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
- * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
- *
- * Red Hat Author(s): Behdad Esfahbod
- */
-
-#ifndef HB_OT_SHAPE_PRIVATE_H
-#define HB_OT_SHAPE_PRIVATE_H
-
-#include "hb-private.h"
-
-#include "hb-shape.h"
-
-
-HB_BEGIN_DECLS
-
-HB_INTERNAL hb_bool_t
-_hb_ot_substitute_complex (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features,
- unsigned int num_features);
-
-HB_INTERNAL hb_bool_t
-_hb_ot_position_complex (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features,
- unsigned int num_features);
-
-HB_END_DECLS
-
-#endif /* HB_OT_SHAPE_PRIVATE_H */
diff --git a/src/hb-ot-shape-private.hh b/src/hb-ot-shape-private.hh
new file mode 100644
index 0000000..1183a63
--- /dev/null
+++ b/src/hb-ot-shape-private.hh
@@ -0,0 +1,53 @@
+/*
+ * Copyright (C) 2009 Red Hat, Inc.
+ *
+ * This is part of HarfBuzz, a text shaping library.
+ *
+ * Permission is hereby granted, without written agreement and without
+ * license or royalty fees, to use, copy, modify, and distribute this
+ * software and its documentation for any purpose, provided that the
+ * above copyright notice and the following two paragraphs appear in
+ * all copies of this software.
+ *
+ * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
+ * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
+ * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
+ * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
+ * DAMAGE.
+ *
+ * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
+ * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
+ * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
+ * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
+ *
+ * Red Hat Author(s): Behdad Esfahbod
+ */
+
+#ifndef HB_OT_SHAPE_PRIVATE_H
+#define HB_OT_SHAPE_PRIVATE_H
+
+#include "hb-private.h"
+
+#include "hb-shape.h"
+
+
+HB_BEGIN_DECLS
+
+HB_INTERNAL hb_bool_t
+_hb_ot_substitute_complex (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features,
+ unsigned int num_features);
+
+HB_INTERNAL hb_bool_t
+_hb_ot_position_complex (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features,
+ unsigned int num_features);
+
+HB_END_DECLS
+
+#endif /* HB_OT_SHAPE_PRIVATE_H */
diff --git a/src/hb-ot-shape.c b/src/hb-ot-shape.c
deleted file mode 100644
index 7ff8166..0000000
--- a/src/hb-ot-shape.c
+++ /dev/null
@@ -1,164 +0,0 @@
-/*
- * Copyright (C) 2009 Red Hat, Inc.
- *
- * This is part of HarfBuzz, a text shaping library.
- *
- * Permission is hereby granted, without written agreement and without
- * license or royalty fees, to use, copy, modify, and distribute this
- * software and its documentation for any purpose, provided that the
- * above copyright notice and the following two paragraphs appear in
- * all copies of this software.
- *
- * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
- * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
- * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
- * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
- * DAMAGE.
- *
- * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
- * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
- * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
- * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
- * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
- *
- * Red Hat Author(s): Behdad Esfahbod
- */
-
-#include "hb-ot-shape-private.h"
-
-#include "hb-buffer-private.h"
-
-#include "hb-ot-layout.h"
-
-hb_tag_t default_features[] = {
- /* GSUB */
- HB_TAG('c','c','m','p'),
- HB_TAG('l','o','c','l'),
- HB_TAG('l','i','g','a'),
- HB_TAG('c','l','i','g'),
- /* GPOS */
- HB_TAG('k','e','r','n'),
- HB_TAG('m','a','r','k'),
- HB_TAG('m','k','m','k'),
-};
-
-
-static void
-add_feature (hb_face_t *face,
- hb_tag_t table_tag,
- unsigned int feature_index,
- unsigned int *lookups,
- unsigned int *num_lookups,
- unsigned int room_lookups)
-{
- unsigned int i = room_lookups - *num_lookups;
- hb_ot_layout_feature_get_lookup_indexes (face, table_tag, feature_index, 0,
- &i,
- lookups + *num_lookups);
- *num_lookups += i;
-}
-
-static int
-cmp_lookups (const void *p1, const void *p2)
-{
- unsigned int a = * (const unsigned int *) p1;
- unsigned int b = * (const unsigned int *) p2;
-
- return a - b;
-}
-
-static void
-setup_lookups (hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features,
- unsigned int num_features,
- hb_tag_t table_tag,
- unsigned int *lookups,
- unsigned int *num_lookups)
-{
- unsigned int i, j, script_index, language_index, feature_index, room_lookups;
-
- room_lookups = *num_lookups;
- *num_lookups = 0;
-
- hb_ot_layout_table_choose_script (face, table_tag,
- hb_ot_tags_from_script (buffer->script),
- &script_index);
- hb_ot_layout_script_find_language (face, table_tag, script_index,
- hb_ot_tag_from_language (buffer->language),
- &language_index);
-
- if (hb_ot_layout_language_get_required_feature_index (face, table_tag, script_index, language_index,
- &feature_index))
- add_feature (face, table_tag, feature_index, lookups, num_lookups, room_lookups);
-
- for (i = 0; i < ARRAY_LENGTH (default_features); i++)
- {
- if (hb_ot_layout_language_find_feature (face, table_tag, script_index, language_index,
- default_features[i],
- &feature_index))
- add_feature (face, table_tag, feature_index, lookups, num_lookups, room_lookups);
- }
-
- qsort (lookups, *num_lookups, sizeof (lookups[0]), cmp_lookups);
-
- if (*num_lookups)
- {
- for (i = 1, j = 0; i < *num_lookups; i++)
- if (lookups[i] != lookups[j])
- lookups[++j] = lookups[i];
- lookups[j++] = lookups[i - 1];
- *num_lookups = j;
- }
-}
-
-
-hb_bool_t
-_hb_ot_substitute_complex (hb_font_t *font HB_UNUSED,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features,
- unsigned int num_features)
-{
- unsigned int lookups[1000];
- unsigned int num_lookups = ARRAY_LENGTH (lookups);
- unsigned int i;
-
- if (!hb_ot_layout_has_substitution (face))
- return FALSE;
-
- setup_lookups (face, buffer, features, num_features,
- HB_OT_TAG_GSUB,
- lookups, &num_lookups);
-
- for (i = 0; i < num_lookups; i++)
- hb_ot_layout_substitute_lookup (face, buffer, lookups[i], 0xFFFF);
-
- return TRUE;
-}
-
-hb_bool_t
-_hb_ot_position_complex (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features,
- unsigned int num_features)
-{
- unsigned int lookups[1000];
- unsigned int num_lookups = ARRAY_LENGTH (lookups);
- unsigned int i;
-
- if (!hb_ot_layout_has_positioning (face))
- return FALSE;
-
- setup_lookups (face, buffer, features, num_features,
- HB_OT_TAG_GPOS,
- lookups, &num_lookups);
-
- for (i = 0; i < num_lookups; i++)
- hb_ot_layout_position_lookup (font, face, buffer, lookups[i], 0xFFFF);
-
- hb_ot_layout_position_finish (font, face, buffer);
-
- return TRUE;
-}
diff --git a/src/hb-ot-shape.cc b/src/hb-ot-shape.cc
new file mode 100644
index 0000000..61f67cd
--- /dev/null
+++ b/src/hb-ot-shape.cc
@@ -0,0 +1,164 @@
+/*
+ * Copyright (C) 2009 Red Hat, Inc.
+ *
+ * This is part of HarfBuzz, a text shaping library.
+ *
+ * Permission is hereby granted, without written agreement and without
+ * license or royalty fees, to use, copy, modify, and distribute this
+ * software and its documentation for any purpose, provided that the
+ * above copyright notice and the following two paragraphs appear in
+ * all copies of this software.
+ *
+ * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
+ * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
+ * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
+ * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
+ * DAMAGE.
+ *
+ * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
+ * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
+ * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
+ * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
+ *
+ * Red Hat Author(s): Behdad Esfahbod
+ */
+
+#include "hb-ot-shape-private.hh"
+
+#include "hb-buffer-private.hh"
+
+#include "hb-ot-layout.h"
+
+hb_tag_t default_features[] = {
+ /* GSUB */
+ HB_TAG('c','c','m','p'),
+ HB_TAG('l','o','c','l'),
+ HB_TAG('l','i','g','a'),
+ HB_TAG('c','l','i','g'),
+ /* GPOS */
+ HB_TAG('k','e','r','n'),
+ HB_TAG('m','a','r','k'),
+ HB_TAG('m','k','m','k'),
+};
+
+
+static void
+add_feature (hb_face_t *face,
+ hb_tag_t table_tag,
+ unsigned int feature_index,
+ unsigned int *lookups,
+ unsigned int *num_lookups,
+ unsigned int room_lookups)
+{
+ unsigned int i = room_lookups - *num_lookups;
+ hb_ot_layout_feature_get_lookup_indexes (face, table_tag, feature_index, 0,
+ &i,
+ lookups + *num_lookups);
+ *num_lookups += i;
+}
+
+static int
+cmp_lookups (const void *p1, const void *p2)
+{
+ unsigned int a = * (const unsigned int *) p1;
+ unsigned int b = * (const unsigned int *) p2;
+
+ return a - b;
+}
+
+static void
+setup_lookups (hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features,
+ unsigned int num_features,
+ hb_tag_t table_tag,
+ unsigned int *lookups,
+ unsigned int *num_lookups)
+{
+ unsigned int i, j, script_index, language_index, feature_index, room_lookups;
+
+ room_lookups = *num_lookups;
+ *num_lookups = 0;
+
+ hb_ot_layout_table_choose_script (face, table_tag,
+ hb_ot_tags_from_script (buffer->script),
+ &script_index);
+ hb_ot_layout_script_find_language (face, table_tag, script_index,
+ hb_ot_tag_from_language (buffer->language),
+ &language_index);
+
+ if (hb_ot_layout_language_get_required_feature_index (face, table_tag, script_index, language_index,
+ &feature_index))
+ add_feature (face, table_tag, feature_index, lookups, num_lookups, room_lookups);
+
+ for (i = 0; i < ARRAY_LENGTH (default_features); i++)
+ {
+ if (hb_ot_layout_language_find_feature (face, table_tag, script_index, language_index,
+ default_features[i],
+ &feature_index))
+ add_feature (face, table_tag, feature_index, lookups, num_lookups, room_lookups);
+ }
+
+ qsort (lookups, *num_lookups, sizeof (lookups[0]), cmp_lookups);
+
+ if (*num_lookups)
+ {
+ for (i = 1, j = 0; i < *num_lookups; i++)
+ if (lookups[i] != lookups[j])
+ lookups[++j] = lookups[i];
+ lookups[j++] = lookups[i - 1];
+ *num_lookups = j;
+ }
+}
+
+
+hb_bool_t
+_hb_ot_substitute_complex (hb_font_t *font HB_UNUSED,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features,
+ unsigned int num_features)
+{
+ unsigned int lookups[1000];
+ unsigned int num_lookups = ARRAY_LENGTH (lookups);
+ unsigned int i;
+
+ if (!hb_ot_layout_has_substitution (face))
+ return FALSE;
+
+ setup_lookups (face, buffer, features, num_features,
+ HB_OT_TAG_GSUB,
+ lookups, &num_lookups);
+
+ for (i = 0; i < num_lookups; i++)
+ hb_ot_layout_substitute_lookup (face, buffer, lookups[i], 0xFFFF);
+
+ return TRUE;
+}
+
+hb_bool_t
+_hb_ot_position_complex (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features,
+ unsigned int num_features)
+{
+ unsigned int lookups[1000];
+ unsigned int num_lookups = ARRAY_LENGTH (lookups);
+ unsigned int i;
+
+ if (!hb_ot_layout_has_positioning (face))
+ return FALSE;
+
+ setup_lookups (face, buffer, features, num_features,
+ HB_OT_TAG_GPOS,
+ lookups, &num_lookups);
+
+ for (i = 0; i < num_lookups; i++)
+ hb_ot_layout_position_lookup (font, face, buffer, lookups[i], 0xFFFF);
+
+ hb_ot_layout_position_finish (font, face, buffer);
+
+ return TRUE;
+}
diff --git a/src/hb-shape.c b/src/hb-shape.c
deleted file mode 100644
index 6818891..0000000
--- a/src/hb-shape.c
+++ /dev/null
@@ -1,258 +0,0 @@
-/*
- * Copyright (C) 2009 Red Hat, Inc.
- *
- * This is part of HarfBuzz, a text shaping library.
- *
- * Permission is hereby granted, without written agreement and without
- * license or royalty fees, to use, copy, modify, and distribute this
- * software and its documentation for any purpose, provided that the
- * above copyright notice and the following two paragraphs appear in
- * all copies of this software.
- *
- * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
- * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
- * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
- * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
- * DAMAGE.
- *
- * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
- * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
- * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
- * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
- * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
- *
- * Red Hat Author(s): Behdad Esfahbod
- */
-
-#include "hb-private.h"
-
-#include "hb-shape.h"
-
-#include "hb-buffer-private.h"
-
-#include "hb-ot-shape-private.h"
-
-
-/* Prepare */
-
-static inline hb_bool_t
-is_variation_selector (hb_codepoint_t unicode)
-{
- return unlikely ((unicode >= 0x180B && unicode <= 0x180D) || /* MONGOLIAN FREE VARIATION SELECTOR ONE..THREE */
- (unicode >= 0xFE00 && unicode <= 0xFE0F) || /* VARIATION SELECTOR-1..16 */
- (unicode >= 0xE0100 && unicode <= 0xE01EF)); /* VARIATION SELECTOR-17..256 */
-}
-
-static void
-hb_form_clusters (hb_buffer_t *buffer)
-{
- unsigned int count;
-
- count = buffer->in_length;
- for (buffer->in_pos = 1; buffer->in_pos < count; buffer->in_pos++)
- if (buffer->unicode->get_general_category (IN_CURGLYPH()) == HB_CATEGORY_NON_SPACING_MARK)
- IN_CLUSTER (buffer->in_pos) = IN_CLUSTER (buffer->in_pos - 1);
-}
-
-static hb_direction_t
-hb_ensure_native_direction (hb_buffer_t *buffer)
-{
- hb_direction_t original_direction = buffer->direction;
-
- /* TODO vertical */
- if (HB_DIRECTION_IS_HORIZONTAL (original_direction) &&
- original_direction != _hb_script_get_horizontal_direction (buffer->script))
- {
- hb_buffer_reverse_clusters (buffer);
- buffer->direction ^= 1;
- }
-
- return original_direction;
-}
-
-
-/* Substitute */
-
-static void
-hb_mirror_chars (hb_buffer_t *buffer)
-{
- unsigned int count;
- hb_unicode_get_mirroring_func_t get_mirroring = buffer->unicode->get_mirroring;
-
- if (HB_DIRECTION_IS_FORWARD (buffer->direction))
- return;
-
- count = buffer->in_length;
- for (buffer->in_pos = 0; buffer->in_pos < count; buffer->in_pos++) {
- IN_CURGLYPH() = get_mirroring (IN_CURGLYPH());
- }
-}
-
-static void
-hb_map_glyphs (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer)
-{
- unsigned int count;
-
- if (unlikely (!buffer->in_length))
- return;
- count = buffer->in_length - 1;
- for (buffer->in_pos = 0; buffer->in_pos < count; buffer->in_pos++) {
- if (unlikely (is_variation_selector (IN_NEXTGLYPH()))) {
- IN_CURGLYPH() = hb_font_get_glyph (font, face, IN_CURGLYPH(), IN_NEXTGLYPH());
- buffer->in_pos++;
- } else {
- IN_CURGLYPH() = hb_font_get_glyph (font, face, IN_CURGLYPH(), 0);
- }
- }
- IN_CURGLYPH() = hb_font_get_glyph (font, face, IN_CURGLYPH(), 0);
-}
-
-static void
-hb_substitute_default (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features HB_UNUSED,
- unsigned int num_features HB_UNUSED)
-{
- hb_mirror_chars (buffer);
- hb_map_glyphs (font, face, buffer);
-}
-
-static hb_bool_t
-hb_substitute_complex (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features,
- unsigned int num_features)
-{
- return _hb_ot_substitute_complex (font, face, buffer, features, num_features);
-}
-
-static void
-hb_substitute_fallback (hb_font_t *font HB_UNUSED,
- hb_face_t *face HB_UNUSED,
- hb_buffer_t *buffer HB_UNUSED,
- hb_feature_t *features HB_UNUSED,
- unsigned int num_features HB_UNUSED)
-{
- /* TODO Arabic */
-}
-
-
-/* Position */
-
-static void
-hb_position_default (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features HB_UNUSED,
- unsigned int num_features HB_UNUSED)
-{
- unsigned int count;
-
- hb_buffer_clear_positions (buffer);
-
- count = buffer->in_length;
- for (buffer->in_pos = 0; buffer->in_pos < count; buffer->in_pos++) {
- hb_glyph_metrics_t metrics;
- hb_font_get_glyph_metrics (font, face, IN_CURGLYPH(), &metrics);
- CURPOSITION()->x_advance = metrics.x_advance;
- CURPOSITION()->y_advance = metrics.y_advance;
- }
-}
-
-static hb_bool_t
-hb_position_complex (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features,
- unsigned int num_features)
-{
- return _hb_ot_position_complex (font, face, buffer, features, num_features);
-}
-
-static void
-hb_position_fallback (hb_font_t *font HB_UNUSED,
- hb_face_t *face HB_UNUSED,
- hb_buffer_t *buffer HB_UNUSED,
- hb_feature_t *features HB_UNUSED,
- unsigned int num_features HB_UNUSED)
-{
- /* TODO Mark pos */
-}
-
-static void
-hb_truetype_kern (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features HB_UNUSED,
- unsigned int num_features HB_UNUSED)
-{
- unsigned int count;
-
- /* TODO Check for kern=0 */
- count = buffer->in_length;
- for (buffer->in_pos = 1; buffer->in_pos < count; buffer->in_pos++) {
- hb_position_t kern, kern1, kern2;
- kern = hb_font_get_kerning (font, face, IN_GLYPH(buffer->in_pos - 1), IN_CURGLYPH());
- kern1 = kern >> 1;
- kern2 = kern - kern1;
- POSITION(buffer->in_pos - 1)->x_advance += kern1;
- CURPOSITION()->x_advance += kern2;
- CURPOSITION()->x_offset += kern2;
- }
-}
-
-static void
-hb_position_fallback_visual (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features,
- unsigned int num_features)
-{
- hb_truetype_kern (font, face, buffer, features, num_features);
-}
-
-
-/* Shape */
-
-void
-hb_shape (hb_font_t *font,
- hb_face_t *face,
- hb_buffer_t *buffer,
- hb_feature_t *features,
- unsigned int num_features)
-{
- hb_direction_t original_direction;
- hb_bool_t substitute_fallback, position_fallback;
-
- hb_form_clusters (buffer);
-
- hb_substitute_default (font, face, buffer, features, num_features);
-
- /* We do this after substitute_default because mirroring needs to
- * see the original direction. */
- original_direction = hb_ensure_native_direction (buffer);
-
- substitute_fallback = !hb_substitute_complex (font, face, buffer, features, num_features);
-
- if (substitute_fallback)
- hb_substitute_fallback (font, face, buffer, features, num_features);
-
- hb_position_default (font, face, buffer, features, num_features);
-
- position_fallback = !hb_position_complex (font, face, buffer, features, num_features);
-
- if (position_fallback)
- hb_position_fallback (font, face, buffer, features, num_features);
-
- if (HB_DIRECTION_IS_BACKWARD (buffer->direction))
- hb_buffer_reverse (buffer);
-
- if (position_fallback)
- hb_position_fallback_visual (font, face, buffer, features, num_features);
-
- buffer->direction = original_direction;
-}
diff --git a/src/hb-shape.cc b/src/hb-shape.cc
new file mode 100644
index 0000000..ef10375
--- /dev/null
+++ b/src/hb-shape.cc
@@ -0,0 +1,258 @@
+/*
+ * Copyright (C) 2009 Red Hat, Inc.
+ *
+ * This is part of HarfBuzz, a text shaping library.
+ *
+ * Permission is hereby granted, without written agreement and without
+ * license or royalty fees, to use, copy, modify, and distribute this
+ * software and its documentation for any purpose, provided that the
+ * above copyright notice and the following two paragraphs appear in
+ * all copies of this software.
+ *
+ * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
+ * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
+ * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
+ * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
+ * DAMAGE.
+ *
+ * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
+ * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
+ * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
+ * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
+ * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
+ *
+ * Red Hat Author(s): Behdad Esfahbod
+ */
+
+#include "hb-private.h"
+
+#include "hb-shape.h"
+
+#include "hb-buffer-private.hh"
+
+#include "hb-ot-shape-private.hh"
+
+
+/* Prepare */
+
+static inline hb_bool_t
+is_variation_selector (hb_codepoint_t unicode)
+{
+ return unlikely ((unicode >= 0x180B && unicode <= 0x180D) || /* MONGOLIAN FREE VARIATION SELECTOR ONE..THREE */
+ (unicode >= 0xFE00 && unicode <= 0xFE0F) || /* VARIATION SELECTOR-1..16 */
+ (unicode >= 0xE0100 && unicode <= 0xE01EF)); /* VARIATION SELECTOR-17..256 */
+}
+
+static void
+hb_form_clusters (hb_buffer_t *buffer)
+{
+ unsigned int count;
+
+ count = buffer->in_length;
+ for (buffer->in_pos = 1; buffer->in_pos < count; buffer->in_pos++)
+ if (buffer->unicode->get_general_category (IN_CURGLYPH()) == HB_CATEGORY_NON_SPACING_MARK)
+ IN_CLUSTER (buffer->in_pos) = IN_CLUSTER (buffer->in_pos - 1);
+}
+
+static hb_direction_t
+hb_ensure_native_direction (hb_buffer_t *buffer)
+{
+ hb_direction_t original_direction = buffer->direction;
+
+ /* TODO vertical */
+ if (HB_DIRECTION_IS_HORIZONTAL (original_direction) &&
+ original_direction != _hb_script_get_horizontal_direction (buffer->script))
+ {
+ hb_buffer_reverse_clusters (buffer);
+ buffer->direction = HB_DIRECTION_REVERSE (buffer->direction);
+ }
+
+ return original_direction;
+}
+
+
+/* Substitute */
+
+static void
+hb_mirror_chars (hb_buffer_t *buffer)
+{
+ unsigned int count;
+ hb_unicode_get_mirroring_func_t get_mirroring = buffer->unicode->get_mirroring;
+
+ if (HB_DIRECTION_IS_FORWARD (buffer->direction))
+ return;
+
+ count = buffer->in_length;
+ for (buffer->in_pos = 0; buffer->in_pos < count; buffer->in_pos++) {
+ IN_CURGLYPH() = get_mirroring (IN_CURGLYPH());
+ }
+}
+
+static void
+hb_map_glyphs (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer)
+{
+ unsigned int count;
+
+ if (unlikely (!buffer->in_length))
+ return;
+ count = buffer->in_length - 1;
+ for (buffer->in_pos = 0; buffer->in_pos < count; buffer->in_pos++) {
+ if (unlikely (is_variation_selector (IN_NEXTGLYPH()))) {
+ IN_CURGLYPH() = hb_font_get_glyph (font, face, IN_CURGLYPH(), IN_NEXTGLYPH());
+ buffer->in_pos++;
+ } else {
+ IN_CURGLYPH() = hb_font_get_glyph (font, face, IN_CURGLYPH(), 0);
+ }
+ }
+ IN_CURGLYPH() = hb_font_get_glyph (font, face, IN_CURGLYPH(), 0);
+}
+
+static void
+hb_substitute_default (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features HB_UNUSED,
+ unsigned int num_features HB_UNUSED)
+{
+ hb_mirror_chars (buffer);
+ hb_map_glyphs (font, face, buffer);
+}
+
+static hb_bool_t
+hb_substitute_complex (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features,
+ unsigned int num_features)
+{
+ return _hb_ot_substitute_complex (font, face, buffer, features, num_features);
+}
+
+static void
+hb_substitute_fallback (hb_font_t *font HB_UNUSED,
+ hb_face_t *face HB_UNUSED,
+ hb_buffer_t *buffer HB_UNUSED,
+ hb_feature_t *features HB_UNUSED,
+ unsigned int num_features HB_UNUSED)
+{
+ /* TODO Arabic */
+}
+
+
+/* Position */
+
+static void
+hb_position_default (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features HB_UNUSED,
+ unsigned int num_features HB_UNUSED)
+{
+ unsigned int count;
+
+ hb_buffer_clear_positions (buffer);
+
+ count = buffer->in_length;
+ for (buffer->in_pos = 0; buffer->in_pos < count; buffer->in_pos++) {
+ hb_glyph_metrics_t metrics;
+ hb_font_get_glyph_metrics (font, face, IN_CURGLYPH(), &metrics);
+ CURPOSITION()->x_advance = metrics.x_advance;
+ CURPOSITION()->y_advance = metrics.y_advance;
+ }
+}
+
+static hb_bool_t
+hb_position_complex (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features,
+ unsigned int num_features)
+{
+ return _hb_ot_position_complex (font, face, buffer, features, num_features);
+}
+
+static void
+hb_position_fallback (hb_font_t *font HB_UNUSED,
+ hb_face_t *face HB_UNUSED,
+ hb_buffer_t *buffer HB_UNUSED,
+ hb_feature_t *features HB_UNUSED,
+ unsigned int num_features HB_UNUSED)
+{
+ /* TODO Mark pos */
+}
+
+static void
+hb_truetype_kern (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features HB_UNUSED,
+ unsigned int num_features HB_UNUSED)
+{
+ unsigned int count;
+
+ /* TODO Check for kern=0 */
+ count = buffer->in_length;
+ for (buffer->in_pos = 1; buffer->in_pos < count; buffer->in_pos++) {
+ hb_position_t kern, kern1, kern2;
+ kern = hb_font_get_kerning (font, face, IN_GLYPH(buffer->in_pos - 1), IN_CURGLYPH());
+ kern1 = kern >> 1;
+ kern2 = kern - kern1;
+ POSITION(buffer->in_pos - 1)->x_advance += kern1;
+ CURPOSITION()->x_advance += kern2;
+ CURPOSITION()->x_offset += kern2;
+ }
+}
+
+static void
+hb_position_fallback_visual (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features,
+ unsigned int num_features)
+{
+ hb_truetype_kern (font, face, buffer, features, num_features);
+}
+
+
+/* Shape */
+
+void
+hb_shape (hb_font_t *font,
+ hb_face_t *face,
+ hb_buffer_t *buffer,
+ hb_feature_t *features,
+ unsigned int num_features)
+{
+ hb_direction_t original_direction;
+ hb_bool_t substitute_fallback, position_fallback;
+
+ hb_form_clusters (buffer);
+
+ hb_substitute_default (font, face, buffer, features, num_features);
+
+ /* We do this after substitute_default because mirroring needs to
+ * see the original direction. */
+ original_direction = hb_ensure_native_direction (buffer);
+
+ substitute_fallback = !hb_substitute_complex (font, face, buffer, features, num_features);
+
+ if (substitute_fallback)
+ hb_substitute_fallback (font, face, buffer, features, num_features);
+
+ hb_position_default (font, face, buffer, features, num_features);
+
+ position_fallback = !hb_position_complex (font, face, buffer, features, num_features);
+
+ if (position_fallback)
+ hb_position_fallback (font, face, buffer, features, num_features);
+
+ if (HB_DIRECTION_IS_BACKWARD (buffer->direction))
+ hb_buffer_reverse (buffer);
+
+ if (position_fallback)
+ hb_position_fallback_visual (font, face, buffer, features, num_features);
+
+ buffer->direction = original_direction;
+}
commit c3df649f258b334e93c7626a43cd8ebfbd5a610e
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Tue May 11 13:54:12 2010 -0400
Fix comment
diff --git a/src/hb-buffer-private.h b/src/hb-buffer-private.h
index d4a1641..bc562ba 100644
--- a/src/hb-buffer-private.h
+++ b/src/hb-buffer-private.h
@@ -54,8 +54,7 @@ typedef struct _hb_internal_glyph_position_t {
uint32_t back : 16; /* number of glyphs to go back
for drawing current glyph */
int32_t cursive_chain : 16; /* character to which this connects,
- may be positive or negative; used
- only internally */
+ may be positive or negative */
} hb_internal_glyph_position_t;
ASSERT_STATIC (sizeof (hb_glyph_info_t) == sizeof (hb_internal_glyph_info_t));
More information about the HarfBuzz
mailing list