' * ' * Copyright (C) 2015 il, Lance ' * ' * This program is free software; you can redistribute it and/or ' * modify it under the terms of the GNU General Public License ' * as published by the Free Software Foundation; either version 2 ' * of the License, or (at your option) any later version. ' * ' * This program is distributed in the hope that it will be useful, ' * but WITHOUT ANY WARRANTY; without even the implied warranty of ' * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ' * GNU General Public License for more details. ' * ' * You should have received a copy of the GNU General Public License ' * along with this program; if not, write to the Free Software ' * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 'il '1.0 '&il_GameCreator:il 'Modified heavily by Lance, hell this might as well be a complete re-write from scratch. Nothing of iL's code even remains. ' BEGIN CONFIGURATION SETTINGS, You can and SHOULD change these values. -Lance GameBotName = "YOUR_GameBot" GameBotPw = "1234" HostBotName = "Your_HostBot" HostBotOwner = "YourWar2Name" 'Not actually used but here it is. AutoHostGameInterval = 0 ' This is in MINUTES. Every 15 minutes the bot will try to host a game itself. Setting this to 0 will cause the bot to not autohost anything. -Lance UseTeamviewer = "Yes" ' Set to NO if you do not use Teamviewer. I use it, so it's here. This removes the Nag Screen from the remote server when you disconnect from it and then re-maximizes War2. -Lance ' END CONFIGURATION SETTINGS, You should not touch anything else unless you are a programmer. -Lance ' Define some globals -Lance Public GameBotCounter, GameBotStatus, RebootCounter, AutoHostGameCounter, TeamViewerNagScreenCounter, Username, GameOwner, MapName, MapSpeed, MapSettings, GameType, StartTime, GameTeams, MapResources, OnePeon, MapFixedOrder, GamePassword, ForceStart 'Create a Tick event that we can use sort of like a Cronjob or to simulate Realtime statuses such as where the bot is, etc. -Lance CreateObj "LongTimer", "Tick_Event" Tick_Event.Interval = 1 Tick_Event.Enabled = True ' Load Autoit COM Object. This is required to control the mouse! If mouse movements/clicks dont work, then you need to install AUTOIT from here: https://www.autoitscript.com/cgi-bin/getfile.pl?autoit3/autoit-v3-setup.exe -Lance Set oAutoIt = CreateObject("AutoItX3.Control") Set Shell = CreateObject("wscript.shell") 'Initialize some counters that are used in the Ticks events. -Lance GameBotCounter = 0 TeamViewerNagScreenCounter = 0 If AutoHostGameInterval > 0 Then AutoHostGameCounter = AutoHostGameInterval * 60 '---------------------------------------------------------- BEGIN Stealthbot Hooks system is called "Events". All "Events" (AKA Hooks) begin with Event_NameOfEvent -Lance ' ----------------- user whispers command --------------------- Sub Event_WhisperFromUser(Username, Flags, Message, Ping) cmd_found = 0 map_start_time = 2 'Put all SINGLE word commands here. Multi-word commands are handled below. If (Message = "start") Then If (GameBotStatus = "in game") Then Select Case Username Case GameOwner AddQ "/w " & Username & " starting game now" ForceStart = 1 'StartGame Case GameBotName AddQ "/w " & Username & " starting game now" ForceStart = 1 'StartGame Case HostBotName AddQ "/w " & Username & " starting game now" ForceStart = 1 'StartGame Case Else AddQ "/w " & Username & " you are not game owner to start it" End Select Else AddQ "/w " & Username & " There is no game currently running." End If Exit Sub End If 'For some reason the original reset that iL developed used nncron rather than VBScript to do the loading and killing of war2. This method doesnt require the war2 icon to be in a specific location on the Desktop -Lance If (Message = "reboot") Then RebootWar2 Exit Sub End If if (Message = "help") Then Msg Username, "Commands are in [] symbols:" Msg Username, "[gow ef 4] Start game in 4 minutes" Msg Username, "[Kick 2] Kick player in slot 2, change number to desired slot." Msg Username, "[Ban 2] Ban player in slot 2, DONT use this please, its rude. Only use to ban annoying players, not newbies!!!!" Msg Username, "[reboot] If Gamebot is stuck in a game or not in chat, use this to reboot it. Abuse will result in banning of bot usage, all reboot commands are logged." Msg Username, "[start] When in a game lobby, this starts the game" Msg Username, "END OF COMMAND LIST" Exit Sub End If cmd_array = Split(trim(Message)) If (arrLength(cmd_array) > 0) Then If ((cmd_array(0) = "gow") And (arrLength(cmd_array) = 3)) Then MapSettings = trim(cmd_array(0) & " " & cmd_array(1)) MapSpeed = trim(cmd_array(1)) MapName = trim(cmd_array(0)) StartTime = trim(cmd_array(2)) GameType = "Melee" GameTeams = "2s" MapResources = "High" MapFixedOrder = "No" OnePeon = "Yes" GamePassword = "" GameOwner = Username If (IsNumeric(StartTime) = False) Then AddQ "/w " & Username & " Invalid delay time, please try again." Exit Sub End If If (StartTime > 15) Then StartTime = 15 End If If (StartTime < 1) Then StartTime = 1 End If If GameBotStatus = "in channel" Then CreateGame Username, MapName, MapSpeed, MapSettings, GameType, StartTime, GameTeams, MapResources, OnePeon, MapFixedOrder, GamePassword Exit Sub Else AddQ "/w " & Username & " please, wait for " & GameBotName &" to join a channel." End If End If 'Put all Multi-word commands here -Lance If (cmd_array(0) = "kick" And GameOwner = Username) Then kick cmd_array(1) Exit Sub End If If (cmd_array(0) = "ban" And GameOwner = Username) Then ban cmd_array(1) Exit Sub End If End If 'Print a simple help screen if no command was found. Displaying this to the HostBotName user would result in an infinite loop so we dont allow that. -Lance If Username <> HostBotName Then AddQ "/w " & Username & " Please type '/msg " & HostBotName & " help for a list of available commands." End If End Sub Sub Tick_Event_Timer() 'Check the Gamebots status every 5 seconds GameBotCounter = GameBotCounter + 1 If GameBotCounter = 5 Then AddQ "/whois " & GameBotName GameBotCounter = 0 End If If UseTeamviewer = "Yes" Then TeamViewerNagScreenCounter = TeamViewerNagScreenCounter + 1 If TeamViewerNagScreenCounter > 5 Then TeamViewerNagScreenCounter = 0 If oAutoIt.WinGetState("Sponsored session") > 0 Then oAutoIt.WinActivate "Sponsored session" Sleep(1) oAutoIt.Send "{ENTER}" Sleep(2) oAutoIt.WinActivate "Warcraft II" End If TeamViewerNagScreenCounter = 0 End If End If If AutoHostGameInterval > 0 Then AutoHostGameCounter = AutoHostGameCounter - 1 If AutoHostGameCounter <= 0 Then Msg HostBotName, "gow ef 5" AutoHostGameCounter = AutoHostGameInterval * 60 End If End If End Sub Sub Event_ServerInfo(Message) If InStr(Message, GameBotName & " is using") Then If InStr(Message, "private game") Then GameBotStatus = "in game" RebootCounter = 0 Exit Sub End If If InStr(Message, "in game") Then 'Yes that is 2 spaces between in game, there is a typo in the PVPGN server. -Lance GameBotStatus = "in game" RebootCounter = 0 Exit Sub End If If InStr(Message, "in channel") Then GameBotStatus = "in channel" RebootCounter = 0 Exit Sub End If End If If InStr(Message, "User was last seen on") Then GameBotStatus = "unknown" End If If GameBotStatus = "unknown" Then 'Couldnt find Bot for 1m30s so lets try to restart it RebootCounter = RebootCounter + 1 If RebootCounter > 90 Then RebootCounter = 0 RebootWar2 End If End If End Sub '------------------------------------------------------------END EVENTS/Hooks Section -Lance ' ------------------------------------ BEGIN UTILITY FUNCTIONS -Lance 'Generic Create game function. Map names, creation mouse/click locations are defined elsewhere. -Lance Sub CreateGame(GameOwner, MapName, MapSpeed, MapSettings, GameType, StartTime, GameTeams, MapResources, OnePeon, MapFixedOrder, GamePassword) 'Send out the notifications to players about the game. -Lance AddQ GameOwner & " requested " & MapName & " " & MapSpeed & ", game will autostart in " & StartTime & " minutes." AddQ "/w " & GameOwner & " please, type '/msg " & HostBotName & " start' to start the game early or the game will autostart in " & map_start_time & " minutes." 'Open Create Game screen SendKeysToWar2 "{ALTDOWN}c{ALTUP}" GamePassword = "" SetGameName MapName & " " & MapSpeed & " Owner: " & GameOwner SetGamePassword GamePassword SetMap MapName SetMapSpeed MapSpeed SetGameType GameType SetMapResources MapResources SetOnePeon OnePeon SetMapFixedOrder MapFixedOrder SendKeysToWar2 "{ENTER}" StartTimer = StartTime * 60 StartCounter = 0 Do While StartTimer > 0 If ForceStart = 1 Then AddQ GameBotStatus Exit Do End If 'If StrComp(GameBotStatus, "in game") <> 0 Then ' AddQ GameBotStatus ' Exit Do 'End If StartTimer = StartTimer - 1 StartCounter = StartCounter + 1 If StartCounter = 30 Then 'Msg users every 30 secs the status of the timer SendKeysToWar2 StartTimer / 60 & " Minutes b4 Autostart{ENTER}" StartCounter = 0 End If Sleep(1) Loop SendKeysToWar2 "Starting....{ENTER}" ' Let'r Rip! -Lance StartGame 'Reset all the variables -Lance ForceStart = 0 StartCounter = 0 StartTimer = 0 GameOwner = "" MapName = "" MapSpeed = "" MapSettings = "" GameType = "" StartTime = 0 GameTeams = "" MapResources = "" OnePeon = "" MapFixedOrder = "" GamePassword = "" 'If 'IsInGame = 4 'BotInChat = 0 'GameOwner = Username 'Else 'AddQ "/w " & Username & " please, wait for " & GameBotName &" to join the channel." End Sub Sub SetMapFixedOrder(MapFixedOrder) If MapFixedOrder = "Yes" Then SendKeysToWar2 "{ALTDOWN}f{ALTUP}" End Sub Sub SetOnePeon(OnePeon) If OnePeon = "No" Then SendKeysToWar2 "{ALTDOWN}o{ALTUP}" End Sub Sub SetGameName(GameName) SendKeysToWar2 "{ALTDOWN}n{ALTUP}" SendKeysToWar2 GameName End Sub Sub SetGamePassword(GamePassword) SendKeysToWar2 "{ALTDOWN}p{ALTUP}" SendKeysToWar2 GamePassword End Sub Sub SetGameType(GameType) 'Highlight the GameType selector -Lance SendKeysToWar2 "{ALTDOWN}t{ALTUP}" SendKeysToWar2 "{DOWN}" 'Move the slider all the way to the Top (TvB) -Lance SendKeysToWar2 "{UP}{UP}{UP}{UP}{UP}{UP}" Select Case GameType Case "TvB" SendKeysToWar2 "{ENTER}" Case "Melee" SendKeysToWar2 "{DOWN}{ENTER}" Case "FFA" SendKeysToWar2 "{DOWN}{DOWN}{ENTER}" Case Else SendKeysToWar2 "{DOWN}{ENTER}" 'Default to Melee End Select End Sub ' Each map is a Sub routine, so the name of the map (IE: GoW) is the sub routine you should make. It contains all the logic for navigating to the map and selecting it. See gow for example. -Lance Sub SetMap(MapName) 'Bring up the Map browser SendKeysToWar2 "{ALTDOWN}b{ALTUP}" If MapName = "gow" Then GoW End Sub Sub SetMapSpeed(MapSpeed) 'Highlight the Speed selector -Lance SendKeysToWar2 "{ALTDOWN}s{ALTUP}" 'Move the slider all the way to the Left (SLOWEST SPEED) -Lance SendKeysToWar2 "{LEFT}{LEFT}{LEFT}{LEFT}{LEFT}{LEFT}{LEFT}{LEFT}" Select Case MapSpeed Case "ef" SendKeysToWar2 "{RIGHT}{RIGHT}{RIGHT}{RIGHT}{RIGHT}{RIGHT}{RIGHT}" Case "f" SendKeysToWar2 "{RIGHT}{RIGHT}{RIGHT}{RIGHT}{RIGHT}{RIGHT}{RIGHT}{RIGHT}" Case Else SendKeysToWar2 "{RIGHT}{RIGHT}{RIGHT}{RIGHT}{RIGHT}{RIGHT}{RIGHT}" ' Default to EF End Select End Sub Sub SetMapSettings End Sub Sub SetGameTeams(GameTeams) Select Case GameTeams Case "1v1" Case "2v2" Case "3v3" Case Else End Select End Sub Sub SetMapResources(MapResources) 'Highlight the Resources Selector -Lance SendKeysToWar2 "{ALTDOWN}r{ALTUP}" SendKeysToWar2 "{DOWN}" 'Move resources all the way to Top -Lance SendKeysToWar2 "{UP}{UP}{UP}{UP}" Select Case MapResources Case "High" SendKeysToWar2 "{DOWN}{DOWN}{DOWN}{DOWN}{ENTER}" Case "Medium" SendKeysToWar2 "{DOWN}{DOWN}{DOWN}{ENTER}" Case "Low" SendKeysToWar2 "{DOWN}{DOWN}{ENTER}" Case "Random" SendKeysToWar2 "{DOWN}{ENTER}" Case "Default" SendKeysToWar2 "{ENTER}" Case Else SendKeysToWar2 "{DOWN}{DOWN}{DOWN}{DOWN}{ENTER}" ' Default to High End Select End Sub ' -------------- All Maps Subs should go here, Naming convention is up to you but I recommend using the mapnames like I have for GoW -Lance Sub GoW() SendKeysToWar2 "{HOME}" SendKeysToWar2 "c{ENTER}" SendKeysToWar2 "g{ENTER}" End Sub ' Because VBs is one of the stupidest languages in the scripting world, there is no Sleep() function that can be used in StealthBot. So, fuck you VBS, I am SCHMARTER THAN YOU. We use ping to simulate a Sleep function. -Lance Sub Sleep(seconds) Shell.Run "%COMSPEC% /c ping localhost -n " _ & seconds+1, 0, True End Sub 'Duh, Start a game :D -Lance Sub StartGame() 'Slap the OK button in War2 -Lance SendKeysToWar2 "{ALTDOWN}o{ALTUP}" 'If there are no opponents a msg will pop up that requires us to click OK. To get around this, we do the following. We dont need to cancel the game as we take care of that in the QuitGame function -Lance SendKeysToWar2 "{ENTER}" 'Wait 15 seconds to Quit the game. Sleep(15) QuitGame End Sub Sub QuitGame() 'In case there were no players when we tried to start, this will exit the game. -Lance SendKeysToWar2 "{ALTDOWN}c{ALTUP}" SendClickToWar2 "primary", 10, 10, "Click" SendKeysToWar2 "e" 'I dont use eqq because that does not always work. If the bot takes a long time, it might change to ess (surrender vs Quit for draw). So we use clicks instead. SendClickToWar2 "primary", 300, 190, "Click" SendClickToWar2 "primary", 300, 220, "Click" Sleep(10) 'This should Exit the Draw screen. -Lance SendKeysToWar2 "{ENTER}" End Sub ' Utility function to Send the GameBotPw to the War2 Login Screen. I use primary instead of 'left' in case of left handed users. -Lance Sub SendGameBotLoginPassword() SendClickToWar2 "primary", 220, 284, "DoubleClick" SendKeysToWar2 GameBotPw End Sub ' Utility function to Send the GameBotName to the War2 Login screen. -Lance Sub SendGameBotLoginName() SendClickToWar2 "Left", 260, 220, "DoubleClick" SendKeysToWar2 GameBotName End Sub 'Utility function to send mouse clicks to War2 via Autoit -Lance Sub SendClickToWar2(Button, Horizontal, Vertical, Position) 'Since ControlClick does NOT work with War2, we're forced to use this crap. Moving the mouse with ControlClick works, but actually doing the click does not because it's a Full Screen game and not a real window. -Lance If oAutoIt.WinGetState("Warcraft II") <> 3 AND oAutoIt.WinGetState("Warcraft II") <> 15 Then oAutoIt.WinActivate "Warcraft II" Sleep(3) End If oAutoIt.MouseMove Horizontal, Vertical If Position = "Click" Then oAutoIt.MouseClick Button End If If Position = "DoubleClick" Then oAutoIt.MouseClick Button oAutoIt.MouseClick Button End If If Position = "Down" Then oAutoIt.MouseDown Button End If If Position = "Up" Then oAutoIt.MouseUp Button End If 'oAutoIt.Sleep(500) Sleep(1) End Sub 'Utility function to sent keys to War2 window via Autoit -Lance Sub SendKeysToWar2(Keys) 'Activate isnt really necessary but I put it here just in case. -Lance If oAutoIt.WinGetState("Warcraft II") <> 3 AND oAutoIt.WinGetState("Warcraft II") <> 15 Then oAutoIt.WinActivate "Warcraft II" Sleep(7) End If oAutoIt.ControlSend "Warcraft II", "", "", Keys 'oAutoIt.Sleep(500) Sleep(1) End Sub ' Utility function to msg a user -Lance Sub Msg(Username,Message) AddQ("/w " & Username & " " & Message) End Sub 'Bans a user from the specified game slot -Lance Sub Ban (Slot) If (Slot = 2) Then oAutoIt.MouseMove 65, 65 oAutoIt.MouseDown oAutoIt.MouseMove 65, 140 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 3) Then oAutoIt.MouseMove 65, 90 oAutoIt.MouseDown oAutoIt.MouseMove 65, 165 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 4) Then oAutoIt.MouseMove 65, 115 oAutoIt.MouseDown oAutoIt.MouseMove 65, 190 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 5) Then oAutoIt.MouseMove 65, 140 oAutoIt.MouseDown oAutoIt.MouseMove 65, 215 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 6) Then oAutoIt.MouseMove 65, 165 oAutoIt.MouseDown oAutoIt.MouseMove 65, 240 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 7) Then oAutoIt.MouseMove 65, 190 oAutoIt.MouseDown oAutoIt.MouseMove 65, 265 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 8) Then oAutoIt.MouseMove 65, 215 oAutoIt.MouseDown oAutoIt.MouseMove 65, 290 oAutoIt.MouseUp SendKeys "{ENTER}" End If End Sub 'Duh, kicks a user from the specified game slot -Lance Sub Kick (Slot) If (Slot = 2) Then oAutoIt.MouseMove 65, 65 oAutoIt.MouseDown oAutoIt.MouseMove 65, 90 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 3) Then oAutoIt.MouseMove 65, 90 oAutoIt.MouseDown oAutoIt.MouseMove 65, 115 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 4) Then oAutoIt.MouseMove 65, 115 oAutoIt.MouseDown oAutoIt.MouseMove 65, 140 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 5) Then oAutoIt.MouseMove 65, 140 oAutoIt.MouseDown oAutoIt.MouseMove 65, 165 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 6) Then oAutoIt.MouseMove 65, 165 oAutoIt.MouseDown oAutoIt.MouseMove 65, 190 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 7) Then oAutoIt.MouseMove 65, 190 oAutoIt.MouseDown oAutoIt.MouseMove 65, 215 oAutoIt.MouseUp SendKeys "{ENTER}" End If If (Slot = 8) Then oAutoIt.MouseMove 65, 215 oAutoIt.MouseDown oAutoIt.MouseMove 65, 240 oAutoIt.MouseUp SendKeys "{ENTER}" End If End Sub 'This will kill any running War2 Process and attempt to re-login the GameBotName -Lance Sub RebootWar2() ' Log all calls to Reboot -Lance Log("Rebooted by " & Username) 'Not sure why, but the CWD needs to be changed since the CWD field does not work in the Autoit.Run function when executed througb VBScript -Lance OriginalCWD = Shell.CurrentDirectory Shell.CurrentDirectory = "c:\war2combat" 'Use Autoit to try to kill War2 and then give it 2 seconds to close. -Lance oAutoIt.WinKill "Warcraft II" Sleep(2) 'WinKill is UNRELIABLE. IE: If war2 is at the login screen, WinKill will fail for some reason. IDK Why, so I replace it with a real kill command if the window is still open. -Lance state = oAutoIt.WinGetState("Warcraft II") If state > 0 Then Shell.Run "CMD /k taskkill /f /fi ""WINDOWTITLE eq Warcraft II"" & exit" End If 'Run War2 via Autoit -Lance oAutoIt.Run "War2Launcher.bat" 'Set the CWD back to Stealthbot or bad things WILL happen lmao -Lance Shell.CurrentDirectory = OriginalCWD 'Give war2 about 15 secs to load -Lance 'oAutoIt.WinWaitActive "", "Warcraft II", 15 Sleep(15) 'Connect to RU server -Lance SendKeysToWar2 "-{Delay 100}m{Delay 100}e{Delay 100}c" 'Wait for connection to RU to complete (3 secs) -Lance Sleep(5) 'Click the username box, delete any usernames there, and then type our GameBotName -Lance SendGameBotLoginName 'Click the password box, delete any passwords there, and then type our GameBotPw -Lance SendGameBotLoginPassword 'Hit enter to actually login. -Lance SendKeysToWar2 "{ENTER}" 'Give bot 3 secs to login and then set the away msg -Lance Sleep(5) SendKeysToWar2 "/away To get a list of commands to use me type /msg " & HostBotName & " help{ENTER}" AddQ("EF_GameBot has been rebooted by: " & Username) 'VBScript likes to kick us out and display a long running script message, this is an attempt to avoid that. This is also why I use Autoit.ControlClick and Autoit.ControlSend rather than Stealthbot's SendKeys command because even if war2 gets minimized, the control functions from autoit will still do their job. -Lance oAutoIt.WinActivate "Warcraft II" End Sub Function arrLength(vArray) ItemCount = 0 For ItemIndex = 0 To UBound(vArray) If Not(vArray(ItemIndex)) = Empty Then ItemCount = ItemCount + 1 End If Next arrLength = ItemCount End Function ' ------------------------------------ END Utility Functions -Lance ' -------------- Functions to depreciate -Lance ' Send Keys to the Gamebot. For hostbot use AddQ instead -Lance Sub SendKeys(Keys) Shell.sendkeys Keys End Sub ' ----------------- Create file ------------------------------- Sub CreateFile(Filename) Set fso = CreateObject("Scripting.FileSystemObject") Set file = fso.OpenTextFile(Filename,2,True) file.close End Sub ' ----------------- Delete file ------------------------------- Sub DeleteFile(Filename) Set fso = CreateObject("Scripting.FileSystemObject") Set file = fso.DeleteFile(Filename) file.close End Sub ' ----------------- Write to file ----------------------------- Sub WriteToFile(Filename,Message) Set fso = CreateObject("Scripting.FileSystemObject") Set file = fso.OpenTextFile(Filename, 2, True) file.WriteLine Message file.Close End Sub ' ----------------- log --------------------------------------- Sub Log(Message) AddQ "/w " & HostBotOwner & " " & Message End Sub