Commit 2c77643e authored by Jacek Caban's avatar Jacek Caban Committed by Alexandre Julliard

gdi32: Support passing an array of chars to NtGdiGetCharWidthW.

And use it for GetCharWidthA. Signed-off-by: 's avatarJacek Caban <jacek@codeweavers.com> Signed-off-by: 's avatarHuw Davies <huw@codeweavers.com> Signed-off-by: 's avatarAlexandre Julliard <julliard@winehq.org>
parent baa60569
......@@ -380,7 +380,8 @@ static BOOL CDECL nulldrv_GetCharABCWidthsI( PHYSDEV dev, UINT first, UINT count
return FALSE;
}
static BOOL CDECL nulldrv_GetCharWidth( PHYSDEV dev, UINT first, UINT last, INT *buffer )
static BOOL CDECL nulldrv_GetCharWidth( PHYSDEV dev, UINT first, UINT count,
const WCHAR *chars, INT *buffer )
{
return FALSE;
}
......
......@@ -3089,27 +3089,29 @@ static BOOL CDECL font_GetCharABCWidthsI( PHYSDEV dev, UINT first, UINT count, W
/*************************************************************
* font_GetCharWidth
*/
static BOOL CDECL font_GetCharWidth( PHYSDEV dev, UINT first, UINT last, INT *buffer )
static BOOL CDECL font_GetCharWidth( PHYSDEV dev, UINT first, UINT count,
const WCHAR *chars, INT *buffer )
{
struct font_physdev *physdev = get_font_dev( dev );
UINT c, i;
ABC abc;
UINT c;
if (!physdev->font)
{
dev = GET_NEXT_PHYSDEV( dev, pGetCharWidth );
return dev->funcs->pGetCharWidth( dev, first, last, buffer );
return dev->funcs->pGetCharWidth( dev, first, count, chars, buffer );
}
TRACE( "%p, %d, %d, %p\n", physdev->font, first, last, buffer );
TRACE( "%p, %d, %d, %p\n", physdev->font, first, count, buffer );
EnterCriticalSection( &font_cs );
for (c = first; c <= last; c++)
for (i = 0; i < count; i++)
{
c = chars ? chars[i] : i + first;
if (get_glyph_outline( physdev->font, c, GGO_METRICS, NULL, &abc, 0, NULL, NULL ) == GDI_ERROR)
buffer[c - first] = 0;
buffer[i] = 0;
else
buffer[c - first] = abc.abcA + abc.abcB + abc.abcC;
buffer[i] = abc.abcA + abc.abcB + abc.abcC;
}
LeaveCriticalSection( &font_cs );
return TRUE;
......@@ -4864,25 +4866,26 @@ static LPSTR FONT_GetCharsByRangeA(HDC hdc, UINT firstChar, UINT lastChar, PINT
/***********************************************************************
* NtGdiGetCharWidthW (win32u.@)
*/
BOOL WINAPI NtGdiGetCharWidthW( HDC hdc, UINT firstChar, UINT lastChar, WCHAR *chars,
BOOL WINAPI NtGdiGetCharWidthW( HDC hdc, UINT first, UINT last, WCHAR *chars,
ULONG flags, void *buf )
{
UINT i;
UINT i, count = last;
BOOL ret;
PHYSDEV dev;
DC * dc = get_dc_ptr( hdc );
if (!dc) return FALSE;
if (!chars) count = last - first + 1;
dev = GET_DC_PHYSDEV( dc, pGetCharWidth );
ret = dev->funcs->pGetCharWidth( dev, firstChar, lastChar, buf );
ret = dev->funcs->pGetCharWidth( dev, first, count, chars, buf );
if (ret)
{
INT *buffer = buf;
/* convert device units to logical */
for( i = firstChar; i <= lastChar; i++, buffer++ )
*buffer = width_to_LP( dc, *buffer );
for (i = 0; i < count; i++)
buffer[i] = width_to_LP( dc, buffer[i] );
}
release_dc_ptr( dc );
return ret;
......@@ -6479,7 +6482,7 @@ BOOL WINAPI GetCharWidthFloatW( HDC hdc, UINT first, UINT last, float *buffer )
}
dev = GET_DC_PHYSDEV( dc, pGetCharWidth );
if ((ret = dev->funcs->pGetCharWidth( dev, first, last, ibuffer )))
if ((ret = dev->funcs->pGetCharWidth( dev, first, last - first + 1, NULL, ibuffer )))
{
float scale = fabs( dc->xformVport2World.eM11 ) / 16.0f;
for (i = first; i <= last; ++i)
......
......@@ -1580,12 +1580,13 @@ BOOL WINAPI GetCharWidth32W( HDC hdc, UINT first, UINT last, INT *buffer )
return NtGdiGetCharWidthW( hdc, first, last, NULL, NTGDI_GETCHARWIDTH_INT, buffer );
}
static char *get_chars_by_range( HDC hdc, UINT first, UINT last, INT *byte_len )
static WCHAR *get_chars_by_range( HDC hdc, UINT first, UINT last, INT *ret_len )
{
INT i, count = last - first + 1;
WCHAR *wstr;
char *str;
UINT mbcp;
UINT c;
LPSTR str;
if (count <= 0)
return NULL;
......@@ -1628,8 +1629,9 @@ static char *get_chars_by_range( HDC hdc, UINT first, UINT last, INT *byte_len )
}
str[i] = '\0';
*byte_len = i;
return str;
wstr = text_mbtowc( hdc, str, i, ret_len, NULL );
HeapFree( GetProcessHeap(), 0, str );
return wstr;
}
/***********************************************************************
......@@ -1638,28 +1640,12 @@ static char *get_chars_by_range( HDC hdc, UINT first, UINT last, INT *byte_len )
*/
BOOL WINAPI GetCharWidth32A( HDC hdc, UINT first, UINT last, INT *buffer )
{
INT i, wlen;
LPSTR str;
LPWSTR wstr;
BOOL ret = TRUE;
str = get_chars_by_range( hdc, first, last, &i );
if (str == NULL)
return FALSE;
wstr = text_mbtowc( hdc, str, i, &wlen, NULL );
for(i = 0; i < wlen; i++)
{
if(!GetCharWidth32W( hdc, wstr[i], wstr[i], buffer ))
{
ret = FALSE;
break;
}
buffer++;
}
WCHAR *chars;
INT count;
BOOL ret;
HeapFree( GetProcessHeap(), 0, str );
HeapFree( GetProcessHeap(), 0, wstr );
if (!(chars = get_chars_by_range( hdc, first, last, &count ))) return FALSE;
ret = NtGdiGetCharWidthW( hdc, 0, count, chars, NTGDI_GETCHARWIDTH_INT, buffer );
HeapFree( GetProcessHeap(), 0, chars );
return ret;
}
......@@ -343,28 +343,30 @@ BOOL CDECL PSDRV_GetTextExtentExPoint(PHYSDEV dev, LPCWSTR str, INT count, LPINT
/***********************************************************************
* PSDRV_GetCharWidth
*/
BOOL CDECL PSDRV_GetCharWidth(PHYSDEV dev, UINT firstChar, UINT lastChar, LPINT buffer)
BOOL CDECL PSDRV_GetCharWidth(PHYSDEV dev, UINT first, UINT count, const WCHAR *chars, INT *buffer)
{
PSDRV_PDEVICE *physDev = get_psdrv_dev( dev );
UINT i;
UINT i, c;
if (physDev->font.fontloc == Download)
{
dev = GET_NEXT_PHYSDEV( dev, pGetCharWidth );
return dev->funcs->pGetCharWidth( dev, firstChar, lastChar, buffer );
return dev->funcs->pGetCharWidth( dev, first, count, chars, buffer );
}
TRACE("U+%.4X U+%.4X\n", firstChar, lastChar);
TRACE("U+%.4X +%u\n", first, count);
if (lastChar > 0xffff || firstChar > lastChar)
for (i = 0; i < count; ++i)
{
SetLastError(ERROR_INVALID_PARAMETER);
return FALSE;
}
c = chars ? chars[i] : first + i;
for (i = firstChar; i <= lastChar; ++i)
{
*buffer = floor( PSDRV_UVMetrics(i, physDev->font.fontinfo.Builtin.afm)->WX
if (c > 0xffff)
{
SetLastError(ERROR_INVALID_PARAMETER);
return FALSE;
}
*buffer = floor( PSDRV_UVMetrics(c, physDev->font.fontinfo.Builtin.afm)->WX
* physDev->font.fontinfo.Builtin.scale + 0.5 );
TRACE("U+%.4X: %i\n", i, *buffer);
++buffer;
......
......@@ -439,7 +439,7 @@ extern INT CDECL PSDRV_ExtEscape( PHYSDEV dev, INT nEscape, INT cbInput, LPCVOID
extern BOOL CDECL PSDRV_ExtTextOut( PHYSDEV dev, INT x, INT y, UINT flags,
const RECT *lprect, LPCWSTR str, UINT count, const INT *lpDx ) DECLSPEC_HIDDEN;
extern BOOL CDECL PSDRV_FillPath( PHYSDEV dev ) DECLSPEC_HIDDEN;
extern BOOL CDECL PSDRV_GetCharWidth(PHYSDEV dev, UINT firstChar, UINT lastChar, LPINT buffer) DECLSPEC_HIDDEN;
extern BOOL CDECL PSDRV_GetCharWidth(PHYSDEV dev, UINT first, UINT count, const WCHAR *chars, INT *buffer) DECLSPEC_HIDDEN;
extern BOOL CDECL PSDRV_GetTextExtentExPoint(PHYSDEV dev, LPCWSTR str, INT count, LPINT alpDx) DECLSPEC_HIDDEN;
extern BOOL CDECL PSDRV_GetTextMetrics(PHYSDEV dev, TEXTMETRICW *metrics) DECLSPEC_HIDDEN;
extern BOOL CDECL PSDRV_LineTo(PHYSDEV dev, INT x, INT y) DECLSPEC_HIDDEN;
......
......@@ -99,7 +99,7 @@ struct gdi_dc_funcs
UINT (CDECL *pGetBoundsRect)(PHYSDEV,RECT*,UINT);
BOOL (CDECL *pGetCharABCWidths)(PHYSDEV,UINT,UINT,LPABC);
BOOL (CDECL *pGetCharABCWidthsI)(PHYSDEV,UINT,UINT,WORD*,LPABC);
BOOL (CDECL *pGetCharWidth)(PHYSDEV,UINT,UINT,LPINT);
BOOL (CDECL *pGetCharWidth)(PHYSDEV,UINT,UINT,const WCHAR*,LPINT);
BOOL (CDECL *pGetCharWidthInfo)(PHYSDEV,void*);
INT (CDECL *pGetDeviceCaps)(PHYSDEV,INT);
BOOL (CDECL *pGetDeviceGammaRamp)(PHYSDEV,LPVOID);
......@@ -169,7 +169,7 @@ struct gdi_dc_funcs
};
/* increment this when you change the DC function table */
#define WINE_GDI_DRIVER_VERSION 64
#define WINE_GDI_DRIVER_VERSION 65
#define GDI_PRIORITY_NULL_DRV 0 /* null driver */
#define GDI_PRIORITY_FONT_DRV 100 /* any font driver */
......
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