Aric Stewart : usp10: Use a bsearch function to find a glyph in the LogClust array.
Alexandre Julliard
julliard at winehq.org
Mon Jan 30 14:05:57 CST 2012
Module: wine
Branch: master
Commit: 4df4929198696161e1daf7ee006997e425654a15
URL: http://source.winehq.org/git/wine.git/?a=commit;h=4df4929198696161e1daf7ee006997e425654a15
Author: Aric Stewart <aric at codeweavers.com>
Date: Mon Jan 30 07:30:08 2012 -0600
usp10: Use a bsearch function to find a glyph in the LogClust array.
---
dlls/usp10/opentype.c | 7 +++-
dlls/usp10/shape.c | 60 +++++++++++++++++-------------------------
dlls/usp10/usp10.c | 52 +++++++++++++++++++++++++++++++++---
dlls/usp10/usp10_internal.h | 2 +
4 files changed, 78 insertions(+), 43 deletions(-)
diff --git a/dlls/usp10/opentype.c b/dlls/usp10/opentype.c
index c30d513..3c0af41 100644
--- a/dlls/usp10/opentype.c
+++ b/dlls/usp10/opentype.c
@@ -438,9 +438,12 @@ void OpenType_GDEF_UpdateGlyphProps(HDC hdc, ScriptCache *psc, const WORD *pwGly
int char_count = 0;
int k;
- for (k = 0; k < cChars; k++)
- if (pwLogClust[k] == i)
+ k = USP10_FindGlyphInLogClust(pwLogClust, cChars, i);
+ if (k >= 0)
+ {
+ for (; k < cChars && pwLogClust[k] == i; k++)
char_count++;
+ }
class = GDEF_get_glyph_class(psc->GDEF_Table, pwGlyphs[i]);
diff --git a/dlls/usp10/shape.c b/dlls/usp10/shape.c
index a893f7e..5ba6e6f 100644
--- a/dlls/usp10/shape.c
+++ b/dlls/usp10/shape.c
@@ -2359,13 +2359,11 @@ static void ShapeCharGlyphProp_Default( HDC hdc, ScriptCache* psc, SCRIPT_ANALYS
int char_index[20];
int char_count = 0;
- for (k = 0; k < cChars; k++)
+ k = USP10_FindGlyphInLogClust(pwLogClust, cChars, i);
+ if (k>=0)
{
- if (pwLogClust[k] == i)
- {
- char_index[char_count] = k;
- char_count++;
- }
+ for (; k < cChars && pwLogClust[k] == i; k++)
+ char_index[char_count++] = k;
}
if (char_count == 0)
@@ -2425,13 +2423,11 @@ static void ShapeCharGlyphProp_Arabic( HDC hdc, ScriptCache *psc, SCRIPT_ANALYSI
int char_count = 0;
BOOL isInit, isFinal;
- for (k = 0; k < cChars; k++)
+ k = USP10_FindGlyphInLogClust(pwLogClust, cChars, i);
+ if (k>=0)
{
- if (pwLogClust[k] == i)
- {
- char_index[char_count] = k;
- char_count++;
- }
+ for (; k < cChars && pwLogClust[k] == i; k++)
+ char_index[char_count++] = k;
}
isInit = (i == initGlyph || (i+dirR > 0 && i+dirR < cGlyphs && spaces[i+dirR]));
@@ -2534,13 +2530,11 @@ static void ShapeCharGlyphProp_Thai( HDC hdc, ScriptCache *psc, SCRIPT_ANALYSIS
int char_index[20];
int char_count = 0;
- for (k = 0; k < cChars; k++)
+ k = USP10_FindGlyphInLogClust(pwLogClust, cChars, i);
+ if (k>=0)
{
- if (pwLogClust[k] == i)
- {
- char_index[char_count] = k;
- char_count++;
- }
+ for (; k < cChars && pwLogClust[k] == i; k++)
+ char_index[char_count++] = k;
}
if (char_count == 0)
@@ -2581,13 +2575,11 @@ static void ShapeCharGlyphProp_None( HDC hdc, ScriptCache* psc, SCRIPT_ANALYSIS*
int char_index[20];
int char_count = 0;
- for (k = 0; k < cChars; k++)
+ k = USP10_FindGlyphInLogClust(pwLogClust, cChars, i);
+ if (k>=0)
{
- if (pwLogClust[k] == i)
- {
- char_index[char_count] = k;
- char_count++;
- }
+ for (; k < cChars && pwLogClust[k] == i; k++)
+ char_index[char_count++] = k;
}
if (char_count == 0)
@@ -2614,13 +2606,11 @@ static void ShapeCharGlyphProp_Tibet( HDC hdc, ScriptCache* psc, SCRIPT_ANALYSIS
int char_index[20];
int char_count = 0;
- for (k = 0; k < cChars; k++)
+ k = USP10_FindGlyphInLogClust(pwLogClust, cChars, i);
+ if (k>=0)
{
- if (pwLogClust[k] == i)
- {
- char_index[char_count] = k;
- char_count++;
- }
+ for (; k < cChars && pwLogClust[k] == i; k++)
+ char_index[char_count++] = k;
}
if (char_count == 0)
@@ -2658,13 +2648,11 @@ static void ShapeCharGlyphProp_BaseIndic( HDC hdc, ScriptCache *psc, SCRIPT_ANAL
int char_index[20];
int char_count = 0;
- for (k = 0; k < cChars; k++)
+ k = USP10_FindGlyphInLogClust(pwLogClust, cChars, i);
+ if (k>=0)
{
- if (pwLogClust[k] == i)
- {
- char_index[char_count] = k;
- char_count++;
- }
+ for (; k < cChars && pwLogClust[k] == i; k++)
+ char_index[char_count++] = k;
}
if (override_gsub)
diff --git a/dlls/usp10/usp10.c b/dlls/usp10/usp10.c
index ef8a7ac..beecce9 100644
--- a/dlls/usp10/usp10.c
+++ b/dlls/usp10/usp10.c
@@ -25,6 +25,7 @@
*/
#include <stdarg.h>
+#include <stdlib.h>
#include "windef.h"
#include "winbase.h"
@@ -703,6 +704,11 @@ typedef struct {
int* logical2visual;
} StringAnalysis;
+typedef struct {
+ BOOL ascending;
+ WORD target;
+} FindGlyph_struct;
+
static inline void *heap_alloc(SIZE_T size)
{
return HeapAlloc(GetProcessHeap(), 0, size);
@@ -881,6 +887,46 @@ static WORD get_char_script( LPCWSTR str, INT index, INT end, INT *consumed)
return SCRIPT_UNDEFINED;
}
+static int compare_FindGlyph(const void *a, const void* b)
+{
+ const FindGlyph_struct *find = (FindGlyph_struct*)a;
+ const WORD *idx= (WORD*)b;
+ int rc = 0;
+
+ if ( find->target > *idx)
+ rc = 1;
+ else if (find->target < *idx)
+ rc = -1;
+
+ if (!find->ascending)
+ rc *= -1;
+ return rc;
+}
+
+int USP10_FindGlyphInLogClust(const WORD* pwLogClust, int cChars, WORD target)
+{
+ FindGlyph_struct fgs;
+ WORD *ptr;
+ INT k;
+
+ if (pwLogClust[0] < pwLogClust[cChars-1])
+ fgs.ascending = TRUE;
+ else
+ fgs.ascending = FALSE;
+
+ fgs.target = target;
+ ptr = bsearch(&fgs, pwLogClust, cChars, sizeof(WORD), compare_FindGlyph);
+
+ if (!ptr)
+ return -1;
+
+ for (k = (ptr - pwLogClust)-1; k >= 0 && pwLogClust[k] == target; k--)
+ ;
+ k++;
+
+ return k;
+}
+
/***********************************************************************
* DllMain
*
@@ -1873,13 +1919,9 @@ error:
static inline BOOL does_glyph_start_cluster(const SCRIPT_VISATTR *pva, const WORD *pwLogClust, int cChars, int glyph, int direction)
{
- int i;
-
if (pva[glyph].fClusterStart)
return TRUE;
- for (i = 0; i < cChars; i++)
- if (pwLogClust[i] == glyph) break;
- if (i != cChars)
+ if (USP10_FindGlyphInLogClust(pwLogClust, cChars, glyph) >= 0)
return TRUE;
return FALSE;
diff --git a/dlls/usp10/usp10_internal.h b/dlls/usp10/usp10_internal.h
index 02beaf6..558eb55 100644
--- a/dlls/usp10/usp10_internal.h
+++ b/dlls/usp10/usp10_internal.h
@@ -204,6 +204,8 @@ typedef void (*reorder_function)(LPWSTR pwChar, IndicSyllable *syllable, lexical
#define BIDI_WEAK 2
#define BIDI_NEUTRAL 0
+int USP10_FindGlyphInLogClust(const WORD* pwLogClust, int cChars, WORD target) DECLSPEC_HIDDEN;
+
BOOL BIDI_DetermineLevels( LPCWSTR lpString, INT uCount, const SCRIPT_STATE *s,
const SCRIPT_CONTROL *c, WORD *lpOutLevels ) DECLSPEC_HIDDEN;
BOOL BIDI_GetStrengths(LPCWSTR lpString, INT uCount, const SCRIPT_CONTROL *c,
More information about the wine-cvs
mailing list