📄 justify2.c
字号:
/*-----------------------------------------
JUSTIFY2.C -- Justified Type Program #2
(c) Charles Petzold, 1998
-----------------------------------------*/
#include <windows.h>
#include "resource.h"
#define OUTWIDTH 6 // Width of formatted output in inches
#define LASTCHAR 127 // Last character code used in text
LRESULT CALLBACK WndProc (HWND, UINT, WPARAM, LPARAM) ;
TCHAR szAppName[] = TEXT ("Justify2") ;
int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance,
PSTR szCmdLine, int iCmdShow)
{
HWND hwnd ;
MSG msg ;
WNDCLASS wndclass ;
wndclass.style = CS_HREDRAW | CS_VREDRAW ;
wndclass.lpfnWndProc = WndProc ;
wndclass.cbClsExtra = 0 ;
wndclass.cbWndExtra = 0 ;
wndclass.hInstance = hInstance ;
wndclass.hIcon = LoadIcon (NULL, IDI_APPLICATION) ;
wndclass.hCursor = LoadCursor (NULL, IDC_ARROW) ;
wndclass.hbrBackground = (HBRUSH) GetStockObject (WHITE_BRUSH) ;
wndclass.lpszMenuName = szAppName ;
wndclass.lpszClassName = szAppName ;
if (!RegisterClass (&wndclass))
{
MessageBox (NULL, TEXT ("This program requires Windows NT!"),
szAppName, MB_ICONERROR) ;
return 0 ;
}
hwnd = CreateWindow (szAppName, TEXT ("Justified Type #2"),
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, CW_USEDEFAULT,
CW_USEDEFAULT, CW_USEDEFAULT,
NULL, NULL, hInstance, NULL) ;
ShowWindow (hwnd, iCmdShow) ;
UpdateWindow (hwnd) ;
while (GetMessage (&msg, NULL, 0, 0))
{
TranslateMessage (&msg) ;
DispatchMessage (&msg) ;
}
return msg.wParam ;
}
void DrawRuler (HDC hdc, RECT * prc)
{
static int iRuleSize [16] = { 360, 72, 144, 72, 216, 72, 144, 72,
288, 72, 144, 72, 216, 72, 144, 72 } ;
int i, j ;
POINT ptClient ;
SaveDC (hdc) ;
// Set Logical Twips mapping mode
SetMapMode (hdc, MM_ANISOTROPIC) ;
SetWindowExtEx (hdc, 1440, 1440, NULL) ;
SetViewportExtEx (hdc, GetDeviceCaps (hdc, LOGPIXELSX),
GetDeviceCaps (hdc, LOGPIXELSY), NULL) ;
// Move the origin to a half inch from upper left
SetWindowOrgEx (hdc, -720, -720, NULL) ;
// Find the right margin (quarter inch from right)
ptClient.x = prc->right ;
ptClient.y = prc->bottom ;
DPtoLP (hdc, &ptClient, 1) ;
ptClient.x -= 360 ;
// Draw the rulers
MoveToEx (hdc, 0, -360, NULL) ;
LineTo (hdc, OUTWIDTH * 1440, -360) ;
MoveToEx (hdc, -360, 0, NULL) ;
LineTo (hdc, -360, ptClient.y) ;
for (i = 0, j = 0 ; i <= ptClient.x && i <= OUTWIDTH * 1440 ;
i += 1440 / 16, j++)
{
MoveToEx (hdc, i, -360, NULL) ;
LineTo (hdc, i, -360 - iRuleSize [j % 16]) ;
}
for (i = 0, j = 0 ; i <= ptClient.y ; i += 1440 / 16, j++)
{
MoveToEx (hdc, -360, i, NULL) ;
LineTo (hdc, -360 - iRuleSize [j % 16], i) ;
}
RestoreDC (hdc, -1) ;
}
/*----------------------------------------------------------------------
GetCharDesignWidths: Gets character widths for font as large as the
original design size
----------------------------------------------------------------------*/
UINT GetCharDesignWidths (HDC hdc, UINT uFirst, UINT uLast, int * piWidths)
{
HFONT hFont, hFontDesign ;
LOGFONT lf ;
OUTLINETEXTMETRIC otm ;
hFont = GetCurrentObject (hdc, OBJ_FONT) ;
GetObject (hFont, sizeof (LOGFONT), &lf) ;
// Get outline text metrics (we'll only be using a field that is
// independent of the DC the font is selected into)
otm.otmSize = sizeof (OUTLINETEXTMETRIC) ;
GetOutlineTextMetrics (hdc, sizeof (OUTLINETEXTMETRIC), &otm) ;
// Create a new font based on the design size
lf.lfHeight = - (int) otm.otmEMSquare ;
lf.lfWidth = 0 ;
hFontDesign = CreateFontIndirect (&lf) ;
// Select the font into the DC and get the character widths
SaveDC (hdc) ;
SetMapMode (hdc, MM_TEXT) ;
SelectObject (hdc, hFontDesign) ;
GetCharWidth (hdc, uFirst, uLast, piWidths) ;
SelectObject (hdc, hFont) ;
RestoreDC (hdc, -1) ;
// Clean up
DeleteObject (hFontDesign) ;
return otm.otmEMSquare ;
}
/*---------------------------------------------------------------------
GetScaledWidths: Gets floating point character widths for selected
font size
---------------------------------------------------------------------*/
void GetScaledWidths (HDC hdc, double * pdWidths)
{
double dScale ;
HFONT hFont ;
int aiDesignWidths [LASTCHAR + 1] ;
int i ;
LOGFONT lf ;
UINT uEMSquare ;
// Call function above
uEMSquare = GetCharDesignWidths (hdc, 0, LASTCHAR, aiDesignWidths) ;
// Get LOGFONT for current font in device context
hFont = GetCurrentObject (hdc, OBJ_FONT) ;
GetObject (hFont, sizeof (LOGFONT), &lf) ;
// Scale the widths and store as floating point values
dScale = (double) -lf.lfHeight / (double) uEMSquare ;
for (i = 0 ; i <= LASTCHAR ; i++)
pdWidths[i] = dScale * aiDesignWidths[i] ;
}
/*--------------------------------------------------------------
GetTextExtentFloat: Calculates text width in floating point
--------------------------------------------------------------*/
double GetTextExtentFloat (double * pdWidths, PTSTR psText, int iCount)
{
double dWidth = 0 ;
int i ;
for (i = 0 ; i < iCount ; i++)
dWidth += pdWidths [psText[i]] ;
return dWidth ;
}
/*------------------------------------------------------------------
Justify: Based on design units for screen/printer compatibility
------------------------------------------------------------------*/
void Justify (HDC hdc, PTSTR pText, RECT * prc, int iAlign)
{
double dWidth, adWidths[LASTCHAR + 1] ;
int xStart, yStart, cSpaceChars ;
PTSTR pBegin, pEnd ;
SIZE size ;
// Fill the adWidths array with floating point character widths
GetScaledWidths (hdc, adWidths) ;
yStart = prc->top ;
do // for each text line
{
cSpaceChars = 0 ; // initialize number of spaces in line
while (*pText == ' ') // skip over leading spaces
pText++ ;
pBegin = pText ; // set pointer to char at beginning of line
do // until the line is known
{
pEnd = pText ; // set pointer to char at end of line
// skip to next space
while (*pText != '\0' && *pText++ != ' ') ;
if (*pText == '\0')
break ;
// after each space encountered, calculate extents
cSpaceChars++ ;
dWidth = GetTextExtentFloat (adWidths, pBegin,
pText - pBegin - 1) ;
}
while (dWidth < (double) (prc->right - prc->left)) ;
cSpaceChars-- ; // discount last space at end of line
while (*(pEnd - 1) == ' ') // eliminate trailing spaces
{
pEnd-- ;
cSpaceChars-- ;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -