differentrain 发表于 2014-6-20 02:58

今天和朋友学了会儿Excel,折腾到2点半..

本帖最后由 differentrain 于 2014-6-20 16:05 编辑

不怎么用Office系列,今天偶然和朋友聊起来,突发奇想用Excel做了个扫雷的修改器....
虽然不会Excel,不过VB咱小时候还是学过的...

我用的Win7的扫雷,其他版本的估计不行..可以停止计时和在表格中现实地雷位置...
附件就是那个表格...如果版本不对就直接看代码部分自己复制过去也行..
顺便说,VBA简直反人类..MS为什么不出VBA.NET啊...大段的代码要自己写,而且抽象性巨差....






【控件】

窗体:frmMain
按钮:btnCatchGame,btnRefresh
选择框:chkGameTime



【代码】


Option Explicit


Private Declare Function CreateToolhelp32Snapshot Lib "kernel32" (ByVal dwFlags As Long, ByVal th32ProcessID As Long) As Long
Private Declare Function module32First Lib "kernel32" Alias "Module32First" (ByVal hSnapShot As Long, lppe As moduleENTRY32) As Long
Private Declare Function module32Next Lib "kernel32" Alias "Module32Next" (ByVal hSnapShot As Long, lppe As moduleENTRY32) As Long
Private Declare Function Process32First Lib "kernel32" (ByVal hSnapShot As Long, lppe As PROCESSENTRY32) As Long
Private Declare Function Process32Next Lib "kernel32" (ByVal hSnapShot As Long, lppe As PROCESSENTRY32) As Long
Private Declare Function lstrcmpi Lib "kernel32" Alias "lstrcmpiA" (ByVal lpString1 As String, ByVal lpString2 As String) As Long


Private Declare Function OpenProcess Lib "kernel32" (ByVal dwDesiredAccess As Long, ByVal bInheritHandle As Long, ByVal dwProcessId As Long) As Long
Private Declare Function WriteProcessMemory Lib "kernel32" (ByVal hProcess As Long, ByVal lpBaseAddress As Any, lpBuffer As Any, ByVal nSize As Long, lpNumberOfBytesWritten As Long) As Long
Private Declare Function ReadProcessMemory Lib "kernel32" (ByVal hProcess As Long, ByVal lpBaseAddress As Any, lpBuffer As Any, ByVal nSize As Long, lpNumberOfBytesWritten As Long) As Long
Private Declare Function CloseHandle Lib "kernel32" (ByVal hObject As Long) As Long


Private Const TH32CS_SNAPPROCESS = &H2
Private Const TH32CS_SNAPmodule = &H8
Private Const CB_SHOWDROPDOWN = &H157
Private Type moduleENTRY32
    dwSize As Long
    th32ModuleID As Long
    th32ProcessID As Long
    GlblcntUsage As Long
    ProccntUsage As Long
    modBaseAddr As Long
    modBaseSize As Long
    hModule As Long
    szModule As String * 256
    szExePath As String * 1024
End Type

Private Type PROCESSENTRY32
    dwSize As Long
    cntUsage As Long
    th32ProcessID As Long
    th32DefaultHeapID As Long
    th32ModuleID As Long
    cntThreads As Long
    th32ParentProcessID As Long
    pcPriClassBase As Long
    dwFlags As Long
    szExeFile As String * 1024
End Type



Private Const PROCESS_ALL_ACCESS = &H1F0FFF
Private hProcess As Long
Private PID As Long


Private Type asmNum
    nuM1 As Byte
    nuM2 As Byte
    nuM3 As Byte
End Type

Private adrTime As Long
Private adrMine As Long

Private Function GetProcIdByName(ByVal ProcName As String) As Long
    Dim PE32 As PROCESSENTRY32
    Dim Procid As Long
    Dim hSnapShot As Long
    hSnapShot = CreateToolhelp32Snapshot(ByVal TH32CS_SNAPPROCESS, ByVal 0)
    PE32.dwSize = LenB(PE32)
    Process32First hSnapShot, PE32
    Do
      If lstrcmpi(Trim$(ProcName), Trim$(PE32.szExeFile)) = 0 Then
            Procid = PE32.th32ProcessID
            Exit Do
      End If
      PE32.szExeFile = vbNullString
    Loop Until Process32Next(hSnapShot, PE32) = 0
    CloseHandle hSnapShot
      GetProcIdByName = Procid
End Function



Private Function GetModuleBaseByProcName(ByVal ModuleName As String) As Long

    Dim ME32 As moduleENTRY32, ModuleBase As Long
    Dim hSnapShot As Long
    hSnapShot = CreateToolhelp32Snapshot(ByVal TH32CS_SNAPmodule, ByVal PID)
    ME32.dwSize = LenB(ME32)
    module32First hSnapShot, ME32
   
    Do
   
      If lstrcmpi(Trim$(ModuleName), Trim$(ME32.szModule)) = 0 Then
            ModuleBase = ME32.modBaseAddr
            Exit Do
      End If
      
      ME32.szModule = vbNullString
   
    Loop Until module32Next(hSnapShot, ME32) = 0
    CloseHandle hSnapShot
    GetModuleBaseByProcName = ModuleBase

End Function


Private Function GetMemory(ByVal Adderss As Long, Optional Length As Byte = 4) As Long
ReadProcessMemory hProcess, Adderss, GetMemory, Length, 0
End Function
Private Sub SetMemoryAsm(ByVal Adderss As Long, NumVal As asmNum)
WriteProcessMemory hProcess, Adderss, NumVal, 3, 0
End Sub


Private Function FindGame() As Boolean
   
    PID = GetProcIdByName("MineSweeper.exe")
   
    Select Case PID
      Case 0
            FindGame = False
      Case Else
            Dim adrBase As Long
            adrBase = GetModuleBaseByProcName("MineSweeper.exe")
            adrTime = adrBase + &H21446
            adrMine = adrBase + &H868B4
            FindGame = True
    End Select
End Function

Private Sub TrainerState(ByVal State As Boolean)
    chkGameTime.Enabled = State
    btnRefresh.Enabled = State
    Select Case State
      Case True
            btnCatchGame.Caption = "ReleaseGame"
      Case False
            btnCatchGame.Caption = "CatchGame"
            chkGameTime.Value = False
    End Select
End Sub


Private Sub AsmState(ByVal State As Boolean)
    Dim asm As asmNum
    Select Case State
      Case True
            asm.nuM1 = &H90
            asm.nuM2 = &H90
            asm.nuM3 = &H90
      Case False
            asm.nuM1 = &HD9
            asm.nuM2 = &H58
            asm.nuM3 = &H1C
    End Select
    Call SetMemoryAsm(adrTime, asm)
End Sub


Private Sub chkGameTime_Click()
   AsmState (chkGameTime.Value)
End Sub


Private Sub isOpen(ByVal State As Boolean)
      Select Case State
      Case True
            If FindGame = True Then
                hProcess = OpenProcess(PROCESS_ALL_ACCESS, False, PID)
                TrainerState (True)
            End If
      Case False
            If FindGame = True Then
               AsmState (False)
               CloseHandle hProcess
            End If
    End Select
End Sub


Private Sub btnCatchGame_Click()
    Select Case btnCatchGame.Caption
      Case "CatchGame"
            isOpen (True)
      Case "ReleaseGame"
            isOpen (False)
            TrainerState (False)
    End Select
End Sub

Private Sub btnRefresh_Click()

    Dim mineColumn As Byte, mineLine As Byte
    Dim adrPoint As Long, adrTemp As Long, adrColumn As Long
    Dim i As Byte, j As Byte

   
   
    btnRefresh.Enabled = False
   
    adrTemp = GetMemory(adrMine)
    adrPoint = GetMemory(adrTemp + &H10)
   
    mineLine = GetMemory(adrPoint + &H8) - 1
    mineColumn = GetMemory(adrPoint + &HC) - 1
   
    adrPoint = GetMemory(adrPoint + &H44)
    adrPoint = GetMemory(adrPoint + &HC)
   
   
   
    For i = 0 To 30
      adrColumn = GetMemory(adrPoint + i * 4)
      adrColumn = GetMemory(adrColumn + &HC)
      For j = 0 To 23
            If i > mineColumn Or j > mineLine Then
                Sheet1.Cells(j + 1, i + 1) = ""
            Else
                Sheet1.Cells(j + 1, i + 1) = GetMemory(adrColumn + j, 1)
            End If
      Next j
    Next i
    btnRefresh.Enabled = True
   
   
End Sub

Private Sub UserForm_Initialize()
    TrainerState (False)
    Sheet1.Cells(1, 2) = 1
End Sub

Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)
    isOpen (False)
End Sub




NataieChan 发表于 2014-6-21 18:42


事實證明Excel是有盡頭的﹗(謎:你是閒到甚麼程度?﹗)

NataieChan 发表于 2014-6-20 12:29

excel在我們這裡是必學的…

止慈 发表于 2014-6-20 12:45

厉害还有源码,学习
excel我只拿来做最简单的表格。。

尗又 发表于 2014-6-20 18:24

完全看不懂!!!!。。。

不明觉厉只能跪

NataieChan 发表于 2014-6-20 18:49

尗又 发表于 2014-6-20 18:24
完全看不懂!!!!。。。

不明觉厉只能跪

這位很厲害噠﹗帶了修改器來報道﹗大慈姐姐很歡喜的樣子…

止慈 发表于 2014-6-20 19:00

NataieChan 发表于 2014-6-20 18:49
這位很厲害噠﹗帶了修改器來報道﹗大慈姐姐很歡喜的樣子…

哈哈那是,因为我对修改器的东西比较感兴趣啊

NataieChan 发表于 2014-6-20 20:32

止慈 发表于 2014-6-20 19:00
哈哈那是,因为我对修改器的东西比较感兴趣啊

莫非你勤制修改器的目的是因為懶得自己去玩…

止慈 发表于 2014-6-20 20:57

NataieChan 发表于 2014-6-20 20:32
莫非你勤制修改器的目的是因為懶得自己去玩…
不算勤,不过目的确实是为了省事。自己在玩的时候发现很多不合理的地方,比如说接通告,我要一家家转3D、跑进场景、走一段路、去点制作人、看目前有什么通告——这里还只是看到目前有什么通告,还不一定想接,也不一定能接,或者现在就能接。玩得烦了就自己琢磨减少一下流程,毕竟游戏是要有乐趣,但鼠标点多了也太繁琐。
而且我玩游戏是修改派,不修改无乐趣。。

有点跑题了。。再回到excel上,小N你们学校里都学用excel做什么?我会的只有最基本的表格和加加减减求和比较之类的。。

再想起来,我因为需要,想过用excel设计一个东西,大概也是存一定数据然后按自己需求可以随机提取之类的,搜到一篇文章还提供了源码的,结果源码链接无效了。。



止慈 于 2014-6-20 21:12:09 补充以下内容

求指教。。打开附件excel,启用宏以后,那个窗体怎么出现。。我编辑宏能看到源代码,excel不会那么多不知道怎么让那个窗体出现。。

在我这里
mineLine = GetMemory(adrPoint + &H8) - 1
会溢出

不过没关系,只是做着玩玩的,不用修~我是试着运行了一下然后出了这个错误,就顺便说一下


NataieChan 发表于 2014-6-20 21:15

止慈 发表于 2014-6-20 20:57
不算勤,不过目的确实是为了省事。自己在玩的时候发现很多不合理的地方,比如说接通告,我要一家家转3D、 ...

做各種奇怪的東西…說起都是淚…最討厭排名…很麻煩…


NataieChan 于 2014-6-20 21:19:08 补充以下内容

做各種的圖…

止慈 发表于 2014-6-20 21:23

NataieChan 发表于 2014-6-20 21:15
做各種奇怪的東西…說起都是淚…最討厭排名…很麻煩…


做什么奇怪的东西说出来让我们乐一乐

排名还好啊,不过也许你们的是比较复杂的排名,那就麻烦点吧。。

以下是编辑:

刚刚没看到你补充的。做各种的图的话确实比较麻烦。。
页: [1] 2 3
查看完整版本: 今天和朋友学了会儿Excel,折腾到2点半..