From 9ab4884c58a4de506ca43c761b1d55769dfc0614 Mon Sep 17 00:00:00 2001 From: Matthew Finnicum Date: Sat, 24 Jun 2006 16:27:11 -0400 Subject: [PATCH] riched20: Implement WM_SETFONT and its conformance tests --- dlls/riched20/editor.c | 75 ++++++++++++++++++++++++++++++++++++++++-- dlls/riched20/tests/editor.c | 64 ++++++++++++++++++++++++++++++++++++ 2 files changed, 136 insertions(+), 3 deletions(-) diff --git a/dlls/riched20/editor.c b/dlls/riched20/editor.c index 21f951e..467e4d3 100644 --- a/dlls/riched20/editor.c +++ b/dlls/riched20/editor.c @@ -132,10 +132,11 @@ + WM_COPY + WM_CUT + WM_GETDLGCODE (the current implementation is incomplete) + + WM_GETFONT + WM_GETTEXT (ANSI&Unicode) + WM_GETTEXTLENGTH (ANSI version sucks) + WM_PASTE - - WM_SETFONT + + WM_SETFONT + WM_SETTEXT (resets undo stack !) (proper style?) ANSI&Unicode - WM_STYLECHANGING - WM_STYLECHANGED (things like read-only flag) @@ -1381,7 +1382,7 @@ static const char * const richedit_messa static const char * get_msg_name(UINT msg) { - if (msg >= EM_GETSEL && msg <= EM_SETLIMITTEXT) + if (msg >= EM_GETSEL && msg <= EM_CHARFROMPOS) return edit_messages[msg - EM_GETSEL]; if (msg >= EM_CANPASTE && msg <= EM_GETIMEMODEBIAS) return richedit_messages[msg - EM_CANPASTE]; @@ -1434,7 +1435,6 @@ LRESULT WINAPI RichEditANSIWndProc(HWND UNSUPPORTED_MSG(EM_SETTYPOGRAPHYOPTIONS) UNSUPPORTED_MSG(EM_SETWORDBREAKPROCEX) UNSUPPORTED_MSG(EM_SHOWSCROLLBAR) - UNSUPPORTED_MSG(WM_SETFONT) UNSUPPORTED_MSG(WM_STYLECHANGING) UNSUPPORTED_MSG(WM_STYLECHANGED) /* UNSUPPORTED_MSG(WM_UNICHAR) FIXME missing in Wine headers */ @@ -1836,6 +1836,75 @@ LRESULT WINAPI RichEditANSIWndProc(HWND return 0; } + case WM_SETFONT: + { + /* wParam - Handle to the font. If this parameter is NULL, + the control uses the default system font to draw text. + * lParam - The low-order word of lParam specifies whether the control + should be redrawn immediately upon setting the font. + * Expected Behaviour (documentation is lacking): + * 1 - Change the default font for the control + * 2 - Change all text currently in the control to the new font + * 3 - After SETFONT, text pasted in the old font will remain that font. + * 4 - Do not unselect / alter cursor location. + * 5 - Keep current scroll position + * 6 - Even if lParam is false, a repaint should be queued. + */ + + CHARFORMAT2W p; + LOGFONTW lf; + HDC hdc; + int prevScrollPosY; + + ZeroMemory(&p,sizeof(p)); + p.cbSize = sizeof(CHARFORMAT2W); + + if ((HFONT *)wParam == NULL) + wParam = (WPARAM)GetStockObject(SYSTEM_FONT); + + hdc = GetDC(editor->hWnd); + + /* Create a LOGFONT from the passed in HFONT */ + GetObjectW((HFONT*)wParam,sizeof(LOGFONTW),&lf); + + /* We use the old default format, then only modify its font */ + ME_GetDefaultCharFormat(editor, &p); + + p.bCharSet = lf.lfCharSet; + p.bPitchAndFamily = lf.lfPitchAndFamily; + p.wWeight = lf.lfWeight; + p.yHeight = -MulDiv(lf.lfHeight, 1440, GetDeviceCaps(hdc, LOGPIXELSY)); + CopyMemory(p.szFaceName,lf.lfFaceName,sizeof(lf.lfFaceName)); + + /* The scrollbar gets reset, so we need to move it back when we're done. */ + prevScrollPosY = editor->nScrollPosY; + + ME_SetCharFormat(editor, 0, ME_GetTextLength(editor), &p); + ME_SetDefaultCharFormat(editor, &p); + + /* A bigger font means we might need to rewrap */ + ME_MarkAllForWrapping(editor); + ME_WrapMarkedParagraphs(editor); + + editor->nScrollPosY = prevScrollPosY; + SetScrollPos(hWnd, SB_VERT, editor->nScrollPosY, TRUE); + ME_UpdateScrollBar(editor); + + /* InvalidateRect causes a WM_PAINT message to be added to the queue */ + InvalidateRect(editor->hWnd, NULL, TRUE); + + /* This is an immediate repaint. It dosn't wait for the queue to be procesed*/ + if (LOWORD(lParam)) + ME_Repaint(editor); + + ME_CommitUndo(editor); + + return 0; + } + case WM_GETFONT: + { + return (LRESULT)editor->pBuffer->pDefaultStyle->hFont; + } case WM_SETTEXT: { ME_InternalDeleteText(editor, 0, ME_GetTextLength(editor)); diff --git a/dlls/riched20/tests/editor.c b/dlls/riched20/tests/editor.c index c71ca7f..d4c3640 100644 --- a/dlls/riched20/tests/editor.c +++ b/dlls/riched20/tests/editor.c @@ -811,6 +811,69 @@ static void test_EM_SETUNDOLIMIT() DestroyWindow(hwndRichEdit); } +static void test_WM_SETFONT() +{ + /* There is no invalid input or error conditions for this function. + * NULL wParam and lParam just fall back to their default values + * It should be noted that even if you use a gibberish name for your fonts + * here, it will still work because the name is stored. They will display as + * System, but will report their name to be whatever they were created as */ + + HWND hwndRichEdit = new_richedit(NULL); + HFONT testFont1 = CreateFontA (0,0,0,0,FW_LIGHT, 0, 0, 0, ANSI_CHARSET, + OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | + FF_DONTCARE, "Marlett"); + HFONT testFont2 = CreateFontA (0,0,0,0,FW_LIGHT, 0, 0, 0, ANSI_CHARSET, + OUT_TT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | + FF_DONTCARE, "MS Sans Serif"); + HFONT testFont3 = CreateFontA (0,0,0,0,FW_LIGHT, 0, 0, 0, ANSI_CHARSET, + OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | + FF_DONTCARE, "Courier"); + LOGFONTA sentLogFont; + CHARFORMAT2A returnedCF2A; + + returnedCF2A.cbSize = sizeof(returnedCF2A); + + SendMessage(hwndRichEdit, WM_SETTEXT, 0, (LPARAM) "x"); + SendMessage(hwndRichEdit, WM_SETFONT, (WPARAM)testFont1,(LPARAM) MAKELONG((WORD) TRUE, 0)); + SendMessage(hwndRichEdit, EM_GETCHARFORMAT, SCF_DEFAULT, (LPARAM) &returnedCF2A); + + GetObjectA(testFont1, sizeof(LOGFONTA), &sentLogFont); + ok (!strcmp(sentLogFont.lfFaceName,returnedCF2A.szFaceName), + "EM_GETCHARFOMAT: Returned wrong font on test 1. Sent: %s, Returned: %s\n", + sentLogFont.lfFaceName,returnedCF2A.szFaceName); + + //ok (0,"Test 1 Sent: %s Recieved: %s",sentLogFont.bPitchAndFamily,lfPitchAndFamily); + + SendMessage(hwndRichEdit, WM_SETFONT, (WPARAM)testFont2,(LPARAM) MAKELONG((WORD) TRUE, 0)); + SendMessage(hwndRichEdit, EM_GETCHARFORMAT, SCF_DEFAULT, (LPARAM) &returnedCF2A); + GetObjectA(testFont2, sizeof(LOGFONTA), &sentLogFont); + ok (!strcmp(sentLogFont.lfFaceName,returnedCF2A.szFaceName), + "EM_GETCHARFOMAT: Returned wrong font on test 2. Sent: %s, Returned: %s\n", + sentLogFont.lfFaceName,returnedCF2A.szFaceName); + + SendMessage(hwndRichEdit, WM_SETFONT, (WPARAM)testFont3,(LPARAM) MAKELONG((WORD) TRUE, 0)); + SendMessage(hwndRichEdit, EM_GETCHARFORMAT, SCF_DEFAULT, (LPARAM) &returnedCF2A); + GetObjectA(testFont3, sizeof(LOGFONTA), &sentLogFont); + ok (!strcmp(sentLogFont.lfFaceName,returnedCF2A.szFaceName), + "EM_GETCHARFOMAT: Returned wrong font on test 3. Sent: %s, Returned: %s\n", + sentLogFont.lfFaceName,returnedCF2A.szFaceName); + + /* This last test is special since we send in NULL. We clear the variables + * and just compare to "System" instead of the sent in font name. */ + ZeroMemory(&returnedCF2A,sizeof(returnedCF2A)); + ZeroMemory(&sentLogFont,sizeof(sentLogFont)); + returnedCF2A.cbSize = sizeof(returnedCF2A); + + SendMessage(hwndRichEdit, WM_SETFONT, (WPARAM)NULL,(LPARAM) MAKELONG((WORD) TRUE, 0)); + SendMessage(hwndRichEdit, EM_GETCHARFORMAT, SCF_DEFAULT, (LPARAM) &returnedCF2A); + GetObjectA(NULL, sizeof(LOGFONTA), &sentLogFont); + ok (!strcmp("System",returnedCF2A.szFaceName), + "EM_GETCHARFOMAT: Returned wrong font on test 4. Sent: NULL, Returned: %s. Expected \"System\".\n",returnedCF2A.szFaceName); + + DestroyWindow(hwndRichEdit); +} + START_TEST( editor ) { @@ -830,6 +893,7 @@ START_TEST( editor ) test_WM_GETTEXT(); test_EM_AUTOURLDETECT(); test_EM_SETUNDOLIMIT(); + test_WM_SETFONT(); /* Set the environment variable WINETEST_RICHED20 to keep windows * responsive and open for 30 seconds. This is useful for debugging. -- 1.4.0