API и FreeBasic. (Рисование текста с помощью GDI)

Рисование текста в GDI можно осуществлять с помощью функций TextOut, DrawText и DrawTextEx. Все три функции рисуют с помощью шрифта и цветов, заранее указанных в контексте. Создание шрифтов рассматривалось в этой статье. Единственно перед использованием функций рисования текста, шрифт надо выбрать в контекст с помощью SelectObject. Ну и конечно освободить объект шрифта, когда он более не требуется. В принципе и изменение цвета должно быть вам знакомо, поскольку функции, используемые для изменения цвета в контексте (SetBkColor, SetTextColor), тоже уже рассматривались здесь. Единственно хочется упомянуть функцию SetBkMode, которая позволит рисовать текст без фона (с прозрачностью).

Сама функция SetBkMode определятся так:

SetBkMode(_
    As HDC hdc,_ ' контекст
    As Integer iBkMode _ ' флаг, определящий режим рисования (OPAQUE - фон установленный в контексте, TRANSPARENT - прозрачный фон)
   ) As Integer

Функция TextOut проста в использовании и поэтому менее гибка. Она рисует однострочную строку , используя начальные координаты.

Ее прототип:

TextOut( _
  As HDC hdc,_ 'контекст
  As Integer nXStart,_  ' начальная координата по оси X
  As Integer nYStart,_  ' начальная координата по оси Y  
  As LPCTSTR lpString,_ ' указатель на строку
  As Integer cbString _ ' длина строки
) As BOOL


Функция DrawText используется для вывода форматированного текста в заданный прямоугольник. Основное преимущество этой функции по отношению к TextOut , это возможность рисовать многострочные поля.

DrawText(_
  As HDC hDC,_ ' контекст
  As LPCTSTR lpString,_ ' указатель на строку
  As Integer nCount,_ ' длина строки
  As LPRECT lpRect,_ ' указатель на структуру RECT для указания поля вывода текста
  As Uinteger uFormat _ ' флаг, определяющий метод форматирования текста
) As Integer


uFormat может быть:

  • DT_SINGLELINE - Oднострочная строка
  • DT_BOTTOM - Выравнивание текста по нижней части прямоугольника. (только для однострочных совместно с флагом DT_SINGLELINE)
  • DT_TOP - Выравнивание текста по верхней части прямоугольника
  • DT_CENTER - Выравнивание текста по центру горизонтально
  • DT_VCENTER - Выравнивание текста по центру вертикально (только для однострочных совместно с флагом DT_SINGLELINE)
  • DT_LEFT - Выравнивание текста по левой части прямоугольника
  • DT_RIGHT - Выравнивание текста по правой части прямоугольника
  • DT_WORDBREAK - Переносит слова для многострочного рисования

Это не все флаги, остальные можете посмотреть здесь

Функция DrawTextEx является расширенным вариантом функции DrawText. Ее прототип отличается только дополненным параметром: указатель на структуру DRAWTEXTPARAMS, которая немного расширяет возможности форматирования текста.

Пример:

#INCLUDE "windows.bi"
Dim msg As MSG
Dim As WNDCLASSEX wc
Dim As String NameClass="MyClass"
Dim As HINSTANCE Hinst=GetModuleHandle(0)
Dim Shared As HFONT font

Sub Draw_Text(hdc As HDC)

    Dim As Zstring Ptr _
    szText1 = @"Однострочный текст",_
    szText2 = @!"Многострочный \r\n текст"


    'Выбираем шрифт в контекст
    Dim As HFONT oldFont = SelectObject(hdc,Cast(HGDIOBJ,font))

    'Делаем цвет фона текста прозрачным
    SetBkMode(hdc,TRANSPARENT)

    'Устанавливаем цвет текста
    SetTextColor(hdc, &hABCDEF)

   ' Рисуем однострочный текст
    TextOut(hdc,10,10,szText1,Len(*szText1))

    'Устанавливаем цвет текста
    SetTextColor(hdc, &hFEDCBA) 
    
    'Выставляем координаты прямоугольника для вывода
    
    Dim As RECT r = Type(50,50,250,150)
    
    ' Рисуем многострочный текст
    DrawText(hdc,szText2,Len(*szText2),@r,DT_WORDBREAK)  

    ' устанавливаем шрифт по умолчанию
    SelectObject(hdc,oldFont)

End Sub

Function wndproc(hwnd As HWND, msg As Uinteger,_
    wparam As WPARAM, lparam As LPARAM) As Integer

    Static canvas As HWND

    Select Case msg
        Case WM_CREATE
            canvas = CreateWindowEx(0,"Static","",WS_VISIBLE Or WS_CHILD,10,10,260,150,hwnd,Cast(HMENU,1),0,0)
            ' Создаем контекст устройства
            Dim As HDC hdc = CreateDC("DISPLAY",0,0,0)
            ' Производим калькуляцию
            Dim As Integer size = -MulDiv(16, GetDeviceCaps(hdc, LOGPIXELSY), 72)
            ' Удаляем контекст устройства
            DeleteDC(hdc)
            ' Создаем шрифт Courier 16
            font  = CreateFont(size,0,15*10,0,700,0,0,0, _
            DEFAULT_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS,_
            DEFAULT_QUALITY, DEFAULT_PITCH Or FF_DONTCARE,"Courier")
        Case WM_PAINT
            Dim ps As PAINTSTRUCT
            BeginPaint(canvas,@ps)
            Draw_Text(ps.hDC)
            EndPaint(canvas,@ps)
        Case WM_DESTROY
            DeleteObject(font)
            PostQuitMessage(0)
    End Select
    Return DefWindowProc(hwnd,msg,wparam,lparam)
End Function

With wc
    .cbSize=SizeOf(WNDCLASSEX)
    .style=CS_HREDRAW Or CS_VREDRAW
    .lpfnWndProc=@wndproc
    .hInstance=Hinst
    .hIcon=LoadIcon(0,IDI_QUESTION)
    .hCursor=LoadCursor(0,IDC_ARROW)
    .hbrBackground=Cast(HBRUSH,COLOR_WINDOW)
    .lpszClassName=StrPtr(NameClass)
    .hIconSm=.hIcon
End With

If RegisterClassEx(@wc)=0 Then
    Print "Register error, press any key"
    Sleep
    End
Endif

CreateWindowEx(0,NameClass,"Рисование текста",_
WS_VISIBLE Or WS_OVERLAPPEDWINDOW,100,100,280,170,0,0,Hinst,0)

While GetMessage(@msg,0,0,0)
    TranslateMessage(@msg)
    DispatchMessage(@msg)
Wend


drawtext.png

содержание | назад | вперед