⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 bezier.asm

📁 在汇编程序中很难控制图形的变化
💻 ASM
字号:
;-----------------------------------------
;   Bezier.asm -- Bezier Slines Demo
;   based on Charles Petzold's Bezier.C
;   Translated into assembly 7/4/99 by
;   Ron Thomas Ron_Thom@Compuserve.com	
;-----------------------------------------
.386				; 32 bit when .386 appears before .MODEL
.MODEL FLAT,STDCALL

include windows.inc
include user32.inc
include kernel32.inc
include gdi32.inc

includelib user32.lib
includelib kernel32.lib
includelib gdi32.lib

WinMain		PROTO   :DWORD, :DWORD, :DWORD, :SDWORD

PolyBezier	PROTO	STDCALL hdc:DWORD, apt:DWORD, num:DWORD
DrawBezier	PROTO	STDCALL hdc:DWORD, apt:POINT

WHITE_PEN	EQU	6
BLACK_PEN	EQU	7
MK_LBUTTON	EQU	1
MK_RBUTTON	EQU	2

.data
ClassName db "SimpleWinClass",0
AppName   db "Bezier Splines",0
				
BezPoints	STRUCT		; 4 pairs of DWORD coordinates (x,y), (8 bytes/pair) 

Spt		POINT	{}	; Line start point
Cp1		POINT	{}	; Control point 1
Cp2		POINT	{}	; Control point 2
Ept		POINT	{}	; Line end point

BezPoints	ENDS

apt	BezPoints	{}
	
.data?
hInstance HINSTANCE ?
CommandLine LPSTR ?

LOWORD	MACRO 		;; Retrieves the low word from double word lParam

	mov	eax,lParam
	and	eax,0FFFFh	;; Set cxClient to low word 
	ENDM

HIWORD	MACRO 		;; Retrieves the high word from double word lParam

	mov	ebx,lParam
	shr	ebx,16		;; Shift 16 for high word to set cyClient to high word
				
	ENDM
;---------------------------------------------------------------------------
.code
start:
	invoke GetModuleHandle, NULL
	mov    hInstance,eax
	invoke GetCommandLine
        invoke WinMain, hInstance,NULL,CommandLine, SW_SHOWDEFAULT
	invoke ExitProcess,eax

WinMain proc hInst:HINSTANCE,hPrevInst:HINSTANCE,CmdLine:LPSTR,CmdShow:SDWORD

	LOCAL wc:WNDCLASSEX
	LOCAL msg:MSG
        LOCAL hwnd:HWND

	mov   wc.cbSize,SIZEOF WNDCLASSEX
	mov   wc.style, CS_HREDRAW or CS_VREDRAW
	mov   wc.lpfnWndProc, OFFSET WndProc
	mov   wc.cbClsExtra,NULL
	mov   wc.cbWndExtra,NULL
        push  hInstance
        pop   wc.hInstance
	mov   wc.hbrBackground,COLOR_WINDOW+1
	mov   wc.lpszMenuName,NULL
	mov   wc.lpszClassName,OFFSET ClassName
        invoke LoadIcon,NULL,IDI_APPLICATION
	mov   wc.hIcon,eax
        mov   wc.hIconSm,0
        invoke LoadCursor,NULL,IDC_ARROW
	mov   wc.hCursor,eax 
        invoke RegisterClassEx, addr wc

        INVOKE CreateWindowEx,NULL,ADDR ClassName,ADDR AppName,\
           WS_OVERLAPPEDWINDOW,CW_USEDEFAULT,\
           CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,NULL,NULL,\
           hInst,NULL
        mov   hwnd,eax
        INVOKE ShowWindow, hwnd,SW_SHOWNORMAL
        INVOKE UpdateWindow, hwnd
        .WHILE TRUE
                INVOKE GetMessage, ADDR msg,NULL,0,0
                .BREAK .IF (!eax)
                INVOKE TranslateMessage, ADDR msg
                INVOKE DispatchMessage, ADDR msg
        .ENDW
        mov     eax,msg.wParam
        ret
WinMain endp

WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM

        LOCAL hdc:HDC
        LOCAL ps:PAINTSTRUCT
	
	mov   eax,uMsg

	.IF eax==WM_SIZE		; lParam gives new window size in cxClient & cyClient

	LOWORD				; Get low word from lParam in eax (cxClient)
	HIWORD				; Get high "	"	"     ebx (cyClient)

;	Set the End points [apt(0) & apt(3)] and Control points [apt(1) &apt(2)]
;	(Coord pairs are at offsets of 0,8,16 and 24 bytes in apt)
  
	shr	eax,2			
	mov	apt.Spt.x,eax		; Set to cxClient/4	;
	shr	ebx,1					   	; 1st end Point
	mov	apt.Spt.y,ebx		; Set to cyClient/2	;

	mov	apt.Ept.y,ebx		; y coord 2nd end point 

	shl	eax,1
	mov	apt.Cp1.x,eax		; Set to cxClient/2	; x coords for control points
	mov	apt.Cp2.x,eax		;			; 1 and 2

	shr	ebx,1
	mov	apt.Cp1.y,ebx		; Set to cyClient/4	; y coord CP 1 

	add	ebx,apt.Spt.y		; Add cyClient/2 to cyClient/4 	
	mov	apt.Cp2.y,ebx		; Set to 3*cyClient/4	; y coord CP 2

	mov	eax,apt.Cp1.x
	add	eax,apt.Spt.x		; Add cxClient/2 to cxClient/4 	
	mov	apt.Ept.x,eax		; Set to 3*cxClient/4	; y coord 2nd end point

	.ELSEIF	eax==WM_LBUTTONDOWN || eax==WM_RBUTTONDOWN || eax==WM_MOUSEMOVE

	  .IF (wParam & MK_LBUTTON) || (wParam & MK_RBUTTON)

	    invoke GetDC, hWnd
	    mov	hdc,eax
	    invoke  GetStockObject, WHITE_PEN
	    invoke  SelectObject, hdc,eax
	    invoke  DrawBezier, hdc, apt	; Paint out the bezier curve 

	    .IF (wParam & MK_LBUTTON)
		LOWORD				; With mouse functions, lParam returns 
		HIWORD				; the cursor coordinates in cxClient & cyClient
		mov	apt.Cp1.x,eax		; Reset Control Point 1		
		mov	apt.Cp1.y,ebx		;
	    .ENDIF

      	    .IF (wParam & MK_RBUTTON)
		LOWORD
		HIWORD
		mov	apt.Cp2.x,eax		; Reset Control Point 2
		mov	apt.Cp2.y,ebx		;
	    .ENDIF

  	    invoke  GetStockObject, BLACK_PEN
	    invoke  SelectObject, hdc,eax
            invoke  DrawBezier, hdc, apt	; Draw the bezier curve
	    invoke  ReleaseDC, hWnd,hdc
	
	  .ENDIF
 						
        .ELSEIF eax==WM_PAINT

	    invoke  InvalidateRect, hWnd, NULL, TRUE

            invoke  BeginPaint, hWnd, ADDR ps
            mov	hdc,eax			; Obtain the handle to device context before
					; selecting GDI object into it
	    invoke  DrawBezier, hdc, apt
	   
            invoke  EndPaint, hWnd, ADDR ps

	.ELSEIF eax==WM_DESTROY

	    invoke  PostQuitMessage,NULL
        .ELSE

            invoke  DefWindowProc, hWnd, uMsg, wParam, lParam
            ret

	.ENDIF
        xor    eax,eax
	ret

WndProc endp


DrawBezier  PROC  Hdc:DWORD, aapt:POINT
	
	invoke	PolyBezier, Hdc, ADDR aapt, 4

	invoke	MoveToEx, Hdc, apt.Spt.x, apt.Spt.y, NULL	; Set start point for line
	invoke	LineTo, Hdc, apt.Cp1.x, apt.Cp1.y		; from CP 1 to 1st end point
 	
	invoke	MoveToEx, Hdc, apt.Cp2.x, apt.Cp2.y, NULL	; Set start point for line 
	invoke	LineTo, Hdc, apt.Ept.x, apt.Ept.y		; from CP 2 to 2nd end point
 
	ret
DrawBezier	ENDP

        end start

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -