Commit 6c3659c3 authored by Aric Stewart's avatar Aric Stewart Committed by Alexandre Julliard

usp10: Improve ScriptItemize with a SCRIPT_CONTROL and SCRIPT_STATE set.

Reduce bidi duplications from gdi32 by using the newly corrected usp10 functions.
parent 50aa0215
......@@ -8,6 +8,7 @@ IMPORTLIB = gdi32
IMPORTS = advapi32 kernel32 ntdll
EXTRAINCL = @FREETYPEINCL@ @FONTCONFIGINCL@
EXTRALIBS = @CARBONLIB@
DELAYIMPORTS = usp10
C_SRCS = \
bidi.c \
......
......@@ -7,6 +7,7 @@ IMPORTLIB = usp10
IMPORTS = gdi32 kernel32
C_SRCS = \
bidi.c \
usp10.c
@MAKE_DLL_RULES@
......@@ -3,6 +3,7 @@
*
* Copyright 2005 Steven Edwards for CodeWeavers
* Copyright 2006 Hans Leidekker
* Copyright 2010 CodeWeavers, Aric Stewart
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
......@@ -32,6 +33,8 @@
#include "winnls.h"
#include "usp10.h"
#include "usp10_internal.h"
#include "wine/debug.h"
#include "wine/unicode.h"
......@@ -524,6 +527,7 @@ HRESULT WINAPI ScriptItemize(const WCHAR *pwcInChars, int cInChars, int cMaxItem
int cnt = 0, index = 0;
int New_Script = SCRIPT_UNDEFINED;
WORD *levels = NULL;
TRACE("%s,%d,%d,%p,%p,%p,%p\n", debugstr_wn(pwcInChars, cInChars), cInChars, cMaxItems,
psControl, psState, pItems, pcItems);
......@@ -531,6 +535,24 @@ HRESULT WINAPI ScriptItemize(const WCHAR *pwcInChars, int cInChars, int cMaxItem
if (!pwcInChars || !cInChars || !pItems || cMaxItems < 2)
return E_INVALIDARG;
if (psState && psControl)
{
int i;
levels = heap_alloc_zero(cInChars * sizeof(WORD));
if (!levels)
return E_OUTOFMEMORY;
BIDI_DetermineLevels(pwcInChars, cInChars, psState, psControl, levels);
for (i = 0; i < cInChars; i++)
if (levels[i]!=levels[0])
break;
if (i >= cInChars)
{
heap_free(levels);
levels = NULL;
}
}
pItems[index].iCharPos = 0;
memset(&pItems[index].a, 0, sizeof(SCRIPT_ANALYSIS));
......@@ -549,15 +571,29 @@ HRESULT WINAPI ScriptItemize(const WCHAR *pwcInChars, int cInChars, int cMaxItem
if (pwcInChars[cnt] >= Latin_start && pwcInChars[cnt] <= Latin_stop)
pItems[index].a.eScript = Script_Latin;
if (pItems[index].a.eScript == Script_Arabic)
if (levels)
{
pItems[index].a.fRTL = odd(levels[cnt]);
pItems[index].a.fLayoutRTL = odd(levels[cnt]);
pItems[index].a.s.uBidiLevel = levels[cnt];
}
else if (pItems[index].a.eScript == Script_Arabic)
{
pItems[index].a.s.uBidiLevel = 1;
pItems[index].a.fRTL = 1;
pItems[index].a.fLayoutRTL = 1;
}
TRACE("New_Script=%d, eScript=%d index=%d cnt=%d iCharPos=%d\n",
New_Script, pItems[index].a.eScript, index, cnt,
TRACE("New_Level=%i New_Script=%d, eScript=%d index=%d cnt=%d iCharPos=%d\n",
levels?levels[cnt]:-1, New_Script, pItems[index].a.eScript, index, cnt,
pItems[index].iCharPos);
for (cnt=1; cnt < cInChars; cnt++)
{
if (levels && (levels[cnt] == pItems[index].a.s.uBidiLevel))
continue;
if (pwcInChars[cnt] == '\r')
New_Script = Script_CR;
else
......@@ -578,9 +614,9 @@ HRESULT WINAPI ScriptItemize(const WCHAR *pwcInChars, int cInChars, int cMaxItem
else
New_Script = SCRIPT_UNDEFINED;
if (New_Script != pItems[index].a.eScript)
if ((levels && (levels[cnt] != pItems[index].a.s.uBidiLevel)) || New_Script != pItems[index].a.eScript)
{
TRACE("New_Script=%d, eScript=%d ", New_Script, pItems[index].a.eScript);
TRACE("New_Level = %i, New_Script=%d, eScript=%d ", levels?levels[cnt]:-1, New_Script, pItems[index].a.eScript);
index++;
if (index+1 > cMaxItems)
return E_OUTOFMEMORY;
......@@ -588,9 +624,18 @@ HRESULT WINAPI ScriptItemize(const WCHAR *pwcInChars, int cInChars, int cMaxItem
pItems[index].iCharPos = cnt;
memset(&pItems[index].a, 0, sizeof(SCRIPT_ANALYSIS));
if (New_Script == Script_Arabic)
if (levels)
{
pItems[index].a.fRTL = odd(levels[cnt]);
pItems[index].a.fLayoutRTL = odd(levels[cnt]);
pItems[index].a.s.uBidiLevel = levels[cnt];
}
else if (New_Script == Script_Arabic)
{
pItems[index].a.s.uBidiLevel = 1;
pItems[index].a.fRTL = 1;
pItems[index].a.fLayoutRTL = 1;
}
pItems[index].a.eScript = New_Script;
TRACE("index=%d cnt=%d iCharPos=%d\n", index, cnt, pItems[index].iCharPos);
......@@ -610,6 +655,7 @@ HRESULT WINAPI ScriptItemize(const WCHAR *pwcInChars, int cInChars, int cMaxItem
/* Set SCRIPT_ITEM */
pItems[index+1].iCharPos = cnt; /* the last + 1 item
contains the ptr to the lastchar */
heap_free(levels);
return S_OK;
}
......
/*
* Implementation of Uniscribe Script Processor (usp10.dll)
*
* Copyright 2010 CodeWeavers, Aric Stewart
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*
*/
#define odd(x) ((x) & 1)
BOOL BIDI_DetermineLevels( LPCWSTR lpString, INT uCount, const SCRIPT_STATE *s,
const SCRIPT_CONTROL *c, WORD *lpOutLevels );
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment