[CPAL] Add palette entry and enable palette flag API
authorEbrahim Byagowi <ebrahim@gnu.org>
Sun, 21 Oct 2018 06:14:16 +0000 (09:44 +0330)
committerKhaled Hosny <khaledhosny@eglug.org>
Mon, 22 Oct 2018 08:17:31 +0000 (10:17 +0200)
src/hb-ot-color-cpal-table.hh
src/hb-ot-color.cc
src/hb-ot-color.h
test/api/test-ot-color.c

index f86e5b9..2c9ac5f 100644 (file)
@@ -48,32 +48,47 @@ struct CPALV1Tail
   friend struct CPAL;
 
   inline bool
-  sanitize (hb_sanitize_context_t *c, const void *base, unsigned int palettes) const
+  sanitize (hb_sanitize_context_t *c, const void *base,
+           unsigned int palettes, unsigned int paletteEntries) const
   {
     TRACE_SANITIZE (this);
     return_trace (c->check_struct (this) &&
                  (base+paletteFlagsZ).sanitize (c, palettes) &&
-                 (base+paletteLabelZ).sanitize (c, palettes) /*&&
-                 (base+paletteEntryLabelZ).sanitize (c, palettes)*/);
+                 (base+paletteLabelZ).sanitize (c, palettes) &&
+                 (base+paletteEntryLabelZ).sanitize (c, paletteEntries));
   }
 
   private:
-  #if 0
   inline hb_ot_color_palette_flags_t
-  get_palette_flags (const void *base, unsigned int palette) const
+  get_palette_flags (const void *base, unsigned int palette,
+                    unsigned int palettes_count) const
   {
-    // range checked at the CPAL caller
+    if (unlikely (palette >= palettes_count))
+      return HB_OT_COLOR_PALETTE_FLAG_DEFAULT;
+
     return (hb_ot_color_palette_flags_t) (uint32_t) (base+paletteFlagsZ)[palette];
   }
-  #endif
 
   inline unsigned int
-  get_palette_name_id (const void *base, unsigned int palette) const
+  get_palette_name_id (const void *base, unsigned int palette,
+                      unsigned int palettes_count) const
   {
-    // range checked at the CPAL caller
+    if (unlikely (palette >= palettes_count))
+      return HB_NAME_ID_INVALID;
+
     return (base+paletteLabelZ)[palette];
   }
 
+  inline unsigned int
+  get_palette_entry_name_id (const void *base, unsigned int palette_entry,
+                            unsigned int palettes_entries_count) const
+  {
+    if (unlikely (palette_entry >= palettes_entries_count))
+      return HB_NAME_ID_INVALID;
+
+    return (base+paletteEntryLabelZ)[palette_entry];
+  }
+
   protected:
   LOffsetTo<UnsizedArrayOf<HBUINT32>, false>
                paletteFlagsZ;          /* Offset from the beginning of CPAL table to
@@ -83,12 +98,12 @@ struct CPALV1Tail
                paletteLabelZ;          /* Offset from the beginning of CPAL table to
                                         * the Palette Labels Array. Set to 0 if no
                                         * array is provided. */
-  /*LOffsetTo<UnsizedArrayOf<HBUINT16>, false>
-               paletteEntryLabelZ;*/   /* Offset from the beginning of CPAL table to
+  LOffsetTo<UnsizedArrayOf<HBUINT16>, false>
+               paletteEntryLabelZ;     /* Offset from the beginning of CPAL table to
                                         * the Palette Entry Label Array. Set to 0
                                         * if no array is provided. */
   public:
-  DEFINE_SIZE_STATIC (/*12*/8);
+  DEFINE_SIZE_STATIC (12);
 };
 
 typedef HBUINT32 BGRAColor;
@@ -115,7 +130,7 @@ struct CPAL
       return_trace (true);
 
     const CPALV1Tail &v1 = StructAfter<CPALV1Tail> (*this);
-    return_trace (likely (v1.sanitize (c, this, numPalettes)));
+    return_trace (likely (v1.sanitize (c, this, numPalettes, numPaletteEntries)));
   }
 
   inline unsigned int get_size (void) const
@@ -123,35 +138,38 @@ struct CPAL
     return min_size + numPalettes * sizeof (HBUINT16);
   }
 
-  #if 0
   inline hb_ot_color_palette_flags_t get_palette_flags (unsigned int palette) const
   {
-    if (unlikely (version == 0 || palette >= numPalettes))
+    if (unlikely (version == 0))
       return HB_OT_COLOR_PALETTE_FLAG_DEFAULT;
 
     const CPALV1Tail& cpal1 = StructAfter<CPALV1Tail> (*this);
-    return cpal1.get_palette_flags (this, palette);
+    return cpal1.get_palette_flags (this, palette, numPalettes);
   }
-  #endif
 
   inline unsigned int get_palette_name_id (unsigned int palette) const
   {
-    if (unlikely (version == 0 || palette >= numPalettes))
+    if (unlikely (version == 0))
       return HB_NAME_ID_INVALID;
 
     const CPALV1Tail& cpal1 = StructAfter<CPALV1Tail> (*this);
-    return cpal1.get_palette_name_id (this, palette);
+    return cpal1.get_palette_name_id (this, palette, numPalettes);
   }
 
-  inline unsigned int get_palette_count () const
+  inline unsigned int get_palette_entry_name_id (unsigned int palette_entry) const
   {
-    return numPalettes;
+    if (unlikely (version == 0))
+      return HB_NAME_ID_INVALID;
+
+    const CPALV1Tail& cpal1 = StructAfter<CPALV1Tail> (*this);
+    return cpal1.get_palette_entry_name_id (this, palette_entry, numPaletteEntries);
   }
 
+  inline unsigned int get_palette_count () const
+  { return numPalettes; }
+
   inline unsigned int get_palette_entries_count () const
-  {
-    return numPaletteEntries;
-  }
+  { return numPaletteEntries; }
 
   bool
   get_color_record_argb (unsigned int color_index, unsigned int palette, hb_color_t* color) const
index 8d444ab..1fbb381 100644 (file)
@@ -84,7 +84,7 @@ hb_ot_color_has_colr_data (hb_face_t *face)
  * hb_ot_color_get_palette_count:
  * @face: a font face.
  *
- * Returns: whether CPAL table available
+ * Returns:
  *
  * Since: REPLACEME
  */
@@ -95,6 +95,57 @@ hb_ot_color_get_palette_count (hb_face_t *face)
 }
 
 /**
+ * hb_ot_color_get_palette_name_id:
+ * @face: a font face.
+ * @palette: the index of the color palette whose name is being requested.
+ *
+ * Retrieves the name id of a color palette. For example, a color font can
+ * have themed palettes like "Spring", "Summer", "Fall", and "Winter".
+ *
+ * Returns: an identifier within @face's `name` table.
+ * If the requested palette has no name, or if @face has no colors,
+ * or if @palette is not between 0 and hb_ot_color_get_palette_count(),
+ * the result is 0xFFFF. The implementation does not check whether
+ * the returned palette name id is actually in @face's `name` table.
+ *
+ * Since: REPLACEME
+ */
+hb_name_id_t
+hb_ot_color_get_palette_name_id (hb_face_t *face, unsigned int palette)
+{
+  return _get_cpal (face).get_palette_name_id (palette);
+}
+
+/**
+ * hb_ot_color_get_palette_count:
+ * @face: a font face.
+ *
+ * Returns: Number of entries on each palette
+ *
+ * Since: REPLACEME
+ */
+unsigned int
+hb_ot_color_get_palette_entry_count (hb_face_t *face)
+{
+  return _get_cpal (face).get_palette_entries_count ();
+}
+
+/**
+ * hb_ot_color_get_palette_entry_name_id:
+ * @face: a font face.
+ * @palette_entry:
+ *
+ * Returns: Name ID associated with an palette entry, e.g. eye color
+ *
+ * Since: REPLACEME
+ */
+hb_name_id_t
+hb_ot_color_get_palette_entry_name_id (hb_face_t *face, unsigned int palette_entry)
+{
+  return _get_cpal (face).get_palette_entry_name_id (palette_entry);
+}
+
+/**
  * hb_ot_color_get_palette_colors:
  * @face:         a font face.
  * @palette:      the index of the color palette whose colors
@@ -150,6 +201,17 @@ hb_ot_color_get_palette_colors (hb_face_t      *face,
   return cpal.get_palette_entries_count ();
 }
 
+/**
+ * hb_ot_color_get_color_layers:
+ * @gid:
+ * @start_offset:
+ * @count:  (inout) (optional):
+ * @color_indices: (array length=color_count) (optional):
+ *
+ * Returns:
+ *
+ * Since: REPLACEME
+ */
 unsigned int
 hb_ot_color_get_color_layers (hb_face_t        *face,
                              hb_codepoint_t    gid,
@@ -180,29 +242,6 @@ hb_ot_color_get_color_layers (hb_face_t        *face,
 }
 
 /**
- * hb_ot_color_get_palette_name_id:
- * @face: a font face.
- * @palette: the index of the color palette whose name is being requested.
- *
- * Retrieves the name id of a color palette. For example, a color font can
- * have themed palettes like "Spring", "Summer", "Fall", and "Winter".
- *
- * Returns: an identifier within @face's `name` table.
- * If the requested palette has no name, or if @face has no colors,
- * or if @palette is not between 0 and hb_ot_color_get_palette_count(),
- * the result is 0xFFFF. The implementation does not check whether
- * the returned palette name id is actually in @face's `name` table.
- *
- * Since: REPLACEME
- */
-hb_name_id_t
-hb_ot_color_get_palette_name_id (hb_face_t *face, unsigned int palette)
-{
-  return _get_cpal (face).get_palette_name_id (palette);
-}
-
-#if 0
-/**
  * hb_ot_color_get_palette_flags:
  * @face: a font face
  * @palette: the index of the color palette whose flags are being requested
@@ -219,25 +258,3 @@ hb_ot_color_get_palette_flags (hb_face_t *face, unsigned int palette)
   const OT::CPAL& cpal = _get_cpal(face);
   return cpal.get_palette_flags (palette);
 }
-
-/*
- * Following parts to be moved to a public header.
- */
-
-/**
- * hb_ot_color_palette_flags_t:
- * @HB_OT_COLOR_PALETTE_FLAG_DEFAULT: default indicating that there is nothing special to note about a color palette.
- * @HB_OT_COLOR_PALETTE_FLAG_FOR_LIGHT_BACKGROUND: flag indicating that the color palette is suitable for rendering text on light background.
- * @HB_OT_COLOR_PALETTE_FLAG_FOR_DARK_BACKGROUND: flag indicating that the color palette is suitable for rendering text on dark background.
- *
- * Since: DONTREPLACEME
- */
-typedef enum { /*< flags >*/
-  HB_OT_COLOR_PALETTE_FLAG_DEFAULT = 0x00000000u,
-  HB_OT_COLOR_PALETTE_FLAG_FOR_LIGHT_BACKGROUND = 0x00000001u,
-  HB_OT_COLOR_PALETTE_FLAG_FOR_DARK_BACKGROUND = 0x00000002u,
-} hb_ot_color_palette_flags_t;
-
-HB_EXTERN hb_ot_color_palette_flags_t
-hb_ot_color_get_palette_flags (hb_face_t *face, unsigned int palette);
-#endif
index 62e873b..25b6217 100644 (file)
@@ -51,6 +51,12 @@ HB_EXTERN hb_name_id_t
 hb_ot_color_get_palette_name_id (hb_face_t *face, unsigned int palette);
 
 HB_EXTERN unsigned int
+hb_ot_color_get_palette_entry_count (hb_face_t *face);
+
+HB_EXTERN hb_name_id_t
+hb_ot_color_get_palette_entry_name_id (hb_face_t *face, unsigned int palette_entry);
+
+HB_EXTERN unsigned int
 hb_ot_color_get_palette_colors (hb_face_t      *face,
                                unsigned int    palette,      /* default=0 */
                                unsigned int    start_offset,
@@ -65,6 +71,23 @@ hb_ot_color_get_color_layers (hb_face_t       *face,
                              hb_codepoint_t  *gids,         /* OUT */
                              unsigned int    *color_indices /* OUT */);
 
+/**
+ * hb_ot_color_palette_flags_t:
+ * @HB_OT_COLOR_PALETTE_FLAG_DEFAULT: default indicating that there is nothing special to note about a color palette.
+ * @HB_OT_COLOR_PALETTE_FLAG_FOR_LIGHT_BACKGROUND: flag indicating that the color palette is suitable for rendering text on light background.
+ * @HB_OT_COLOR_PALETTE_FLAG_FOR_DARK_BACKGROUND: flag indicating that the color palette is suitable for rendering text on dark background.
+ *
+ * Since: REPLACEME
+ */
+typedef enum { /*< flags >*/
+  HB_OT_COLOR_PALETTE_FLAG_DEFAULT = 0x00000000u,
+  HB_OT_COLOR_PALETTE_FLAG_FOR_LIGHT_BACKGROUND = 0x00000001u,
+  HB_OT_COLOR_PALETTE_FLAG_FOR_DARK_BACKGROUND = 0x00000002u,
+} hb_ot_color_palette_flags_t;
+
+HB_EXTERN hb_ot_color_palette_flags_t
+hb_ot_color_get_palette_flags (hb_face_t *face, unsigned int palette);
+
 HB_END_DECLS
 
 #endif /* HB_OT_COLOR_H */
index 1065c4a..843cf33 100644 (file)
@@ -129,6 +129,7 @@ test_hb_ot_color_get_palette_count (void)
   g_assert_cmpint (hb_ot_color_get_palette_count (cpal_v1), ==, 3);
 }
 
+
 static void
 test_hb_ot_color_get_palette_name_id_empty (void)
 {
@@ -137,6 +138,7 @@ test_hb_ot_color_get_palette_name_id_empty (void)
   g_assert_cmpint (hb_ot_color_get_palette_name_id (hb_face_get_empty(), 1), ==, HB_NAME_ID_INVALID);
 }
 
+
 static void
 test_hb_ot_color_get_palette_name_id_v0 (void)
 {
@@ -147,6 +149,7 @@ test_hb_ot_color_get_palette_name_id_v0 (void)
   g_assert_cmpint (hb_ot_color_get_palette_name_id (cpal_v0, 2), ==, HB_NAME_ID_INVALID);
 }
 
+
 static void
 test_hb_ot_color_get_palette_name_id_v1 (void)
 {
@@ -158,7 +161,7 @@ test_hb_ot_color_get_palette_name_id_v1 (void)
   g_assert_cmpint (hb_ot_color_get_palette_name_id (cpal_v1, 3), ==, HB_NAME_ID_INVALID);
 }
 
-#if 0
+
 static void
 test_hb_ot_color_get_palette_flags_empty (void)
 {
@@ -189,7 +192,6 @@ test_hb_ot_color_get_palette_flags_v1 (void)
   /* numPalettes=3, so palette #3 is out of bounds */
   g_assert_cmpint (hb_ot_color_get_palette_flags (cpal_v0, 3), ==, HB_OT_COLOR_PALETTE_FLAG_DEFAULT);
 }
-#endif
 
 
 static void
@@ -290,6 +292,28 @@ test_hb_ot_color_get_palette_colors_v1 (void)
   assert_color_rgba (colors, 2, 0x77, 0x77, 0x77, 0x77);  /* untouched */
 }
 
+
+static void
+test_hb_ot_color_get_palette_entry (void)
+{
+  hb_face_t *empty = hb_face_get_empty ();
+
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_count (empty), ==, 0);
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_count (cpal_v0), ==, 2);
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_count (cpal_v1), ==, 2);
+
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_name_id (empty, 0), ==, HB_NAME_ID_INVALID);
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_name_id (empty, 1), ==, HB_NAME_ID_INVALID);
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_name_id (empty, 2), ==, HB_NAME_ID_INVALID);
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_name_id (cpal_v0, 0), ==, HB_NAME_ID_INVALID);
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_name_id (cpal_v0, 1), ==, HB_NAME_ID_INVALID);
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_name_id (cpal_v0, 2), ==, HB_NAME_ID_INVALID);
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_name_id (cpal_v1, 0), ==, HB_NAME_ID_INVALID);
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_name_id (cpal_v1, 1), ==, 256);
+  g_assert_cmpuint (hb_ot_color_get_palette_entry_name_id (cpal_v1, 2), ==, HB_NAME_ID_INVALID);
+}
+
+
 static void
 test_hb_ot_color_get_color_layers (void)
 {
@@ -328,12 +352,13 @@ main (int argc, char **argv)
   hb_test_add (test_hb_ot_color_get_palette_name_id_empty);
   hb_test_add (test_hb_ot_color_get_palette_name_id_v0);
   hb_test_add (test_hb_ot_color_get_palette_name_id_v1);
-  // hb_test_add (test_hb_ot_color_get_palette_flags_empty);
-  // hb_test_add (test_hb_ot_color_get_palette_flags_v0);
-  // hb_test_add (test_hb_ot_color_get_palette_flags_v1);
+  hb_test_add (test_hb_ot_color_get_palette_flags_empty);
+  hb_test_add (test_hb_ot_color_get_palette_flags_v0);
+  hb_test_add (test_hb_ot_color_get_palette_flags_v1);
   hb_test_add (test_hb_ot_color_get_palette_colors_empty);
   hb_test_add (test_hb_ot_color_get_palette_colors_v0);
   hb_test_add (test_hb_ot_color_get_palette_colors_v1);
+  hb_test_add (test_hb_ot_color_get_palette_entry);
   hb_test_add (test_hb_ot_color_get_color_layers);
   status = hb_test_run();
   hb_face_destroy (cpal_v0);