639 lines
18 KiB
C
639 lines
18 KiB
C
/*
|
||
* tkWinFont.c --
|
||
*
|
||
* Contains the Windows implementation of the platform-independant
|
||
* font package interface.
|
||
*
|
||
* Copyright (c) 1995-1997 Sun Microsystems, Inc.
|
||
* Copyright (c) 1994 Software Research Associates, Inc.
|
||
*
|
||
* See the file "license.terms" for information on usage and redistribution
|
||
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
|
||
*
|
||
* SCCS: @(#) tkWinFont.c 1.20 97/05/14 15:45:30
|
||
*/
|
||
|
||
#include "tkWinInt.h"
|
||
#include "tkFont.h"
|
||
|
||
/*
|
||
* The following structure represents Windows' implementation of a font.
|
||
*/
|
||
|
||
typedef struct WinFont {
|
||
TkFont font; /* Stuff used by generic font package. Must
|
||
* be first in structure. */
|
||
HFONT hFont; /* Windows information about font. */
|
||
HWND hwnd; /* Toplevel window of application that owns
|
||
* this font, used for getting HDC. */
|
||
} WinFont;
|
||
|
||
/*
|
||
* The following structure is used as to map between the Tcl strings
|
||
* that represent the system fonts and the numbers used by Windows.
|
||
*/
|
||
|
||
static TkStateMap systemMap[] = {
|
||
{ANSI_FIXED_FONT, "ansifixed"},
|
||
{ANSI_VAR_FONT, "ansi"},
|
||
{DEVICE_DEFAULT_FONT, "device"},
|
||
{OEM_FIXED_FONT, "oemfixed"},
|
||
{SYSTEM_FIXED_FONT, "systemfixed"},
|
||
{SYSTEM_FONT, "system"},
|
||
{-1, NULL}
|
||
};
|
||
|
||
#define ABS(x) (((x) < 0) ? -(x) : (x))
|
||
|
||
static TkFont * AllocFont _ANSI_ARGS_((TkFont *tkFontPtr,
|
||
Tk_Window tkwin, HFONT hFont));
|
||
static char * GetProperty _ANSI_ARGS_((CONST TkFontAttributes *faPtr,
|
||
CONST char *option));
|
||
static int CALLBACK WinFontFamilyEnumProc _ANSI_ARGS_((ENUMLOGFONT *elfPtr,
|
||
NEWTEXTMETRIC *ntmPtr, int fontType,
|
||
LPARAM lParam));
|
||
|
||
|
||
/*
|
||
*---------------------------------------------------------------------------
|
||
*
|
||
* TkpGetNativeFont --
|
||
*
|
||
* Map a platform-specific native font name to a TkFont.
|
||
*
|
||
* Results:
|
||
* The return value is a pointer to a TkFont that represents the
|
||
* native font. If a native font by the given name could not be
|
||
* found, the return value is NULL.
|
||
*
|
||
* Every call to this procedure returns a new TkFont structure,
|
||
* even if the name has already been seen before. The caller should
|
||
* call TkpDeleteFont() when the font is no longer needed.
|
||
*
|
||
* The caller is responsible for initializing the memory associated
|
||
* with the generic TkFont when this function returns and releasing
|
||
* the contents of the generic TkFont before calling TkpDeleteFont().
|
||
*
|
||
* Side effects:
|
||
* None.
|
||
*
|
||
*---------------------------------------------------------------------------
|
||
*/
|
||
|
||
TkFont *
|
||
TkpGetNativeFont(tkwin, name)
|
||
Tk_Window tkwin; /* For display where font will be used. */
|
||
CONST char *name; /* Platform-specific font name. */
|
||
{
|
||
int object;
|
||
HFONT hFont;
|
||
|
||
object = TkFindStateNum(NULL, NULL, systemMap, name);
|
||
if (object < 0) {
|
||
return NULL;
|
||
}
|
||
hFont = GetStockObject(object);
|
||
if (hFont == NULL) {
|
||
panic("TkpGetNativeFont: can't allocate stock font");
|
||
}
|
||
|
||
return AllocFont(NULL, tkwin, hFont);
|
||
}
|
||
|
||
/*
|
||
*---------------------------------------------------------------------------
|
||
*
|
||
* TkpGetFontFromAttributes --
|
||
*
|
||
* Given a desired set of attributes for a font, find a font with
|
||
* the closest matching attributes.
|
||
*
|
||
* Results:
|
||
* The return value is a pointer to a TkFont that represents the
|
||
* font with the desired attributes. If a font with the desired
|
||
* attributes could not be constructed, some other font will be
|
||
* substituted automatically. NULL is never returned.
|
||
*
|
||
* Every call to this procedure returns a new TkFont structure,
|
||
* even if the specified attributes have already been seen before.
|
||
* The caller should call TkpDeleteFont() to free the platform-
|
||
* specific data when the font is no longer needed.
|
||
*
|
||
* The caller is responsible for initializing the memory associated
|
||
* with the generic TkFont when this function returns and releasing
|
||
* the contents of the generic TkFont before calling TkpDeleteFont().
|
||
*
|
||
* Side effects:
|
||
* None.
|
||
*
|
||
*---------------------------------------------------------------------------
|
||
*/
|
||
TkFont *
|
||
TkpGetFontFromAttributes(tkFontPtr, tkwin, faPtr)
|
||
TkFont *tkFontPtr; /* If non-NULL, store the information in
|
||
* this existing TkFont structure, rather than
|
||
* allocating a new structure to hold the
|
||
* font; the existing contents of the font
|
||
* will be released. If NULL, a new TkFont
|
||
* structure is allocated. */
|
||
Tk_Window tkwin; /* For display where font will be used. */
|
||
CONST TkFontAttributes *faPtr; /* Set of attributes to match. */
|
||
{
|
||
LOGFONT lf;
|
||
HFONT hFont;
|
||
Window window;
|
||
HWND hwnd;
|
||
HDC hdc;
|
||
|
||
window = Tk_WindowId(((TkWindow *) tkwin)->mainPtr->winPtr);
|
||
hwnd = (window == None) ? NULL : TkWinGetHWND(window);
|
||
|
||
hdc = GetDC(hwnd);
|
||
lf.lfHeight = -faPtr->pointsize;
|
||
if (lf.lfHeight < 0) {
|
||
lf.lfHeight = MulDiv(lf.lfHeight,
|
||
254 * WidthOfScreen(Tk_Screen(tkwin)),
|
||
720 * WidthMMOfScreen(Tk_Screen(tkwin)));
|
||
}
|
||
lf.lfWidth = 0;
|
||
lf.lfEscapement = 0;
|
||
lf.lfOrientation = 0;
|
||
lf.lfWeight = (faPtr->weight == TK_FW_NORMAL) ? FW_NORMAL : FW_BOLD;
|
||
lf.lfItalic = faPtr->slant;
|
||
lf.lfUnderline = faPtr->underline;
|
||
lf.lfStrikeOut = faPtr->overstrike;
|
||
lf.lfCharSet = DEFAULT_CHARSET;
|
||
lf.lfOutPrecision = OUT_DEFAULT_PRECIS;
|
||
lf.lfClipPrecision = CLIP_DEFAULT_PRECIS;
|
||
lf.lfQuality = DEFAULT_QUALITY;
|
||
lf.lfPitchAndFamily = DEFAULT_PITCH | FF_DONTCARE;
|
||
if (faPtr->family == NULL) {
|
||
lf.lfFaceName[0] = '\0';
|
||
} else {
|
||
lstrcpyn(lf.lfFaceName, faPtr->family, sizeof(lf.lfFaceName));
|
||
}
|
||
ReleaseDC(hwnd, hdc);
|
||
|
||
/*
|
||
* Replace the standard X and Mac family names with the names that
|
||
* Windows likes.
|
||
*/
|
||
|
||
if ((stricmp(lf.lfFaceName, "Times") == 0)
|
||
|| (stricmp(lf.lfFaceName, "New York") == 0)) {
|
||
strcpy(lf.lfFaceName, "Times New Roman");
|
||
} else if ((stricmp(lf.lfFaceName, "Courier") == 0)
|
||
|| (stricmp(lf.lfFaceName, "Monaco") == 0)) {
|
||
strcpy(lf.lfFaceName, "Courier New");
|
||
} else if ((stricmp(lf.lfFaceName, "Helvetica") == 0)
|
||
|| (stricmp(lf.lfFaceName, "Geneva") == 0)) {
|
||
strcpy(lf.lfFaceName, "Arial");
|
||
}
|
||
|
||
hFont = CreateFontIndirect(&lf);
|
||
if (hFont == NULL) {
|
||
hFont = GetStockObject(SYSTEM_FONT);
|
||
if (hFont == NULL) {
|
||
panic("TkpGetFontFromAttributes: cannot get system font");
|
||
}
|
||
}
|
||
return AllocFont(tkFontPtr, tkwin, hFont);
|
||
}
|
||
|
||
/*
|
||
*---------------------------------------------------------------------------
|
||
*
|
||
* TkpDeleteFont --
|
||
*
|
||
* Called to release a font allocated by TkpGetNativeFont() or
|
||
* TkpGetFontFromAttributes(). The caller should have already
|
||
* released the fields of the TkFont that are used exclusively by
|
||
* the generic TkFont code.
|
||
*
|
||
* Results:
|
||
* None.
|
||
*
|
||
* Side effects:
|
||
* TkFont is deallocated.
|
||
*
|
||
*---------------------------------------------------------------------------
|
||
*/
|
||
|
||
void
|
||
TkpDeleteFont(tkFontPtr)
|
||
TkFont *tkFontPtr; /* Token of font to be deleted. */
|
||
{
|
||
WinFont *fontPtr;
|
||
|
||
fontPtr = (WinFont *) tkFontPtr;
|
||
DeleteObject(fontPtr->hFont);
|
||
ckfree((char *) fontPtr);
|
||
}
|
||
|
||
/*
|
||
*---------------------------------------------------------------------------
|
||
*
|
||
* TkpGetFontFamilies, WinFontEnumFamilyProc --
|
||
*
|
||
* Return information about the font families that are available
|
||
* on the display of the given window.
|
||
*
|
||
* Results:
|
||
* interp->result is modified to hold a list of all the available
|
||
* font families.
|
||
*
|
||
* Side effects:
|
||
* None.
|
||
*
|
||
*---------------------------------------------------------------------------
|
||
*/
|
||
|
||
void
|
||
TkpGetFontFamilies(interp, tkwin)
|
||
Tcl_Interp *interp; /* Interp to hold result. */
|
||
Tk_Window tkwin; /* For display to query. */
|
||
{
|
||
Window window;
|
||
HWND hwnd;
|
||
HDC hdc;
|
||
|
||
window = Tk_WindowId(tkwin);
|
||
hwnd = (window == (Window) NULL) ? NULL : TkWinGetHWND(window);
|
||
|
||
hdc = GetDC(hwnd);
|
||
#ifdef STk_CODE
|
||
Tcl_AppendResult(interp, "(", NULL);
|
||
#endif
|
||
EnumFontFamilies(hdc, NULL, (FONTENUMPROC) WinFontFamilyEnumProc,
|
||
(LPARAM) interp);
|
||
#ifdef STk_CODE
|
||
Tcl_AppendResult(interp, ")", NULL);
|
||
#endif
|
||
ReleaseDC(hwnd, hdc);
|
||
}
|
||
|
||
/* ARGSUSED */
|
||
|
||
static int CALLBACK
|
||
WinFontFamilyEnumProc(elfPtr, ntmPtr, fontType, lParam)
|
||
ENUMLOGFONT *elfPtr; /* Logical-font data. */
|
||
NEWTEXTMETRIC *ntmPtr; /* Physical-font data (not used). */
|
||
int fontType; /* Type of font (not used). */
|
||
LPARAM lParam; /* Interp to hold result. */
|
||
{
|
||
Tcl_Interp *interp;
|
||
|
||
interp = (Tcl_Interp *) lParam;
|
||
#ifdef STk_CODE
|
||
Tcl_AppendResult(interp, " \"", elfPtr->elfLogFont.lfFaceName, "\"", NULL);
|
||
#else
|
||
Tcl_AppendElement(interp, elfPtr->elfLogFont.lfFaceName);
|
||
#endif
|
||
return 1;
|
||
}
|
||
|
||
/*
|
||
*---------------------------------------------------------------------------
|
||
*
|
||
* Tk_MeasureChars --
|
||
*
|
||
* Determine the number of characters from the string that will fit
|
||
* in the given horizontal span. The measurement is done under the
|
||
* assumption that Tk_DrawChars() will be used to actually display
|
||
* the characters.
|
||
*
|
||
* Results:
|
||
* The return value is the number of characters from source that
|
||
* fit into the span that extends from 0 to maxLength. *lengthPtr is
|
||
* filled with the x-coordinate of the right edge of the last
|
||
* character that did fit.
|
||
*
|
||
* Side effects:
|
||
* None.
|
||
*
|
||
*---------------------------------------------------------------------------
|
||
*/
|
||
int
|
||
Tk_MeasureChars(tkfont, source, numChars, maxLength, flags, lengthPtr)
|
||
Tk_Font tkfont; /* Font in which characters will be drawn. */
|
||
CONST char *source; /* Characters to be displayed. Need not be
|
||
* '\0' terminated. */
|
||
int numChars; /* Maximum number of characters to consider
|
||
* from source string. */
|
||
int maxLength; /* If > 0, maxLength specifies the longest
|
||
* permissible line length; don't consider any
|
||
* character that would cross this
|
||
* x-position. If <= 0, then line length is
|
||
* unbounded and the flags argument is
|
||
* ignored. */
|
||
int flags; /* Various flag bits OR-ed together:
|
||
* TK_PARTIAL_OK means include the last char
|
||
* which only partially fit on this line.
|
||
* TK_WHOLE_WORDS means stop on a word
|
||
* boundary, if possible.
|
||
* TK_AT_LEAST_ONE means return at least one
|
||
* character even if no characters fit. */
|
||
int *lengthPtr; /* Filled with x-location just after the
|
||
* terminating character. */
|
||
{
|
||
WinFont *fontPtr;
|
||
HDC hdc;
|
||
HFONT hFont;
|
||
int curX, curIdx;
|
||
|
||
fontPtr = (WinFont *) tkfont;
|
||
|
||
hdc = GetDC(fontPtr->hwnd);
|
||
hFont = SelectObject(hdc, fontPtr->hFont);
|
||
|
||
if (numChars == 0) {
|
||
curX = 0;
|
||
curIdx = 0;
|
||
} else if (maxLength <= 0) {
|
||
SIZE size;
|
||
|
||
GetTextExtentPoint32(hdc, source, numChars, &size);
|
||
curX = size.cx;
|
||
curIdx = numChars;
|
||
} else {
|
||
int max;
|
||
int *partials;
|
||
SIZE size;
|
||
|
||
partials = (int *) ckalloc(numChars * sizeof (int));
|
||
GetTextExtentExPoint(hdc, source, numChars, maxLength, &max,
|
||
partials, &size);
|
||
|
||
if ((flags & TK_WHOLE_WORDS) && max < numChars) {
|
||
int sawSpace;
|
||
int i;
|
||
|
||
sawSpace = 0;
|
||
i = max;
|
||
while (i >= 0 && !isspace(source[i])) {
|
||
--i;
|
||
}
|
||
while (i >= 0 && isspace(source[i])) {
|
||
sawSpace = 1;
|
||
--i;
|
||
}
|
||
|
||
/*
|
||
* If a space char was not found, and the flag for forcing
|
||
* at least on (or more) chars to be drawn is false, then
|
||
* set MAX to zero so no text is drawn. Otherwise, if a
|
||
* space was found, set max to be one char past the space.
|
||
*/
|
||
|
||
if ((i < 0) && !(flags & TK_AT_LEAST_ONE)) {
|
||
max = 0;
|
||
} else if (sawSpace) {
|
||
max = i + 1;
|
||
}
|
||
|
||
}
|
||
|
||
if (max == 0) {
|
||
curX = 0;
|
||
} else {
|
||
curX = partials[max - 1];
|
||
}
|
||
|
||
if (((flags & TK_PARTIAL_OK) && max < numChars && curX < maxLength)
|
||
|| ((flags & TK_AT_LEAST_ONE) && max == 0 && numChars > 0)) {
|
||
/*
|
||
* We want to include the first character that didn't
|
||
* quite fit. Call the function again to include the
|
||
* width of the extra character.
|
||
*/
|
||
|
||
GetTextExtentExPoint(hdc, source, max + 1, 0, NULL, partials,
|
||
&size);
|
||
curX = partials[max];
|
||
++max;
|
||
|
||
}
|
||
|
||
ckfree((char *) partials);
|
||
curIdx = max;
|
||
}
|
||
|
||
SelectObject(hdc, hFont);
|
||
ReleaseDC(fontPtr->hwnd, hdc);
|
||
|
||
*lengthPtr = curX;
|
||
return curIdx;
|
||
}
|
||
|
||
/*
|
||
*---------------------------------------------------------------------------
|
||
*
|
||
* Tk_DrawChars --
|
||
*
|
||
* Draw a string of characters on the screen.
|
||
*
|
||
* Results:
|
||
* None.
|
||
*
|
||
* Side effects:
|
||
* Information gets drawn on the screen.
|
||
*
|
||
*---------------------------------------------------------------------------
|
||
*/
|
||
|
||
void
|
||
Tk_DrawChars(display, drawable, gc, tkfont, source, numChars, x, y)
|
||
Display *display; /* Display on which to draw. */
|
||
Drawable drawable; /* Window or pixmap in which to draw. */
|
||
GC gc; /* Graphics context for drawing characters. */
|
||
Tk_Font tkfont; /* Font in which characters will be drawn;
|
||
* must be the same as font used in GC. */
|
||
CONST char *source; /* Characters to be displayed. Need not be
|
||
* '\0' terminated. All Tk meta-characters
|
||
* (tabs, control characters, and newlines)
|
||
* should be stripped out of the string that
|
||
* is passed to this function. If they are
|
||
* not stripped out, they will be displayed as
|
||
* regular printing characters. */
|
||
int numChars; /* Number of characters in string. */
|
||
int x, y; /* Coordinates at which to place origin of
|
||
* string when drawing. */
|
||
{
|
||
HDC dc;
|
||
HFONT hFont;
|
||
TkWinDCState state;
|
||
WinFont *fontPtr;
|
||
|
||
fontPtr = (WinFont *) gc->font;
|
||
display->request++;
|
||
|
||
if (drawable == None) {
|
||
return;
|
||
}
|
||
|
||
dc = TkWinGetDrawableDC(display, drawable, &state);
|
||
|
||
SetROP2(dc, tkpWinRopModes[gc->function]);
|
||
|
||
if ((gc->fill_style == FillStippled
|
||
|| gc->fill_style == FillOpaqueStippled)
|
||
&& gc->stipple != None) {
|
||
TkWinDrawable *twdPtr = (TkWinDrawable *)gc->stipple;
|
||
HBRUSH oldBrush, stipple;
|
||
HBITMAP oldBitmap, bitmap;
|
||
HDC dcMem;
|
||
TEXTMETRIC tm;
|
||
SIZE size;
|
||
|
||
if (twdPtr->type != TWD_BITMAP) {
|
||
panic("unexpected drawable type in stipple");
|
||
}
|
||
|
||
/*
|
||
* Select stipple pattern into destination dc.
|
||
*/
|
||
|
||
dcMem = CreateCompatibleDC(dc);
|
||
|
||
stipple = CreatePatternBrush(twdPtr->bitmap.handle);
|
||
SetBrushOrgEx(dc, gc->ts_x_origin, gc->ts_y_origin, NULL);
|
||
oldBrush = SelectObject(dc, stipple);
|
||
|
||
SetTextAlign(dcMem, TA_LEFT | TA_TOP);
|
||
SetTextColor(dcMem, gc->foreground);
|
||
SetBkMode(dcMem, TRANSPARENT);
|
||
SetBkColor(dcMem, RGB(0, 0, 0));
|
||
|
||
hFont = SelectObject(dcMem, fontPtr->hFont);
|
||
|
||
/*
|
||
* Compute the bounding box and create a compatible bitmap.
|
||
*/
|
||
|
||
GetTextExtentPoint(dcMem, source, numChars, &size);
|
||
GetTextMetrics(dcMem, &tm);
|
||
size.cx -= tm.tmOverhang;
|
||
bitmap = CreateCompatibleBitmap(dc, size.cx, size.cy);
|
||
oldBitmap = SelectObject(dcMem, bitmap);
|
||
|
||
/*
|
||
* The following code is tricky because fonts are rendered in multiple
|
||
* colors. First we draw onto a black background and copy the white
|
||
* bits. Then we draw onto a white background and copy the black bits.
|
||
* Both the foreground and background bits of the font are ANDed with
|
||
* the stipple pattern as they are copied.
|
||
*/
|
||
|
||
PatBlt(dcMem, 0, 0, size.cx, size.cy, BLACKNESS);
|
||
TextOut(dcMem, 0, 0, source, numChars);
|
||
BitBlt(dc, x, y - tm.tmAscent, size.cx, size.cy, dcMem,
|
||
0, 0, 0xEA02E9);
|
||
PatBlt(dcMem, 0, 0, size.cx, size.cy, WHITENESS);
|
||
TextOut(dcMem, 0, 0, source, numChars);
|
||
BitBlt(dc, x, y - tm.tmAscent, size.cx, size.cy, dcMem,
|
||
0, 0, 0x8A0E06);
|
||
|
||
/*
|
||
* Destroy the temporary bitmap and restore the device context.
|
||
*/
|
||
|
||
SelectObject(dcMem, hFont);
|
||
SelectObject(dcMem, oldBitmap);
|
||
DeleteObject(bitmap);
|
||
DeleteDC(dcMem);
|
||
SelectObject(dc, oldBrush);
|
||
DeleteObject(stipple);
|
||
} else {
|
||
SetTextAlign(dc, TA_LEFT | TA_BASELINE);
|
||
SetTextColor(dc, gc->foreground);
|
||
SetBkMode(dc, TRANSPARENT);
|
||
hFont = SelectObject(dc, fontPtr->hFont);
|
||
TextOut(dc, x, y, source, numChars);
|
||
SelectObject(dc, hFont);
|
||
}
|
||
TkWinReleaseDrawableDC(drawable, dc, &state);
|
||
}
|
||
|
||
/*
|
||
*---------------------------------------------------------------------------
|
||
*
|
||
* AllocFont --
|
||
*
|
||
* Helper for TkpGetNativeFont() and TkpGetFontFromAttributes().
|
||
* Allocates and intializes the memory for a new TkFont that
|
||
* wraps the platform-specific data.
|
||
*
|
||
* Results:
|
||
* Returns pointer to newly constructed TkFont.
|
||
*
|
||
* The caller is responsible for initializing the fields of the
|
||
* TkFont that are used exclusively by the generic TkFont code, and
|
||
* for releasing those fields before calling TkpDeleteFont().
|
||
*
|
||
* Side effects:
|
||
* Memory allocated.
|
||
*
|
||
*---------------------------------------------------------------------------
|
||
*/
|
||
|
||
static TkFont *
|
||
AllocFont(tkFontPtr, tkwin, hFont)
|
||
TkFont *tkFontPtr; /* If non-NULL, store the information in
|
||
* this existing TkFont structure, rather than
|
||
* allocating a new structure to hold the
|
||
* font; the existing contents of the font
|
||
* will be released. If NULL, a new TkFont
|
||
* structure is allocated. */
|
||
Tk_Window tkwin; /* For display where font will be used. */
|
||
HFONT hFont; /* Windows information about font. */
|
||
{
|
||
HWND hwnd;
|
||
WinFont *fontPtr;
|
||
HDC hdc;
|
||
TEXTMETRIC tm;
|
||
Window window;
|
||
char buf[LF_FACESIZE];
|
||
TkFontAttributes *faPtr;
|
||
|
||
if (tkFontPtr != NULL) {
|
||
fontPtr = (WinFont *) tkFontPtr;
|
||
DeleteObject(fontPtr->hFont);
|
||
} else {
|
||
fontPtr = (WinFont *) ckalloc(sizeof(WinFont));
|
||
}
|
||
|
||
window = Tk_WindowId(((TkWindow *) tkwin)->mainPtr->winPtr);
|
||
hwnd = (window == None) ? NULL : TkWinGetHWND(window);
|
||
|
||
hdc = GetDC(hwnd);
|
||
hFont = SelectObject(hdc, hFont);
|
||
GetTextFace(hdc, sizeof(buf), buf);
|
||
GetTextMetrics(hdc, &tm);
|
||
|
||
fontPtr->font.fid = (Font) fontPtr;
|
||
|
||
faPtr = &fontPtr->font.fa;
|
||
faPtr->family = Tk_GetUid(buf);
|
||
faPtr->pointsize = MulDiv(tm.tmHeight - tm.tmInternalLeading,
|
||
720 * WidthMMOfScreen(Tk_Screen(tkwin)),
|
||
254 * WidthOfScreen(Tk_Screen(tkwin)));
|
||
faPtr->weight = (tm.tmWeight > FW_MEDIUM) ? TK_FW_BOLD : TK_FW_NORMAL;
|
||
faPtr->slant = (tm.tmItalic != 0) ? TK_FS_ITALIC : TK_FS_ROMAN;
|
||
faPtr->underline = (tm.tmUnderlined != 0) ? 1 : 0;
|
||
faPtr->overstrike = (tm.tmStruckOut != 0) ? 1 : 0;
|
||
|
||
fontPtr->font.fm.ascent = tm.tmAscent;
|
||
fontPtr->font.fm.descent = tm.tmDescent;
|
||
fontPtr->font.fm.maxWidth = tm.tmMaxCharWidth;
|
||
fontPtr->font.fm.fixed = !(tm.tmPitchAndFamily & TMPF_FIXED_PITCH);
|
||
|
||
hFont = SelectObject(hdc, hFont);
|
||
ReleaseDC(hwnd, hdc);
|
||
|
||
fontPtr->hFont = hFont;
|
||
fontPtr->hwnd = hwnd;
|
||
|
||
return (TkFont *) fontPtr;
|
||
}
|
||
|