雨林GG 发表于 2016-12-23 09:53:47

seniors大侠的《简单小时钟》如何用鼠标拖动指针使其转动?

教学需要用鼠标拖动分针或时针转动来学习时钟,搜了不少网页都是如何画的,可自己又没有能力来完成,只能来求助大家了。还请有的同志嘴下留情,饶了我~
      现在我的问题是,如何判断鼠标是在分针或者时针上,官网上搜了个判断点是否在某形状内的,但seniors大侠代码中,指针经过旋转了,无法来拼代码了!~
      代码都提供在下面的附件中,希望能得到您的帮助!~
原贴时钟代码:

#include <WindowsConstants.au3>
#include <WinAPIEx.au3>
#include <GDIPlusex.au3>
;~ #include <APIConstants.au3>

OnAutoItExitRegister("ExitFunc")
Global $Timer_Second = 1
Global $SecondDelay = 50
Global $BackColor =
Global $TextColor =
Global $ScaleColor =
Global $ClockwiseColor =
Global $SecondColor =
Global $colorI = 0
Global $Toumin = 255
Global $FontFile = @ScriptDir & '\ETHNOCEN.TTF'
Global $hGui = GUICreate("沙漏", 211, 211, -1, -1, $WS_POPUP, BitOR($WS_EX_LAYERED, $WS_EX_TOOLWINDOW, $WS_EX_TOPMOST))
Global $hSecond = GUICreate("", 211, 211, 5, 5, $WS_POPUP, BitOR($WS_EX_LAYERED, $WS_EX_MDICHILD, $WS_EX_TRANSPARENT), $hGui)

_GDIPlus_Startup()

Draw_Watch()
Global $hCallback = DllCallbackRegister("My_winProc", "int", "hWnd;uint;wparam;lparam")
Global $tCallback = DllCallbackGetPtr($hCallback)
Global $CallProc = _WinAPI_SetWindowLong($hGui, -4, $tCallback)
GUISetState(@SW_SHOW, $hGui)
GUISetState(@SW_SHOW, $hSecond)
_WinAPI_SetTimer($hGui, $Timer_Second, $SecondDelay, 0)
Do
      Sleep(10)
Until GUIGetMsg() = -3

Func ExitFunc()
      _WinAPI_KillTimer($hGui, $Timer_Second)
      _WinAPI_SetWindowLong($hGui, -4, $CallProc)
      _GDIPlus_Shutdown()
      GUIDelete($hGui)
EndFunc   ;==>ExitFunc

Func second()
      Local $hBitmap = _WinAPI_CreateBitmap(211, 211, 1, 32)
      Local $hCDC = _WinAPI_CreateCompatibleDC(0)
      Local $hOld = _WinAPI_SelectObject($hCDC, $hBitmap)
      Local $hGraphics = _GDIPlus_GraphicsCreateFromHDC($hCDC)
      _GDIPlus_GraphicsClear($hGraphics, 0x00000000)
      _GDIPlus_GraphicsSetSmoothingMode($hGraphics, 2)
      _GDIPlus_GraphicsSetInterpolationMode($hGraphics, 7)
      ;画时针
      Local $hPath = _GDIPlus_PathCreate()
      _GDIPlus_PathAddLine($hPath, -5, 0, 40, 0)
      Local $hMatrix = _GDIPlus_MatrixCreate()
      Local $hourAng = (@HOUR + @MIN / 60) * 30 - 90
      _GDIPlus_MatrixTranslate($hMatrix, 106, 106)
      _GDIPlus_MatrixRotate($hMatrix, $hourAng)
      _GDIPlus_PathTransform($hPath, $hMatrix)
      Local $hPen = _GDIPlus_PenCreate($ClockwiseColor[$colorI], 3)
      DllCall($ghGDIPDll, "uint", "GdipDrawPath", "hwnd", $hGraphics, "hwnd", $hPen, "hwnd", $hPath)
                _GDIPlus_PenDispose($hPen)
      _GDIPlus_PathDispose($hPath)
      _GDIPlus_MatrixDispose($hMatrix)
                _GDIPlus_PenDispose($hPen)
                $hourAng=0
      ;画分针
      $hPath = _GDIPlus_PathCreate()
      _GDIPlus_PathAddLine($hPath, -6, 0, 48, 0)
      $hMatrix = _GDIPlus_MatrixCreate()
      Local $miniuteAng = (@MIN + @SEC / 60) * 6 - 90
      _GDIPlus_MatrixTranslate($hMatrix, 106, 106)
      _GDIPlus_MatrixRotate($hMatrix, $miniuteAng)
      _GDIPlus_PathTransform($hPath, $hMatrix)
      $hPen = _GDIPlus_PenCreate($ClockwiseColor[$colorI], 2)
      DllCall($ghGDIPDll, "uint", "GdipDrawPath", "hwnd", $hGraphics, "hwnd", $hPen, "hwnd", $hPath)
                _GDIPlus_PenDispose($hPen)
      _GDIPlus_PathDispose($hPath)
      _GDIPlus_MatrixDispose($hMatrix)
                $miniuteAng = 0
      ;画秒针
                $hPath = _GDIPlus_PathCreate()
      secondPath($hPath, 8, 70, 3, 10)
      $hMatrix = _GDIPlus_MatrixCreate()
      Local $secondAng = (@SEC + @MSEC / 1000) * 6 - 90
      _GDIPlus_MatrixTranslate($hMatrix, 106, 106)
      _GDIPlus_MatrixRotate($hMatrix, $secondAng)
      _GDIPlus_PathTransform($hPath, $hMatrix)
      Local $hBrush = _GDIPlus_BrushCreateSolid($SecondColor[$colorI])
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)
      _GDIPlus_MatrixDispose($hMatrix)
                $secondAng = 0
      ;画转轴
      _GDIPlus_PathReset($hPath)
      _GDIPlus_PathAddEllipse($hPath, 105, 105, 2, 2)
      $hBrush = _GDIPlus_BrushCreateSolid(0xFF000000)
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)      
      _GDIPlus_PathDispose($hPath)

      _GDIPlus_GraphicsDispose($hGraphics)
      _WinAPI_SelectObject($hCDC, $hOld)
      _WinAPI_DeleteDC($hCDC)
      _WinAPI_UpdateLayeredWindowEx($hSecond, -1, -1, $hBitmap, $Toumin, 1)
      _WinAPI_DeleteObject($hBitmap)
      _WinAPI_EmptyWorkingSet()
EndFunc   ;==>second

Func Draw_Watch()
      Local $hBitmap = _WinAPI_CreateBitmap(211, 211, 1, 32)
      Local $hCDC = _WinAPI_CreateCompatibleDC(0)
      Local $hOld = _WinAPI_SelectObject($hCDC, $hBitmap)
      Local $hGraphics = _GDIPlus_GraphicsCreateFromHDC($hCDC)
      _GDIPlus_GraphicsClear($hGraphics, 0x00000000)
      _GDIPlus_GraphicsSetSmoothingMode($hGraphics, 2)
      _GDIPlus_GraphicsSetInterpolationMode($hGraphics, 7)
      ;画表处壳
      Local $hPath = _GDIPlus_PathCreate(1)
      _GDIPlus_PathAddEllipse($hPath, 0, 0, 210, 210)
      _GDIPlus_PathAddEllipse($hPath, 150, 0, 60, 60)
      Local $hPen = _GDIPlus_PenCreate(0xFF999999)
                DllCall($ghGDIPDll, "uint", "GdipDrawPath", "hwnd", $hGraphics, "hwnd", $hPen, "hwnd", $hPath)
                _GDIPlus_PenDispose($hPen)
      Local $hBrush = _GDIPlus_LineBrushCreate(0, 0, 106, 106, 0xFF989898, 0xFFFFFFFF, 3)
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)
      _GDIPlus_PathReset($hPath)
      _GDIPlus_PathAddEllipse($hPath, 8, 8, 194, 194)
      $hBrush = _GDIPlus_LineBrushCreate(0, 0, 0, 210, 0xFF989898, 0xFFFFFFFF)
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)
      ;表的内部底色
      _GDIPlus_PathReset($hPath)
      _GDIPlus_PathAddEllipse($hPath, 12, 12, 186, 186)
      $hBrush = _GDIPlus_BrushCreateSolid($BackColor[$colorI])
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)
      _GDIPlus_PathDispose($hPath)
      ;表盘小刻度
      $hBrush = _GDIPlus_BrushCreateSolid($ScaleColor[$colorI])
      $hPath = WatchPath(180, 5, 0.5, 6)
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)
      _GDIPlus_PathReset($hPath)
      ;表盘大刻度
      $hBrush = _GDIPlus_BrushCreateSolid($ScaleColor[$colorI])
      $hPath = WatchPath(180, 8, 1, 30)
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)
      _GDIPlus_PathReset($hPath)
      ;表内的文字
      Local $pi = 3.14159265358979, $rad
      Local $hFormat = _GDIPlus_StringFormatCreate(0x0004)
      _GDIPlus_StringFormatSetAlign($hFormat, 1);1为居中显示
      Local $hFontCollection = _GDIPlus_PrivateCollectionCreate()
      _GDIPlus_PrivateCollectionAddFontFile($hFontCollection, $FontFile)
      Local $hFamilyList = _GDIPlus_FontCollectionGetFamilyList($hFontCollection)
      Local $hFamily = $hFamilyList;因为只加了一个字体,所以是1;_GDIPlus_FontFamilyCreate();"Ethnocentric")
      Local $tLayout = _GDIPlus_RectFCreate(0, 0)
      For $i = 1 To 12
                $rad = $i * $pi / 6
                $xx = 106 + Sin($rad) * 70
                $yy = 100 - Cos($rad) * 70
                $tLayout = _GDIPlus_RectFCreate($xx, $yy)
                _GDIPlus_PathAddString($hPath, $i, $tLayout, $hFamily, 0, 16, $hFormat)
                $hBrush = _GDIPlus_BrushCreateSolid($TextColor[$colorI])
                DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                              _GDIPlus_BrushDispose($hBrush)
                _GDIPlus_PathReset($hPath)
                        Next
                ;耳朵上的3
      $tLayout = _GDIPlus_RectFCreate(185, 12)
      _GDIPlus_PathAddString($hPath, "3", $tLayout, $hFamily, 0, 24, $hFormat)
      $hBrush = _GDIPlus_BrushCreateSolid($TextColor[$colorI])
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)
      _GDIPlus_PathReset($hPath)
      ;标志A
      $tLayout = _GDIPlus_RectFCreate(105, 50)
      _GDIPlus_PathAddString($hPath, "A", $tLayout, $hFamily, 0, 32, $hFormat)
      $hBrush = _GDIPlus_BrushCreateSolid($TextColor[$colorI])
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)
                ;下方网址
                $tLayout = _GDIPlus_RectFCreate(105, 150)
      _GDIPlus_PathAddString($hPath, "Autoitx.com", $tLayout, $hFamily, 0, 6, $hFormat)
      $hBrush = _GDIPlus_BrushCreateSolid($TextColor[$colorI])
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)
;~         _GDIPlus_FontFamilyDispose($hFamily);说明里看到私有字体集中的字体族不用释放
;~            _GDIPlus_PrivateFontCollectionDispose($hFontCollection);释放私有字体集时出错,只能注释掉了
      _GDIPlus_StringFormatDispose($hFormat)
                ;玻璃效果,本来应该放在指针后再画,为了减少CPU占用,就放在指针下面,一般也看不出
                _GDIPlus_PathReset($hPath)
      _GDIPlus_PathAddArc($hPath, 14, 14, 182, 182, -83, -194)
      _GDIPlus_PathAddArc($hPath, 105, -95, 186, 400, 153, 54)
                _GDIPlus_PathCloseFigures($hPath)
      $tRectF = _GDIPlus_RectFCreate(12, 12, 115, 198)
      $hBrush = _GDIPlus_LineBrushCreateFromRectWithAngle($tRectF, 0xAAFFFFFF, 0x00FFFFFF, 70)
      Local $tBlends
      $tBlends = 3
      $tBlends = 0
      $tBlends = 0.0
      $tBlends = 1
      $tBlends = 0.55
      $tBlends = 1
      $tBlends = 1.0
      _GDIPlus_LineBrushSetBlend($hBrush, $tBlends)
      DllCall($ghGDIPDll, "uint", "GdipFillPath", "hwnd", $hGraphics, "hwnd", $hBrush, "hwnd", $hPath)
                _GDIPlus_BrushDispose($hBrush)
      _GDIPlus_PathDispose($hPath)
               
      _GDIPlus_GraphicsDispose($hGraphics)
      _WinAPI_SelectObject($hCDC, $hOld)
      _WinAPI_DeleteDC($hCDC)
      _WinAPI_UpdateLayeredWindowEx($hGui, -1, -1, $hBitmap, $Toumin, 1)
      _WinAPI_DeleteObject($hBitmap)
      _WinAPI_EmptyWorkingSet()
EndFunc   ;==>Draw_Watch

Func My_winProc($hWnd, $Msg, $wParam, $lParam)
      Switch $Msg
                Case 0x0084;WM_NCHITTEST
                        Return $HTCAPTION
                Case 0x00A3;WM_NCLMOUSEDBCLK
                        Exit
                Case 0x0113;$WM_TIMER
                        second()
                Case 0x00A8;WM_NCMBUTTONUP
                        $Toumin -= 128
                        If $Toumin < 0 Then $Toumin = 255
                        Draw_Watch()
                Case 0x00A5;WM_NCRBUTTONUP
                        $colorI += 1
                        If $colorI > 2 Then $colorI = 0
                        Draw_Watch()
      EndSwitch
      Return _WinAPI_CallWindowProc($CallProc, $hWnd, $Msg, $wParam, $lParam)
EndFunc   ;==>My_winProc

Func secondPath($hPath, $Left, $Right, $Height, $rad)
      _GDIPlus_PathAddLine($hPath, -$Left, -$Height / 2, $Right, -0.5)
      _GDIPlus_PathAddLine($hPath, $Right, -0.5, $Right, 0.5)
      _GDIPlus_PathAddLine($hPath, $Right, 0.5, -$Left, $Height / 2)
      _GDIPlus_PathAddLine($hPath, -$Left, $Height / 2, -$Left, -$Height / 2)
      _GDIPlus_PathAddEllipse($hPath, $Right - $rad - 5, -$rad / 2, $rad, $rad)
      _GDIPlus_PathAddEllipse($hPath, $Right - $rad - 3, -$rad / 2 + 2, $rad - 4, $rad - 4)
EndFunc   ;==>secondPath

Func ScalePath($R, $Height, $nStartAngle, $nSweepAngle)
      Local $hPath = _GDIPlus_PathCreate()
      _GDIPlus_PathAddArc($hPath, 15, 15, $R, $R, $nStartAngle, $nSweepAngle)
      _GDIPlus_PathAddArc($hPath, $Height + 15, $Height + 15, $R - $Height * 2, $R - $Height * 2, $nStartAngle + $nSweepAngle, -$nSweepAngle)
      _GDIPlus_PathCloseFigures($hPath)
      Return $hPath
EndFunc   ;==>ScalePath

Func WatchPath($R, $Height, $sweepAng, $step)
      Local $hPath1 = _GDIPlus_PathCreate()
      Local $startAng = -$sweepAng / 2
      For $Ang = $startAng To 360 - $sweepAng Step $step
                $hPath = ScalePath($R, $Height, $Ang, $sweepAng)
                _GDIPlus_PathAddPath($hPath1, $hPath, False)
                _GDIPlus_PathDispose($hPath)
      Next
      Return $hPath1
EndFunc   ;==>WatchPath

页: [1]
查看完整版本: seniors大侠的《简单小时钟》如何用鼠标拖动指针使其转动?