Вращение изображения с прозрачностью GDI+

Данный пример меня просили написать на немецком форуме. Я написал, но видно автору это уже не нужно, а может просто занят (в общем неважно :) )

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

Платформа: Windows
Автор: Станислав Будинов

rotategdiplus.png

#INCLUDE "windows.bi"
#INCLUDE "win/gdiplus.bi"
Using GDIPLUS
Dim wc As WNDCLASSEX
Dim  msg As MSG
Dim ULONG_PTR_01 As ULONG_PTR
Dim GDIPLUSSTARTUPINPUT_01 As GDIPLUSSTARTUPINPUT
GDIPLUSSTARTUPINPUT_01.GdiplusVersion = 1
If (GdiplusStartup(@ULONG_PTR_01, @GDIPLUSSTARTUPINPUT_01, NULL) <> 0) Then
    Print "FAIL"
Endif

Function Load_imageA(Byval path As String) As Any Ptr
    Dim GPIMAGE_01 As GPBITMAP Ptr
    Var blen = (Len(path)*2)+2
    Dim As Wstring Ptr wbuf
    wbuf  = Allocate( blen )
    MultiByteToWideChar(CP_ACP, 0, path, -1, wbuf, blen)
    If (GDIPLOADIMAGEFROMFILE( *wbuf, @GPIMAGE_01) <> 0) Then
        Print "FAIL"
    End If
    Deallocate(wbuf)
    Return GPIMAGE_01
End Function

Sub OnPaint(compHdc As HDC,hbmpSource As PVOID,gp_ As PVOID)
    Dim As PVOID GpGraphics,hbmpDest
    Dim As Uinteger Wsource,Hsource,WDest,HDest
    Dim As Integer X = 50 , Y = 50 , Xr = 50 , Yr = 50
   Static As Single angle,Xscale,Yscale
   Xscale = angle/300
   Yscale = Xscale
    GdipCreateBitmapFromScan0(100, 100, NULL, PixelFormat32bppARGB, NULL, @hbmpDest)
    GdipCreateFromHDC(compHdc,@GpGraphics)  
    GdipGetImageWidth(hbmpSource,@Wsource)
    GdipGetImageHeight(hbmpSource,@Hsource)
    GdipGetImageWidth(Cast(GpIMAGE Ptr,hbmpDest),@WDest)
    GdipGetImageHeight(Cast(GpIMAGE Ptr,hbmpDest),@HDest)
   GdipDrawImageRect(GpGraphics,gp_ , 0, 0,Wdest,Hdest)
    If Xscale<>0 Then
        GdipScaleWorldTransform(GpGraphics,Xscale,Yscale,MatrixOrderAppend)
    Endif
    GdipRotateWorldTransform(GpGraphics, angle, 1)
    GdipTranslateWorldTransform(GpGraphics, X, Y, 1)
    GdipDrawImageRectI(GpGraphics,hbmpSource , Xr , Yr , -Wsource, -Hsource)
    GdipResetWorldTransform(GpGraphics) 
    angle= angle+3
    If angle>=360 Then angle=0
    GdipDisposeImage(hbmpDest)
    GdipDeleteGraphics(GpGraphics)
End Sub

Function WndProc(hWnd As HWND,uMsg As UINT,wParam As WPARAM,lParam As LPARAM) As Integer
    Dim ps As PAINTSTRUCT
    Static As HDC compHdc,hdc
    Static As PVOID hbmpSource,gp_

    Select Case uMsg
        Case WM_CLOSE
            GdipDisposeImage(gp_)
            GdipDisposeImage(hbmpSource)
            KillTimer(hwnd,1)
            DeleteDC(compHdc)
            PostQuitMessage(0)
        Case WM_TIMER
            OnPaint(compHdc,hbmpSource,gp_)
            InvalidateRect(hwnd,0,0)
        Case WM_CREATE
            gp_=Load_imageA("BG.png")
            hbmpSource=Load_imageA("source.png")            
            hdc=GetDC(GetDesktopWindow)
            compHdc=CreateCompatibleDC(hdc)
            Var bitmap = CreateCompatibleBitmap(hdc,GetSystemMetrics(SM_CXSCREEN),GetSystemMetrics(SM_CYSCREEN))
            SelectObject(compHdc,bitmap)
            DeleteObject(bitmap)
            ReleaseDC(GetDesktopWindow,hdc)
            SetTimer(hwnd,1,10,0)
        Case WM_PAINT
            BeginPaint(hWnd,@ps)
            BitBlt(ps.hdc,ps.rcPaint.left,ps.rcPaint.top,ps.rcPaint.right-ps.rcPaint.left,ps.rcPaint.bottom-ps.rcPaint.top,compHdc,ps.rcPaint.left,ps.rcPaint.top,SRCCOPY)
            EndPaint(hWnd,@ps)
            Return 0
        Case Else
            Return DefWindowProc(hWnd,uMsg,wParam,lParam)
    End Select
End Function

With wc
    .hInstance=GetModuleHandle(0)
    .cbSize=SizeOf(WNDCLASSEX)
    .style=CS_HREDRAW Or CS_VREDRAW
    .lpfnWndProc=@WndProc
    .lpszClassName=StrPtr("class")
    .hCursor=LoadCursor(NULL,IDC_ARROW)
End With
RegisterClassEx(@wc)
CreateWindowEx(0,wc.lpszClassName,"DrawGDI+",WS_OVERLAPPEDWINDOW Or WS_VISIBLE,200,200,280,255,0,0,wc.hInstance,0)

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

Скачать