16.4.4.1. Дополнительные возможности API-функций

Замечу, что все богатство изобразительных возможностей Windows далеко не исчерпывается набором свойств и методов класса TCanvas: этот класс инкапсулирует лишь наиболее популярные приемы работы с чертежными инструментами. В этом разделе перечисляются некоторые функции Windows, которые не инкапсулирует класс TCanvas и которые способны значительно разнообразить текстовый вывод (именно он наиболее обеднен узкими рамками TCanvas).

Некоторые текстовые функции API

type TLogFont = record

If Height: Integer;

IfWidth: Integer; IfEs-

capment: Integer; IfOri-

entation: Integer; IfWeight: Integer;

If Italic: Byte; IfUnder-

line: Byte; IfStrikeOut:

Byte; IfCharSet: Byte;

IfOutPrecision: Byte;

IfClipPrecision: Byte;

IfQuality: Byte; IfPitchAndFamily: Byte;

1fFaceName: PChar ;

end;

function CreateFont(Font:

TLogFont): hFont;

Создает новый шрифт на основе данных в параметре Font. Назначение полей структуры TLogFont см. после таблицы

function DrawText(DC:hDC; pText: PChar; varRect:'TRect; Format:UINT): Integer; | В прямоугольнике Rect выводит многострочный текст, на который указывает pText. Параметр Format используется для форматирования (см.ниже)
function ExtTextOut(DC: hDC; X, Y: Integer; Op tions: Integer; Rect: TRect; pText: PChar; Count: Integer; PX: PInteger): Bool; | Выводит текст с нестандартными меж сим вольными расстояниями: X, Y - верхняя левая точка текста; Options - параметр, управляющий выводом (см. ниже); Rect - ограничивающий прямоугольник; pText - указатель на строку вывода; Count - количество выводимых символов; px - указатель на массивцелочисленных значений, определяющих межсимвольные расстояния: 1-й параметр - расстояние от 1-го до 2-го символа; 2-й параметр- расстояние от 2-го до 3-го символа и т. д.; если какой-то параметр равен 0, используется умалчиваемое межсимвольное расстояние
function GetBkColor(DC:hDC): TColor; | Возвращает цвет фона
function GetBkMode(DC:hDC) : Integer; | Возвращает режим прорисовки фона: Opaque - фон прорисовывается заново при выводе текста; Transparent - фон не прорисовывается
function GetTextAlign(DC: hDC) : Integer; | Возвращает выравнивание текста
function GetTextCharacterExtra(DC: hDC): Integer; | Возвращает межсимвольное расстояние
function SetBkColor(DC:hDC; Color: TColor): TColor; | Устанавливает новый цвет фона и возвращает старый, если обращение успешно
function SetBkMode(DC:hDC; Mode: Integer): Integer; | Устанавливает новый режим прорисовки фона и возвращает старый, если операция успешна
function SetTextAlign(DC: hDC; Flags: Integer): Integer; | Устанавливает новое выравнивание текста и возвращает старое, если вызов успешен
function SetTextCharacterExtra(DC: hDC; CharExtra: Integer): Integer; | Устанавливает новое межсимвольное расстояние и возвращает старое, если вызов успешен

Отдельные поля структуры TLogFont для функции CreateFontIndirect имеют следующий смысл:

if Height - высота шрифта в пунктах (1 пункт = 1/72 дюйма); если больше 0, определяет высоту “знакоместа” (с учетом выступающих над заглавным символом элементов в буквах Е, И), если меньше нуля - высоту “чистого” символа, если 0 - высоту выбирает Windows;

if width - средняя ширина символа; если 0, ширину устанавливает Windows;

ifEscapment - угол наклона базовой линии текста в десятых долях градуса относительно горизонтального направления; положительные значения - поворот по часовой стрелке; в Windows 95/98 совпадает СIfOrientation;

iforientation - угол наклона символов по отношению к базовой линии; в Windows NT для шрифтов True Type может отличаться от ifEscapment; для этого следует установить режим устройства отображения равным gm_Advanced (по умолчанию устанавливается gm_Compatible);

IfWeight - плотность шрифта (fm_DontCare=0 - плотность выбирает Windows; fm_Thin=100 - очень тонкий шрифт;

fm_ExtraLight=200 - очень светлый; fm_Light=300 - светлый;

fm_Normal=400 - нормальный; fm_Medium=500 - утолщенный;

fm_SemiBold=600 - полужирный; fm_Bcld=700 - жирный;

fm_ExtraBold=800 - усиленный; fm_Heavy=900 - тяжелый);

ifitalic, ifunderiine, ifStrikeOut - ненулевое значение означает соответственно наклонный, перечеркнутый и подчеркнутый шрифт;

IfCharSet - Набор символов (ANSI_CharSet=0, Default_CharSet=l;

Symbol_CharSet=2;ShiftJis_CharSet=128;OEM_CharSet=255);

ifoutprecision - точность представления шрифта; рекомендуется out__TT_prec (выбирает True Type и векторные шрифты, если есть несколько разновидностей одноименных шрифтов) или out_TT_oniy_prec (только True Type);

ifclipprecision - определяет точность отсечения надписи границами области прорисовки (Clip_Character_Precis, Clip_Embedded, Clip_Mask, Clip_TT_Always, Clip_Default_Precis - рекомендуется, Clip_LH_Angles, Clip_Stroke_Precis);

IfQuality - Определяет качество прорисовки (Default_Quality, Draft_Quality,Proof_Quality);

ifpitchAndFamily - в четырех младших разрядах указывается тип шрифта, в четырех старших ~ его семейство;

IfFaceName - имя гарнитуры шрифта.

Вот как реализован этот пример.

procedure TForm1.FormPaint(Sender:TObject) ;

var

X: Integer;

LF: TLogFont;

Fnt: HFont;

const

Text = 'Лучшая в мире система программирования';

begin

// Определяем параметры нового шрифта

FillChar(LF, SizeOf(LF), 0) ;

with LF do

begin

If Height := 20;

If Weight := fw_Normal;

If Underline := 1;

If Escapement := 450;

StrPCopy(lfFaceName, 'Courier New Cyr');

end;

with Forml.Canvas do

begin

// Создаем шрифт

Fnt := CreateFontIndirect(LF) ;

// Присваиваем его дескриптор шрифту канвы

Font.Handle := Fnt;

// Выводим текст под углом +45 градусов

Text0ut(0, 300, Text);

X := TextWidth(Text) ;

DeleteObject(Fnt); // Удаляем ненужный шрифт

// Изменяем параметры шрифта

with LF do

begin

If Height := 90;

IfEscapement := -900;

IfWeight := fw_Heavy;

StrPCopy(LF.lfFaceName, 'Arial Cyr');

end;

Fnt := CreateFontIndirect(LF); // Создаем новый шрифт

Font.Handle := Fnt;

Font.Color := clRed;

// Выводим с наклоном -90 градусов

TextOut(X-10, 10, 'Delphi 5');

DeleteObject(Fnt); // Удаляем ненужный шрифт

end;

end;

Параметр Format функции DrawText может содержать один или несколько следующих флагов.

Возможные значения параметра Format функции DrawText

dt Bottom | Текст прижимается к нижней части области Rect
dtCalcRect | Разрешает динамически изменять размеры области Rect
dtCenter | Текст центрируется по горизонтали
dtEditControl | Функция дублирует свойства отображения многострочного тестового редактора. В частности, таким же способом вычисляется средняя ширина символа и не показывается частично видимая последняя строка
dtExpandTabs | Символы табуляции заменяются пробелами
dt ExternalLeading | В высоту строки включается высота межстрочного интервала
dtLeft | Текст прижимается к левой части области Rect
dtNoClip | Текст не отсекается границами Rect
dtNoPrefix | Символы & не заменяются подчеркиванием
dtRight | Текст прижимается к правой части области Rect
dt SingleLine | Весь текст выводится единственной строкой, символы EOLN игнорируются
dt TabsStop | Символы табуляции не заменяются пробелами
dtTop | Текст прижимается к верхней части области R'ect
dtVCenter | Текст центрируется по вертикали
dtWordBreak | Разрешает переход на новую строку при достижении пра вой границы Rect; разрыв строки - на границе слова; символы EOLN также переводят вывод на следующую строку

Если установлен флаг dt_caicRect, функция изменяет высоту и ширину прямоугольника так, чтобы вывести весь текст, но сам текст не выводится. Если в тексте несколько строк, ширина вывода не меняется. Функция возвращает истинную высоту прямоугольника вывода.

Параметр options функции ExtTextOut может быть комбинацией следующих значений:

eto_Сlipped - текст будет отсекаться границами Rect;

eto_Gliph_index - блокирует обработку языковым драйвером;

eto_opaque - фон перерисовывается заново;

eto_RTLReading - вывод для чтения справа налево. При выводе текста стандартными методами rcanvas всегда заново прорисовывается фон символов (цвет фона возвращает функция GetBkColor). Если цвет фона символов отличается от фона канвы, вывод сопровождается неприятными побочными эффектами. Если в предыдущем примере для формы оставить стандартный цвет ciFaceBtn, окно вывода будет таким, как на рис. 16.6. Конечно, с помощью функции setBkcoior можно установить цвет формы совпадающим с цветом канвы, однако это не всегда возможно. Ясно, что установить переменный цвет функцией SetBkcoior невозможно. Более того, заглавные надписи программ Setup.exe также традиционно выводятся утолщенным наклонным шрифтом Times New Roman белыми буквами с черной тенью. Реализовать такой эффект достаточно просто: нужно вообще отказаться от прорисовки фона, установив с помощью функции SetBkMode режим Transparent, и вывести надпись дважды: первый раз черным цветом, а второй -белым, сместив вторую надпись немного влево и вверх относительно первой. Следующий листинг иллюстрирует сказанное.

procedure TForm1.FormPaint(Sender: TObject);

var

Y: Integer;

Blue: Byte;

const

Text = 'Фон для программы Setup.exe';

begin

with Forml.Canvas do

begin

for Y := 0 to Forml.Height-1 do

begin

// Уменьшаем интенсивность цвета с ростом ординаты Y

Blue := Round($FF*(Forml.Height-Y)/Forml.Height);

Pen.Color := RGB(0, 0, Blue); // Формируем цвет

MoveTo(0, Y); // Чертим линию

LineTo(Forml.Width-1, Y) ;

end; // for Y := 0 to Forml.Height-1 do Font.Size := 32;

Font.Style := [fsBold, fsltalic, fsUnderline];

Font.Name := 'Times New Roman";

// Это обращение накладывает текст на фон SetBkMode(Handle, Transparent);

// Сначала выводим тень надписи

Font.Color := clBlack;

Text0ut(40, 30, Text);

// Теперь саму надпись Font.Color := clWhite;

Text0ut(36, 26, Text)

end; // with Forml.Canvas do end;

Замечу, что любая заливка фона, в том числе его прорисовка, реализуется с помощью кисти. Поэтому отказаться от прорисовки фона текста можно, если установить стиль кисти bsciear: вместо

SetBkMode(Handle, Transparent);

можно использовать

Brush.Style := bsClear;