winex11.drv: Map coordinates before calling send_mouse_input.
[wine/zf.git] / dlls / comdlg32 / fontdlg.c
blobe2c8eb2b3ad1dc36c3c6d0cd6688a6830a07fb6b
1 /*
2 * COMMDLG - Font Dialog
4 * Copyright 1994 Martin Ayotte
5 * Copyright 1996 Albrecht Kleine
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
22 #include <ctype.h>
23 #include <stdlib.h>
24 #include <stdarg.h>
25 #include <stdio.h>
26 #include <string.h>
27 #include "windef.h"
28 #include "winbase.h"
29 #include "winnls.h"
30 #include "wingdi.h"
31 #include "winuser.h"
32 #include "commdlg.h"
33 #include "dlgs.h"
34 #include "wine/debug.h"
35 #include "wine/heap.h"
36 #include "cderr.h"
37 #include "cdlg.h"
39 WINE_DEFAULT_DEBUG_CHANNEL(commdlg);
41 typedef struct
43 HWND hWnd1;
44 HWND hWnd2;
45 LPCHOOSEFONTW lpcf32w;
46 int added;
47 } CFn_ENUMSTRUCT, *LPCFn_ENUMSTRUCT;
50 static const WCHAR strWineFontData[] = L"__WINE_FONTDLGDATA";
51 static const WCHAR strWineFontData_a[] = L"__WINE_FONTDLGDATA_A";
53 /* image list with TrueType bitmaps and more */
54 static HIMAGELIST himlTT = 0;
55 #define TTBITMAP_XSIZE 20 /* x-size of the bitmaps */
57 static INT_PTR CALLBACK FormatCharDlgProcA(HWND hDlg, UINT uMsg, WPARAM wParam, LPARAM lParam);
58 static INT_PTR CALLBACK FormatCharDlgProcW(HWND hDlg, UINT uMsg, WPARAM wParam, LPARAM lParam);
60 /* There is a table here of all charsets, and the sample text for each.
61 * There is a second table that translates a charset into an index into
62 * the first table.
65 #define CI(cs) ((IDS_CHARSET_##cs)-IDS_CHARSET_ANSI)
67 static const WCHAR * const sample_lang_text[]={
68 L"AaBbYyZz", /* Western and default */
69 L"Symbol", /* Symbol */
70 L"Aa\x3042\x3041\x30a2\x30a1\x4e9c\x5b87", /* Shift JIS */
71 L"\xac00\xb098\xb2e4" "AaBYyZz", /* Hangul */
72 L"\x5fae\x8f6f\x4e2d\x6587\x8f6f\x4ef6", /* GB2312 */
73 L"\x4e2d\x6587\x5b57\x578b\x7bc4\x4f8b", /* BIG5 */
74 L"AaBb\x0391\x03b1\x0392\x03b2", /* Greek */
75 L"AaBb\x011e\x011f\x015e\x015f", /* Turkish */
76 L"AaBb\x05e0\x05e1\x05e9\x05ea", /* Hebrew */
77 L"AaBb\x0627\x0628\x062c\x062f\x0647\x0648\x0632", /* Arabic */
78 L"AaBbYyZz", /* Baltic */
79 L"AaBb\x01a0\x01a1\x01af\x01b0", /* Vietnamese */
80 L"AaBb\x0411\x0431\x0424\x0444", /* Cyrillic */
81 L"AaBb\x00c1\x00e1\x00d4\x00f4", /* East European */
82 L"AaBb\x0e2d\x0e31\x0e01\x0e29\x0e23\x0e44\x0e17\x0e22", /* Thai */
83 L"\xac00\xb098\xb2e4" "AaBYyZz", /* Johab */
84 L"AaBbYyZz", /* Mac */
85 L"AaBb\x00f8\x00f1\x00fd", /* OEM */
86 /* the following character sets actually behave different (Win2K observation):
87 * the sample string is 'sticky': it uses the sample string of the previous
88 * selected character set. That behaviour looks like some default, which is
89 * not (yet) implemented. */
90 L"AaBb", /* VISCII */
91 L"AaBb", /* TCVN */
92 L"AaBb", /* KOI-8 */
93 L"AaBb", /* ISO-8859-3 */
94 L"AaBb", /* ISO-8859-4 */
95 L"AaBb", /* ISO-8859-10 */
96 L"AaBb" /* Celtic */
100 static const BYTE CHARSET_ORDER[256]={
101 CI(ANSI), 0, CI(SYMBOL), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
102 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
103 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
104 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
105 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, CI(MAC), 0, 0,
106 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
107 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
108 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
109 CI(JIS), CI(HANGUL), CI(JOHAB), 0, 0, 0, CI(GB2312), 0, CI(BIG5), 0, 0, 0, 0, 0, 0, 0,
110 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
111 0, CI(GREEK), CI(TURKISH), CI(VIETNAMESE), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
112 0, CI(HEBREW), CI(ARABIC), 0, 0, 0, 0, 0, 0, 0, CI(BALTIC), 0, 0, 0, 0, 0,
113 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, CI(RUSSIAN), 0, 0, 0,
114 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, CI(THAI), 0,
115 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, CI(EE), 0,
116 CI(VISCII), CI(TCVN), CI(KOI8), CI(ISO3), CI(ISO4), CI(ISO10), CI(CELTIC), 0, 0, 0, 0, 0, 0, 0, 0, CI(OEM),
119 static const struct {
120 DWORD mask;
121 const char *name;
122 } cfflags[] = {
123 #define XX(x) { x, #x },
124 XX(CF_SCREENFONTS)
125 XX(CF_PRINTERFONTS)
126 XX(CF_SHOWHELP)
127 XX(CF_ENABLEHOOK)
128 XX(CF_ENABLETEMPLATE)
129 XX(CF_ENABLETEMPLATEHANDLE)
130 XX(CF_INITTOLOGFONTSTRUCT)
131 XX(CF_USESTYLE)
132 XX(CF_EFFECTS)
133 XX(CF_APPLY)
134 XX(CF_ANSIONLY)
135 XX(CF_NOVECTORFONTS)
136 XX(CF_NOSIMULATIONS)
137 XX(CF_LIMITSIZE)
138 XX(CF_FIXEDPITCHONLY)
139 XX(CF_WYSIWYG)
140 XX(CF_FORCEFONTEXIST)
141 XX(CF_SCALABLEONLY)
142 XX(CF_TTONLY)
143 XX(CF_NOFACESEL)
144 XX(CF_NOSTYLESEL)
145 XX(CF_NOSIZESEL)
146 XX(CF_SELECTSCRIPT)
147 XX(CF_NOSCRIPTSEL)
148 XX(CF_NOVERTFONTS)
149 #undef XX
152 static void _dump_cf_flags(DWORD cflags)
154 unsigned int i;
156 for (i = 0; i < ARRAY_SIZE(cfflags); i++)
157 if (cfflags[i].mask & cflags)
158 TRACE("%s|",cfflags[i].name);
159 TRACE("\n");
162 /***********************************************************************
163 * ChooseFontW (COMDLG32.@)
165 * Create a font dialog box.
167 * PARAMS
168 * lpChFont [I/O] in: information to initialize the dialog box.
169 * out: User's color selection
171 * RETURNS
172 * TRUE: Ok button clicked.
173 * FALSE: Cancel button clicked, or error.
175 BOOL WINAPI ChooseFontW(LPCHOOSEFONTW lpChFont)
177 LPCVOID template;
178 HRSRC hResInfo;
179 HINSTANCE hDlginst;
180 HGLOBAL hDlgTmpl;
182 TRACE("(%p)\n", lpChFont);
184 if ( (lpChFont->Flags&CF_ENABLETEMPLATEHANDLE)!=0 )
186 template=lpChFont->hInstance;
187 } else
189 if ( (lpChFont->Flags&CF_ENABLETEMPLATE)!=0 )
191 hDlginst=lpChFont->hInstance;
192 if( !(hResInfo = FindResourceW(hDlginst, lpChFont->lpTemplateName,
193 (LPWSTR)RT_DIALOG)))
195 COMDLG32_SetCommDlgExtendedError(CDERR_FINDRESFAILURE);
196 return FALSE;
198 } else
200 hDlginst=COMDLG32_hInstance;
201 if (!(hResInfo = FindResourceW(hDlginst, L"CHOOSE_FONT", (LPWSTR)RT_DIALOG)))
203 COMDLG32_SetCommDlgExtendedError(CDERR_FINDRESFAILURE);
204 return FALSE;
207 if (!(hDlgTmpl = LoadResource(hDlginst, hResInfo )) ||
208 !(template = LockResource( hDlgTmpl )))
210 COMDLG32_SetCommDlgExtendedError(CDERR_LOADRESFAILURE);
211 return FALSE;
214 if (TRACE_ON(commdlg))
215 _dump_cf_flags(lpChFont->Flags);
217 if (lpChFont->Flags & CF_SELECTSCRIPT)
218 FIXME(": unimplemented flag (ignored)\n");
220 return DialogBoxIndirectParamW(COMDLG32_hInstance, template,
221 lpChFont->hwndOwner, FormatCharDlgProcW, (LPARAM)lpChFont );
224 /***********************************************************************
225 * ChooseFontA (COMDLG32.@)
227 * See ChooseFontW.
229 BOOL WINAPI ChooseFontA(LPCHOOSEFONTA lpChFont)
231 LPCVOID template;
232 HRSRC hResInfo;
233 HINSTANCE hDlginst;
234 HGLOBAL hDlgTmpl;
236 TRACE("(%p)\n", lpChFont);
238 if ( (lpChFont->Flags&CF_ENABLETEMPLATEHANDLE)!=0 )
240 template=lpChFont->hInstance;
241 } else
243 if ( (lpChFont->Flags&CF_ENABLETEMPLATE)!=0 )
245 hDlginst=lpChFont->hInstance;
246 if( !(hResInfo = FindResourceA(hDlginst, lpChFont->lpTemplateName,
247 (LPSTR)RT_DIALOG)))
249 COMDLG32_SetCommDlgExtendedError(CDERR_FINDRESFAILURE);
250 return FALSE;
252 } else
254 hDlginst=COMDLG32_hInstance;
255 if (!(hResInfo = FindResourceW(hDlginst, L"CHOOSE_FONT", (LPWSTR)RT_DIALOG)))
257 COMDLG32_SetCommDlgExtendedError(CDERR_FINDRESFAILURE);
258 return FALSE;
261 if (!(hDlgTmpl = LoadResource(hDlginst, hResInfo )) ||
262 !(template = LockResource( hDlgTmpl )))
264 COMDLG32_SetCommDlgExtendedError(CDERR_LOADRESFAILURE);
265 return FALSE;
268 if (TRACE_ON(commdlg))
269 _dump_cf_flags(lpChFont->Flags);
270 if (lpChFont->Flags & CF_SELECTSCRIPT)
271 FIXME(": unimplemented flag (ignored)\n");
273 return DialogBoxIndirectParamA(COMDLG32_hInstance, template,
274 lpChFont->hwndOwner, FormatCharDlgProcA, (LPARAM)lpChFont );
277 #define TEXT_EXTRAS 4
278 #define TEXT_COLORS 16
280 static const COLORREF textcolors[TEXT_COLORS]=
282 0x00000000L,0x00000080L,0x00008000L,0x00008080L,
283 0x00800000L,0x00800080L,0x00808000L,0x00808080L,
284 0x00c0c0c0L,0x000000ffL,0x0000ff00L,0x0000ffffL,
285 0x00ff0000L,0x00ff00ffL,0x00ffff00L,0x00FFFFFFL
288 /***********************************************************************
289 * CFn_HookCallChk32 [internal]
291 static BOOL CFn_HookCallChk32(const CHOOSEFONTW *lpcf)
293 if (lpcf)
294 if(lpcf->Flags & CF_ENABLEHOOK)
295 if (lpcf->lpfnHook)
296 return TRUE;
297 return FALSE;
300 /*************************************************************************
301 * AddFontFamily [internal]
303 static INT AddFontFamily(const ENUMLOGFONTEXW *lpElfex, const NEWTEXTMETRICEXW *lpNTM,
304 UINT nFontType, const CHOOSEFONTW *lpcf, HWND hwnd, LPCFn_ENUMSTRUCT e)
306 int i;
307 WORD w;
308 const LOGFONTW *lplf = &(lpElfex->elfLogFont);
310 TRACE("font=%s (nFontType=%d)\n", debugstr_w(lplf->lfFaceName), nFontType);
312 if (lpcf->Flags & CF_FIXEDPITCHONLY)
313 if (!(lplf->lfPitchAndFamily & FIXED_PITCH))
314 return 1;
315 if (lpcf->Flags & CF_ANSIONLY)
316 if (lplf->lfCharSet != ANSI_CHARSET)
317 return 1;
318 if (lpcf->Flags & CF_TTONLY)
319 if (!(nFontType & TRUETYPE_FONTTYPE))
320 return 1;
321 if (lpcf->Flags & CF_NOVERTFONTS)
322 if (lplf->lfFaceName[0] == '@')
323 return 1;
325 if (e) e->added++;
327 i=SendMessageW(hwnd, CB_FINDSTRINGEXACT, 0, (LPARAM)lplf->lfFaceName);
328 if (i == CB_ERR) {
329 i = SendMessageW(hwnd, CB_ADDSTRING, 0, (LPARAM)lplf->lfFaceName);
330 if( i != CB_ERR) {
331 /* store some important font information */
332 w = (lplf->lfPitchAndFamily) << 8 |
333 (HIWORD(lpNTM->ntmTm.ntmFlags) & 0xff);
334 SendMessageW(hwnd, CB_SETITEMDATA, i, MAKELONG(nFontType,w));
337 return 1;
340 /*************************************************************************
341 * FontFamilyEnumProc32 [internal]
343 static INT WINAPI FontFamilyEnumProc(const ENUMLOGFONTEXW *lpElfex,
344 const TEXTMETRICW *metrics, DWORD dwFontType, LPARAM lParam)
346 LPCFn_ENUMSTRUCT e;
347 e=(LPCFn_ENUMSTRUCT)lParam;
348 return AddFontFamily( lpElfex, (const NEWTEXTMETRICEXW *) metrics,
349 dwFontType, e->lpcf32w, e->hWnd1, e);
352 /*************************************************************************
353 * SetFontStylesToCombo2 [internal]
355 * Fill font style information into combobox (without using font.c directly)
357 static BOOL SetFontStylesToCombo2(HWND hwnd, HDC hdc, const LOGFONTW *lplf)
359 #define FSTYLES 4
360 struct FONTSTYLE
362 int italic;
363 int weight;
364 UINT resId;
366 static const struct FONTSTYLE fontstyles[FSTYLES]={
367 { 0, FW_NORMAL, IDS_FONT_REGULAR },
368 { 1, FW_NORMAL, IDS_FONT_ITALIC },
369 { 0, FW_BOLD, IDS_FONT_BOLD },
370 { 1, FW_BOLD, IDS_FONT_BOLD_ITALIC }
372 HFONT hf;
373 TEXTMETRICW tm;
374 int i,j;
375 LOGFONTW lf;
377 lf = *lplf;
379 for (i=0;i<FSTYLES;i++)
381 lf.lfItalic=fontstyles[i].italic;
382 lf.lfWeight=fontstyles[i].weight;
383 hf=CreateFontIndirectW(&lf);
384 hf=SelectObject(hdc,hf);
385 GetTextMetricsW(hdc,&tm);
386 hf=SelectObject(hdc,hf);
387 DeleteObject(hf);
388 /* font successful created ? */
389 if (((fontstyles[i].weight == FW_NORMAL && tm.tmWeight <= FW_MEDIUM) ||
390 (fontstyles[i].weight == FW_BOLD && tm.tmWeight > FW_MEDIUM)) &&
391 ((tm.tmItalic != 0)==fontstyles[i].italic))
393 WCHAR name[64];
394 LoadStringW(COMDLG32_hInstance, fontstyles[i].resId, name, 64);
395 j=SendMessageW(hwnd,CB_ADDSTRING,0,(LPARAM)name );
396 if (j==CB_ERR) return TRUE;
397 j=SendMessageW(hwnd, CB_SETITEMDATA, j,
398 MAKELONG(tm.tmWeight,fontstyles[i].italic));
399 if (j==CB_ERR) return TRUE;
402 return FALSE;
405 /*************************************************************************
406 * AddFontSizeToCombo3 [internal]
408 static BOOL AddFontSizeToCombo3(HWND hwnd, UINT h, const CHOOSEFONTW *lpcf)
410 int j;
411 WCHAR buffer[20];
413 if ( (!(lpcf->Flags & CF_LIMITSIZE)) ||
414 ((lpcf->Flags & CF_LIMITSIZE) && (h >= lpcf->nSizeMin) && (h <= lpcf->nSizeMax)))
416 swprintf(buffer, ARRAY_SIZE(buffer), L"%d", h);
417 j=SendMessageW(hwnd, CB_FINDSTRINGEXACT, -1, (LPARAM)buffer);
418 if (j==CB_ERR)
420 j=SendMessageW(hwnd, CB_INSERTSTRING, -1, (LPARAM)buffer);
421 if (j!=CB_ERR) j = SendMessageW(hwnd, CB_SETITEMDATA, j, h);
422 if (j==CB_ERR) return TRUE;
425 return FALSE;
428 /*************************************************************************
429 * SetFontSizesToCombo3 [internal]
431 static BOOL SetFontSizesToCombo3(HWND hwnd, const CHOOSEFONTW *lpcf)
433 static const BYTE sizes[]={6,7,8,9,10,11,12,14,16,18,20,22,24,26,28,36,48,72};
434 unsigned int i;
436 for (i = 0; i < ARRAY_SIZE(sizes); i++)
437 if (AddFontSizeToCombo3(hwnd, sizes[i], lpcf)) return TRUE;
438 return FALSE;
441 /*************************************************************************
442 * CFn_GetDC [internal]
444 static inline HDC CFn_GetDC(const CHOOSEFONTW *lpcf)
446 HDC ret = ((lpcf->Flags & CF_PRINTERFONTS) && lpcf->hDC) ?
447 lpcf->hDC :
448 GetDC(0);
449 if(!ret) ERR("HDC failure!!!\n");
450 return ret;
453 /*************************************************************************
454 * GetScreenDPI [internal]
456 static inline int GetScreenDPI(void)
458 HDC hdc;
459 int result;
461 hdc = GetDC(0);
462 result = GetDeviceCaps(hdc, LOGPIXELSY);
463 ReleaseDC(0, hdc);
465 return result;
468 /*************************************************************************
469 * CFn_ReleaseDC [internal]
471 static inline void CFn_ReleaseDC(const CHOOSEFONTW *lpcf, HDC hdc)
473 if(!((lpcf->Flags & CF_PRINTERFONTS) && lpcf->hDC))
474 ReleaseDC(0, hdc);
477 /*************************************************************************
478 * select_combo_item [internal]
480 static void select_combo_item( HWND dialog, int id, int sel )
482 HWND combo = GetDlgItem( dialog, id );
483 SendMessageW( combo, CB_SETCURSEL, sel, 0 );
484 SendMessageW( dialog, WM_COMMAND, MAKEWPARAM( id, CBN_SELCHANGE ), (LPARAM)combo );
487 /***********************************************************************
488 * AddFontStyle [internal]
490 static INT AddFontStyle( const ENUMLOGFONTEXW *lpElfex, const NEWTEXTMETRICEXW *lpNTM,
491 UINT nFontType, const CHOOSEFONTW *lpcf, HWND hcmb2, HWND hcmb3, HWND hDlg)
493 int i;
494 const LOGFONTW *lplf = &(lpElfex->elfLogFont);
495 HWND hcmb5;
496 HDC hdc;
498 TRACE("(nFontType=%d)\n",nFontType);
499 TRACE(" %s h=%d w=%d e=%d o=%d wg=%d i=%d u=%d s=%d"
500 " ch=%d op=%d cp=%d q=%d pf=%xh\n",
501 debugstr_w(lplf->lfFaceName),lplf->lfHeight,lplf->lfWidth,
502 lplf->lfEscapement,lplf->lfOrientation,
503 lplf->lfWeight,lplf->lfItalic,lplf->lfUnderline,
504 lplf->lfStrikeOut,lplf->lfCharSet, lplf->lfOutPrecision,
505 lplf->lfClipPrecision,lplf->lfQuality, lplf->lfPitchAndFamily);
506 if (nFontType & RASTER_FONTTYPE)
508 INT points;
509 points = MulDiv( lpNTM->ntmTm.tmHeight - lpNTM->ntmTm.tmInternalLeading,
510 72, GetScreenDPI());
511 if (AddFontSizeToCombo3(hcmb3, points, lpcf))
512 return 0;
513 } else if (SetFontSizesToCombo3(hcmb3, lpcf)) return 0;
515 if (!SendMessageW(hcmb2, CB_GETCOUNT, 0, 0))
517 BOOL res;
518 if(!(hdc = CFn_GetDC(lpcf))) return 0;
519 res = SetFontStylesToCombo2(hcmb2,hdc,lplf);
520 CFn_ReleaseDC(lpcf, hdc);
521 if (res)
522 return 0;
524 if (!( hcmb5 = GetDlgItem(hDlg, cmb5))) return 1;
525 i = SendMessageW( hcmb5, CB_FINDSTRINGEXACT, 0,
526 (LPARAM)lpElfex->elfScript);
527 if( i == CB_ERR) {
528 i = SendMessageW( hcmb5, CB_ADDSTRING, 0,
529 (LPARAM)lpElfex->elfScript);
530 if( i != CB_ERR)
531 SendMessageW( hcmb5, CB_SETITEMDATA, i, lplf->lfCharSet);
533 return 1 ;
536 static void CFn_FitFontSize( HWND hDlg, int points)
538 int i,n;
540 /* look for fitting font size in combobox3 */
541 n=SendDlgItemMessageW(hDlg, cmb3, CB_GETCOUNT, 0, 0);
542 for (i=0;i<n;i++)
544 if (points == (int)SendDlgItemMessageW
545 (hDlg,cmb3, CB_GETITEMDATA,i,0))
547 select_combo_item( hDlg, cmb3, i );
548 return;
552 /* no default matching size, set text manually */
553 SetDlgItemInt(hDlg, cmb3, points, TRUE);
556 static BOOL CFn_FitFontStyle( HWND hDlg, LONG packedstyle )
558 LONG id;
559 int i;
560 /* look for fitting font style in combobox2 */
561 for (i=0;i<TEXT_EXTRAS;i++)
563 id = SendDlgItemMessageW(hDlg, cmb2, CB_GETITEMDATA, i, 0);
564 if (packedstyle == id)
566 select_combo_item( hDlg, cmb2, i );
567 return TRUE;
570 return FALSE;
574 static BOOL CFn_FitCharSet( HWND hDlg, int charset )
576 int i,n,cs;
577 /* look for fitting char set in combobox5 */
578 n=SendDlgItemMessageW(hDlg, cmb5, CB_GETCOUNT, 0, 0);
579 for (i=0;i<n;i++)
581 cs =SendDlgItemMessageW(hDlg, cmb5, CB_GETITEMDATA, i, 0);
582 if (charset == cs)
584 select_combo_item( hDlg, cmb5, i );
585 return TRUE;
588 /* no charset fits: select the first one in the list */
589 select_combo_item( hDlg, cmb5, 0 );
590 return FALSE;
593 /***********************************************************************
594 * FontStyleEnumProc32 [internal]
596 static INT WINAPI FontStyleEnumProc( const ENUMLOGFONTEXW *lpElfex,
597 const TEXTMETRICW *metrics, DWORD dwFontType, LPARAM lParam )
599 LPCFn_ENUMSTRUCT s=(LPCFn_ENUMSTRUCT)lParam;
600 HWND hcmb2=s->hWnd1;
601 HWND hcmb3=s->hWnd2;
602 HWND hDlg=GetParent(hcmb3);
603 return AddFontStyle( lpElfex, (const NEWTEXTMETRICEXW *) metrics,
604 dwFontType, s->lpcf32w, hcmb2, hcmb3, hDlg);
607 /***********************************************************************
608 * CFn_WMInitDialog [internal]
610 static LRESULT CFn_WMInitDialog(HWND hDlg, LPARAM lParam, LPCHOOSEFONTW lpcf)
612 HDC hdc;
613 int i,j;
614 BOOL init = FALSE;
615 long pstyle;
616 CFn_ENUMSTRUCT s;
617 LPLOGFONTW lpxx;
618 HCURSOR hcursor=SetCursor(LoadCursorW(0,(LPWSTR)IDC_WAIT));
620 SetPropW(hDlg, strWineFontData, lpcf);
621 lpxx=lpcf->lpLogFont;
622 TRACE("WM_INITDIALOG lParam=%08lX\n", lParam);
624 if (lpcf->lStructSize != sizeof(CHOOSEFONTW))
626 ERR("structure size failure!!!\n");
627 EndDialog (hDlg, 0);
628 return FALSE;
630 if (!himlTT)
631 himlTT = ImageList_LoadImageW( COMDLG32_hInstance, MAKEINTRESOURCEW(38),
632 TTBITMAP_XSIZE, 0, CLR_DEFAULT, IMAGE_BITMAP, 0);
634 /* Set effect flags */
635 if((lpcf->Flags & CF_EFFECTS) && (lpcf->Flags & CF_INITTOLOGFONTSTRUCT))
637 if(lpxx->lfUnderline)
638 CheckDlgButton(hDlg, chx2, TRUE);
639 if(lpxx->lfStrikeOut)
640 CheckDlgButton(hDlg, chx1, TRUE);
643 if (!(lpcf->Flags & CF_SHOWHELP) || !IsWindow(lpcf->hwndOwner))
644 ShowWindow(GetDlgItem(hDlg,pshHelp),SW_HIDE);
645 if (!(lpcf->Flags & CF_APPLY))
646 ShowWindow(GetDlgItem(hDlg,psh3),SW_HIDE);
647 if (lpcf->Flags & CF_NOSCRIPTSEL)
648 EnableWindow(GetDlgItem(hDlg,cmb5),FALSE);
649 if (lpcf->Flags & CF_EFFECTS)
651 for (i=0;i<TEXT_COLORS;i++)
653 WCHAR name[30];
655 if (LoadStringW(COMDLG32_hInstance, IDS_COLOR_BLACK+i, name, ARRAY_SIZE(name)) == 0)
656 lstrcpyW(name, L"[color name]");
657 j=SendDlgItemMessageW(hDlg, cmb4, CB_ADDSTRING, 0, (LPARAM)name);
658 SendDlgItemMessageW(hDlg, cmb4, CB_SETITEMDATA, j, textcolors[i]);
659 /* look for a fitting value in color combobox */
660 if (textcolors[i]==lpcf->rgbColors)
661 SendDlgItemMessageW(hDlg,cmb4, CB_SETCURSEL,j,0);
664 else
666 ShowWindow(GetDlgItem(hDlg,cmb4),SW_HIDE);
667 ShowWindow(GetDlgItem(hDlg,chx1),SW_HIDE);
668 ShowWindow(GetDlgItem(hDlg,chx2),SW_HIDE);
669 ShowWindow(GetDlgItem(hDlg,grp1),SW_HIDE);
670 ShowWindow(GetDlgItem(hDlg,stc4),SW_HIDE);
672 if(!(hdc = CFn_GetDC(lpcf)))
674 EndDialog (hDlg, 0);
675 return FALSE;
677 s.hWnd1=GetDlgItem(hDlg,cmb1);
678 s.lpcf32w=lpcf;
679 do {
680 LOGFONTW elf;
681 s.added = 0;
682 elf.lfCharSet = DEFAULT_CHARSET; /* enum all charsets */
683 elf.lfPitchAndFamily = 0;
684 elf.lfFaceName[0] = '\0'; /* enum all fonts */
685 if (!EnumFontFamiliesExW(hdc, &elf, (FONTENUMPROCW)FontFamilyEnumProc, (LPARAM)&s, 0))
687 TRACE("EnumFontFamiliesEx returns 0\n");
688 break;
690 if (s.added) break;
691 if (lpcf->Flags & CF_FIXEDPITCHONLY) {
692 FIXME("No font found with fixed pitch only, dropping flag.\n");
693 lpcf->Flags &= ~CF_FIXEDPITCHONLY;
694 continue;
696 if (lpcf->Flags & CF_TTONLY) {
697 FIXME("No font found with truetype only, dropping flag.\n");
698 lpcf->Flags &= ~CF_TTONLY;
699 continue;
701 break;
702 } while (1);
705 if (lpcf->Flags & CF_INITTOLOGFONTSTRUCT)
707 /* look for fitting font name in combobox1 */
708 j=SendDlgItemMessageW(hDlg,cmb1,CB_FINDSTRING,-1,(LPARAM)lpxx->lfFaceName);
709 if (j!=CB_ERR)
711 INT height = lpxx->lfHeight < 0 ? -lpxx->lfHeight :
712 lpxx->lfHeight;
713 INT points;
714 int charset = lpxx->lfCharSet;
715 points = MulDiv( height, 72, GetScreenDPI());
716 pstyle = MAKELONG(lpxx->lfWeight > FW_MEDIUM ? FW_BOLD:
717 FW_NORMAL,lpxx->lfItalic !=0);
718 select_combo_item( hDlg, cmb1, j );
719 init = TRUE;
720 /* look for fitting font style in combobox2 */
721 CFn_FitFontStyle(hDlg, pstyle);
722 /* look for fitting font size in combobox3 */
723 CFn_FitFontSize(hDlg, points);
724 CFn_FitCharSet( hDlg, charset );
727 if (!init)
729 select_combo_item( hDlg, cmb1, 0 );
730 select_combo_item( hDlg, cmb2, 0 );
731 select_combo_item( hDlg, cmb3, 0 );
732 select_combo_item( hDlg, cmb5, 0 );
734 /* limit text length user can type in as font size */
735 SendDlgItemMessageW(hDlg, cmb3, CB_LIMITTEXT, 5, 0);
737 if ((lpcf->Flags & CF_USESTYLE) && lpcf->lpszStyle)
739 j=SendDlgItemMessageW(hDlg,cmb2,CB_FINDSTRING,-1,(LPARAM)lpcf->lpszStyle);
740 if (j!=CB_ERR) select_combo_item( hDlg, cmb2, j );
742 CFn_ReleaseDC(lpcf, hdc);
743 SetCursor(hcursor);
744 return TRUE;
748 /***********************************************************************
749 * CFn_WMMeasureItem [internal]
751 static LRESULT CFn_WMMeasureItem(HWND hDlg, LPARAM lParam)
753 HDC hdc;
754 HFONT hfontprev;
755 TEXTMETRICW tm;
756 LPMEASUREITEMSTRUCT lpmi=(LPMEASUREITEMSTRUCT)lParam;
757 INT height = 0, cx;
759 if (!himlTT)
760 himlTT = ImageList_LoadImageW( COMDLG32_hInstance, MAKEINTRESOURCEW(38),
761 TTBITMAP_XSIZE, 0, CLR_DEFAULT, IMAGE_BITMAP, 0);
762 ImageList_GetIconSize( himlTT, &cx, &height);
763 lpmi->itemHeight = height + 2;
764 /* use MAX of bitmap height and tm.tmHeight .*/
765 hdc=GetDC(hDlg);
766 if(!hdc) return 0;
767 hfontprev = SelectObject( hdc, (HFONT)SendMessageW( hDlg, WM_GETFONT, 0, 0 ));
768 GetTextMetricsW(hdc, &tm);
769 if( tm.tmHeight > lpmi->itemHeight) lpmi->itemHeight = tm.tmHeight;
770 SelectObject(hdc, hfontprev);
771 ReleaseDC(hDlg, hdc);
772 return 0;
776 /***********************************************************************
777 * CFn_WMDrawItem [internal]
779 static LRESULT CFn_WMDrawItem(LPARAM lParam)
781 HBRUSH hBrush;
782 WCHAR buffer[40];
783 COLORREF cr, oldText=0, oldBk=0;
784 RECT rect;
785 int nFontType;
786 int cx, cy, idx;
787 LPDRAWITEMSTRUCT lpdi = (LPDRAWITEMSTRUCT)lParam;
789 if (lpdi->itemID == (UINT)-1) /* got no items */
790 DrawFocusRect(lpdi->hDC, &lpdi->rcItem);
791 else
793 if (lpdi->CtlType == ODT_COMBOBOX)
795 if (lpdi->itemState & ODS_SELECTED)
797 hBrush=GetSysColorBrush(COLOR_HIGHLIGHT);
798 oldText=SetTextColor(lpdi->hDC, GetSysColor(COLOR_HIGHLIGHTTEXT));
799 oldBk=SetBkColor(lpdi->hDC, GetSysColor(COLOR_HIGHLIGHT));
800 } else
802 hBrush = SelectObject(lpdi->hDC, GetStockObject(LTGRAY_BRUSH));
803 SelectObject(lpdi->hDC, hBrush);
805 FillRect(lpdi->hDC, &lpdi->rcItem, hBrush);
807 else
808 return TRUE; /* this should never happen */
810 rect=lpdi->rcItem;
811 switch (lpdi->CtlID)
813 case cmb1:
814 /* TRACE(commdlg,"WM_Drawitem cmb1\n"); */
815 ImageList_GetIconSize( himlTT, &cx, &cy);
816 SendMessageW(lpdi->hwndItem, CB_GETLBTEXT, lpdi->itemID,
817 (LPARAM)buffer);
818 TextOutW(lpdi->hDC, lpdi->rcItem.left + cx + 4,
819 lpdi->rcItem.top, buffer, lstrlenW(buffer));
820 nFontType = SendMessageW(lpdi->hwndItem, CB_GETITEMDATA, lpdi->itemID,0L);
821 idx = -1;
822 if (nFontType & TRUETYPE_FONTTYPE) {
823 idx = 0; /* picture: TT */
824 if( nFontType & NTM_TT_OPENTYPE)
825 idx = 2; /* picture: O */
826 } else if( nFontType & NTM_PS_OPENTYPE)
827 idx = 3; /* picture: O+ps */
828 else if( nFontType & NTM_TYPE1)
829 idx = 4; /* picture: a */
830 else if( nFontType & DEVICE_FONTTYPE)
831 idx = 1; /* picture: printer */
832 if( idx >= 0)
833 ImageList_Draw( himlTT, idx, lpdi->hDC, lpdi->rcItem.left,
834 (lpdi->rcItem.top + lpdi->rcItem.bottom - cy) / 2, ILD_TRANSPARENT);
835 break;
836 case cmb2:
837 case cmb3:
838 /* TRACE(commdlg,"WM_DRAWITEN cmb2,cmb3\n"); */
839 case cmb5:
840 SendMessageW(lpdi->hwndItem, CB_GETLBTEXT, lpdi->itemID,
841 (LPARAM)buffer);
842 TextOutW(lpdi->hDC, lpdi->rcItem.left,
843 lpdi->rcItem.top, buffer, lstrlenW(buffer));
844 break;
846 case cmb4:
847 /* TRACE(commdlg,"WM_DRAWITEM cmb4 (=COLOR)\n"); */
848 SendMessageW(lpdi->hwndItem, CB_GETLBTEXT, lpdi->itemID,
849 (LPARAM)buffer);
850 TextOutW(lpdi->hDC, lpdi->rcItem.left + 25+5,
851 lpdi->rcItem.top, buffer, lstrlenW(buffer));
852 cr = SendMessageW(lpdi->hwndItem, CB_GETITEMDATA, lpdi->itemID,0L);
853 hBrush = CreateSolidBrush(cr);
854 if (hBrush)
856 hBrush = SelectObject (lpdi->hDC, hBrush) ;
857 rect.right=rect.left+25;
858 rect.top++;
859 rect.left+=5;
860 rect.bottom--;
861 Rectangle( lpdi->hDC, rect.left, rect.top,
862 rect.right, rect.bottom );
863 DeleteObject( SelectObject (lpdi->hDC, hBrush)) ;
865 rect=lpdi->rcItem;
866 rect.left+=25+5;
867 break;
869 default:
870 return TRUE; /* this should never happen */
872 if (lpdi->itemState & ODS_SELECTED)
874 SetTextColor(lpdi->hDC, oldText);
875 SetBkColor(lpdi->hDC, oldBk);
878 return TRUE;
881 static INT get_dialog_font_point_size(HWND hDlg, CHOOSEFONTW *cf)
883 BOOL invalid_size = FALSE;
884 INT i, size;
886 i = SendDlgItemMessageW(hDlg, cmb3, CB_GETCURSEL, 0, 0);
887 if (i != CB_ERR)
888 size = LOWORD(SendDlgItemMessageW(hDlg, cmb3, CB_GETITEMDATA , i, 0));
889 else
891 WCHAR buffW[8], *endptrW;
893 GetDlgItemTextW(hDlg, cmb3, buffW, ARRAY_SIZE(buffW));
894 size = wcstol(buffW, &endptrW, 10);
895 invalid_size = size == 0 && *endptrW;
897 if (size == 0)
898 size = 10;
901 cf->iPointSize = 10 * size;
902 cf->lpLogFont->lfHeight = -MulDiv(cf->iPointSize, GetScreenDPI(), 720);
903 return invalid_size ? -1 : size;
906 /***********************************************************************
907 * CFn_WMCommand [internal]
909 static LRESULT CFn_WMCommand(HWND hDlg, WPARAM wParam, LPARAM lParam, LPCHOOSEFONTW lpcf)
911 int i;
912 long l;
913 HDC hdc;
914 BOOL cmb_selected_by_edit = FALSE;
916 if (!lpcf) return FALSE;
918 if(HIWORD(wParam) == CBN_EDITCHANGE)
920 int idx;
921 WCHAR str_edit[256], str_cmb[256];
922 int cmb = LOWORD(wParam);
924 GetDlgItemTextW(hDlg, cmb, str_edit, ARRAY_SIZE(str_edit));
925 idx = SendDlgItemMessageW(hDlg, cmb, CB_FINDSTRING, -1, (LPARAM)str_edit);
926 if(idx != -1)
928 SendDlgItemMessageW(hDlg, cmb, CB_GETLBTEXT, idx, (LPARAM)str_cmb);
930 /* Select listbox entry only if we have an exact match */
931 if(lstrcmpiW(str_edit, str_cmb) == 0)
933 SendDlgItemMessageW(hDlg, cmb, CB_SETCURSEL, idx, 0);
934 SendDlgItemMessageW(hDlg, cmb, CB_SETEDITSEL, 0, -1); /* Remove edit field selection */
935 cmb_selected_by_edit = TRUE;
940 TRACE("WM_COMMAND wParam=%08X lParam=%08lX\n", (LONG)wParam, lParam);
941 switch (LOWORD(wParam))
943 case cmb1:
944 if (HIWORD(wParam) == CBN_SELCHANGE || cmb_selected_by_edit)
946 INT pointsize; /* save current pointsize */
947 LONG pstyle; /* save current style */
948 int charset;
949 int idx;
950 if(!(hdc = CFn_GetDC(lpcf)))
952 EndDialog (hDlg, 0);
953 return TRUE;
955 idx = SendDlgItemMessageW(hDlg, cmb3, CB_GETCURSEL, 0, 0);
956 pointsize = (int)SendDlgItemMessageW( hDlg, cmb3, CB_GETITEMDATA,
957 idx, 0);
958 idx = SendDlgItemMessageW(hDlg, cmb2, CB_GETCURSEL, 0, 0);
959 pstyle = SendDlgItemMessageW(hDlg, cmb2, CB_GETITEMDATA, idx, 0);
960 idx = SendDlgItemMessageW(hDlg, cmb5, CB_GETCURSEL, 0, 0);
961 charset = SendDlgItemMessageW(hDlg, cmb5, CB_GETITEMDATA, idx, 0);
963 SendDlgItemMessageW(hDlg, cmb2, CB_RESETCONTENT, 0, 0);
964 SendDlgItemMessageW(hDlg, cmb3, CB_RESETCONTENT, 0, 0);
965 SendDlgItemMessageW(hDlg, cmb5, CB_RESETCONTENT, 0, 0);
966 i=SendDlgItemMessageW(hDlg, cmb1, CB_GETCURSEL, 0, 0);
967 if (i!=CB_ERR)
969 HCURSOR hcursor=SetCursor(LoadCursorW(0,(LPWSTR)IDC_WAIT));
970 CFn_ENUMSTRUCT s;
971 LOGFONTW enumlf;
972 SendDlgItemMessageW(hDlg, cmb1, CB_GETLBTEXT, i,
973 (LPARAM)enumlf.lfFaceName);
974 TRACE("WM_COMMAND/cmb1 =>%s\n", debugstr_w(enumlf.lfFaceName));
975 s.hWnd1=GetDlgItem(hDlg, cmb2);
976 s.hWnd2=GetDlgItem(hDlg, cmb3);
977 s.lpcf32w=lpcf;
978 enumlf.lfCharSet = DEFAULT_CHARSET; /* enum all charsets */
979 enumlf.lfPitchAndFamily = 0;
980 EnumFontFamiliesExW(hdc, &enumlf,
981 (FONTENUMPROCW)FontStyleEnumProc, (LPARAM)&s, 0);
982 CFn_FitFontStyle(hDlg, pstyle);
983 if( pointsize != CB_ERR) CFn_FitFontSize(hDlg, pointsize);
984 if( charset != CB_ERR) CFn_FitCharSet( hDlg, charset );
985 SetCursor(hcursor);
987 CFn_ReleaseDC(lpcf, hdc);
989 break;
990 case chx1:
991 case chx2:
992 case cmb2:
993 case cmb3:
994 case cmb5:
995 if (HIWORD(wParam) == CBN_SELCHANGE || HIWORD(wParam) == BN_CLICKED || cmb_selected_by_edit)
997 WCHAR str[256];
998 WINDOWINFO wininfo;
999 LPLOGFONTW lpxx=lpcf->lpLogFont;
1001 TRACE("WM_COMMAND/cmb2,3 =%08lX\n", lParam);
1003 /* face name */
1004 i=SendDlgItemMessageW(hDlg,cmb1,CB_GETCURSEL,0,0);
1005 if (i==CB_ERR)
1006 GetDlgItemTextW( hDlg, cmb1, str, ARRAY_SIZE(str));
1007 else
1009 SendDlgItemMessageW(hDlg,cmb1,CB_GETLBTEXT,i,
1010 (LPARAM)str);
1011 l=SendDlgItemMessageW(hDlg,cmb1,CB_GETITEMDATA,i,0);
1012 lpcf->nFontType = LOWORD(l);
1013 /* FIXME: lpcf->nFontType |= .... SIMULATED_FONTTYPE and so */
1014 /* same value reported to the EnumFonts
1015 call back with the extra FONTTYPE_... bits added */
1016 lpxx->lfPitchAndFamily = HIWORD(l) >> 8;
1018 lstrcpynW(lpxx->lfFaceName, str, ARRAY_SIZE(lpxx->lfFaceName));
1020 /* style */
1021 i=SendDlgItemMessageW(hDlg, cmb2, CB_GETCURSEL, 0, 0);
1022 if (i!=CB_ERR)
1024 l=SendDlgItemMessageW(hDlg, cmb2, CB_GETITEMDATA, i, 0);
1025 if (0!=(lpxx->lfItalic=HIWORD(l)))
1026 lpcf->nFontType |= ITALIC_FONTTYPE;
1027 if ((lpxx->lfWeight=LOWORD(l)) > FW_MEDIUM)
1028 lpcf->nFontType |= BOLD_FONTTYPE;
1031 /* size */
1032 get_dialog_font_point_size(hDlg, lpcf);
1034 /* charset */
1035 if (lpcf->Flags & CF_NOSCRIPTSEL)
1036 lpxx->lfCharSet = DEFAULT_CHARSET;
1037 else
1039 i=SendDlgItemMessageW(hDlg, cmb5, CB_GETCURSEL, 0, 0);
1040 if (i!=CB_ERR)
1041 lpxx->lfCharSet=SendDlgItemMessageW(hDlg, cmb5, CB_GETITEMDATA, i, 0);
1042 else
1043 lpxx->lfCharSet = DEFAULT_CHARSET;
1045 lpxx->lfStrikeOut=IsDlgButtonChecked(hDlg,chx1);
1046 lpxx->lfUnderline=IsDlgButtonChecked(hDlg,chx2);
1047 lpxx->lfWidth=lpxx->lfOrientation=lpxx->lfEscapement=0;
1048 lpxx->lfOutPrecision=OUT_DEFAULT_PRECIS;
1049 lpxx->lfClipPrecision=CLIP_DEFAULT_PRECIS;
1050 lpxx->lfQuality=DEFAULT_QUALITY;
1052 wininfo.cbSize=sizeof(wininfo);
1054 if( GetWindowInfo( GetDlgItem( hDlg, stc5), &wininfo ) )
1056 MapWindowPoints( 0, hDlg, (LPPOINT) &wininfo.rcWindow, 2);
1057 InvalidateRect( hDlg, &wininfo.rcWindow, TRUE );
1060 break;
1062 case cmb4:
1063 i=SendDlgItemMessageW(hDlg, cmb4, CB_GETCURSEL, 0, 0);
1064 if (i!=CB_ERR)
1066 WINDOWINFO wininfo;
1068 lpcf->rgbColors = SendDlgItemMessageW(hDlg, cmb4, CB_GETITEMDATA, i, 0);
1069 wininfo.cbSize=sizeof(wininfo);
1071 if( GetWindowInfo( GetDlgItem( hDlg, stc5), &wininfo ) )
1073 MapWindowPoints( 0, hDlg, (LPPOINT) &wininfo.rcWindow, 2);
1074 InvalidateRect( hDlg, &wininfo.rcWindow, TRUE );
1077 break;
1079 case psh15:
1080 i=RegisterWindowMessageW( HELPMSGSTRINGW );
1081 if (lpcf->hwndOwner)
1082 SendMessageW(lpcf->hwndOwner, i, 0, (LPARAM)GetPropW(hDlg, strWineFontData));
1083 break;
1085 case IDOK:
1087 WCHAR msgW[80];
1088 INT pointsize;
1090 pointsize = get_dialog_font_point_size(hDlg, lpcf);
1091 if (pointsize == -1)
1093 LoadStringW(COMDLG32_hInstance, IDS_FONT_SIZE_INPUT, msgW, ARRAY_SIZE(msgW));
1094 MessageBoxW(hDlg, msgW, NULL, MB_OK | MB_ICONINFORMATION);
1095 return TRUE;
1098 if ( (!(lpcf->Flags & CF_LIMITSIZE)) ||
1099 ( (lpcf->Flags & CF_LIMITSIZE) &&
1100 (lpcf->iPointSize >= 10 * lpcf->nSizeMin) &&
1101 (lpcf->iPointSize <= 10 * lpcf->nSizeMax)))
1102 EndDialog(hDlg, TRUE);
1103 else
1105 WCHAR format[80];
1106 DWORD_PTR args[2];
1107 LoadStringW(COMDLG32_hInstance, IDS_FONT_SIZE, format, ARRAY_SIZE(format));
1108 args[0] = lpcf->nSizeMin;
1109 args[1] = lpcf->nSizeMax;
1110 FormatMessageW(FORMAT_MESSAGE_FROM_STRING|FORMAT_MESSAGE_ARGUMENT_ARRAY,
1111 format, 0, 0, msgW, ARRAY_SIZE(msgW),
1112 (__ms_va_list*)args);
1113 MessageBoxW(hDlg, msgW, NULL, MB_OK);
1115 return(TRUE);
1117 case IDCANCEL:
1118 EndDialog(hDlg, FALSE);
1119 return(TRUE);
1121 return(FALSE);
1124 static LRESULT CFn_WMDestroy(HWND hwnd, LPCHOOSEFONTW lpcfw)
1126 LPCHOOSEFONTA lpcfa;
1127 LPSTR lpszStyle;
1128 LPLOGFONTA lpLogFonta;
1129 int len;
1131 if (!lpcfw) return FALSE;
1133 lpcfa = GetPropW(hwnd, strWineFontData_a);
1134 lpLogFonta = lpcfa->lpLogFont;
1135 lpszStyle = lpcfa->lpszStyle;
1136 memcpy(lpcfa, lpcfw, sizeof(CHOOSEFONTA));
1137 lpcfa->lpLogFont = lpLogFonta;
1138 lpcfa->lpszStyle = lpszStyle;
1139 memcpy(lpcfa->lpLogFont, lpcfw->lpLogFont, sizeof(LOGFONTA));
1140 WideCharToMultiByte(CP_ACP, 0, lpcfw->lpLogFont->lfFaceName,
1141 LF_FACESIZE, lpcfa->lpLogFont->lfFaceName, LF_FACESIZE, 0, 0);
1143 if((lpcfw->Flags & CF_USESTYLE) && lpcfw->lpszStyle) {
1144 len = WideCharToMultiByte(CP_ACP, 0, lpcfw->lpszStyle, -1, NULL, 0, 0, 0);
1145 WideCharToMultiByte(CP_ACP, 0, lpcfw->lpszStyle, -1, lpcfa->lpszStyle, len, 0, 0);
1146 heap_free(lpcfw->lpszStyle);
1149 heap_free(lpcfw->lpLogFont);
1150 heap_free(lpcfw);
1151 SetPropW(hwnd, strWineFontData, 0);
1153 return TRUE;
1156 static LRESULT CFn_WMPaint(HWND hDlg, WPARAM wParam, LPARAM lParam, const CHOOSEFONTW *lpcf)
1158 WINDOWINFO info;
1160 if (!lpcf) return FALSE;
1162 info.cbSize=sizeof(info);
1163 if( GetWindowInfo( GetDlgItem( hDlg, stc5), &info ) )
1165 PAINTSTRUCT ps;
1166 HDC hdc;
1167 HFONT hOrigFont;
1168 LOGFONTW lf = *(lpcf->lpLogFont);
1170 MapWindowPoints( 0, hDlg, (LPPOINT) &info.rcWindow, 2);
1171 hdc = BeginPaint( hDlg, &ps );
1173 TRACE("erase %d, rect=%s\n", ps.fErase, wine_dbgstr_rect(&ps.rcPaint));
1175 /* Paint frame */
1176 DrawEdge( hdc, &info.rcWindow, EDGE_SUNKEN, BF_RECT|BF_ADJUST );
1178 /* Draw the sample text itself */
1179 hOrigFont = SelectObject( hdc, CreateFontIndirectW( &lf ) );
1180 SetTextColor( hdc, lpcf->rgbColors );
1181 SetBkMode( hdc, TRANSPARENT );
1183 DrawTextW( hdc,
1184 sample_lang_text[CHARSET_ORDER[lpcf->lpLogFont->lfCharSet]],
1185 -1, &info.rcWindow, DT_CENTER|DT_VCENTER|DT_SINGLELINE );
1187 DeleteObject(SelectObject( hdc, hOrigFont ));
1188 EndPaint( hDlg, &ps );
1190 return FALSE;
1193 /***********************************************************************
1194 * FormatCharDlgProcA [internal]
1196 static INT_PTR CALLBACK FormatCharDlgProcA(HWND hDlg, UINT uMsg, WPARAM wParam, LPARAM lParam)
1198 LPCHOOSEFONTW lpcfw;
1199 LPCHOOSEFONTA lpcfa;
1200 INT_PTR res = FALSE;
1201 int len;
1203 if (uMsg!=WM_INITDIALOG) {
1204 lpcfw = GetPropW(hDlg, strWineFontData);
1205 if (lpcfw && CFn_HookCallChk32(lpcfw))
1206 res=CallWindowProcA((WNDPROC)lpcfw->lpfnHook, hDlg, uMsg, wParam, lParam);
1207 if (res)
1208 return res;
1209 } else {
1210 lpcfa=(LPCHOOSEFONTA)lParam;
1211 SetPropW(hDlg, strWineFontData_a, (HANDLE)lParam);
1213 lpcfw = heap_alloc(sizeof(*lpcfw));
1214 memcpy(lpcfw, lpcfa, sizeof(CHOOSEFONTA));
1215 lpcfw->lpLogFont = heap_alloc(sizeof(*lpcfw->lpLogFont));
1216 memcpy(lpcfw->lpLogFont, lpcfa->lpLogFont, sizeof(LOGFONTA));
1217 MultiByteToWideChar(CP_ACP, 0, lpcfa->lpLogFont->lfFaceName,
1218 LF_FACESIZE, lpcfw->lpLogFont->lfFaceName, LF_FACESIZE);
1220 if((lpcfa->Flags & CF_USESTYLE) && lpcfa->lpszStyle) {
1221 len = MultiByteToWideChar(CP_ACP, 0, lpcfa->lpszStyle, -1, NULL, 0);
1222 lpcfw->lpszStyle = heap_alloc(len * sizeof(WCHAR));
1223 MultiByteToWideChar(CP_ACP, 0, lpcfa->lpszStyle, -1, lpcfw->lpszStyle, len);
1226 if (!CFn_WMInitDialog(hDlg, lParam, lpcfw))
1228 TRACE("CFn_WMInitDialog returned FALSE\n");
1229 return FALSE;
1231 if (CFn_HookCallChk32(lpcfw))
1232 return CallWindowProcA((WNDPROC)lpcfa->lpfnHook,hDlg,WM_INITDIALOG,wParam,lParam);
1234 switch (uMsg)
1236 case WM_MEASUREITEM:
1237 return CFn_WMMeasureItem(hDlg,lParam);
1238 case WM_DRAWITEM:
1239 return CFn_WMDrawItem(lParam);
1240 case WM_COMMAND:
1241 return CFn_WMCommand(hDlg, wParam, lParam, lpcfw);
1242 case WM_DESTROY:
1243 return CFn_WMDestroy(hDlg, lpcfw);
1244 case WM_CHOOSEFONT_GETLOGFONT:
1246 LOGFONTA *logfont = (LOGFONTA *)lParam;
1247 TRACE("WM_CHOOSEFONT_GETLOGFONT lParam=%08lX\n", lParam);
1248 memcpy( logfont, lpcfw->lpLogFont, FIELD_OFFSET( LOGFONTA, lfFaceName ));
1249 WideCharToMultiByte( CP_ACP, 0, lpcfw->lpLogFont->lfFaceName, LF_FACESIZE,
1250 logfont->lfFaceName, LF_FACESIZE, NULL, NULL );
1251 break;
1253 case WM_PAINT:
1254 return CFn_WMPaint(hDlg, wParam, lParam, lpcfw);
1256 return res;
1259 /***********************************************************************
1260 * FormatCharDlgProcW [internal]
1262 static INT_PTR CALLBACK FormatCharDlgProcW(HWND hDlg, UINT uMsg, WPARAM wParam, LPARAM lParam)
1264 LPCHOOSEFONTW lpcf;
1265 INT_PTR res = FALSE;
1267 if (uMsg!=WM_INITDIALOG)
1269 lpcf= GetPropW(hDlg, strWineFontData);
1270 if (lpcf && CFn_HookCallChk32(lpcf))
1271 res=CallWindowProcW((WNDPROC)lpcf->lpfnHook, hDlg, uMsg, wParam, lParam);
1272 if (res)
1273 return res;
1275 else
1277 lpcf=(LPCHOOSEFONTW)lParam;
1278 if (!CFn_WMInitDialog(hDlg, lParam, lpcf))
1280 TRACE("CFn_WMInitDialog returned FALSE\n");
1281 return FALSE;
1283 if (CFn_HookCallChk32(lpcf))
1284 return CallWindowProcW((WNDPROC)lpcf->lpfnHook,hDlg,WM_INITDIALOG,wParam,lParam);
1286 switch (uMsg)
1288 case WM_MEASUREITEM:
1289 return CFn_WMMeasureItem(hDlg, lParam);
1290 case WM_DRAWITEM:
1291 return CFn_WMDrawItem(lParam);
1292 case WM_COMMAND:
1293 return CFn_WMCommand(hDlg, wParam, lParam, lpcf);
1294 case WM_DESTROY:
1295 return TRUE;
1296 case WM_CHOOSEFONT_GETLOGFONT:
1297 TRACE("WM_CHOOSEFONT_GETLOGFONT lParam=%08lX\n", lParam);
1298 memcpy( (LOGFONTW *)lParam, lpcf->lpLogFont, sizeof(LOGFONTW) );
1299 break;
1300 case WM_PAINT:
1301 return CFn_WMPaint(hDlg, wParam, lParam, lpcf);
1303 return res;