Hi NoCforMe!
Win64 Tutorial #5a: Painting with Rotation Text
tiny theory in Russian (https://wasm.in/threads/skazki-djadjushki-rimusa-o-x64.31832/#post-383765)
; GUI #
include win64a.inc
.code
WinMain proc
local msg:MSG
xor ebx,ebx
mov esi,IMAGE_BASE
mov edi,offset ClassName
mov ecx,offset FileName
invoke LoadCursorFromFile
mov r12,rax
mov ecx,0FF0000h
invoke CreateSolidBrush
push r12 ;hIconSm
push rdi ;lpszClassName
push rbx ;lpszMenuName
push rax ;hbrBackground
push 10003h ;hCursor
push r12 ;hIcon
push rsi ;hInstance
push rbx ;cbClsExtra & cbWndExtra
pushaddr WndProc ;lpfnWndProc
push sizeof WNDCLASSEX;cbSize & style
invoke RegisterClassEx,esp ;addr WNDCLASSEX
push rbx
push rsi ;rsi=400000h
shr esi,7 ;Special CreateWindow position value CW_USEDEFAULT=8000h
push rbx
push rbx
push rsi
push rsi
push rsi
push rsi
sub esp,20h
invoke CreateWindowEx,0,edi,edi,WS_OVERLAPPEDWINDOW or WS_VISIBLE
;создаем таймер #0 на 50mSec
invoke SetTimer,eax,0,50,0
; +---------------------------+
; | entering the message loop |
; +---------------------------+
lea edi,msg
@@: invoke GetMessage,edi,0,0,0
invoke DispatchMessage,edi
jmp @b
WinMain endp
WndProc proc hwnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM
local ps:PAINTSTRUCT
local newFont:qword
local oldFont:qword
local x1:dword
local y1:dword
local hDC:qword
local lpPoint:POINT
mov hwnd,rcx
cmp edx,WM_DESTROY
je wmDESTROY
cmp edx,WM_PAINT
je wmPAINT
cmp edx,WM_SIZE
je wmSIZE
cmp edx,WM_TIMER
je wmTIMER
leave
jmp NtdllDefWindowProc_
wmDESTROY:invoke KillTimer,,0;уничтожаем таймер #0
invoke RtlExitUserProcess,0
wmSIZE: mov edx,offset expRect
invoke GetClientRect ;получаем размеры клиентской области.
;Размеры возвращаются в переменную expRect
mov eax,expRect.bottom
shr eax,1
mov y,eax ;y-координата середины экрана
mov eax,expRect.right
shr eax,1
mov x,eax ;x-координата середины экрана
jmp wmBYE
wmTIMER:fninit
fld angle2;угол наклона строки в радианах
fadd pi_mul_1_6_div_180 ;увеличиваем угол наклона строки на 1,6 градуса
fst angle2 fmul _1800_div_pi ;переводим радианы в градусы
fsub _1800 ;угол наклона букв в строке отстает от угла наклона строки на 90 градусов
fld st(0)
fmul one_div_3600
fsubp st(1),st(0)
fistp angle ;делим угол наклона букв на 360 градусов и запоминаем остаток
invoke InvalidateRect,,0,TRUE;перерисовываем текст с текущим значением угла
jmp wmBYE
wmPAINT:lea edx,ps
invoke BeginPaint
mov hDC,rax
invoke SetTextColor,hDC,32C8C8h;RGB=50,200,200 золотистые буквы
invoke SetBkColor,hDC,0FF0000h;RGB=0,0,255 на синем фоне
;создаем шрифт с углом вращения, указанным в lfEscapement и lfOrientation
pushaddr expFont
push DEFAULT_PITCH or FF_SCRIPT
push rbx ;DEFAULT_QUALITY=0
push rbx ;CLIP_DEFAULT_PRECIS=0
push rbx ;OUT_DEFAULT_PRECIS=0
push OEM_CHARSET
push rbx
push rbx
push rbx
push 400
sub esp,20h
invoke CreateFont,26,12,angle,r8
mov newFont,rax
invoke SelectObject,hDC,eax
mov oldFont,rax
;---------вывожу текст
mov qword ptr [rsp+20h],sizeof expTxt;длина строки
mov r9d,offset expTxt ;адрес строки
;---------рассчитываю положение начала текста
fld angle2;угол наклона строки в радианах
fsincos ;в st(0) синус угла, в st(1) косинус
mov y1,227 ;половина гипотенузы
fimul y1 ;гипотенуза * sin = x
fistp x1
mov edx,x
add edx,x1
fimul y1 ;гипотенуза * cos = y
fistp y1 ;-y
mov r8d,y
sub r8d,y1
invoke TextOut,hDC
invoke DeleteObject,newFont ;delete the new font
invoke SelectObject,hDC,oldFont;return the old font to the system
invoke EndPaint,hwnd,&ps
wmBYE:leave
retn
WndProc endp
;---------------------------------------
ClassName db "Uncle Remus tales:#5 Painting with Rotation Text",0
expTxt db "Win64 assembly with MASM is great and easy!",0
expFont db "script",0
angle dq 0
angle2 dq 3.14159265358979323846264338328
pi_mul_1_6_div_180 dq 0.02792526803190927323077905229;pi*1,6/180
_1800_div_pi dq 572.957795130823208767981548141;1800/pi
_1800 dq 1800.0
one_div_3600 dq 0.00027777777777777777777777778;1/3600 ;
hIcon dq ?
FileName db "br_Rabbit3.cur",0
expRect RECT <>
x dd ?
y dd ?
end
(https://wasm.in/attachments/image01-png.4713/)
tut06.zip (https://wasm.in/attachments/tut_06-zip.344/)