找回密码
 加入
搜索
查看: 11893|回复: 10

[交流] 第十一讲 GDI+画笔及线型

[复制链接]
发表于 2013-5-31 22:19:56 | 显示全部楼层 |阅读模式
GDI+的画笔,有两种
_GDIPlus_PenCreate,纯色画笔
_GDIPlus_PenCreate2,画刷型画笔
画笔和线型的设置
1、_GDIPlus_PenSetCompoundArray设置复合画笔,也就是把画笔分成几根,可以同时画几根线
2、_GDIPlus_PenSetLineJoin设置画笔转角处的连接方式
3、_GDIPlus_PenSetStartCap、_GDIPlus_PenSetEndCap设置笔头笔尾的样式
4、_GDIPlus_PenSetAlignment设置对齐方式
5、_GDIPlus_PenSetDashStyle设置线型,预设的有5种,还可以自定义
6、画笔缩放和旋转等,缩放和旋转由于没法测试成功,只能作罢
自己看源码体会一下
不知道有没有人做作业,布置一个自定义线帽,线帽为五角星的作业

#include <APIConstants.au3>
#include <WinAPIEx.au3>
#include <GDIPlus.au3>
#include <GDIPlusEx.au3>
#include <GuiSlider.au3>
Global $startX = 50, $startY = 20, $lineWidth = 100, $penWidth = 10
GUICreate("第十一讲 GDI+画笔及线型", 500, 400)
$nCtrlId = GUICtrlCreatePic("", 0, 0, 500, 200)
$hPicWnd = GUICtrlGetHandle($nCtrlId)

Global $rect[4][2], $Cap[4], $lineJoin[4], $DashCap[3], $line[3], $iStartCap, $iEndCap, $iLineJoin = 0, $iDashCap = 0
init()
GUIRegisterMsg($WM_HSCROLL, "onHSCROLL")
GUISetState()

update()

While 1
        $Msg = GUIGetMsg()
        Switch $Msg
                Case -3
                        ExitLoop
                Case $lineJoin[0], $lineJoin[1], $lineJoin[2], $lineJoin[3]
                        $iLineJoin = $Msg - $lineJoin[0]
                        update()
                Case $DashCap[0], $DashCap[1], $DashCap[2]
                        $iDashCap = $Msg - $DashCap[0]
                        If $iDashCap > 0 Then $iDashCap += 1
                        update()
                Case $line[0], $line[1], $line[2]
                        update()
        EndSwitch
WEnd

GUIDelete()
Exit

Func init()
        GUICtrlCreateLabel("直线起点X", 5, 205)
        $rect[0][0] = GUICtrlCreateSlider(60, 205, 100)
        GUICtrlSetLimit(-1, 50, 0)
        GUICtrlSetData(-1, $startX)
        $rect[0][1] = GUICtrlCreateLabel("", 170, 205, 40, 25)
        GUICtrlSetData(-1, $startX)

        GUICtrlCreateLabel("直线起点Y", 5, 235)
        $rect[1][0] = GUICtrlCreateSlider(60, 235, 100)
        GUICtrlSetLimit(-1, 50, 0)
        GUICtrlSetData(-1, $startY)
        $rect[1][1] = GUICtrlCreateLabel("", 170, 235, 40, 25)
        GUICtrlSetData(-1, $startY)

        GUICtrlCreateLabel("直线长度", 255, 205)
        $rect[2][0] = GUICtrlCreateSlider(310, 205, 100)
        GUICtrlSetLimit(-1, 150, 0)
        GUICtrlSetData(-1, $lineWidth)
        _GUICtrlSlider_SetTicFreq(-1, 50)
        $rect[2][1] = GUICtrlCreateLabel("", 420, 205, 40, 25)
        GUICtrlSetData(-1, $lineWidth)
        ;$hPen = _GDIPlus_PenCreate(0xFFFF0000, $penWidth)设置画笔宽度
        GUICtrlCreateLabel("画笔宽", 255, 235)
        $rect[3][0] = GUICtrlCreateSlider(310, 235, 100)
        GUICtrlSetLimit(-1, 30, 0)
        GUICtrlSetData(-1, $penWidth)
        $rect[3][1] = GUICtrlCreateLabel("", 420, 235, 40, 25)
        GUICtrlSetData(-1, $penWidth)
;~ $iStartCap
;~ 起点线帽的样式:
;~ 0x00 - 直线以方形线帽结束.
;~ 0x01 - 方形线帽. 直线在方形中心结束. 方形宽高为线宽.
;~ 0x02 - 圆形端点. 直线在圆形中心结束. 圆形直径为线宽.
;~ 0x03 - 三角形线帽. 直线在三角形基线结束. 三角形基线为线宽.
;~ 0x10 - 线帽不固定.
;~ 0x11 - 线终点以方形固定. 方形中心为线的最后一点. 方形宽高大于线宽.
;~ 0x12 - 线终点以圆形固定. 圆形中心为线的最后一点. 圆宽于线.
;~ 0x13 - 线终点以钻石形固定(方形旋转45度). 钻石形中心为线的最后一点. 钻石形宽于线.
;~ 0x14 - 线终点以箭头固定. 箭头顶点为线的最后一点. 箭头宽于线.
;~ 0xff - 线帽由CustomLineCap对象创建.
;~ $iEndCap
;~ 终点线帽的样式(与$iStartCap相同)
;~ $iDashCap
;~ 破折号的起点和终点线帽:
;~ 0 - 两端点均为方形线帽
;~ 2 - 两端点均为圆形线帽
;~ 3 - 两端点均为三角形线帽的最后一点. 箭头宽于线.
;~ _GDIPlus_PenSetLineCap( $hPen, $iStartCap, $iEndCap, $iDashCap )
;~ _GDIPlus_PenSetStartCap($hPen, $iEndCap)
;~ _GDIPlus_PenSetEndCap($hPen, $iEndCap)
;~ _GDIPlus_PenSetDashCap($hPen[, $iDash = 0])
        GUICtrlCreateLabel("起点形状", 5, 265)
        $Cap[0] = GUICtrlCreateSlider(60, 265, 100)
        GUICtrlSetLimit(-1, 9, 0)
        GUICtrlSetData(-1, 0)
        _GUICtrlSlider_SetTicFreq(-1, 1)
        $Cap[1] = GUICtrlCreateLabel("", 170, 265, 40, 25)
        GUICtrlSetData(-1, "直线")
        
        GUICtrlCreateLabel("终点形状", 255, 265)
        $Cap[2] = GUICtrlCreateSlider(310, 265, 100)
        GUICtrlSetLimit(-1, 9, 0)
        GUICtrlSetData(-1, 0)
        _GUICtrlSlider_SetTicFreq(-1, 1)
        $Cap[3] = GUICtrlCreateLabel("", 420, 265, 40, 25)
        GUICtrlSetData(-1, "直线")
;~ _GDIPlus_PenSetLineJoin( $hPen, $iLineJoin )
;~ $iLineJoin
;~ 线连接类型:
;~ 0 - 线连接生成一个锐角
;~ 1 - 线连接生成一个对角Line join produces a diagonal corner.
;~ 2 - 线连接在两线间生成平滑的圆弧
;~ 3 - 线连接生成一个锐角剪切角
        GUICtrlCreateLabel("线连接类型", 5, 295)
        GUIStartGroup()
        $lineJoin[0] = GUICtrlCreateRadio("锐角连接", 105, 295)
        GUICtrlSetState(-1, 1)
        $lineJoin[1] = GUICtrlCreateRadio("对角连接", 205, 295)
        $lineJoin[2] = GUICtrlCreateRadio("圆弧连接", 305, 295)
        $lineJoin[3] = GUICtrlCreateRadio("切角连接", 405, 295)
        GUICtrlCreateLabel("虚线连接样式", 5, 325)
        GUIStartGroup()
        $DashCap[0] = GUICtrlCreateRadio("方形", 105, 325)
        GUICtrlSetState(-1, 1)
        $DashCap[1] = GUICtrlCreateRadio("圆形", 205, 325)
        $DashCap[2] = GUICtrlCreateRadio("三角", 305, 325)
        GUICtrlCreateLabel("直线类型", 5, 355)
        GUIStartGroup()
        $line[0] = GUICtrlCreateRadio("实线", 105, 355)
        GUICtrlSetState(-1, 1)
        $line[1] = GUICtrlCreateRadio("虚线", 205, 355)
        $line[2] = GUICtrlCreateRadio("复合", 305, 355)
EndFunc   ;==>init

Func onHSCROLL($hWnd, $iMsg, $wParam, $lParam)
        Switch _WinAPI_GetDlgCtrlID($lParam)
                Case $rect[0][0]
                        $startX = GUICtrlRead($rect[0][0])
                        GUICtrlSetData($rect[0][1], $startX)
                Case $rect[1][0]
                        $startY = GUICtrlRead($rect[1][0])
                        GUICtrlSetData($rect[1][1], $startY)
                Case $rect[2][0]
                        $lineWidth = GUICtrlRead($rect[2][0])
                        GUICtrlSetData($rect[2][1], $lineWidth)
                Case $rect[3][0]
                        $penWidth = GUICtrlRead($rect[3][0])
                        GUICtrlSetData($rect[3][1], $penWidth)
                Case $Cap[0]
                        $iStartCap = GUICtrlRead($Cap[0])
                        $iStartCap = setDate($iStartCap, 1)
                Case $Cap[2]
                        $iEndCap = GUICtrlRead($Cap[2])
                        $iEndCap = setDate($iEndCap, 3)
        EndSwitch
        update()
EndFunc   ;==>onHSCROLL

Func setDate($nCap, $n)
        Switch $nCap
                Case 0
                        GUICtrlSetData($Cap[$n], "直线")
                Case 1
                        GUICtrlSetData($Cap[$n], "方形")
                Case 2
                        GUICtrlSetData($Cap[$n], "圆形")
                Case 3
                        GUICtrlSetData($Cap[$n], "三角")
                Case 4
                        GUICtrlSetData($Cap[$n], "不固定")
                        $nCap += 12
                Case 5
                        GUICtrlSetData($Cap[$n], "大方形")
                        $nCap += 12
                Case 6
                        GUICtrlSetData($Cap[$n], "大圆形")
                        $nCap += 12
                Case 7
                        GUICtrlSetData($Cap[$n], "大钻石")
                        $nCap += 12
                Case 8
                        GUICtrlSetData($Cap[$n], "箭头")
                        $nCap += 12
                Case 9
                        GUICtrlSetData($Cap[$n], "自定义")
                        $nCap = 0xFF
        EndSwitch
        Return $nCap
EndFunc   ;==>setDate

Func update()
        Local $HWND_CX = _WinAPI_GetWindowWidth($hPicWnd)
        Local $HWND_CY = _WinAPI_GetWindowHeight($hPicWnd)
        _GDIPlus_Startup()
        $hGraphics = _GDIPlus_GraphicsCreateFromHWND($hPicWnd)
        $hBitmap = _GDIPlus_BitmapCreateFromGraphics($HWND_CX, $HWND_CY, $hGraphics)
        $hBackbuffer = _GDIPlus_ImageGetGraphicsContext($hBitmap)
        _GDIPlus_GraphicsClear($hBackbuffer, 0xFFECE9D8)
        _GDIPlus_GraphicsSetSmoothingMode($hBackbuffer, 2);光滑模式,2为8*8抗距齿
        TextureBrushComp($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 TextureBrushComp($hGraphics)
        Local $hPen = _GDIPlus_PenCreate(0xFFFF0000, $penWidth);左边红色画笔
        
        Local $hBrush = _GDIPlus_LineBrushCreate(0, 0, 10, 10, 0xFFFFFF00, 0xFFFF0000)
        Local $hpen2 = _GDIPlus_PenCreate2($hBrush, $penWidth)
        _GDIPlus_BrushDispose($hBrush);右边渐变画笔
        ;如果虚线设置虚线,及虚线连接样式
        If GUICtrlRead($line[1]) = 1 Then
                _GDIPlus_PenSetDashStyle($hPen, 1);虚线
                _GDIPlus_PenSetDashCap($hPen, $iDashCap)
                _GDIPlus_PenSetDashStyle($hPen2, 2);点线
                _GDIPlus_PenSetDashCap($hPen2, $iDashCap)
        EndIf
;~         ;复合画笔指同时画多条线,$aCompounds[5] = [4, 0, 0.2, 0.5, 1]指二条线,第一条是画笔宽从0-0.2,第二条是从画笔宽0.5-1
        If GUICtrlRead($line[2]) = 1 Then
                Local $aCompounds[5] = [4, 0, 0.2, 0.5, 1]
                _GDIPlus_PenSetCompoundArray($hPen, $aCompounds);复合画笔
                _GDIPlus_PenSetCompoundArray($hPen2, $aCompounds);复合画笔
        EndIf
        ;设置连接方式
        _GDIPlus_PenSetLineJoin($hPen, $iLineJoin)
        _GDIPlus_PenSetLineJoin($hPen2, $iLineJoin)
        Local $aPoints[4][2] = [[3, 3],[$startX, $startY + 60],[$startX + $lineWidth, $startY + 60],[$startX + $lineWidth, $startY + 140]]
        ;绘制黑色参考线,左边界,右边界,中心线
        _GDIPlus_GraphicsDrawLine($hGraphics, $startX, $startY, $startX, $startY + 40)
        _GDIPlus_GraphicsDrawLine($hGraphics, $startX + $lineWidth, $startY, $startX + $lineWidth, $startY + 40)
        _GDIPlus_GraphicsDrawLine($hGraphics, $startX - 20, $startY + 20, $startX + $lineWidth + 20, $startY + 20)
        ;设置笔帽
        _GDIPlus_PenSetStartCap($hPen, $iStartCap)
        _GDIPlus_PenSetEndCap($hPen, $iEndCap)
        _GDIPlus_PenSetStartCap($hPen2, $iStartCap)
        _GDIPlus_PenSetEndCap($hPen2, $iEndCap)
        ;左边图形
        _GDIPlus_GraphicsDrawLine($hGraphics, $startX, $startY + 20, $startX + $lineWidth, $startY + 20, $hPen)
        _GDIPlus_GraphicsDrawPolygon($hGraphics, $aPoints, $hPen)
        ;右边图形
        _GDIPlus_GraphicsTranslateTransform($hGraphics, 250, 0)
        _GDIPlus_GraphicsDrawLine($hGraphics, $startX, $startY + 20, $startX + $lineWidth, $startY + 20, $hPen2)
        _GDIPlus_GraphicsDrawPolygon($hGraphics, $aPoints, $hPen2)
        ;释放画笔
        _GDIPlus_PenDispose($hPen)
        _GDIPlus_PenDispose($hPen2)
;_GDIPlus_PenSetMiterLimit( $hPen, $nMiterLimit )
;$nMiterLimit
;指定画笔对象的斜切限制的实际数字. 如该值小于1则以1替代
;斜切限制没有调试出效果,所以不用了
;===================================================
;_GDIPlus_PenSetAlignment($hPen,1)
;这句的作用是画封闭图形时,让线向内对齐
;==========不作演示了===============================
EndFunc   ;==>TextureBrushComp

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?加入

×

评分

参与人数 5威望 +2 金钱 +115 贡献 +31 收起 理由
xms77 + 10
afan + 2 + 50 + 5 +
lpxx + 50 + 11
楼上风云 + 15 我想起了我曾经的一贴,GDI显示汉字笔顺。学 ...
hzxymkb + 5 ++

查看全部评分

发表于 2013-5-31 22:37:00 | 显示全部楼层
这回坐定沙发了!哈哈!
发表于 2013-5-31 22:48:42 | 显示全部楼层
真要学习了!
发表于 2013-5-31 23:26:01 | 显示全部楼层
回复 1# seniors

一群码农,就这么痴痴地过周末
发表于 2013-5-31 23:27:18 | 显示全部楼层
回复 2# hzxymkb

水哥多久不见,越发小气了。才贡献5大元?
发表于 2013-6-1 11:16:52 | 显示全部楼层
不错啊。。学习一下。。
 楼主| 发表于 2013-6-1 11:46:09 | 显示全部楼层
回复 4# 楼上风云
汉字笔顺是路径问题,下次讲路径时看,能不能把路径读出来,分析一下
发表于 2013-6-1 13:39:05 | 显示全部楼层
六一都不去过节,这种精神可贵啊!
发表于 2013-6-2 20:26:18 | 显示全部楼层
s大有新课了没?很期待啊!
发表于 2013-6-3 20:51:52 | 显示全部楼层
我也顶一个支持一下!
发表于 2016-10-3 14:24:00 | 显示全部楼层
"D:\Users\Administrator\Desktop\dddd.au3"(222,64) : error: _GDIPlus_PenSetCompoundArray(): undefined function.
您需要登录后才可以回帖 登录 | 加入

本版积分规则

QQ|手机版|小黑屋|AUTOIT CN ( 鲁ICP备19019924号-1 )谷歌 百度

GMT+8, 2024-3-28 20:54 , Processed in 0.083795 second(s), 21 queries .

Powered by Discuz! X3.5 Licensed

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表