第十三讲 GDI+区域及剪切区域
一、GDI+区域1、建立_GDIPlus_RegionCreate;创建空区域
_GDIPlus_RegionCreateFromHrgn;从GDI区域句柄建立GDI+区域
_GDIPlus_RegionCreateFromPath;从路径对象建立区域
_GDIPlus_RegionCreateFromRect;建立矩形区域
_GDIPlus_RegionCreateFromRgnData;从区域数据建立区域GDI+的路径和区域与GDI的路径和区域不同,GDI只能有一个路径和区域,而GDI+可以同时有多个路径和区域
2、区域混合_GDIPlus_RegionCombinePath;区域与路径混合
_GDIPlus_RegionCombineRect;区域与矩形混合
_GDIPlus_RegionCombineRegion;区域与区域混合;~ 区域的相交模式:
;~ 0 - 用新区域替换已存在的区域
;~ 1 - 用区域自身和新区域的相交部分替换已存在的区域
;~ 2 - 用区域自身和新区域的结合部分替换已存在的区域
;~ 3 - 对两个区域执行异或(XOR)操作的结果替换已存在的区域位于两区域的XOR部分的点表示它在其中一个但不同时在两个区域中
;~ 4 - 用区域自身和新区域外部替换已存在的区域
;~ 5 - 用在已存在区域的外部的新区域部分替换已存在的区域
3、区域的填充
区域没有描边,只有填充,填充函数在3.3.7.15中有误
改为如下吧
Func _GDIPlus__GraphicsFillRegion($hGraphics, $hRegion, $hBrush = 0)
Local $iTmpErr, $iTmpExt, $aResult
__GDIPlus_BrushDefCreate($hBrush)
$aResult = DllCall($ghGDIPDll, "uint", "GdipFillRegion", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hRegion)
$iTmpErr = @error
$iTmpExt = @extended
__GDIPlus_BrushDefDispose()
If $iTmpErr Then Return SetError($iTmpErr, $iTmpExt, False)
$GDIP_STATUS = $aResult
Return $aResult = 0
EndFunc ;==>_GDIPlus__GraphicsFillRegion
二、剪切区域(画布的剪切区域)
剪切区域和区域是两回事,应该都叫区域我就放一起了
画布设置了剪切区域后,所有的绘制操作,只有在剪切区域时才能绘制
建立方法_GDIPlus_GraphicsSetClipHrgn
_GDIPlus_GraphicsSetClipPath
_GDIPlus_GraphicsSetClipRect
_GDIPlus_GraphicsSetClipRegion剪切区域的混合模式和区域的混合模式一样
剪切区域的释放
_GDIPlus_GraphicsResetClip($hGraphics)
例子中,右下二个就是剪切区域
#include <APIConstants.au3>
#include <WinAPIEx.au3>
#include <GDIPlus.au3>
#include <GDIPlusEx.au3>
GUICreate("第十三讲 GDI+区域", 500, 200)
$nCtrlId = GUICtrlCreatePic("", 0, 0, 500, 200)
$hPicWnd = GUICtrlGetHandle($nCtrlId)
GUISetState()
update()
While 1
$Msg = GUIGetMsg()
Switch $Msg
Case -3
ExitLoop
EndSwitch
WEnd
GUIDelete()
Exit
Func update()
Local $HWND_CX = _WinAPI_GetWindowWidth($hPicWnd)
Local $HWND_CY = _WinAPI_GetWindowHeight($hPicWnd)
_GDIPlus_Startup()
$hGraphics = _GDIPlus_GraphicsCreateFromHWND($hPicWnd)
_GDIPlus_GraphicsSetSmoothingMode($hGraphics, 2)
$hBitmap = _GDIPlus_BitmapCreateFromGraphics($HWND_CX, $HWND_CY, $hGraphics)
$hBackbuffer = _GDIPlus_ImageGetGraphicsContext($hBitmap)
_GDIPlus_GraphicsClear($hBackbuffer, 0xFFECE9D8)
_GDIPlus_GraphicsSetSmoothingMode($hBackbuffer, 2);光滑模式,2为8*8抗距齿
CombinemodeComp($hBackbuffer)
_GDIPlus_GraphicsDrawImageRect($hGraphics, $hBitmap, 0, 0, $HWND_CX, $HWND_CY)
_GDIPlus_BitmapDispose($hBitmap)
_GDIPlus_GraphicsDispose($hBackbuffer)
_GDIPlus_GraphicsDispose($hGraphics)
_GDIPlus_Shutdown()
EndFunc ;==>update
;混合模式对比
Func CombinemodeComp($hGraphics)
Local $hPen = _GDIPlus_PenCreate(0xFFFF0000, 1)
Local $hBrush = _GDIPlus_BrushCreateSolid(0xFFFF0000)
;从矩形区域建立区域
Local $tRectF = _GDIPlus_RectFCreate(10, 20, 80, 30)
Local $hRgn1 = _GDIPlus_RegionCreateFromRect($tRectF)
;从路径建立区域
Local $hPath = _GDIPlus_PathCreate()
_GDIPlus_PathAddEllipse($hPath, 25, 10, 50, 50)
Local $hRgn2 = _GDIPlus_RegionCreateFromPath($hPath)
;~ 区域的相交模式:
;~ 0 - 用新区域替换已存在的区域
;~ 1 - 用区域自身和新区域的相交部分替换已存在的区域
;~ 2 - 用区域自身和新区域的结合部分替换已存在的区域
;~ 3 - 对两个区域执行异或(XOR)操作的结果替换已存在的区域位于两区域的XOR部分的点表示它在其中一个但不同时在两个区域中
;~ 4 - 用区域自身和新区域外部替换已存在的区域
;~ 5 - 用在已存在区域的外部的新区域部分替换已存在的区域
Local $hRgn
For $i = 1 To 5
;复制区域1
$hRgn = _GDIPlus_RegionClone($hRgn1)
;把区域2通过模式$i混合到$hRgn
_GDIPlus_RegionCombineRegion($hRgn, $hRgn2, $i)
;填充$hRgn
_GraphicsFillRegion($hGraphics, $hRgn, $hBrush)
;释放$hRgn
_GDIPlus_RegionDispose($hRgn)
_GDIPlus_GraphicsDrawRect($hGraphics, 5, 5, 90, 60)
_GraphicsDrawString($hGraphics, "混合模式" & $i, 10, 70)
_GDIPlus_GraphicsTranslateTransform($hGraphics, 100, 0)
Next
_GDIPlus_GraphicsResetTransform($hGraphics)
_GDIPlus_GraphicsTranslateTransform($hGraphics, 0, 90)
;绘制$hRgn1和$hRgn2的原始外形,由于区域没有绘制外形的函数,所以直接绘制了原始圆形路径和原始矩形
_GraphicsDrawPath($hGraphics, $hPath, $hPen);原始圆形路径
_GDIPlus_PenSetColor($hPen, 0xFF00FF00)
_GDIPlus_GraphicsDrawRect($hGraphics, 10, 20, 80, 30, $hPen);原始矩形
_GraphicsDrawString($hGraphics, "原区域形状", 10, 70)
;释放
_GDIPlus_PathDispose($hPath)
_GDIPlus_RegionDispose($hRgn1)
_GDIPlus_RegionDispose($hRgn2)
;==============================下面是画布剪切区域的设置======================
Local $hFamily = _GDIPlus_FontFamilyCreate("Arial")
Local $tLayout = _GDIPlus_RectFCreate(0, 0)
$hPath = _GDIPlus_PathCreate()
_GDIPlus_PathAddString($hPath, "Au3", $tLayout, $hFamily, 1, 100)
_GDIPlus_GraphicsTranslateTransform($hGraphics, 100, 0)
_GraphicsDrawPath($hGraphics, $hPath, $hPen)
_GDIPlus_PenSetColor($hPen, 0xFFFF0000)
;从路径获取画布的剪切区域============
_GDIPlus_GraphicsSetClipPath($hGraphics, $hPath)
;以下同心圆超出剪切区域的不会绘制出来
For $i = 0 To 30
_GDIPlus_GraphicsDrawEllipse($hGraphics, 125 - $i * 5, 60 - $i * 5, $i * 10, $i * 10, $hPen)
Next
;使剪切区域无限大,相当于不设置剪切区域
_GDIPlus_GraphicsResetClip($hGraphics)
_GDIPlus_PathDispose($hPath)
;以下设置从区域设置剪切区域================
_GDIPlus_GraphicsTranslateTransform($hGraphics, 250, 0)
$hPath = _GDIPlus_PathCreate(1)
_GDIPlus_PathAddEllipse($hPath, 5, 5, 100, 100)
_GDIPlus_PathAddEllipse($hPath, 80, 5, 30, 30)
_GDIPlus_BrushSetSolidColor($hBrush, 0x33003399)
_GraphicsFillPath($hGraphics, $hPath, $hBrush)
;从路径设置区域
$hRgn = _GDIPlus_RegionCreateFromPath($hPath)
_GDIPlus_PathDispose($hPath)
;从区域设置画布的剪切区域
_GDIPlus_GraphicsSetClipRegion($hGraphics, $hRgn)
_GDIPlus_BrushSetSolidColor($hBrush, 0xFFFF0000)
For $i = 0 To 10
_GraphicsDrawString($hGraphics, "我爱Autoit,I love au3", 0, $i * 14, $hBrush)
Next
_GDIPlus_RegionDispose($hRgn)
_GDIPlus_BrushDispose($hBrush)
_GDIPlus_PenDispose($hPen)
EndFunc ;==>CombinemodeComp
;_GDIPlus_GraphicsDrawString这个函数,我认为他没有设置$hBrush,所以我改成这样就可以用不同的画刷了
Func _GraphicsDrawString($hGraphics, $sString, $nX, $nY, $hBrush = 0, $sFont = "Arial", $nSize = 10, $iFormat = 0)
Local $hFormat = _GDIPlus_StringFormatCreate($iFormat)
Local $hFamily = _GDIPlus_FontFamilyCreate($sFont)
Local $hFont = _GDIPlus_FontCreate($hFamily, $nSize)
Local $tLayout = _GDIPlus_RectFCreate($nX, $nY, 0, 0)
Local $aInfo = _GDIPlus_GraphicsMeasureString($hGraphics, $sString, $hFont, $tLayout, $hFormat)
__GDIPlus_BrushDefCreate($hBrush)
Local $aResult = _GDIPlus_GraphicsDrawStringEx($hGraphics, $sString, $hFont, $aInfo, $hFormat, $hBrush)
Local $iError = @error
__GDIPlus_BrushDefDispose()
_GDIPlus_FontDispose($hFont)
_GDIPlus_FontFamilyDispose($hFamily)
_GDIPlus_StringFormatDispose($hFormat)
Return SetError($iError, 0, $aResult)
EndFunc ;==>_GraphicsDrawString
;下面这两个描路径和填充路径,在3.3.9.5中已经更正了,我用的是3.3.7.15画笔和画刷设置不对,可以改成这样的就行了
Func _GraphicsDrawPath($hGraphics, $hPath, $hPen = 0)
Local $iTmpErr, $iTmpExt, $aResult
__GDIPlus_PenDefCreate($hPen)
$aResult = DllCall($ghGDIPDll, "uint", "GdipDrawPath", "hwnd", $hGraphics, "hwnd", $hPen, "hwnd", $hPath)
$iTmpErr = @error
$iTmpExt = @extended
__GDIPlus_PenDefDispose()
If $iTmpErr Then Return SetError($iTmpErr, $iTmpExt, False)
$GDIP_STATUS = $aResult
Return $aResult = 0
EndFunc ;==>_GraphicsDrawPath
Func _GraphicsFillPath($hGraphics, $hPath, $hBrush = 0)
Local $iTmpErr, $iTmpExt, $aResult
__GDIPlus_BrushDefCreate($hBrush)
$aResult = DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
$iTmpErr = @error
$iTmpExt = @extended
__GDIPlus_BrushDefDispose()
If $iTmpErr Then Return SetError($iTmpErr, $iTmpExt, False)
$GDIP_STATUS = $aResult
Return $aResult = 0
EndFunc ;==>_GraphicsFillPath
Func _GraphicsFillRegion($hGraphics, $hRegion, $hBrush = 0)
Local $iTmpErr, $iTmpExt, $aResult
__GDIPlus_BrushDefCreate($hBrush)
$aResult = DllCall($ghGDIPDll, "uint", "GdipFillRegion", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hRegion)
$iTmpErr = @error
$iTmpExt = @extended
__GDIPlus_BrushDefDispose()
If $iTmpErr Then Return SetError($iTmpErr, $iTmpExt, False)
$GDIP_STATUS = $aResult
Return $aResult = 0
EndFunc ;==>_GraphicsFillRegion 感谢分享,学习了 不知道啥时才能到达你这个高度。 学习了,感谢分享! 反复看了几遍帖子,厉害啊 来学习学习! 高 !实在是高!
页:
[1]