https://git.reactos.org/?p=reactos.git;a=commitdiff;h=806fe486fb3598e3bdb33…
commit 806fe486fb3598e3bdb336226cd93751fe0719c5
Author: winesync <ros-dev(a)reactos.org>
AuthorDate: Mon Sep 21 23:06:33 2020 +0200
Commit: Jérôme Gardou <jerome.gardou(a)reactos.org>
CommitDate: Thu Feb 4 16:37:06 2021 +0100
[WINESYNC] d3dx9: Handle word breaks in ID3DXFont_DrawText.
Signed-off-by: Sven Baars <sbaars(a)codeweavers.com>
Signed-off-by: Matteo Bruni <mbruni(a)codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard(a)winehq.org>
wine commit id e6a1116c2a3b196dea496f77747209f67982652c by Sven Baars
<sbaars(a)codeweavers.com>
---
dll/directx/wine/d3dx9_36/d3dx9.cmake | 2 +-
dll/directx/wine/d3dx9_36/font.c | 61 ++++++++++++++++++++++++++++--
dll/directx/wine/d3dx9_36/precomp.h | 1 +
modules/rostests/winetests/d3dx9_36/core.c | 22 +++++------
sdk/tools/winesync/d3dx9.cfg | 2 +-
5 files changed, 72 insertions(+), 16 deletions(-)
diff --git a/dll/directx/wine/d3dx9_36/d3dx9.cmake
b/dll/directx/wine/d3dx9_36/d3dx9.cmake
index cb8d937a561..082c03e5201 100644
--- a/dll/directx/wine/d3dx9_36/d3dx9.cmake
+++ b/dll/directx/wine/d3dx9_36/d3dx9.cmake
@@ -40,7 +40,7 @@ function(add_d3dx9_target __version)
set_module_type(${module} win32dll)
add_dependencies(${module} d3d_idl_headers)
target_link_libraries(${module} dxguid wine)
- add_importlibs(${module} d3dcompiler_43 d3dxof user32 ole32 gdi32 msvcrt kernel32
ntdll)
+ add_importlibs(${module} d3dcompiler_43 d3dxof usp10 user32 ole32 gdi32 msvcrt
kernel32 ntdll)
add_delay_importlibs(${module} windowscodecs)
add_pch(${module} ../d3dx9_36/precomp.h "${PCH_SKIP_SOURCE}")
add_cd_file(TARGET ${module} DESTINATION reactos/system32 FOR all)
diff --git a/dll/directx/wine/d3dx9_36/font.c b/dll/directx/wine/d3dx9_36/font.c
index 8b122abd14f..28ad573cda9 100644
--- a/dll/directx/wine/d3dx9_36/font.c
+++ b/dll/directx/wine/d3dx9_36/font.c
@@ -22,6 +22,8 @@
#include "d3dx9_private.h"
+
+#include "usp10.h"
#endif /* __REACTOS__ */
WINE_DEFAULT_DEBUG_CHANNEL(d3dx);
@@ -513,10 +515,53 @@ static INT WINAPI ID3DXFontImpl_DrawTextA(ID3DXFont *iface,
ID3DXSprite *sprite,
return ret;
}
+static void word_break(HDC hdc, const WCHAR *str, unsigned int *str_len,
+ unsigned int chars_fit, unsigned int *chars_used, SIZE *size)
+{
+ SCRIPT_LOGATTR *sla;
+ SCRIPT_ANALYSIS sa;
+ unsigned int i;
+
+ *chars_used = 0;
+
+ sla = heap_alloc(*str_len * sizeof(*sla));
+ if (!sla)
+ return;
+
+ memset(&sa, 0, sizeof(sa));
+ sa.eScript = SCRIPT_UNDEFINED;
+
+ ScriptBreak(str, *str_len, &sa, sla);
+
+ /* Work back from the last character that did fit to a place where we can break */
+ i = chars_fit;
+ while (i > 0 && !sla[i].fSoftBreak) /* chars_fit < *str_len so this is
valid */
+ --i;
+
+ /* If the there is no word that fits put in all characters that do fit */
+ if (!sla[i].fSoftBreak)
+ i = chars_fit;
+
+ *chars_used = i;
+ if (sla[i].fWhiteSpace)
+ ++(*chars_used);
+
+ /* Remove extra spaces */
+ while (i > 0 && sla[i-1].fWhiteSpace)
+ --i;
+ *str_len = i;
+
+ /* Remeasure the string */
+ GetTextExtentExPointW(hdc, str, *str_len, 0, NULL, NULL, size);
+ heap_free(sla);
+}
+
static const WCHAR *read_line(HDC hdc, const WCHAR *str, int *count,
- WCHAR *dest, unsigned int *dest_len, int width)
+ WCHAR *dest, unsigned int *dest_len, int width, DWORD format)
{
unsigned int i = 0;
+ int orig_count = *count;
+ int num_fit;
SIZE size;
*dest_len = 0;
@@ -528,7 +573,17 @@ static const WCHAR *read_line(HDC hdc, const WCHAR *str, int *count,
++i;
}
- GetTextExtentExPointW(hdc, dest, *dest_len, width, NULL, NULL, &size);
+ num_fit = 0;
+ GetTextExtentExPointW(hdc, dest, *dest_len, width, &num_fit, NULL, &size);
+
+ if (num_fit < *dest_len && (format & DT_WORDBREAK))
+ {
+ unsigned int chars_used;
+
+ word_break(hdc, dest, dest_len, num_fit, &chars_used, &size);
+ *count = orig_count - chars_used;
+ i = chars_used;
+ }
if (*count && str[i] == '\n')
{
@@ -598,7 +653,7 @@ static INT WINAPI ID3DXFontImpl_DrawTextW(ID3DXFont *iface,
ID3DXSprite *sprite,
{
unsigned int line_len;
- string = read_line(font->hdc, string, &count, line, &line_len,
width);
+ string = read_line(font->hdc, string, &count, line, &line_len, width,
format);
if (!(format & DT_CALCRECT))
{
diff --git a/dll/directx/wine/d3dx9_36/precomp.h b/dll/directx/wine/d3dx9_36/precomp.h
index b6a35522a31..4325ad715c5 100644
--- a/dll/directx/wine/d3dx9_36/precomp.h
+++ b/dll/directx/wine/d3dx9_36/precomp.h
@@ -20,6 +20,7 @@
#include <winbase.h>
#include <wingdi.h>
#include <winuser.h>
+#include <usp10.h>
#include <wine/winternl.h>
diff --git a/modules/rostests/winetests/d3dx9_36/core.c
b/modules/rostests/winetests/d3dx9_36/core.c
index c79f5c1f728..45cde62b3a8 100644
--- a/modules/rostests/winetests/d3dx9_36/core.c
+++ b/modules/rostests/winetests/d3dx9_36/core.c
@@ -722,7 +722,7 @@ static void test_ID3DXFont(IDirect3DDevice9 *device)
todo_wine ok(height == 60, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextA(font, NULL, long_text, -1, &rect, DT_WORDBREAK |
DT_NOCLIP, 0xff00ff);
- todo_wine ok(height == 96, "Got unexpected height %d.\n", height);
+ ok(height == 96, "Got unexpected height %d.\n", height);
SetRect(&rect, 10, 10, 200, 200);
@@ -759,7 +759,7 @@ static void test_ID3DXFont(IDirect3DDevice9 *device)
todo_wine ok(height == 60, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, long_textW, -1, &rect, DT_WORDBREAK |
DT_NOCLIP, 0xff00ff);
- todo_wine ok(height == 96, "Got unexpected height %d.\n", height);
+ ok(height == 96, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"a\na", -1, &rect, 0,
0xff00ff);
ok(height == 24, "Got unexpected height %d.\n", height);
@@ -777,7 +777,7 @@ static void test_ID3DXFont(IDirect3DDevice9 *device)
ok(height == 24, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"a\naaaaa aaaa", -1, &rect,
DT_WORDBREAK, 0xff00ff);
- todo_wine ok(height == 36, "Got unexpected height %d.\n", height);
+ ok(height == 36, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"1\n2\n3\n4\n5\n6", -1,
&rect, 0, 0xff00ff);
ok(height == 48, "Got unexpected height %d.\n", height);
@@ -789,16 +789,16 @@ static void test_ID3DXFont(IDirect3DDevice9 *device)
todo_wine ok(height == 0, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"\t\t\t\t\t\t\t\t\t\ta", -1,
&rect, DT_WORDBREAK, 0xff00ff);
- ok(height == 12, "Got unexpected height %d.\n", height);
+ todo_wine ok(height == 12, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"\taaaaaaaaaa", -1, &rect,
DT_WORDBREAK, 0xff00ff);
todo_wine ok(height == 24, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"\taaaaaaaaaa", -1, &rect,
DT_EXPANDTABS | DT_WORDBREAK, 0xff00ff);
- todo_wine ok(height == 36, "Got unexpected height %d.\n", height);
+ ok(height == 36, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"\taaa\taaa\taaa", -1, &rect,
DT_WORDBREAK, 0xff00ff);
- todo_wine ok(height == 24, "Got unexpected height %d.\n", height);
+ ok(height == 24, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"\taaa\taaa\taaa", -1, &rect,
DT_EXPANDTABS | DT_WORDBREAK, 0xff00ff);
todo_wine ok(height == 48, "Got unexpected height %d.\n", height);
@@ -813,19 +813,19 @@ static void test_ID3DXFont(IDirect3DDevice9 *device)
todo_wine ok(height == 24, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"aaaaaaaaaaaaaaaaaaaa", -1,
&rect, DT_WORDBREAK, 0xff00ff);
- todo_wine ok(height == 36, "Got unexpected height %d.\n", height);
+ ok(height == 36, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"a a", -1,
&rect, DT_WORDBREAK, 0xff00ff);
- todo_wine ok(height == 36, "Got unexpected height %d.\n", height);
+ ok(height == 36, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"aaaa aaaa", -1,
&rect, DT_WORDBREAK, 0xff00ff);
- todo_wine ok(height == 36, "Got unexpected height %d.\n", height);
+ ok(height == 36, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"aaaa aaaa", -1,
&rect, DT_WORDBREAK | DT_RIGHT, 0xff00ff);
- todo_wine ok(height == 36, "Got unexpected height %d.\n", height);
+ ok(height == 36, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"aaaa aaaa", -1,
&rect, DT_WORDBREAK | DT_RIGHT, 0xff00ff);
- todo_wine ok(height == 36, "Got unexpected height %d.\n", height);
+ ok(height == 36, "Got unexpected height %d.\n", height);
height = ID3DXFont_DrawTextW(font, NULL, L"aaaa\naaaa", -1, &rect,
DT_BOTTOM, 0xff00ff);
todo_wine ok(height == 40, "Got unexpected height %d.\n", height);
diff --git a/sdk/tools/winesync/d3dx9.cfg b/sdk/tools/winesync/d3dx9.cfg
index 135d55d8c2f..3d6a83cd72a 100644
--- a/sdk/tools/winesync/d3dx9.cfg
+++ b/sdk/tools/winesync/d3dx9.cfg
@@ -15,4 +15,4 @@ files: {include/d3dx9.h: sdk/include/dxsdk/d3dx9.h, include/d3dx9anim.h:
sdk/inc
include/d3dx9mesh.h: sdk/include/dxsdk/d3dx9mesh.h, include/d3dx9of.h:
sdk/include/dxsdk/d3dx9of.h,
include/d3dx9shader.h: sdk/include/dxsdk/d3dx9shader.h, include/d3dx9shape.h:
sdk/include/dxsdk/d3dx9shape.h,
include/d3dx9tex.h: sdk/include/dxsdk/d3dx9tex.h, include/d3dx9xof.h:
sdk/include/dxsdk/d3dx9xof.h}
-tags: {wine: 6da3e904a1efc921030fdbe34070b981bf57524c}
+tags: {wine: e6a1116c2a3b196dea496f77747209f67982652c}