hb-shape.cc revision 3ca6c4ecc299295b6682fa2b6b9f83b213223bad
115232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod/* 22409d5f8d7dd8b535ce5ea29e933f7db27d33793Behdad Esfahbod * Copyright © 2009 Red Hat, Inc. 315232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * 4c755cb3e3ac55156d0d2ec05adea7a650b97cc41Behdad Esfahbod * This is part of HarfBuzz, a text shaping library. 515232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * 615232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * Permission is hereby granted, without written agreement and without 715232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * license or royalty fees, to use, copy, modify, and distribute this 815232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * software and its documentation for any purpose, provided that the 915232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * above copyright notice and the following two paragraphs appear in 1015232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * all copies of this software. 1115232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * 1215232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR 1315232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES 1415232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN 1515232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH 1615232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * DAMAGE. 1715232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * 1815232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, 1915232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND 2015232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS 2115232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO 2215232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS. 2315232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * 2415232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod * Red Hat Author(s): Behdad Esfahbod 2515232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod */ 2615232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod 27c57d454accff66e5f2c58006e8fb40bc020b6182Behdad Esfahbod#include "hb-private.hh" 2815232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod 2915232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod#include "hb-shape.h" 3015232e26f4a89dab1b6de35ad9d3d16e75bf93d0Behdad Esfahbod 3122da7fd94d6318c52df69d70470a85464ffc533dBehdad Esfahbod#include "hb-buffer-private.hh" 322f50d873680ce0a43b6ec79df1ac946b91f31e63Behdad Esfahbod 3302aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod#ifdef HAVE_UNISCRIBE 3402aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod# include "hb-uniscribe.h" 35305ba8671553cd955c20a54db622666c0bb02532Behdad Esfahbod#endif 3602aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod#ifdef HAVE_OT 3702aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod# include "hb-ot-shape.h" 3802aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod#endif 3902aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod#include "hb-fallback-shape-private.hh" 4002aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod 4102aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbodtypedef hb_bool_t (*hb_shape_func_t) (hb_font_t *font, 4202aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod hb_buffer_t *buffer, 4302aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod const hb_feature_t *features, 4402aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod unsigned int num_features, 4502aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod const char *shaper_options); 4602aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod 4702aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod#define HB_SHAPER_IMPLEMENT(name) {#name, hb_##name##_shape} 4802aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbodstatic const struct hb_shaper_pair_t { 4902aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod const char name[16]; 5002aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod hb_shape_func_t func; 5102aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod} shapers[] = { 5202aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod /* v--- Add new shapers in the right place here */ 5302aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod#ifdef HAVE_UNISCRIBE 5402aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod HB_SHAPER_IMPLEMENT (uniscribe), 5502aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod#endif 5602aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod#ifdef HAVE_OT 5702aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod HB_SHAPER_IMPLEMENT (ot), 5802aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod#endif 5902aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod HB_SHAPER_IMPLEMENT (fallback) /* should be last */ 6002aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod}; 6102aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod#undef HB_SHAPER_IMPLEMENT 6202aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod 6302aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbodstatic class static_shaper_list_t { 6402aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod public: 6502aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod static_shaper_list_t (void) { 6602aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod char *env = getenv ("HB_SHAPER_LIST"); 6702aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_list = NULL; 6802aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod if (!env || !*env) 6902aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod return; 7002aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod unsigned int count = 3; /* initial, fallback, null */ 7102aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod for (const char *p = env; (p == strchr (p, ':')) && p++; ) 7202aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod count++; 7302aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod if (count <= ARRAY_LENGTH (static_shaper_list)) 7402aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_list = static_shaper_list; 7502aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod else 7602aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_list = (const char **) malloc (count * sizeof (shaper_list[0])); 7702aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod 7802aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod count = 0; 7902aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_list[count++] = env; 8002aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod for (char *p = env; (p == strchr (p, ':')) && (*p = '\0', TRUE) && p++; ) 8102aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_list[count++] = p; 8202aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_list[count++] = "fallback"; 8302aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_list[count] = NULL; 8402aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod } 8502aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod const char **shaper_list; 8602aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod const char *static_shaper_list[10]; 8702aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod} env_shaper_list; 8802aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod 8902aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbodhb_bool_t 903ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbodhb_shape_full (hb_font_t *font, 913ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod hb_buffer_t *buffer, 923ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod const hb_feature_t *features, 933ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod unsigned int num_features, 943ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod const char *shaper_options, 953ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod const char **shaper_list) 963286fc0e9adc3f2874c9409e7fdb09e4d2b7dda1Behdad Esfahbod{ 9702aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod if (likely (!shaper_list)) 9802aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_list = env_shaper_list.shaper_list; 9902aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod 10002aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod if (likely (!shaper_list)) { 10102aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod for (unsigned int i = 0; i < ARRAY_LENGTH (shapers); i++) 10202aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod if (likely (shapers[i].func (font, buffer, 10302aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod features, num_features, 10402aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_options))) 10502aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod return TRUE; 10602aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod } else { 10702aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod while (*shaper_list) { 10802aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod for (unsigned int i = 0; i < ARRAY_LENGTH (shapers); i++) 10902aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod if (0 == strcmp (*shaper_list, shapers[i].name) && 11002aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod likely (shapers[i].func (font, buffer, 11102aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod features, num_features, 11202aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_options))) 11302aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod return TRUE; 11402aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod shaper_list++; 1153286fc0e9adc3f2874c9409e7fdb09e4d2b7dda1Behdad Esfahbod } 1163286fc0e9adc3f2874c9409e7fdb09e4d2b7dda1Behdad Esfahbod } 11702aeca985b570763342c35e99af90025bfa088d5Behdad Esfahbod return FALSE; 1183286fc0e9adc3f2874c9409e7fdb09e4d2b7dda1Behdad Esfahbod} 1193ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod 1203ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbodvoid 1213ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbodhb_shape (hb_font_t *font, 1223ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod hb_buffer_t *buffer, 1233ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod const hb_feature_t *features, 1243ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod unsigned int num_features) 1253ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod{ 1263ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod hb_shape_full (font, buffer, features, num_features, NULL, NULL); 1273ca6c4ecc299295b6682fa2b6b9f83b213223badBehdad Esfahbod} 128