Reintegrated UTF-16 stuff we need immediately and prepared the test suite for it.
This commit is contained in:
parent
3f392d04ce
commit
188d9f736f
10
test/test.h
10
test/test.h
|
@ -96,9 +96,19 @@ extern const char testUTF8WithFourByte[];
|
|||
extern const char testUTF8Combined[];
|
||||
extern const char testUTF8InvalidInput[];
|
||||
extern const char testUTF8InvalidOutput[];
|
||||
extern const uint16_t testUTF16Empty[];
|
||||
extern const uint16_t testUTF16ASCIIOnly[];
|
||||
extern const uint16_t testUTF16WithTwoByte[];
|
||||
extern const uint16_t testUTF16WithThreeByte[];
|
||||
extern const uint16_t testUTF16WithFourByte[];
|
||||
extern const uint16_t testUTF16Combined[];
|
||||
extern const uint16_t testUTF16InvalidOutput[];
|
||||
extern bool utf8equal(const char *s, const char *t);
|
||||
extern void utf8diffErrorFull(const char *file, long line, const char *msg, const char *got, const char *want);
|
||||
#define utf8diffError(msg, got, want) utf8diffErrorFull(__FILE__, __LINE__, msg, got, want)
|
||||
extern bool utf16equal(const uint16_t *s, const uint16_t *t);
|
||||
extern void utf16diffErrorFull(const char *file, long line, const char *msg, const uint16_t *got, const uint16_t *want);
|
||||
#define utf16diffError(msg, got, want) utf16diffErrorFull(__FILE__, __LINE__, msg, got, want)
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
|
59
test/utf8.c
59
test/utf8.c
|
@ -43,6 +43,16 @@ const char testUTF8WithFourByte[] = { 0x74, 0xF0, 0x9D, 0x90, 0x9E, 0x73, 0x74,
|
|||
const char testUTF8Combined[] = { 0x74, 0x65, 0xCC, 0x81, 0x73, 0x74, 0 };
|
||||
const char testUTF8InvalidInput[] = { 0x74, 0xC3, 0x29, 0x73, 0x74, 0 };
|
||||
const char testUTF8InvalidOutput[] = { 0x74, 0xEF, 0xBF, 0xBD, 0x29, 0x73, 0x74, 0 };
|
||||
// TODO multiline versions
|
||||
|
||||
const uint16_t testUTF16Empty[] = { 0 };
|
||||
const uint16_t testUTF16ASCIIOnly[] = { 0x0074, 0x0065, 0x0073, 0x0074, 0 };
|
||||
const uint16_t testUTF16WithTwoByte[] = { 0x0074, 0x00E9, 0x0073, 0x0074, 0 };
|
||||
const uint16_t testUTF16WithThreeByte[] = { 0x0074, 0x24D4, 0x0073, 0x0074, 0 };
|
||||
const uint16_t testUTF16WithFourByte[] = { 0x0074, 0xD835, 0xDC1E, 0x0073, 0x0074, 0 };
|
||||
const uint16_t testUTF16Combined[] = { 0x0074, 0x0065, 0x0301, 0x0073, 0x0074, 0 };
|
||||
// no UTF-16 invalid input since we don't input UTF-16
|
||||
const uint16_t testUTF16InvalidOutput[] = { 0x0074, 0xFFFD, 0x0029, 0x0073, 0x0074, 0 };
|
||||
|
||||
// TODO figure out if strcmp() is adequate for this
|
||||
bool utf8equal(const char *s, const char *t)
|
||||
|
@ -91,3 +101,52 @@ void utf8diffErrorFull(const char *file, long line, const char *msg, const char
|
|||
utf8hexdump(b, want);
|
||||
TestErrorfFull(file, line, "%s:" diff("%s"), msg, a, b);
|
||||
}
|
||||
|
||||
bool utf16equal(const uint16_t *s, const uint16_t *t)
|
||||
{
|
||||
for (;;) {
|
||||
if (*s == 0 && *t == 0)
|
||||
return true;
|
||||
if (*s == 0 || *t == 0)
|
||||
return false;
|
||||
if (*s != *t)
|
||||
return false;
|
||||
s++;
|
||||
t++;
|
||||
}
|
||||
}
|
||||
|
||||
static void utf16hexdump(char buf[64], const uint16_t *s)
|
||||
{
|
||||
int i;
|
||||
uint16_t x;
|
||||
|
||||
for (i = 0; i < 60; i += 5) {
|
||||
x = (uint16_t) (*s);
|
||||
s++;
|
||||
buf[i + 0] = "0123456789ABCDEF"[(x & 0xF000) >> 12];
|
||||
buf[i + 1] = "0123456789ABCDEF"[(x & 0x0F00) >> 8];
|
||||
buf[i + 2] = "0123456789ABCDEF"[(x & 0x00F0) >> 4];
|
||||
buf[i + 3] = "0123456789ABCDEF"[x & 0x000F];
|
||||
if (x == 0) {
|
||||
buf[i + 4] = '\0';
|
||||
break;
|
||||
}
|
||||
buf[i + 4] = ' ';
|
||||
}
|
||||
if (i >= 60) {
|
||||
buf[60] = '.';
|
||||
buf[61] = '.';
|
||||
buf[62] = '.';
|
||||
buf[63] = '\0';
|
||||
}
|
||||
}
|
||||
|
||||
void utf16diffErrorFull(const char *file, long line, const char *msg, const uint16_t *got, const uint16_t *want)
|
||||
{
|
||||
char a[64], b[64];
|
||||
|
||||
utf16hexdump(a, got);
|
||||
utf16hexdump(b, want);
|
||||
TestErrorfFull(file, line, "%s:" diff("%s"), msg, a, b);
|
||||
}
|
||||
|
|
|
@ -5,7 +5,9 @@ windows = import('windows')
|
|||
libui_sources += [
|
||||
'windows/controls.cpp',
|
||||
'windows/main.cpp',
|
||||
'windows/utf16.cpp',
|
||||
'windows/utilwin.cpp',
|
||||
'windows/window.cpp',
|
||||
'windows/winhresult.cpp',
|
||||
]
|
||||
|
||||
|
|
|
@ -19,3 +19,7 @@ extern HRESULT uiprivInitUtilWindow(HICON hDefaultIcon, HCURSOR hDefaultCursor);
|
|||
|
||||
// window.cpp
|
||||
extern HRESULT uiprivRegisterWindowClass(HICON hDefaultIcon, HCURSOR hDefaultCursor);
|
||||
|
||||
// utf16.cpp
|
||||
extern WCHAR *uiprivToUTF16(const char *str);
|
||||
extern char *uiprivToUTF8(const WCHAR *wstr);
|
||||
|
|
|
@ -1,9 +1,10 @@
|
|||
// 21 april 2016
|
||||
#include "uipriv_windows.hpp"
|
||||
|
||||
// see http://stackoverflow.com/a/29556509/3408572
|
||||
// TODO clean this up
|
||||
#define emptyUTF16() ((WCHAR *) uiprivAlloc(1 * sizeof (WCHAR), "WCHAR[]"))
|
||||
|
||||
WCHAR *toUTF16(const char *str)
|
||||
WCHAR *uiprivToUTF16(const char *str)
|
||||
{
|
||||
WCHAR *wstr;
|
||||
WCHAR *wp;
|
||||
|
@ -23,7 +24,7 @@ WCHAR *toUTF16(const char *str)
|
|||
return wstr;
|
||||
}
|
||||
|
||||
char *toUTF8(const WCHAR *wstr)
|
||||
char *uiprivToUTF8(const WCHAR *wstr)
|
||||
{
|
||||
char *str;
|
||||
char *sp;
|
||||
|
@ -43,6 +44,8 @@ char *toUTF8(const WCHAR *wstr)
|
|||
return str;
|
||||
}
|
||||
|
||||
#if 0
|
||||
|
||||
WCHAR *utf16dup(const WCHAR *orig)
|
||||
{
|
||||
WCHAR *out;
|
||||
|
@ -147,3 +150,5 @@ WCHAR *itoutf16(int i)
|
|||
s = ss.str(); // to be safe
|
||||
return utf16dup(s.c_str());
|
||||
}
|
||||
|
||||
#endif
|
|
@ -261,17 +261,6 @@ static void uiWindowChildVisibilityChanged(uiWindowsControl *c)
|
|||
uiWindowsControlMinimumSizeChanged(c);
|
||||
}
|
||||
|
||||
char *uiWindowTitle(uiWindow *w)
|
||||
{
|
||||
return uiWindowsWindowText(w->hwnd);
|
||||
}
|
||||
|
||||
void uiWindowSetTitle(uiWindow *w, const char *title)
|
||||
{
|
||||
uiWindowsSetWindowText(w->hwnd, title);
|
||||
// don't queue resize; the caption isn't part of what affects layout and sizing of the client area (it'll be ellipsized if too long)
|
||||
}
|
||||
|
||||
// this is used for both fullscreening and centering
|
||||
// see also https://blogs.msdn.microsoft.com/oldnewthing/20100412-00/?p=14353 and https://blogs.msdn.microsoft.com/oldnewthing/20050505-04/?p=35703
|
||||
static void windowMonitorRect(HWND hwnd, RECT *r)
|
||||
|
@ -606,14 +595,20 @@ const char *uiprivSysWindowTitle(uiWindow *w)
|
|||
void uiprivSysWindowSetTitle(uiWindow *w, const char *title)
|
||||
{
|
||||
struct windowImplData *wi = (struct windowImplData *) uiControlImplData(uiControl(w));
|
||||
WCHAR *wtitle;
|
||||
|
||||
if (wi->title != NULL)
|
||||
uiprivFreeUTF8(wi->title);
|
||||
wi->title = uiprivSanitizeUTF8(title);
|
||||
// TODO
|
||||
wtitle = uiprivToUTF16(wi->title);
|
||||
hr = uiprivHrSetWindowTextW(wi->hwnd, wtitle);
|
||||
uiprivFree(wtitle);
|
||||
if (hr != S_OK) {
|
||||
// TODO
|
||||
}
|
||||
// don't queue resize; the caption isn't part of what affects layout and sizing of the client area (it'll be ellipsized if too long)
|
||||
}
|
||||
|
||||
|
||||
#if 0
|
||||
|
||||
// this cannot queue a resize because it's called by the resize handler
|
||||
|
|
|
@ -82,3 +82,11 @@ HRESULT WINAPI uiprivHrLoadCursorW(HINSTANCE hInstance, LPCWSTR name, HCURSOR *h
|
|||
return lastErrorToHRESULT();
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT WINAPI uiprivHrSetWindowTextW(HWND hwnd, LPCWSTR text)
|
||||
{
|
||||
SetLastError(0);
|
||||
if (SetWindowTextW(hwnd, text) == 0)
|
||||
return lastErrorToHRESULT();
|
||||
return S_OK;
|
||||
}
|
||||
|
|
|
@ -7,3 +7,4 @@ extern HRESULT WINAPI uiprivHrGetMessageW(LPMSG msg, HWND hwnd, UINT filterMin,
|
|||
extern HRESULT WINAPI uiprivHrPostMessageW(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
extern HRESULT WINAPI uiprivHrLoadIconW(HINSTANCE hInstance, LPCWSTR name, HICON *hIcon);
|
||||
extern HRESULT WINAPI uiprivHrLoadCursorW(HINSTANCE hInstance, LPCWSTR name, HCURSOR *hCursor);
|
||||
extern HRESULT WINAPI uiprivHrSetWindowTextW(HWND hwnd, LPCWSTR text);
|
||||
|
|
Loading…
Reference in New Issue