_ddqs. 发表于 2010-10-22 21:25:21

困惑了很久,IE另存为热键实现,终于有点眉目了...

1.热键代码;IE用:快速保存网页……热键……^s(保存网页为文本)

#Include <WinAPIEx.au3>
#include <Process.au3>
#include <PostMessage_UDF.au3>

#include <GUIConstants.au3>
#include <guiconstantsex.au3>
#include <WindowsConstants.au3>
#include <GuiButton.au3>

$filename="gta_sa.exe"

HotKeySet("^s","_cs")
HotKeySet("^{F2}","cf2")
HotKeySet("+{F8}","quit")


HotKeySet("^{F8}","test")
HotKeySet("^{F3}","InsertKeyValue")


While 1
Sleep(1000)       
WEnd

Func quit()
Exit
EndFunc

Func _cs()
        RunWait(@ScriptDir&"\getKeyMsg.exe")
        Sleep(200)
        Send("!f")
        Sleep(200)
        Send("a")
        WinWaitActive("保存网页","",3)
        Send("{tab}")
        Send("{down 3}")
        Send("{Enter 2}")
EndFunc
       
Func cf2()
        RunWait(@ScriptDir&"\getKeyMsg.exe")
        Sleep(200)
        Send("HESOYAM") ;gta_sa作弊码输入,测试不成功!
        ;Sleep(200)
        ;Send("m")
EndFunc



;;;;;
;;;
;;
;2.关键部分__;来源:http://www.autoitx.com/forum.php?mod=viewthread&tid=12977&highlight=%BD%D8%BB%F1%BC%FC%C5%CC;getKeyMsg.au3--如何截获键盘消息,代码来源:http://www.autoitx.com/forum.php?mod=viewthread&tid=12977&highlight=%BD%D8%BB%F1%BC%FC%C5%CC
#NoTrayIcon
#include <WinAPI.au3>
#include <WindowsConstants.au3>
#include <StructureConstants.au3>
#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>

Opt('MustDeclareVars', 1)

Global $hHook, $hStub_KeyProc, $buf = "", $title = "", $title_1 = "", $keycode, $buffer = "", $nMsg

Local $hmod
$hStub_KeyProc = DllCallbackRegister("_KeyProc", "long", "int;wparam;lparam")
$hmod = _WinAPI_GetModuleHandle(0)

$hHook = _WinAPI_SetWindowsHookEx($WH_KEYBOARD_LL, DllCallbackGetPtr($hStub_KeyProc), $hmod)
;MsgBox(0, ":0#", $hHook,3)

While 1
      Sleep(1)
WEnd

;While $hHook
;        MsgBox(0, ":0#", $hHook,3)       
;      Sleep(1000)
;WEnd

Func _KeyProc($nCode, $wParam, $lParam)
      Local $tKEYHOOKS, $wVKey
      $tKEYHOOKS = DllStructCreate($tagKBDLLHOOKSTRUCT, $lParam)
      If $nCode < 0 Then
                Return _WinAPI_CallNextHookEx($hHook, $nCode, $wParam, $lParam)
      EndIf
;      If $wParam = $WM_KEYDOWN Then
;                ;MsgBox(0, ":1#", "拦截:"&$WM_KEYDOWN,1);
;                                Return 1
;      Else
;                Local $flags = DllStructGetData($tKEYHOOKS, "flags")
;                Switch $flags
;                        Case $LLKHF_ALTDOWN
;                              ;MsgBox(0, ":2#", "拦截:"&$LLKHF_ALTDOWN,1)
;                                                                Return 1
;                                EndSwitch
;                                _exit()
;                EndIf
      $wVKey = DllStructGetData($tKEYHOOKS, "vkCode")
      If ($wVKey > 7) Then
                If ($wParam = $WM_KEYDOWN) Then
                        ;ToolTip("{win} was pressed.")
                        Return 1
                ElseIf ($wParam = $WM_KEYUP) Then
                        ;ToolTip("{win} was released.")
                                                _exit()
                EndIf
      EndIf
                ;Return _WinAPI_CallNextHookEx($hHook, $nCode, $wParam, $lParam)
                Return 0
EndFunc   ;==>_KeyProc

Func _exit()
      _WinAPI_UnhookWindowsHookEx($hHook)
      DllCallbackFree($hStub_KeyProc)
      Exit
EndFunc   ;==>_exit
       
编译后运行第一个"热键监控",然后,打开一个网页,鼠标点下页体,再按下Ctrl+s键试下...
{:face (125):}

_ddqs. 发表于 2010-10-23 20:09:53

有个小BUG,报告下...
------------------------
有时调用监听程序,貌似监听不到击键信号就被挂起,还以为与什么不兼容呢,如果已击键解决,则与源码自动化设计不符或与自动发送的键发生混乱
搞个劣办法解决如下,加个计时器定时退出,全部代码重贴:;getKeyMsg.au3--如何截获键盘消息,代码来源:http://www.autoitx.com/forum.php?mod=viewthread&tid=12977&highlight=%BD%D8%BB%F1%BC%FC%C5%CC
#NoTrayIcon
#include <WinAPI.au3>
#include <WindowsConstants.au3>
#include <StructureConstants.au3>
#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>

Opt('MustDeclareVars', 1)

Global $hHook, $hStub_KeyProc, $buf = "", $title = "", $title_1 = "", $keycode, $buffer = "", $nMsg ,$timer=0

Local $hmod
$hStub_KeyProc = DllCallbackRegister("_KeyProc", "long", "int;wparam;lparam")
$hmod = _WinAPI_GetModuleHandle(0)

$hHook = _WinAPI_SetWindowsHookEx($WH_KEYBOARD_LL, DllCallbackGetPtr($hStub_KeyProc), $hmod)
;MsgBox(0, ":0#", $hHook,3)

AdlibRegister("timer");;;;--------------------安全计时

While 1
      Sleep(1)
                If $timer > 2000 Then _exit() ;;;;----2秒-------安全计时;挂起本程序时检测,在限定时间内如果没有键击,则自动退出
WEnd

;While $hHook
;        MsgBox(0, ":0#", $hHook,3)       
;      Sleep(1000)
;WEnd

Func _KeyProc($nCode, $wParam, $lParam)
      Local $tKEYHOOKS, $wVKey
      $tKEYHOOKS = DllStructCreate($tagKBDLLHOOKSTRUCT, $lParam)
      If $nCode < 0 Then
                Return _WinAPI_CallNextHookEx($hHook, $nCode, $wParam, $lParam)
      EndIf
;      If $wParam = $WM_KEYDOWN Then
;                ;MsgBox(0, ":1#", "拦截:"&$WM_KEYDOWN,1);
;                                Return 1
;      Else
;                Local $flags = DllStructGetData($tKEYHOOKS, "flags")
;                Switch $flags
;                        Case $LLKHF_ALTDOWN
;                              ;MsgBox(0, ":2#", "拦截:"&$LLKHF_ALTDOWN,1)
;                                                                Return 1
;                                EndSwitch
;                                _exit()
;                EndIf
      $wVKey = DllStructGetData($tKEYHOOKS, "vkCode")
      If ($wVKey > 7) Then
                If ($wParam = $WM_KEYDOWN) Then
                        ;ToolTip("{win} was pressed.")
                                                If $timer > 250 Then $timer -= 250;;;;--------------------安全计时
                        Return 1
                ElseIf ($wParam = $WM_KEYUP) Then
                        ;ToolTip("{win} was released.")
                                                _exit()
                EndIf
      EndIf
                ;Return _WinAPI_CallNextHookEx($hHook, $nCode, $wParam, $lParam)
                Return 0
EndFunc   ;==>_KeyProc

Func _exit()
      _WinAPI_UnhookWindowsHookEx($hHook)
      DllCallbackFree($hStub_KeyProc)
      Exit
EndFunc   ;==>_exit
       
Func timer();;;;--------------------安全计时
   $timer += 250
EndFunc   ;==>_计时
       

_ddqs. 发表于 2010-10-23 20:14:09

本帖最后由 _ddqs. 于 2010-10-23 20:26 编辑

如果以击键解决,则与源码自动化设计不符或与自动发送的键发生混乱
=========================================================
设定值为500就好,反应速度快点,反正检测也不用等2秒(俺做测试),说li~~~,值多少自己改下,代码:                If $timer > 500 Then _exit() ;;;;--2000 = 2秒-------安全计时;挂起本程序时检测,在限定时间内如果没有键击,则自动退出{:face (355):}

19377708 发表于 2010-10-24 03:15:48

不错的代码,学习下

_ddqs. 发表于 2010-10-25 03:13:29

本帖最后由 _ddqs. 于 2010-10-27 00:12 编辑

重写个----与键盘整合(用选项设置),不用另外再去搞个监听
#NoTrayIcon
#Region ;**** 参数创建于 ACNWrapper_GUI ****
#AutoIt3Wrapper_icon=C:\WINDOWS\system32\SHELL32.dll|-131
#EndRegion ;**** 参数创建于 ACNWrapper_GUI ****


;IE用……快速保存网页为文本……热键……^s
;;;;;测试环境:IE8;;;;;;;;;;;;;;;;;
;
;~ #CS 加入任务栏控制菜单
Opt("TrayMenuMode",1)
Dim $Pause=1

$KillIEitem = TrayCreateItem("I`E`") ;IE被冻……KILL了重启
TrayCreateItem("")
TrayCreateItem("")

$NetTransportitem = TrayCreateItem("流量")
TrayCreateItem("")

$prefsitem        = TrayCreateItem("暂停")
TrayCreateItem("")
$restart        = TrayCreateItem("重启")
TrayCreateItem("")
$exititem        = TrayCreateItem("退出")

TraySetState()
TraySetToolTip("IE用:快速保存网页为文本-热键…Ctrl+s…")
;~#CE

;~ #CS
$mycfg = StringReplace(@ScriptName,".au3","",-1,0)
$mycfg = StringReplace($mycfg,".exe","",-1,0)
$mycfg = @ScriptDir&"\"&$mycfg&".ini"
;Exit ( MsgBox(0,"",$mycfg) )
If Not FileExists($mycfg) Then ;生成配置文件
        iniWrite ($mycfg, "流量","显示", 1)
        FileWrite ($mycfg, ""&@CRLF)
        iniWrite ($mycfg, "关于软件","例行说明","IE用:快速保存网页为文本。热键:Ctrl+s")
        iniWrite ($mycfg, "关于软件","配置日期",@YEAR&"年"&@MON&"月"&@MDAY&"日 "&@HOUR&":"&@MIN&":"&@SEC)
        FileWrite ($mycfg, ""&@CRLF)
EndIf
$ToolTip = IniRead($mycfg, "流量","显示","")
;Exit ( MsgBox(0,"",$ToolTip) )
;~ #CE

Opt("WinTitleMatchMode", 2) ;宽松匹配 ;WinActivate("Windows Internet Explorer")
Opt("SendAttachMode", 1) ;绑定模式(应该是后续的字符操作相当是之前按键盘的延续……现时是这样理解的,如是,则不会出现由于之前键按久了的字符连发乱发,要发也等操作完再去发..)

HotKeySet("^s","_cs")
;~
AdlibRegister("HKSet");;;;----自动设置热键
Func HKSet()
;        If WinActive("Windows Internet Explorer") Or isIE() Then
        If isIE() Then
;        If WinActive("Windows Internet Explorer") Then
                If $Pause Then HotKeySet("^s","_cs") ;启用
                Return
        Else
                HotKeySet("^s") ;取消
                Return
        EndIf
EndFunc
;~

Func _cs()
        $Pause = 0 ;自动函数用
        HotKeySet("^s") ;解除热键,必须的,防止操作没完成之前被再次重复调用
        If Not WinActive("Windows Internet Explorer") Then;如果当前非IE则不执行以下操作,以避免与其他发生窗口冲突
                Sleep(2000); 挂起!以兼容其他软件的快捷键(须连续按2次Ctrl+s才起作用)——最好注册自动函数进行自动检测(上面已使用)
                $Pause = 1
                HotKeySet("^s","_cs") ;启用热键       
                Return
;~        ElseIf Not isIE() Then
;~                 Sleep(2000);
;~                 $Pause = 1
;~                 HotKeySet("^s","_cs")
;~                 Return
        EndIf
        ControlSend ( "Windows Internet Explorer","", "", "!fa" , 0 ) ;
;        Send("!fa")
;        WinActivate("保存网页")
;        MsgBox(0,"","ok")
        $exitloop=0
        While Not WinActive("保存网页")
                If $exitloop > 9 Then ExitLoop ;5秒钟内操作不成功则退出!(有些窗口会限制)
                Sleep(500) ;如果窗口还没出现则挂起
                If Not WinActive("保存网页") Then Send("!fa");循环内发送……用于除错,保证不被系统遗留键击影响以致被挂起……使用键盘整合还是有点不兼容!
                $exitloop += 1
        WEnd
;        WinActivate("保存网页")
;        If WinActive("保存网页") Then ;安全发送
;~                 Send("{tab}")
;~                 Send("{down 3}")
;~                 Send("{ENTER 2}")
;~                Send("!t") ;反应慢
;~                Send("{down 3}")
;~                Send("!s")

;        EndIf
;        ControlSend ( "窗口标题", "窗口文本", 控件ID, "字符串" [, 标志] )
;         ControlSend ( "保存网页","", "", "{TAB}" , 0 ) ;, 1148
        ControlSend ( "保存网页","", "", "{down 3}" , 0 ) ;1136,
        ControlSend ( "保存网页","", "", "{enter}" , 0 ) ;1,

        While WinActive("保存网页")
                Sleep(1000) ;如果当前窗口还在则挂起,原来用于挂起外循环,改用函数了应该也有点作用!
        WEnd
        $Pause = 1
        HotKeySet("^s","_cs") ;启用热键
EndFunc

;~ #CS ;;;;----网络流量
Dim$s = ;$s = 0 ;$s = 0

        $strComputer = "."
        $wbemServices = ObjGet("winmgmts:\\" & $strComputer & "\root\cimv2")

If $ToolTip = 1 Then AdlibRegister("NetTransport",1000)
;~ While 1
;~         NetTransport()
;~         Sleep(1000) ;每秒取值
;~ WEnd

Func NetTransport()
        $wbemObjectSet = $wbemServices.ExecQuery("Select * from Win32_PerfRawData_Tcpip_NetworkInterface")
        For $wbemObject In $wbemObjectSet
                $s = $s + $wbemObject.BytesReceivedPerSec
        Next
        $NetTransport = $s - $s
;<\\---加入(显示流量时:同时提示快捷键状态)
        Switch $Pause
                Case 1
                        $Kset="快捷键已启用"&@CRLF
                Case 0
                        $Kset="快捷键未启用"&@CRLF
        EndSwitch
;---//>
        If $s Then ToolTip($Kset&"网络流量:" & $NetTransport & " Bytes/s", @DesktopWidth - 170, @DesktopHeight - 80,"",1,0)
        $s = $s
        $s = 0

EndFunc

;~#CE

While 1
        ;~ #CS 任务栏菜单控制
        $msg = TrayGetMsg()
        Select
                Case $msg = 0
                        ContinueLoop
                Case $msg = $prefsitem
                        If $Pause Then
                                $Pause = 0
                                HotKeySet("^s")
                        Else
                                $Pause = 1
                                HotKeySet("^s","_cs")
                        EndIf
                Case $msg = $restart
                        Exit( Run(@ScriptFullPath) ) ;必须编译
                Case $msg = $exititem
                        Exit ;Loop

                Case$msg = $NetTransportitem;查看流量
                        If $s Then
                                ToolTip("", @DesktopWidth - 170, @DesktopHeight - 80,"",1,0)
                                AdlibUnRegister("NetTransport")
                                $s = 0
                                iniWrite ($mycfg, "流量","显示", 0)
                        Else
                                AdlibRegister("NetTransport",1000)
                                iniWrite ($mycfg, "流量","显示", 1)
                        EndIf
                Case$msg = $KillIEitem ;IE被冻……KILL了重启
                        $YES = MsgBox(262144+292,"警告","你将要重启IE"&@CRLF&@CRLF&"IE没反应了吗") ;4+32+256+262144
                        If $YES="YES" Or $YES=6Then
                                While ProcessExists("iexplore.exe")
                                        ProcessClose("iexplore.exe")
                                WEnd
                                ShellExecute(@ProgramFilesDir&"\Internet Explorer\iexplore.exe","",@HomeDrive&@HOMEPATH,"open",@SW_MAXIMIZE)
                        EndIf
        EndSelect
        ;~#CE       

;         Sleep(500)
WEnd

Func isIE()       
        Local $states =
        Local $aWList = WinList(), $iWList = ProcessList ("IExplore.exe") ;$iPID = ProcessExists("IExplore.exe")
        For $iec = 1 To $iWList
                For $iCC = 1 To $aWList
                        If $aWList[$iCC] <>"" And WinGetProcess($aWList[$iCC]) = $iWList[$iec] Then
;                                If BitAND(WinGetState($aWList[$iCC]),8) Then Return 1
                                For $isa=0 To 5
                                        If BitAND(WinGetState($aWList[$iCC]),8) = $states[$isa] Then Return 1
                                Next
                        EndIf
                Next
        Next
        Return 0
EndFunc

#CS
;~ ;
;~ ;</-- test - 不知所以,当然不知其所以然 //->
;~ ;
#CE
Exit
#CS
;~ ;
;~ ;</-- test - 不知所以,当然不知其所以然 //->
;~ ;
#CE

a0204080 发表于 2010-10-25 13:45:13

大神 啊
……
努力 学习……{:face (356):}

kingfirekkk 发表于 2010-10-25 14:59:11

不错的代码,值得参考。

_ddqs. 发表于 2010-10-27 18:46:54

{:face (411):}
http://www.autoitx.com/attachment.php?aid=MTE4MjF8NjNhODdlMjZ8MTI4ODE3NjE3N3xhNTAwczcwZWZZQWRGNFZDTTNPRGViOE5IV2FKalo1dzNPUFBNODk0RWR1OUJDOA%3D%3D
管理员,为何:附件下载回来的是.php
请改回.rar
页: [1]
查看完整版本: 困惑了很久,IE另存为热键实现,终于有点眉目了...