-
Posts
397 -
Joined
-
Last visited
Reputation Activity
-
Avvi reacted to TheSmokie in [ToolBox][Vanilla - WOTLK] Many Useful Functions (Custom script)
Hi,
this is a toolbox kit i put together with different some code i had laying around, enjoy!
using robotManager.Helpful; using System; using System.Collections.Generic; using System.Linq; using System.Threading; using wManager.Wow.Bot.Tasks; using wManager.Wow.Enums; using wManager.Wow.Helpers; using wManager.Wow.ObjectManager; public class Tool { public static void LearningSpells(string SpellName) { Lua.LuaDoString(string.Format(@" for i=1,GetNumTrainerServices() do local name = GetTrainerServiceInfo(i) if (name == '{0}') then BuyTrainerService(i) end end ", SpellName.Replace("'", "\'"))); } public static bool RecipeIsKnown(string profession, string RecipeName) { bool Known = Lua.LuaDoString<bool>(string.Format(@" if not TradeSkillFrame then CastSpellByName('{0}') end if TradeSkillFrame:IsVisible() == nil then CastSpellByName('{0}') end numTradeSkills = GetNumTradeSkills() for i = 1, numTradeSkills do tradeSkillName, _, _, _ = GetTradeSkillInfo(i) if (tradeSkillName == '{1}') then return true; end if (TradeSkillFrame:IsVisible()) then TradeSkillFrame:Hide(); end end return false; ", profession, RecipeName)); Thread.Sleep(100); return Known; } // Craft works for Wrath of the Lich king public static void Craft(string profession, string itemName, int quantity) { if (RecipeIsKnown(profession, itemName) == true) { if (Usefuls.WowVersion == 12340) { Lua.LuaDoString(string.Format(@" if not TradeSkillFrame then CastSpellByName('{0}') end if TradeSkillFrame:IsVisible() == nil then CastSpellByName('{0}') end for i=1,GetNumTradeSkills() do local name, _, _, _ = GetTradeSkillInfo(i) if (name == '{1}') then DoTradeSkill(i, {2}) end if (TradeSkillFrame:IsVisible() and {2} < 2) then TradeSkillFrame:Hide(); end end ", profession, itemName, quantity)); } else if (Usefuls.WowVersion == 8606 || Usefuls.WowVersion == 5875) { Lua.LuaDoString(string.Format(@" if not TradeSkillFrame then CastSpellByName('{0}') end if TradeSkillFrame:IsVisible() == nil then CastSpellByName('{0}') end for i=1,GetNumTradeSkills() do local name, _, _, _ = GetTradeSkillInfo(i) if (name == '{1}') then DoTradeSkill(i, {2}) end if (TradeSkillFrame:IsVisible() and {2} < 2) then TradeSkillFrame:Hide(); end end ", profession, itemName, quantity)); } } } public static void RemoveItem(int Itemid) { Lua.LuaDoString(string.Format(@"for i=0,4 do for p=1,36 do if GetContainerItemID(i,p) == {0} then PickupContainerItem(i,p) DeleteCursorItem(); return end end end", Itemid)); } public static void UseItem(int itemID) { Lua.LuaDoString(string.Format(@"for bag = 0,4 do for slot = 1,GetContainerNumSlots(bag) do local item = GetContainerItemID(bag, slot) if (item and item == {0}) then if (GetContainerItemCooldown(bag,slot)==0) then UseContainerItem(bag,slot) return true end end end end ", itemID)); } public static int HasItem(string itemName) { var execute = "local itemCount = 0; " + "for b=0,4 do " + "if GetBagName(b) then " + "for s=1, GetContainerNumSlots(b) do " + "local itemLink = GetContainerItemLink(b, s) " + "if itemLink then " + "local _, stackCount = GetContainerItemInfo(b, s)\t " + "if string.find(itemLink, \"" + itemName + "\") then " + "itemCount = itemCount + stackCount; " + "end " + "end " + "end " + "end " + "end; " + "return itemCount; "; return Lua.LuaDoString<int>(execute); } public static bool Faction(string FactionName) { bool rep = Lua.LuaDoString<bool>("for factionIndex = 1, GetNumFactions() do local name, _, standingId = GetFactionInfo(factionIndex); if string.find(name, '" + FactionName.Replace("'", "\'") + "') then return standingId; end end"); return rep; } public static void AbandonQuest(string questName) { Lua.LuaDoString("local name = '" + questName + "' for i=1,GetNumQuestLogEntries() do local questTitle, level, questTag, suggestedGroup, isHeader, isCollapsed, isComplete = GetQuestLogTitle(i) if string.find(questTitle, name) then SelectQuestLogEntry(i) SetAbandonQuest() AbandonQuest() end end"); } public static bool haveKey(int keyId) { bool haveKey = Lua.LuaDoString<bool>("local itemIdSearch = " + keyId + "; local bag = KEYRING_CONTAINER; for slot = 1,MAX_CONTAINER_ITEMS do local itemLink = GetContainerItemLink(bag,slot); local _, itemCount = GetContainerItemInfo(bag,slot); if itemLink and itemCount then local _,_,itemId = string.find(itemLink, '.*|Hitem:(%d+):.*'); if itemId and tonumber(itemId) == itemIdSearch then return true end end end return false"); return haveKey; } public static void BuyItem(string name, int amount) { Lua.LuaDoString(string.Format(@" local itemName = ""{0}"" local quantity = {1} for i=1, GetMerchantNumItems() do local name = GetMerchantItemInfo(i) if name and name == itemName then BuyMerchantItem(i, quantity) end end", name, amount)); } public static void Sellitem(string ItemName) { Lua.LuaDoString(string.Format(@" local ItemToSell = '{0}' for bag = 0,4,1 do for slot = 1, GetContainerNumSlots(bag), 1 do local name = GetContainerItemLink(bag, slot); if name and string.find(name, ItemToSell) then if (MerchantFrame:IsShown() ) then ShowMerchantSellCursor(1) UseContainerItem(bag, slot) end end end end", ItemName)); } public static bool Face(Vector3 vector3) { var player = new Vector3(vector3); ObjectManager.Me.Rotation = robotManager.Helpful.Math.TargetFacingToRadian(ObjectManager.Me.Position, player); Move.StrafeLeft(); Move.StrafeRight(); return true; } public static void Fish(Vector3 vector3, Vector3 Water, int SkillLineStart, int SkillLineEnd, uint rode, uint sword) { while (Skill.GetValue(SkillLine.Fishing) >= SkillLineStart && Skill.GetValue(SkillLine.Fishing) <= SkillLineEnd) { ItemsManager.UseItem(rode); if (!FishingTask.IsLaunched) { if (GoToTask.ToPosition(vector3, 1.5f)) { Face(Water); FishingTask.LoopFish(); } } } FishingTask.StopLoopFish(); ItemsManager.UseItem(sword); } public static void CheckUpdate() { try { string onlineFile = "Github Raw link"; Quester.Bot.QuesterSetting.Load(); string profileName = "File.xml"; string currentFile = System.Windows.Forms.Application.StartupPath + @"\Profiles\Quester\" + profileName; var currentFileContent = System.IO.File.ReadAllText(currentFile, System.Text.Encoding.UTF8); var onlineFileContent = new System.Net.WebClient { Encoding = System.Text.Encoding.UTF8 }.DownloadString(onlineFile); if (!string.IsNullOrWhiteSpace(currentFileContent) && !string.IsNullOrWhiteSpace(onlineFileContent)) { if (currentFileContent != onlineFileContent) { Logging.Write("New version found, try to update file", (Logging.LogType)1, System.Drawing.Color.Red); System.IO.File.WriteAllText(currentFile, onlineFileContent); Thread.Sleep(500); new Thread(() => robotManager.Products.Products.ProductRestart()).Start(); } } Logging.Write("[Auto Updater]The version on your pc is the latest updated version.", (Logging.LogType)1, System.Drawing.Color.Red); } catch (Exception e) { Logging.WriteError("Auto update: " + e); } } public static int InteractItems(List<string> itemNames, int interactions = int.MaxValue) { if (!itemNames.Any()) return -1; var execute = "local counter = 0; " + "local leftStacks = 0; " + "for b=0,4 do " + "if GetBagName(b) then " + "for s=1, GetContainerNumSlots(b) do " + "local itemLink = GetContainerItemLink(b, s) " + "if itemLink then " + "local _, stackCount = GetContainerItemInfo(b, s)\t" + "if string.find(itemLink, \"" + itemNames.FirstOrDefault() + "\") "; if (itemNames.Count > 1) { execute = itemNames.Where(obj => itemNames.FirstOrDefault() != obj).Aggregate(execute, (current, obj) => current + "or string.find(itemLink, \"" + obj + "\") "); } execute = execute + "then " + "if (counter < " + interactions + ") then " + "UseContainerItem(b, s); " + "counter = counter + 1; " + "else " + "leftStacks = leftStacks + 1;" + "end " + "\tend\tend\tend end end return leftStacks;"; return Lua.LuaDoString<int>(execute); } /// <summary> /// Sends a mail to a recipient. /// </summary> /// <param name="recipient">The recipient.</param> /// <param name="subject">The subject.</param> /// <param name="itemNames">The items to send as names.</param> /// <returns>true if successful ; false if no mailbox available or stacks are left.</returns> public static bool SendItems(string recipient, string subject, List<string> itemNames) { var mailBox = ObjectManager.GetObjectWoWGameObject().FirstOrDefault(i => i.IsMailbox && i.GetDistance <= 5); if (mailBox == null || string.IsNullOrWhiteSpace(recipient)) return false; if (subject.Length == 0) subject = "-"; if (mailBox) { const int delayMs = 800; var timeOut = DateTime.Now.AddSeconds(40); Interact.InteractGameObject(mailBox.GetBaseAddress); Thread.Sleep(delayMs); Lua.LuaDoString("RunMacroText('/click MailFrameTab2');"); Thread.Sleep(delayMs); var leftStack = InteractItems(itemNames, 12); Thread.Sleep(delayMs); Lua.LuaDoString(@"SendMail(\" + recipient + ",\"{subject}\",\" \");"); Thread.Sleep(delayMs * 3); while (leftStack != 0 && DateTime.Now < timeOut) { leftStack = InteractItems(itemNames, 12); Thread.Sleep(delayMs); Lua.LuaDoString(string.Format(@"SendMail(\" + recipient + ",\"{subject}\",\" \");")); Thread.Sleep(delayMs * 3); } Lua.LuaDoString("CloseMail();"); if (leftStack != 0) return false; } return true; } public static bool Achievement(int achievementID, int index) { bool haveAchievement = Lua.LuaDoString<bool>("local achievementID = " + achievementID + "; local indexCriteria = " + index +"; local achievementInfo = {GetAchievementInfo(achievementID)}; if achievementInfo[4] then return achievementInfo[4] end local achCriteriaInfo = {GetAchievementCriteriaInfo(achievementID, indexCriteria)}; return achCriteriaInfo[3];"); return haveAchievement; } } public static class Travel { public static class Flight { //Thunderbluff to Orgrimmar static readonly Vector3 ThunderBluffFlightMaster = new Vector3(-1196.75f, 26.0777f, 176.9492f); static readonly int FlightMasterID = 2995; static readonly Vector3 OrgrimmarPlateform = new Vector3(1676.25f, -4313.45f, 61.79468f); static readonly string Orgrimmar = "Orgrimmar"; //Orgrimmar to Thunderbluff static readonly Vector3 OrgrimmarFlightMaster = new Vector3(1676.25f, -4313.45f, 61.79468f); static readonly int OrgrimmarFlightMasterID = 3310; static readonly Vector3 ThunderBluffPlateform = new Vector3(-1196.75f, 26.0777f, 176.9492f); static readonly string Thunderbluff = "Thunder Bluff"; private static void Wait(Vector3 arrival, int distance) { if (ObjectManager.Me.IsOnTaxi) { while (ObjectManager.Me.Position.DistanceTo(arrival) > distance) { Thread.Sleep(5000); } } } public static bool FlightPathChecker(string FlightPath) { bool Flight = Lua.LuaDoString<bool>(string.Format(@" local node = '{0}' if ( TaxiFrame:IsVisible() ) then for i=1,NumTaxiNodes() do if string.find(TaxiNodeName(i), node) then return true; end end return false; end", FlightPath.Replace("'", "\'"))); return Flight; } public static bool Flying(int npcID, Vector3 vector, string FlightName) { if (!ObjectManager.Me.IsOnTaxi) { while (GoToTask.ToPositionAndIntecractWithNpc(vector, npcID, 1) && !ObjectManager.Me.IsOnTaxi) { if (FlightPathChecker(FlightName) == false) { Logging.Write("[Travel]Flight: " + "Sorry, you do not have the flightpath to " + FlightName); break; } int node; node = Lua.LuaDoString<int>("for i=0,30 do if string.find(TaxiNodeName(i),'" + FlightName + "') then return i end end"); Lua.LuaDoString("TakeTaxiNode(" + node + ")"); } } return true; } public static void ThunderBluffToOrgrimmar() { Flying(FlightMasterID, ThunderBluffFlightMaster, Orgrimmar); Wait(OrgrimmarPlateform, 5); } public static void OrgrimmarToThunderBluff() { Flying(OrgrimmarFlightMasterID, OrgrimmarFlightMaster, Thunderbluff); Wait(ThunderBluffPlateform, 5); } } } How to use Tool:
RunCode (Action): - Tool.LearningSpells("Name Of spell"); // Put in name of the spell you wish to buy. - Tool.Craft("profession", "RecipeName", 1); // This code will only work for Wrath of the lich king - Tool.RemoveItem(55); // Removes item by ID - Tool.UseItem(55); // Uses item by ID - Tool.AbandonQuest("Quest Name"); //Abandon Quest by Name - Tool.Sellitem("Item Name"); // sell item by name - Tool.Fish(new Vector3(1, 1, 1), new Vector3(1, 1, 1), 0, 75, 6562, 111); - Tool.CheckUpdate(); // updates quester profiles from github.raw - Tool.SendItems("name", "note", new List<string> { "Super Healing Potion", }); // mail itemlist to another player If statements : - Tool.RecipeIsKnown("profession", "RecipeName") == true // check if you have this Recipe! If statement! - Tool.HasItem("itemname") <= 0 - Tool.Faction("Name of the faction", 5) == true // add name of faction, and amount of rep you want to check aganst. 42999 is max rep. - Tool.haveKey(KeyID) // checks if you have a key - Tool.Achievement(int achievementID, int index) How to use Travel (RunCode):
Flight : - Travel.Flight.ThunderBluffToOrgrimmar(); - Travel.Flight.OrgrimmarToThunderBluff(); I want to say thank you to both @Droidz For his hints on what the problem with was for some code.
ToolBox has many useful functions to help you develop different products.
Credits (Thanks to these people for there help and or code.) :
@Droidz for Auto updater.
@reaper for his SendMailing code.
@Ordush for his Crafting Code.
@Matenia for all the helpful links and hints to get this project Toolbox. Must respect!
If you find any bugs or want me to implement anything, Join our discord server and send me a message. : https://discordapp.com/invite/xQuhs5C
-
Avvi got a reaction from shoro2 in Avvi's C# Tips & Tricks with Helpful Code Snippets
Hi all,
I figured I'd post some things that I have learned during my time of developing in C#. Perhaps some of this is obvious for some of the more experienced WRobot C# writers, but for me, I had to do a lot of forum searching and experimenting to make progress on any of my work.
How do I get started?
Please see this post by @Droidz
How can I see what Functions are available to me in the WRobot API?
I recommend using some sort of decompiler in order to see what functions are available in the WRobot API. That is, use something such as dotPeek from jetbrains. See this URL: https://www.jetbrains.com/decompiler/ . Once you have this downloaded, open the WRobot Binaries located in the (C:\WRobot\Bin) folder in dotPeek. I cannot even begin to explain how many times the recompiled helped me find useful things I could re-use. As a quick tip, I would suggest taking a look at the wManager.wManager.Wow.Helpers functions that are available. Anything listed as public static <variable type> will be available to use from a Plugin/Profile/Fightclass etc.
What if WRobot doesn't have an available function that I will need?
WRobot doesn't have everything instantly available, so you may need to resort to using some Lua Functions to get information back from the WoW Client. An example of this that I ran into at some point was getting the number of Character Macros someone has.. Of course this is very specific, but please bear with me for the sake of this example :).
WoW Lua Reference: http://wowprogramming.com/docs/api_categories
Using Lua in C#:
This snippet will return a List of integers and set the C# variable numberOfMacros equal to the returned list of the DoString function. To be more specific, it will provide a list of the number of Global account Macros , and the number of Personal Character Macros.
var numberOfMacros = Lua.LuaDoString<List<int>>("return numCharacterMacros");
The below will return just the number Character Macros someone has. If you need a specific variable from a Lua Function, then do the following:
var numPersonalMacros = Lua.LuaDoString<int>("local numAccountMacros, numCharacterMacros = GetNumMacros(); return numCharacterMacros"); The above snippet will set the C# variable numPersonalMacros equal to numCharacterMacros from the lua return value.
Using a Variable in the Lua.LuaDoString. The below will return the text body of the macro that has the id of 121.
var _macroID = 121 string macroBody = Lua.LuaDoString<string>("return GetMacroBody(" + _macroID + ")");
Executing Lua Code in C#
This will leave the party (if the player is in one).
wManager.Wow.Helpers.Lua.RunMacroText("/run LeaveParty()");
What is the difference between Lua.LuaDoString() and RunMacroText()?
The difference is in can be understand in how you think about them. Lua.LuaDoString should be seen as a way to retrieve information.. More specifically, the Lua.LuaDoString's purpose is to have a value returned to it, so that you can assign it to a C# Variable. RunMacroText can be used to do something in game. More specifically, RunMacroText should be used when trying to run some sort of in-game script (such as /cast spell).
Plugin Template C#: Plugin-Template.cs
I have attached a basic plugin template that can be used. In it, I have provided an example of:
A Basic Implementation of the wManager.Plugin.IPlugin Class (including Settings/Initialize/Dispose) Basic loop that will occur while WRobot is running Settings that can be configured from Plugin Page A Category/Short Description for the Plugin Settings An example of Watching for Game Events. An example of OnRunState / OnAfterRunState for WRobot States Watching For Game Events
Sometimes you may find that you need to wait for something to occur in game before you can take a specific action. In WoW / WRobot world, these things are called events. Below are two examples of events. The first event will occur when either the Group Loot Settings change, or a Player Enters/Joins the current Party.The second Event will occur when a System Message is received. I recommend adding this watchForEvents Function in the Initialize function of a plugin, or somewhere where it will only be called once. For an example of this, please see my Plugin Template.
private void watchForEvents() { EventsLuaWithArgs.OnEventsLuaWithArgs += (LuaEventsId id, List<string> args) => { if (id == wManager.Wow.Enums.LuaEventsId.PARTY_MEMBERS_CHANGED) { Logging.Write("Joined Group or something about the current group was changed."); } if (id == wManager.Wow.Enums.LuaEventsId.CHAT_MSG_SYSTEM) { Logging.Write("We Received a System Message."); } }; }
Finding the list of available Game Events:
Each version of the game is different here, so this is where you will need to be careful. By that I mean, some versions of the game may have an event type, but a different version may not. Blizzard was not always consistent in their name accross different versions of the game, so please be careful to test against multiple versions of the game.
Open DotPeek Search for "LuaEventsID" Double Click LuaEventsId in the Assembly Explorer Window. A window will open displaying a list of Events. What do each of these Events mean?
WoW Event Reference: http://wowwiki.wikia.com/wiki/Event_API
(Reminder! Some of these may be different in different versions of the game.)
Watching For WRobot State Changes
In addition to in game events, there are also WRobot 'states'. Similar to Game Events, WRobot states are the particular condition that WRobot is in at a specific time. For example, there is a state called 'MillingState', and another called 'Looting' that come out with WRobot. States are managed by the WRobot FiniteStateMachineEvents Engine. When a State occurs/changes/ends/etc, an event is passed to the FiniteStateMachine (pardon my wording here if this is not 100% correct). There are three main events that we can use to manage our States.
State Events that occur:
OnBeforeCheckIfNeedToRunState - This can be used to CANCEL an event if specific conditions are met. OnRunState - This can be used to do something just as the State is being started. OnAfterRunState - This can be used to do something just as the State has completed.
Example of OnRunState and OnAfterRunState
In this example we are watching for when WRobot starts the ToTown State and when it finishes it. We create a boolean that is set to true when the state is started, and then set it to false when the State is completed. I recommend adding the initializeToTownWatcher() function in the Initialize function of a plugin, or somewhere where it will only be called once. For example of this, please see my Plugin Template.
bool goToTown = false; private void initializeToTownWatcher() { robotManager.Events.FiniteStateMachineEvents.OnRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { goToTown = true; Logging.Write("Going to Town State has been initiated."); } }; robotManager.Events.FiniteStateMachineEvents.OnAfterRunState += (engine, state) => { if (state != null && state.DisplayName == "To Town") { goToTown = false; Logging.Write("We have completed going To Town State."); } }; } Example of OnBeforeCheckIfNeedToRunState
In this example, we catch the state with the name of To Town and cancel it by setting the passed in cancelable parameter to true.
private void cancelToTownState() { robotManager.Events.FiniteStateMachineEvents.OnBeforeCheckIfNeedToRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { Logging.Write("We have cancelled the To Town State"); cancelable.Cancel = true; } }; } Where can I find other WRobot States?
Each version of the WRobot is different, so some versions of WRobot may have a state type, but a different version may not. Please be careful to test against multiple versions of the game/WRobot.
Open DotPeek Expand wManager Module Expand wManager.Wow.Bot.States namespace.
MORE TBA....
The above is my attempt at trying to help newcomers to WRobot at writing their own plugins / fight classes / etc. If there are any questions , suggestions, or even corrections, please do let me know in the comments and I'll be sure to add/update things as they come up!
Thanks,
- Avvi
-
Avvi got a reaction from Razzue in Avvi's C# Tips & Tricks with Helpful Code Snippets
Hi all,
I figured I'd post some things that I have learned during my time of developing in C#. Perhaps some of this is obvious for some of the more experienced WRobot C# writers, but for me, I had to do a lot of forum searching and experimenting to make progress on any of my work.
How do I get started?
Please see this post by @Droidz
How can I see what Functions are available to me in the WRobot API?
I recommend using some sort of decompiler in order to see what functions are available in the WRobot API. That is, use something such as dotPeek from jetbrains. See this URL: https://www.jetbrains.com/decompiler/ . Once you have this downloaded, open the WRobot Binaries located in the (C:\WRobot\Bin) folder in dotPeek. I cannot even begin to explain how many times the recompiled helped me find useful things I could re-use. As a quick tip, I would suggest taking a look at the wManager.wManager.Wow.Helpers functions that are available. Anything listed as public static <variable type> will be available to use from a Plugin/Profile/Fightclass etc.
What if WRobot doesn't have an available function that I will need?
WRobot doesn't have everything instantly available, so you may need to resort to using some Lua Functions to get information back from the WoW Client. An example of this that I ran into at some point was getting the number of Character Macros someone has.. Of course this is very specific, but please bear with me for the sake of this example :).
WoW Lua Reference: http://wowprogramming.com/docs/api_categories
Using Lua in C#:
This snippet will return a List of integers and set the C# variable numberOfMacros equal to the returned list of the DoString function. To be more specific, it will provide a list of the number of Global account Macros , and the number of Personal Character Macros.
var numberOfMacros = Lua.LuaDoString<List<int>>("return numCharacterMacros");
The below will return just the number Character Macros someone has. If you need a specific variable from a Lua Function, then do the following:
var numPersonalMacros = Lua.LuaDoString<int>("local numAccountMacros, numCharacterMacros = GetNumMacros(); return numCharacterMacros"); The above snippet will set the C# variable numPersonalMacros equal to numCharacterMacros from the lua return value.
Using a Variable in the Lua.LuaDoString. The below will return the text body of the macro that has the id of 121.
var _macroID = 121 string macroBody = Lua.LuaDoString<string>("return GetMacroBody(" + _macroID + ")");
Executing Lua Code in C#
This will leave the party (if the player is in one).
wManager.Wow.Helpers.Lua.RunMacroText("/run LeaveParty()");
What is the difference between Lua.LuaDoString() and RunMacroText()?
The difference is in can be understand in how you think about them. Lua.LuaDoString should be seen as a way to retrieve information.. More specifically, the Lua.LuaDoString's purpose is to have a value returned to it, so that you can assign it to a C# Variable. RunMacroText can be used to do something in game. More specifically, RunMacroText should be used when trying to run some sort of in-game script (such as /cast spell).
Plugin Template C#: Plugin-Template.cs
I have attached a basic plugin template that can be used. In it, I have provided an example of:
A Basic Implementation of the wManager.Plugin.IPlugin Class (including Settings/Initialize/Dispose) Basic loop that will occur while WRobot is running Settings that can be configured from Plugin Page A Category/Short Description for the Plugin Settings An example of Watching for Game Events. An example of OnRunState / OnAfterRunState for WRobot States Watching For Game Events
Sometimes you may find that you need to wait for something to occur in game before you can take a specific action. In WoW / WRobot world, these things are called events. Below are two examples of events. The first event will occur when either the Group Loot Settings change, or a Player Enters/Joins the current Party.The second Event will occur when a System Message is received. I recommend adding this watchForEvents Function in the Initialize function of a plugin, or somewhere where it will only be called once. For an example of this, please see my Plugin Template.
private void watchForEvents() { EventsLuaWithArgs.OnEventsLuaWithArgs += (LuaEventsId id, List<string> args) => { if (id == wManager.Wow.Enums.LuaEventsId.PARTY_MEMBERS_CHANGED) { Logging.Write("Joined Group or something about the current group was changed."); } if (id == wManager.Wow.Enums.LuaEventsId.CHAT_MSG_SYSTEM) { Logging.Write("We Received a System Message."); } }; }
Finding the list of available Game Events:
Each version of the game is different here, so this is where you will need to be careful. By that I mean, some versions of the game may have an event type, but a different version may not. Blizzard was not always consistent in their name accross different versions of the game, so please be careful to test against multiple versions of the game.
Open DotPeek Search for "LuaEventsID" Double Click LuaEventsId in the Assembly Explorer Window. A window will open displaying a list of Events. What do each of these Events mean?
WoW Event Reference: http://wowwiki.wikia.com/wiki/Event_API
(Reminder! Some of these may be different in different versions of the game.)
Watching For WRobot State Changes
In addition to in game events, there are also WRobot 'states'. Similar to Game Events, WRobot states are the particular condition that WRobot is in at a specific time. For example, there is a state called 'MillingState', and another called 'Looting' that come out with WRobot. States are managed by the WRobot FiniteStateMachineEvents Engine. When a State occurs/changes/ends/etc, an event is passed to the FiniteStateMachine (pardon my wording here if this is not 100% correct). There are three main events that we can use to manage our States.
State Events that occur:
OnBeforeCheckIfNeedToRunState - This can be used to CANCEL an event if specific conditions are met. OnRunState - This can be used to do something just as the State is being started. OnAfterRunState - This can be used to do something just as the State has completed.
Example of OnRunState and OnAfterRunState
In this example we are watching for when WRobot starts the ToTown State and when it finishes it. We create a boolean that is set to true when the state is started, and then set it to false when the State is completed. I recommend adding the initializeToTownWatcher() function in the Initialize function of a plugin, or somewhere where it will only be called once. For example of this, please see my Plugin Template.
bool goToTown = false; private void initializeToTownWatcher() { robotManager.Events.FiniteStateMachineEvents.OnRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { goToTown = true; Logging.Write("Going to Town State has been initiated."); } }; robotManager.Events.FiniteStateMachineEvents.OnAfterRunState += (engine, state) => { if (state != null && state.DisplayName == "To Town") { goToTown = false; Logging.Write("We have completed going To Town State."); } }; } Example of OnBeforeCheckIfNeedToRunState
In this example, we catch the state with the name of To Town and cancel it by setting the passed in cancelable parameter to true.
private void cancelToTownState() { robotManager.Events.FiniteStateMachineEvents.OnBeforeCheckIfNeedToRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { Logging.Write("We have cancelled the To Town State"); cancelable.Cancel = true; } }; } Where can I find other WRobot States?
Each version of the WRobot is different, so some versions of WRobot may have a state type, but a different version may not. Please be careful to test against multiple versions of the game/WRobot.
Open DotPeek Expand wManager Module Expand wManager.Wow.Bot.States namespace.
MORE TBA....
The above is my attempt at trying to help newcomers to WRobot at writing their own plugins / fight classes / etc. If there are any questions , suggestions, or even corrections, please do let me know in the comments and I'll be sure to add/update things as they come up!
Thanks,
- Avvi
-
Avvi reacted to Stresse in Fastest/Best Way To Regularly Toggle Looting Off/On
@Avvi
You are so awesome! I honestly can't thank you enough (I actually need to spend some time going around and "liking" all the posts you have made that have been so so helpful to me while I try to figure all this out)! You are my god!
One question: If I wanted different times for killing vs looting (if it splits it 50-50, there is going to be a lot of dead time during the looting phase), would I change it to:
public void pluginLoop() { while (Products.IsStarted && _isLaunched) { bool lootStuff = false; if (!Products.InPause) { wManager.wManagerSetting.CurrentSetting.LootMobs = lootStuff; Thread.Sleep(300000); // spend 5 minutes killing shit lootStuff= !lootStuff; Thread.Sleep(60000); //spend 1 minute looting shit } } } I'm going to try that and see what happens, but I have a sneaky suspicion I am going to have overlooked something.
-
Avvi got a reaction from Stresse in Fastest/Best Way To Regularly Toggle Looting Off/On
Oh, well then that's great news! In that case, you can swap out my plugin template's pluginLoop with this:
public void pluginLoop() { bool lootStuff = false; while (Products.IsStarted && _isLaunched) { if (!Products.InPause) { wManager.wManagerSetting.CurrentSetting.LootMobs = lootStuff; lootStuff= !lootStuff; Thread.Sleep(300000); } } }
It will wait 300,000 (5 minutes ) milliseconds and then it will flip the LootMobs value from False to True. After another 300,000 milliseconds (5 minutes ) it will go from True to False. It will flip it over and over until the WRobot it turned off.
Regarding my template, there are a lot of extra things in there. I added them so that there would be examples of many things ? . If you'd like, you can create a Setting that lets you set the milliseconds manually.
Or, you can copy what I've done below. (Replace pluginLoop and pluginSettings : Settings
public void pluginLoop() { bool lootStuff = false; while (Products.IsStarted && _isLaunched) { if (!Products.InPause) { wManager.wManagerSetting.CurrentSetting.LootMobs = lootStuff; lootStuff= !lootStuff; Thread.Sleep(_settings.timetowait); } } } [Serializable] public class pluginSettings : Settings { public pluginSettings() { timetowait = 300000; } [Setting] [Category("General Settings")] [DisplayName("Time to wait before looting stuff")] [Description("This is a Description.")] public int timetowait { get; set; } public static pluginSettings CurrentSetting { get; set; } public bool Save() { try { return Save(AdviserFilePathAndName("TemplateProjectName", ObjectManager.Me.Name + "." + Usefuls.RealmName)); } catch (Exception e) { Logging.WriteError("TemplateProjectName > Save(): " + e); return false; } } public static bool Load() { try { if (File.Exists(AdviserFilePathAndName("TemplateProjectName", ObjectManager.Me.Name + "." + Usefuls.RealmName))) { CurrentSetting = Load<pluginSettings>(AdviserFilePathAndName("TemplateProjectName", ObjectManager.Me.Name + "." + Usefuls.RealmName)); return true; } CurrentSetting = new pluginSettings(); } catch (Exception e) { Logging.WriteError("TemplateProjectName > Load(): " + e); } return false; } }
-
Avvi got a reaction from vanbotter in Avvi's C# Tips & Tricks with Helpful Code Snippets
Hi all,
I figured I'd post some things that I have learned during my time of developing in C#. Perhaps some of this is obvious for some of the more experienced WRobot C# writers, but for me, I had to do a lot of forum searching and experimenting to make progress on any of my work.
How do I get started?
Please see this post by @Droidz
How can I see what Functions are available to me in the WRobot API?
I recommend using some sort of decompiler in order to see what functions are available in the WRobot API. That is, use something such as dotPeek from jetbrains. See this URL: https://www.jetbrains.com/decompiler/ . Once you have this downloaded, open the WRobot Binaries located in the (C:\WRobot\Bin) folder in dotPeek. I cannot even begin to explain how many times the recompiled helped me find useful things I could re-use. As a quick tip, I would suggest taking a look at the wManager.wManager.Wow.Helpers functions that are available. Anything listed as public static <variable type> will be available to use from a Plugin/Profile/Fightclass etc.
What if WRobot doesn't have an available function that I will need?
WRobot doesn't have everything instantly available, so you may need to resort to using some Lua Functions to get information back from the WoW Client. An example of this that I ran into at some point was getting the number of Character Macros someone has.. Of course this is very specific, but please bear with me for the sake of this example :).
WoW Lua Reference: http://wowprogramming.com/docs/api_categories
Using Lua in C#:
This snippet will return a List of integers and set the C# variable numberOfMacros equal to the returned list of the DoString function. To be more specific, it will provide a list of the number of Global account Macros , and the number of Personal Character Macros.
var numberOfMacros = Lua.LuaDoString<List<int>>("return numCharacterMacros");
The below will return just the number Character Macros someone has. If you need a specific variable from a Lua Function, then do the following:
var numPersonalMacros = Lua.LuaDoString<int>("local numAccountMacros, numCharacterMacros = GetNumMacros(); return numCharacterMacros"); The above snippet will set the C# variable numPersonalMacros equal to numCharacterMacros from the lua return value.
Using a Variable in the Lua.LuaDoString. The below will return the text body of the macro that has the id of 121.
var _macroID = 121 string macroBody = Lua.LuaDoString<string>("return GetMacroBody(" + _macroID + ")");
Executing Lua Code in C#
This will leave the party (if the player is in one).
wManager.Wow.Helpers.Lua.RunMacroText("/run LeaveParty()");
What is the difference between Lua.LuaDoString() and RunMacroText()?
The difference is in can be understand in how you think about them. Lua.LuaDoString should be seen as a way to retrieve information.. More specifically, the Lua.LuaDoString's purpose is to have a value returned to it, so that you can assign it to a C# Variable. RunMacroText can be used to do something in game. More specifically, RunMacroText should be used when trying to run some sort of in-game script (such as /cast spell).
Plugin Template C#: Plugin-Template.cs
I have attached a basic plugin template that can be used. In it, I have provided an example of:
A Basic Implementation of the wManager.Plugin.IPlugin Class (including Settings/Initialize/Dispose) Basic loop that will occur while WRobot is running Settings that can be configured from Plugin Page A Category/Short Description for the Plugin Settings An example of Watching for Game Events. An example of OnRunState / OnAfterRunState for WRobot States Watching For Game Events
Sometimes you may find that you need to wait for something to occur in game before you can take a specific action. In WoW / WRobot world, these things are called events. Below are two examples of events. The first event will occur when either the Group Loot Settings change, or a Player Enters/Joins the current Party.The second Event will occur when a System Message is received. I recommend adding this watchForEvents Function in the Initialize function of a plugin, or somewhere where it will only be called once. For an example of this, please see my Plugin Template.
private void watchForEvents() { EventsLuaWithArgs.OnEventsLuaWithArgs += (LuaEventsId id, List<string> args) => { if (id == wManager.Wow.Enums.LuaEventsId.PARTY_MEMBERS_CHANGED) { Logging.Write("Joined Group or something about the current group was changed."); } if (id == wManager.Wow.Enums.LuaEventsId.CHAT_MSG_SYSTEM) { Logging.Write("We Received a System Message."); } }; }
Finding the list of available Game Events:
Each version of the game is different here, so this is where you will need to be careful. By that I mean, some versions of the game may have an event type, but a different version may not. Blizzard was not always consistent in their name accross different versions of the game, so please be careful to test against multiple versions of the game.
Open DotPeek Search for "LuaEventsID" Double Click LuaEventsId in the Assembly Explorer Window. A window will open displaying a list of Events. What do each of these Events mean?
WoW Event Reference: http://wowwiki.wikia.com/wiki/Event_API
(Reminder! Some of these may be different in different versions of the game.)
Watching For WRobot State Changes
In addition to in game events, there are also WRobot 'states'. Similar to Game Events, WRobot states are the particular condition that WRobot is in at a specific time. For example, there is a state called 'MillingState', and another called 'Looting' that come out with WRobot. States are managed by the WRobot FiniteStateMachineEvents Engine. When a State occurs/changes/ends/etc, an event is passed to the FiniteStateMachine (pardon my wording here if this is not 100% correct). There are three main events that we can use to manage our States.
State Events that occur:
OnBeforeCheckIfNeedToRunState - This can be used to CANCEL an event if specific conditions are met. OnRunState - This can be used to do something just as the State is being started. OnAfterRunState - This can be used to do something just as the State has completed.
Example of OnRunState and OnAfterRunState
In this example we are watching for when WRobot starts the ToTown State and when it finishes it. We create a boolean that is set to true when the state is started, and then set it to false when the State is completed. I recommend adding the initializeToTownWatcher() function in the Initialize function of a plugin, or somewhere where it will only be called once. For example of this, please see my Plugin Template.
bool goToTown = false; private void initializeToTownWatcher() { robotManager.Events.FiniteStateMachineEvents.OnRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { goToTown = true; Logging.Write("Going to Town State has been initiated."); } }; robotManager.Events.FiniteStateMachineEvents.OnAfterRunState += (engine, state) => { if (state != null && state.DisplayName == "To Town") { goToTown = false; Logging.Write("We have completed going To Town State."); } }; } Example of OnBeforeCheckIfNeedToRunState
In this example, we catch the state with the name of To Town and cancel it by setting the passed in cancelable parameter to true.
private void cancelToTownState() { robotManager.Events.FiniteStateMachineEvents.OnBeforeCheckIfNeedToRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { Logging.Write("We have cancelled the To Town State"); cancelable.Cancel = true; } }; } Where can I find other WRobot States?
Each version of the WRobot is different, so some versions of WRobot may have a state type, but a different version may not. Please be careful to test against multiple versions of the game/WRobot.
Open DotPeek Expand wManager Module Expand wManager.Wow.Bot.States namespace.
MORE TBA....
The above is my attempt at trying to help newcomers to WRobot at writing their own plugins / fight classes / etc. If there are any questions , suggestions, or even corrections, please do let me know in the comments and I'll be sure to add/update things as they come up!
Thanks,
- Avvi
-
Avvi reacted to vanbotter in Avvi's C# Tips & Tricks with Helpful Code Snippets
Thanks @Matenia Much appreciated! now i can run the bots and sit down to regen rather than looking like an idiot standing still! hurray!
Thank
-
Avvi reacted to Matenia in Avvi's C# Tips & Tricks with Helpful Code Snippets
Everything after run is regular Lua, so if you want to run your macro like that, just do
(Vanilla has no RunMacroText, so it would never work anyway - but more importantly, you should use an IDE to edit your code so you can see things like trying to put 4 quotation marks won't work, because your string ends at ( and then inbetween the next ")" it tries to execute Macro2 as code. See Strings.)
Lua.LuaDoString("RunMacro('Macro2')");
-
Avvi got a reaction from ScripterQQ in Avvi's C# Tips & Tricks with Helpful Code Snippets
Hi all,
I figured I'd post some things that I have learned during my time of developing in C#. Perhaps some of this is obvious for some of the more experienced WRobot C# writers, but for me, I had to do a lot of forum searching and experimenting to make progress on any of my work.
How do I get started?
Please see this post by @Droidz
How can I see what Functions are available to me in the WRobot API?
I recommend using some sort of decompiler in order to see what functions are available in the WRobot API. That is, use something such as dotPeek from jetbrains. See this URL: https://www.jetbrains.com/decompiler/ . Once you have this downloaded, open the WRobot Binaries located in the (C:\WRobot\Bin) folder in dotPeek. I cannot even begin to explain how many times the recompiled helped me find useful things I could re-use. As a quick tip, I would suggest taking a look at the wManager.wManager.Wow.Helpers functions that are available. Anything listed as public static <variable type> will be available to use from a Plugin/Profile/Fightclass etc.
What if WRobot doesn't have an available function that I will need?
WRobot doesn't have everything instantly available, so you may need to resort to using some Lua Functions to get information back from the WoW Client. An example of this that I ran into at some point was getting the number of Character Macros someone has.. Of course this is very specific, but please bear with me for the sake of this example :).
WoW Lua Reference: http://wowprogramming.com/docs/api_categories
Using Lua in C#:
This snippet will return a List of integers and set the C# variable numberOfMacros equal to the returned list of the DoString function. To be more specific, it will provide a list of the number of Global account Macros , and the number of Personal Character Macros.
var numberOfMacros = Lua.LuaDoString<List<int>>("return numCharacterMacros");
The below will return just the number Character Macros someone has. If you need a specific variable from a Lua Function, then do the following:
var numPersonalMacros = Lua.LuaDoString<int>("local numAccountMacros, numCharacterMacros = GetNumMacros(); return numCharacterMacros"); The above snippet will set the C# variable numPersonalMacros equal to numCharacterMacros from the lua return value.
Using a Variable in the Lua.LuaDoString. The below will return the text body of the macro that has the id of 121.
var _macroID = 121 string macroBody = Lua.LuaDoString<string>("return GetMacroBody(" + _macroID + ")");
Executing Lua Code in C#
This will leave the party (if the player is in one).
wManager.Wow.Helpers.Lua.RunMacroText("/run LeaveParty()");
What is the difference between Lua.LuaDoString() and RunMacroText()?
The difference is in can be understand in how you think about them. Lua.LuaDoString should be seen as a way to retrieve information.. More specifically, the Lua.LuaDoString's purpose is to have a value returned to it, so that you can assign it to a C# Variable. RunMacroText can be used to do something in game. More specifically, RunMacroText should be used when trying to run some sort of in-game script (such as /cast spell).
Plugin Template C#: Plugin-Template.cs
I have attached a basic plugin template that can be used. In it, I have provided an example of:
A Basic Implementation of the wManager.Plugin.IPlugin Class (including Settings/Initialize/Dispose) Basic loop that will occur while WRobot is running Settings that can be configured from Plugin Page A Category/Short Description for the Plugin Settings An example of Watching for Game Events. An example of OnRunState / OnAfterRunState for WRobot States Watching For Game Events
Sometimes you may find that you need to wait for something to occur in game before you can take a specific action. In WoW / WRobot world, these things are called events. Below are two examples of events. The first event will occur when either the Group Loot Settings change, or a Player Enters/Joins the current Party.The second Event will occur when a System Message is received. I recommend adding this watchForEvents Function in the Initialize function of a plugin, or somewhere where it will only be called once. For an example of this, please see my Plugin Template.
private void watchForEvents() { EventsLuaWithArgs.OnEventsLuaWithArgs += (LuaEventsId id, List<string> args) => { if (id == wManager.Wow.Enums.LuaEventsId.PARTY_MEMBERS_CHANGED) { Logging.Write("Joined Group or something about the current group was changed."); } if (id == wManager.Wow.Enums.LuaEventsId.CHAT_MSG_SYSTEM) { Logging.Write("We Received a System Message."); } }; }
Finding the list of available Game Events:
Each version of the game is different here, so this is where you will need to be careful. By that I mean, some versions of the game may have an event type, but a different version may not. Blizzard was not always consistent in their name accross different versions of the game, so please be careful to test against multiple versions of the game.
Open DotPeek Search for "LuaEventsID" Double Click LuaEventsId in the Assembly Explorer Window. A window will open displaying a list of Events. What do each of these Events mean?
WoW Event Reference: http://wowwiki.wikia.com/wiki/Event_API
(Reminder! Some of these may be different in different versions of the game.)
Watching For WRobot State Changes
In addition to in game events, there are also WRobot 'states'. Similar to Game Events, WRobot states are the particular condition that WRobot is in at a specific time. For example, there is a state called 'MillingState', and another called 'Looting' that come out with WRobot. States are managed by the WRobot FiniteStateMachineEvents Engine. When a State occurs/changes/ends/etc, an event is passed to the FiniteStateMachine (pardon my wording here if this is not 100% correct). There are three main events that we can use to manage our States.
State Events that occur:
OnBeforeCheckIfNeedToRunState - This can be used to CANCEL an event if specific conditions are met. OnRunState - This can be used to do something just as the State is being started. OnAfterRunState - This can be used to do something just as the State has completed.
Example of OnRunState and OnAfterRunState
In this example we are watching for when WRobot starts the ToTown State and when it finishes it. We create a boolean that is set to true when the state is started, and then set it to false when the State is completed. I recommend adding the initializeToTownWatcher() function in the Initialize function of a plugin, or somewhere where it will only be called once. For example of this, please see my Plugin Template.
bool goToTown = false; private void initializeToTownWatcher() { robotManager.Events.FiniteStateMachineEvents.OnRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { goToTown = true; Logging.Write("Going to Town State has been initiated."); } }; robotManager.Events.FiniteStateMachineEvents.OnAfterRunState += (engine, state) => { if (state != null && state.DisplayName == "To Town") { goToTown = false; Logging.Write("We have completed going To Town State."); } }; } Example of OnBeforeCheckIfNeedToRunState
In this example, we catch the state with the name of To Town and cancel it by setting the passed in cancelable parameter to true.
private void cancelToTownState() { robotManager.Events.FiniteStateMachineEvents.OnBeforeCheckIfNeedToRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { Logging.Write("We have cancelled the To Town State"); cancelable.Cancel = true; } }; } Where can I find other WRobot States?
Each version of the WRobot is different, so some versions of WRobot may have a state type, but a different version may not. Please be careful to test against multiple versions of the game/WRobot.
Open DotPeek Expand wManager Module Expand wManager.Wow.Bot.States namespace.
MORE TBA....
The above is my attempt at trying to help newcomers to WRobot at writing their own plugins / fight classes / etc. If there are any questions , suggestions, or even corrections, please do let me know in the comments and I'll be sure to add/update things as they come up!
Thanks,
- Avvi
-
Avvi got a reaction from Stresse in Avvi's C# Tips & Tricks with Helpful Code Snippets
Hi all,
I figured I'd post some things that I have learned during my time of developing in C#. Perhaps some of this is obvious for some of the more experienced WRobot C# writers, but for me, I had to do a lot of forum searching and experimenting to make progress on any of my work.
How do I get started?
Please see this post by @Droidz
How can I see what Functions are available to me in the WRobot API?
I recommend using some sort of decompiler in order to see what functions are available in the WRobot API. That is, use something such as dotPeek from jetbrains. See this URL: https://www.jetbrains.com/decompiler/ . Once you have this downloaded, open the WRobot Binaries located in the (C:\WRobot\Bin) folder in dotPeek. I cannot even begin to explain how many times the recompiled helped me find useful things I could re-use. As a quick tip, I would suggest taking a look at the wManager.wManager.Wow.Helpers functions that are available. Anything listed as public static <variable type> will be available to use from a Plugin/Profile/Fightclass etc.
What if WRobot doesn't have an available function that I will need?
WRobot doesn't have everything instantly available, so you may need to resort to using some Lua Functions to get information back from the WoW Client. An example of this that I ran into at some point was getting the number of Character Macros someone has.. Of course this is very specific, but please bear with me for the sake of this example :).
WoW Lua Reference: http://wowprogramming.com/docs/api_categories
Using Lua in C#:
This snippet will return a List of integers and set the C# variable numberOfMacros equal to the returned list of the DoString function. To be more specific, it will provide a list of the number of Global account Macros , and the number of Personal Character Macros.
var numberOfMacros = Lua.LuaDoString<List<int>>("return numCharacterMacros");
The below will return just the number Character Macros someone has. If you need a specific variable from a Lua Function, then do the following:
var numPersonalMacros = Lua.LuaDoString<int>("local numAccountMacros, numCharacterMacros = GetNumMacros(); return numCharacterMacros"); The above snippet will set the C# variable numPersonalMacros equal to numCharacterMacros from the lua return value.
Using a Variable in the Lua.LuaDoString. The below will return the text body of the macro that has the id of 121.
var _macroID = 121 string macroBody = Lua.LuaDoString<string>("return GetMacroBody(" + _macroID + ")");
Executing Lua Code in C#
This will leave the party (if the player is in one).
wManager.Wow.Helpers.Lua.RunMacroText("/run LeaveParty()");
What is the difference between Lua.LuaDoString() and RunMacroText()?
The difference is in can be understand in how you think about them. Lua.LuaDoString should be seen as a way to retrieve information.. More specifically, the Lua.LuaDoString's purpose is to have a value returned to it, so that you can assign it to a C# Variable. RunMacroText can be used to do something in game. More specifically, RunMacroText should be used when trying to run some sort of in-game script (such as /cast spell).
Plugin Template C#: Plugin-Template.cs
I have attached a basic plugin template that can be used. In it, I have provided an example of:
A Basic Implementation of the wManager.Plugin.IPlugin Class (including Settings/Initialize/Dispose) Basic loop that will occur while WRobot is running Settings that can be configured from Plugin Page A Category/Short Description for the Plugin Settings An example of Watching for Game Events. An example of OnRunState / OnAfterRunState for WRobot States Watching For Game Events
Sometimes you may find that you need to wait for something to occur in game before you can take a specific action. In WoW / WRobot world, these things are called events. Below are two examples of events. The first event will occur when either the Group Loot Settings change, or a Player Enters/Joins the current Party.The second Event will occur when a System Message is received. I recommend adding this watchForEvents Function in the Initialize function of a plugin, or somewhere where it will only be called once. For an example of this, please see my Plugin Template.
private void watchForEvents() { EventsLuaWithArgs.OnEventsLuaWithArgs += (LuaEventsId id, List<string> args) => { if (id == wManager.Wow.Enums.LuaEventsId.PARTY_MEMBERS_CHANGED) { Logging.Write("Joined Group or something about the current group was changed."); } if (id == wManager.Wow.Enums.LuaEventsId.CHAT_MSG_SYSTEM) { Logging.Write("We Received a System Message."); } }; }
Finding the list of available Game Events:
Each version of the game is different here, so this is where you will need to be careful. By that I mean, some versions of the game may have an event type, but a different version may not. Blizzard was not always consistent in their name accross different versions of the game, so please be careful to test against multiple versions of the game.
Open DotPeek Search for "LuaEventsID" Double Click LuaEventsId in the Assembly Explorer Window. A window will open displaying a list of Events. What do each of these Events mean?
WoW Event Reference: http://wowwiki.wikia.com/wiki/Event_API
(Reminder! Some of these may be different in different versions of the game.)
Watching For WRobot State Changes
In addition to in game events, there are also WRobot 'states'. Similar to Game Events, WRobot states are the particular condition that WRobot is in at a specific time. For example, there is a state called 'MillingState', and another called 'Looting' that come out with WRobot. States are managed by the WRobot FiniteStateMachineEvents Engine. When a State occurs/changes/ends/etc, an event is passed to the FiniteStateMachine (pardon my wording here if this is not 100% correct). There are three main events that we can use to manage our States.
State Events that occur:
OnBeforeCheckIfNeedToRunState - This can be used to CANCEL an event if specific conditions are met. OnRunState - This can be used to do something just as the State is being started. OnAfterRunState - This can be used to do something just as the State has completed.
Example of OnRunState and OnAfterRunState
In this example we are watching for when WRobot starts the ToTown State and when it finishes it. We create a boolean that is set to true when the state is started, and then set it to false when the State is completed. I recommend adding the initializeToTownWatcher() function in the Initialize function of a plugin, or somewhere where it will only be called once. For example of this, please see my Plugin Template.
bool goToTown = false; private void initializeToTownWatcher() { robotManager.Events.FiniteStateMachineEvents.OnRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { goToTown = true; Logging.Write("Going to Town State has been initiated."); } }; robotManager.Events.FiniteStateMachineEvents.OnAfterRunState += (engine, state) => { if (state != null && state.DisplayName == "To Town") { goToTown = false; Logging.Write("We have completed going To Town State."); } }; } Example of OnBeforeCheckIfNeedToRunState
In this example, we catch the state with the name of To Town and cancel it by setting the passed in cancelable parameter to true.
private void cancelToTownState() { robotManager.Events.FiniteStateMachineEvents.OnBeforeCheckIfNeedToRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { Logging.Write("We have cancelled the To Town State"); cancelable.Cancel = true; } }; } Where can I find other WRobot States?
Each version of the WRobot is different, so some versions of WRobot may have a state type, but a different version may not. Please be careful to test against multiple versions of the game/WRobot.
Open DotPeek Expand wManager Module Expand wManager.Wow.Bot.States namespace.
MORE TBA....
The above is my attempt at trying to help newcomers to WRobot at writing their own plugins / fight classes / etc. If there are any questions , suggestions, or even corrections, please do let me know in the comments and I'll be sure to add/update things as they come up!
Thanks,
- Avvi
-
Avvi reacted to Matenia in 2.0.1v Bot closing after 5 min
Maybe in WotLk, but vanilla/TBC performance is overall pretty bad (both the client, and for TBC wRobot has some CPU issues). Most people with really good hardware (state of the art gaming CPU/GPU) can run ~15 clients+bots on one computer.
-
Avvi reacted to yori69 in hanyoo69 is asking for 1-45 profile via email
Hahha well he did it legally and for a good reason, he never broke the rules or anything. Don't put your nose on something you don't know, i can always outsmart kids like you.
-
Avvi reacted to Droidz in hanyoo69 is asking for 1-45 profile via email
I ban him again and remove his subscription (without refund) because it does not respect the rules of use of WRobot
-
Avvi reacted to kpeno in Why is admin using my account?!
My english sux and i have no idea what here talking about, but it's fine
-
Avvi reacted to yori69 in Why is admin using my account?!
By the way, i have proof of other members telling me about your shady action and illegal work. We should report you guys to the authorities, the admin is shady af anyway.
-
Avvi reacted to Marsbar in "Stop bot" option and question about it
A possible enhancement would be to also make sure to not re-enable while "Resting" (Inn's & major cities) as well as maybe using Usefuls.SubMapZoneName to compare it to a list of all the towns and again not re-enable.
-
Avvi reacted to Marsbar in "Stop bot" option and question about it
Would the simple fix for this not just be after its finished its ToTown run that the feature is paused for X minutes giving the bot time to get out of town and the pausing feature is re-enabled after that X variable.
I actually thought this was built into WRobot lol
-
Avvi reacted to Droidz in The begining of the end of WRobot for official servers
Hello,
Following the recent events, I cannot continue to offer you a "safe" bot, for this reason the end of WRobot for official servers is planned.
I'll remove in few weeks of the store the subscriptions for official servers, and 1 month after, I'll remove and block access to WRobot for official Wow servers (during this time, WRobot will continue to be updated (in few days a big update will be release on all WRobot versions), do not be surprised, but that does not change my decision).
We hope you understand, thank you for your support.
Kind regard, Droidz
- This don't affect versions for private servers, and I'll continue to update/upgrade WRobot for private servers.
- I will definitely close WRobot at the latest at the "Battle for Azeroth" pre-patch (Wow version 8.x.x)
- I don't remove now subscriptions for official servers from the store because some users ask me to not do it, but I will add a message in store to warn buyers.
- In next days/weeks I'll edit home page to change the description and say that WRobot is only a private servers bot (to avoid confusion).
- I'll not add support of bliz WoW Legacy Servers (I often have the question)
You can discuss about this here: https://wrobot.eu/forums/topic/8666-ban-wave/
View full article
-
Avvi reacted to Hakzorie in Avvi's C# Tips & Tricks with Helpful Code Snippets
Have Been working with just the Fight Class editor and it takes an insane amount of work to get the functions to work right.
Now that ive seen this guild i will remake my fightclasses using DotPeek.
TY MUCH! and expect some decent fightclasses and such out of me!
-
Avvi got a reaction from Arcangelo in Avvi's C# Tips & Tricks with Helpful Code Snippets
Hi all,
I figured I'd post some things that I have learned during my time of developing in C#. Perhaps some of this is obvious for some of the more experienced WRobot C# writers, but for me, I had to do a lot of forum searching and experimenting to make progress on any of my work.
How do I get started?
Please see this post by @Droidz
How can I see what Functions are available to me in the WRobot API?
I recommend using some sort of decompiler in order to see what functions are available in the WRobot API. That is, use something such as dotPeek from jetbrains. See this URL: https://www.jetbrains.com/decompiler/ . Once you have this downloaded, open the WRobot Binaries located in the (C:\WRobot\Bin) folder in dotPeek. I cannot even begin to explain how many times the recompiled helped me find useful things I could re-use. As a quick tip, I would suggest taking a look at the wManager.wManager.Wow.Helpers functions that are available. Anything listed as public static <variable type> will be available to use from a Plugin/Profile/Fightclass etc.
What if WRobot doesn't have an available function that I will need?
WRobot doesn't have everything instantly available, so you may need to resort to using some Lua Functions to get information back from the WoW Client. An example of this that I ran into at some point was getting the number of Character Macros someone has.. Of course this is very specific, but please bear with me for the sake of this example :).
WoW Lua Reference: http://wowprogramming.com/docs/api_categories
Using Lua in C#:
This snippet will return a List of integers and set the C# variable numberOfMacros equal to the returned list of the DoString function. To be more specific, it will provide a list of the number of Global account Macros , and the number of Personal Character Macros.
var numberOfMacros = Lua.LuaDoString<List<int>>("return numCharacterMacros");
The below will return just the number Character Macros someone has. If you need a specific variable from a Lua Function, then do the following:
var numPersonalMacros = Lua.LuaDoString<int>("local numAccountMacros, numCharacterMacros = GetNumMacros(); return numCharacterMacros"); The above snippet will set the C# variable numPersonalMacros equal to numCharacterMacros from the lua return value.
Using a Variable in the Lua.LuaDoString. The below will return the text body of the macro that has the id of 121.
var _macroID = 121 string macroBody = Lua.LuaDoString<string>("return GetMacroBody(" + _macroID + ")");
Executing Lua Code in C#
This will leave the party (if the player is in one).
wManager.Wow.Helpers.Lua.RunMacroText("/run LeaveParty()");
What is the difference between Lua.LuaDoString() and RunMacroText()?
The difference is in can be understand in how you think about them. Lua.LuaDoString should be seen as a way to retrieve information.. More specifically, the Lua.LuaDoString's purpose is to have a value returned to it, so that you can assign it to a C# Variable. RunMacroText can be used to do something in game. More specifically, RunMacroText should be used when trying to run some sort of in-game script (such as /cast spell).
Plugin Template C#: Plugin-Template.cs
I have attached a basic plugin template that can be used. In it, I have provided an example of:
A Basic Implementation of the wManager.Plugin.IPlugin Class (including Settings/Initialize/Dispose) Basic loop that will occur while WRobot is running Settings that can be configured from Plugin Page A Category/Short Description for the Plugin Settings An example of Watching for Game Events. An example of OnRunState / OnAfterRunState for WRobot States Watching For Game Events
Sometimes you may find that you need to wait for something to occur in game before you can take a specific action. In WoW / WRobot world, these things are called events. Below are two examples of events. The first event will occur when either the Group Loot Settings change, or a Player Enters/Joins the current Party.The second Event will occur when a System Message is received. I recommend adding this watchForEvents Function in the Initialize function of a plugin, or somewhere where it will only be called once. For an example of this, please see my Plugin Template.
private void watchForEvents() { EventsLuaWithArgs.OnEventsLuaWithArgs += (LuaEventsId id, List<string> args) => { if (id == wManager.Wow.Enums.LuaEventsId.PARTY_MEMBERS_CHANGED) { Logging.Write("Joined Group or something about the current group was changed."); } if (id == wManager.Wow.Enums.LuaEventsId.CHAT_MSG_SYSTEM) { Logging.Write("We Received a System Message."); } }; }
Finding the list of available Game Events:
Each version of the game is different here, so this is where you will need to be careful. By that I mean, some versions of the game may have an event type, but a different version may not. Blizzard was not always consistent in their name accross different versions of the game, so please be careful to test against multiple versions of the game.
Open DotPeek Search for "LuaEventsID" Double Click LuaEventsId in the Assembly Explorer Window. A window will open displaying a list of Events. What do each of these Events mean?
WoW Event Reference: http://wowwiki.wikia.com/wiki/Event_API
(Reminder! Some of these may be different in different versions of the game.)
Watching For WRobot State Changes
In addition to in game events, there are also WRobot 'states'. Similar to Game Events, WRobot states are the particular condition that WRobot is in at a specific time. For example, there is a state called 'MillingState', and another called 'Looting' that come out with WRobot. States are managed by the WRobot FiniteStateMachineEvents Engine. When a State occurs/changes/ends/etc, an event is passed to the FiniteStateMachine (pardon my wording here if this is not 100% correct). There are three main events that we can use to manage our States.
State Events that occur:
OnBeforeCheckIfNeedToRunState - This can be used to CANCEL an event if specific conditions are met. OnRunState - This can be used to do something just as the State is being started. OnAfterRunState - This can be used to do something just as the State has completed.
Example of OnRunState and OnAfterRunState
In this example we are watching for when WRobot starts the ToTown State and when it finishes it. We create a boolean that is set to true when the state is started, and then set it to false when the State is completed. I recommend adding the initializeToTownWatcher() function in the Initialize function of a plugin, or somewhere where it will only be called once. For example of this, please see my Plugin Template.
bool goToTown = false; private void initializeToTownWatcher() { robotManager.Events.FiniteStateMachineEvents.OnRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { goToTown = true; Logging.Write("Going to Town State has been initiated."); } }; robotManager.Events.FiniteStateMachineEvents.OnAfterRunState += (engine, state) => { if (state != null && state.DisplayName == "To Town") { goToTown = false; Logging.Write("We have completed going To Town State."); } }; } Example of OnBeforeCheckIfNeedToRunState
In this example, we catch the state with the name of To Town and cancel it by setting the passed in cancelable parameter to true.
private void cancelToTownState() { robotManager.Events.FiniteStateMachineEvents.OnBeforeCheckIfNeedToRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { Logging.Write("We have cancelled the To Town State"); cancelable.Cancel = true; } }; } Where can I find other WRobot States?
Each version of the WRobot is different, so some versions of WRobot may have a state type, but a different version may not. Please be careful to test against multiple versions of the game/WRobot.
Open DotPeek Expand wManager Module Expand wManager.Wow.Bot.States namespace.
MORE TBA....
The above is my attempt at trying to help newcomers to WRobot at writing their own plugins / fight classes / etc. If there are any questions , suggestions, or even corrections, please do let me know in the comments and I'll be sure to add/update things as they come up!
Thanks,
- Avvi
-
Avvi reacted to Matenia in move back if... add code in fightclass editor
//Checks if there's available LoS between your target and the new spot too. !TraceLine.TraceLineGo(ObjectManager.Target.Position, newPos) //check if there's LoS between you and the new Pos !TraceLine.TraceLineGo(newPos) //Then you can use: bool isValid = false; var path = PathFinder.FindPath(newpos, out isValid); if(isValid) { MovementManager.Go(path, false); } This prevents a CPU/memory hog, but only using pathfinding once you confirmed LoS. Also check that no NPC is near newPos.
-
Avvi got a reaction from Enraged in Avvi's C# Tips & Tricks with Helpful Code Snippets
Hi all,
I figured I'd post some things that I have learned during my time of developing in C#. Perhaps some of this is obvious for some of the more experienced WRobot C# writers, but for me, I had to do a lot of forum searching and experimenting to make progress on any of my work.
How do I get started?
Please see this post by @Droidz
How can I see what Functions are available to me in the WRobot API?
I recommend using some sort of decompiler in order to see what functions are available in the WRobot API. That is, use something such as dotPeek from jetbrains. See this URL: https://www.jetbrains.com/decompiler/ . Once you have this downloaded, open the WRobot Binaries located in the (C:\WRobot\Bin) folder in dotPeek. I cannot even begin to explain how many times the recompiled helped me find useful things I could re-use. As a quick tip, I would suggest taking a look at the wManager.wManager.Wow.Helpers functions that are available. Anything listed as public static <variable type> will be available to use from a Plugin/Profile/Fightclass etc.
What if WRobot doesn't have an available function that I will need?
WRobot doesn't have everything instantly available, so you may need to resort to using some Lua Functions to get information back from the WoW Client. An example of this that I ran into at some point was getting the number of Character Macros someone has.. Of course this is very specific, but please bear with me for the sake of this example :).
WoW Lua Reference: http://wowprogramming.com/docs/api_categories
Using Lua in C#:
This snippet will return a List of integers and set the C# variable numberOfMacros equal to the returned list of the DoString function. To be more specific, it will provide a list of the number of Global account Macros , and the number of Personal Character Macros.
var numberOfMacros = Lua.LuaDoString<List<int>>("return numCharacterMacros");
The below will return just the number Character Macros someone has. If you need a specific variable from a Lua Function, then do the following:
var numPersonalMacros = Lua.LuaDoString<int>("local numAccountMacros, numCharacterMacros = GetNumMacros(); return numCharacterMacros"); The above snippet will set the C# variable numPersonalMacros equal to numCharacterMacros from the lua return value.
Using a Variable in the Lua.LuaDoString. The below will return the text body of the macro that has the id of 121.
var _macroID = 121 string macroBody = Lua.LuaDoString<string>("return GetMacroBody(" + _macroID + ")");
Executing Lua Code in C#
This will leave the party (if the player is in one).
wManager.Wow.Helpers.Lua.RunMacroText("/run LeaveParty()");
What is the difference between Lua.LuaDoString() and RunMacroText()?
The difference is in can be understand in how you think about them. Lua.LuaDoString should be seen as a way to retrieve information.. More specifically, the Lua.LuaDoString's purpose is to have a value returned to it, so that you can assign it to a C# Variable. RunMacroText can be used to do something in game. More specifically, RunMacroText should be used when trying to run some sort of in-game script (such as /cast spell).
Plugin Template C#: Plugin-Template.cs
I have attached a basic plugin template that can be used. In it, I have provided an example of:
A Basic Implementation of the wManager.Plugin.IPlugin Class (including Settings/Initialize/Dispose) Basic loop that will occur while WRobot is running Settings that can be configured from Plugin Page A Category/Short Description for the Plugin Settings An example of Watching for Game Events. An example of OnRunState / OnAfterRunState for WRobot States Watching For Game Events
Sometimes you may find that you need to wait for something to occur in game before you can take a specific action. In WoW / WRobot world, these things are called events. Below are two examples of events. The first event will occur when either the Group Loot Settings change, or a Player Enters/Joins the current Party.The second Event will occur when a System Message is received. I recommend adding this watchForEvents Function in the Initialize function of a plugin, or somewhere where it will only be called once. For an example of this, please see my Plugin Template.
private void watchForEvents() { EventsLuaWithArgs.OnEventsLuaWithArgs += (LuaEventsId id, List<string> args) => { if (id == wManager.Wow.Enums.LuaEventsId.PARTY_MEMBERS_CHANGED) { Logging.Write("Joined Group or something about the current group was changed."); } if (id == wManager.Wow.Enums.LuaEventsId.CHAT_MSG_SYSTEM) { Logging.Write("We Received a System Message."); } }; }
Finding the list of available Game Events:
Each version of the game is different here, so this is where you will need to be careful. By that I mean, some versions of the game may have an event type, but a different version may not. Blizzard was not always consistent in their name accross different versions of the game, so please be careful to test against multiple versions of the game.
Open DotPeek Search for "LuaEventsID" Double Click LuaEventsId in the Assembly Explorer Window. A window will open displaying a list of Events. What do each of these Events mean?
WoW Event Reference: http://wowwiki.wikia.com/wiki/Event_API
(Reminder! Some of these may be different in different versions of the game.)
Watching For WRobot State Changes
In addition to in game events, there are also WRobot 'states'. Similar to Game Events, WRobot states are the particular condition that WRobot is in at a specific time. For example, there is a state called 'MillingState', and another called 'Looting' that come out with WRobot. States are managed by the WRobot FiniteStateMachineEvents Engine. When a State occurs/changes/ends/etc, an event is passed to the FiniteStateMachine (pardon my wording here if this is not 100% correct). There are three main events that we can use to manage our States.
State Events that occur:
OnBeforeCheckIfNeedToRunState - This can be used to CANCEL an event if specific conditions are met. OnRunState - This can be used to do something just as the State is being started. OnAfterRunState - This can be used to do something just as the State has completed.
Example of OnRunState and OnAfterRunState
In this example we are watching for when WRobot starts the ToTown State and when it finishes it. We create a boolean that is set to true when the state is started, and then set it to false when the State is completed. I recommend adding the initializeToTownWatcher() function in the Initialize function of a plugin, or somewhere where it will only be called once. For example of this, please see my Plugin Template.
bool goToTown = false; private void initializeToTownWatcher() { robotManager.Events.FiniteStateMachineEvents.OnRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { goToTown = true; Logging.Write("Going to Town State has been initiated."); } }; robotManager.Events.FiniteStateMachineEvents.OnAfterRunState += (engine, state) => { if (state != null && state.DisplayName == "To Town") { goToTown = false; Logging.Write("We have completed going To Town State."); } }; } Example of OnBeforeCheckIfNeedToRunState
In this example, we catch the state with the name of To Town and cancel it by setting the passed in cancelable parameter to true.
private void cancelToTownState() { robotManager.Events.FiniteStateMachineEvents.OnBeforeCheckIfNeedToRunState += (engine, state, cancelable) => { if (state != null && state.DisplayName == "To Town") { Logging.Write("We have cancelled the To Town State"); cancelable.Cancel = true; } }; } Where can I find other WRobot States?
Each version of the WRobot is different, so some versions of WRobot may have a state type, but a different version may not. Please be careful to test against multiple versions of the game/WRobot.
Open DotPeek Expand wManager Module Expand wManager.Wow.Bot.States namespace.
MORE TBA....
The above is my attempt at trying to help newcomers to WRobot at writing their own plugins / fight classes / etc. If there are any questions , suggestions, or even corrections, please do let me know in the comments and I'll be sure to add/update things as they come up!
Thanks,
- Avvi
-
Avvi reacted to pasdoy in Avvi's C# Tips & Tricks with Helpful Code Snippets
Just saw this post. Very good info. Would be nice if it was pinned on page 1.
-
Avvi reacted to ScripterQQ in Error while trying to get distance from Object (Ship)
I took another peak at his code, in fact on the first ship he didn't add a control basically because the ship is always in the zone, but the second ship actually appears/disappears from the zone and goes through "portals", so yea he added a check
ObjectManager.GetWoWGameObjectByyId(ID).Count == 0 I guess both options are valid, I just didn't think about the item ID going out of the zone. Now I stick with the null check and I'm fine, the result is the same :)
Still I prefer his code rather than the classic "Catch Zeppelin/Ship", but that's a matter of preferences
-
Avvi got a reaction from ScripterQQ in Error while trying to get distance from Object (Ship)
I think it might be crashing because FirstOrDefault is not returning an instance of an object. So, you'll need to check if the object returned is null or not before checking its distance property.
For example:
var tram = ObjectManager.GetWoWGameObjectByyId(176082).FirstOrDefault(); if(tram!=null){ var distance = tram.GetDistance(); if(distance<=25){ Logging.Write("Tram is within 25 units"); } else{ Logging.Write("Tram is farther than 25 units"); } } else{ Logging.Write("Tram is null"); }
Also, to be safe, you can wrap the entire thing in a try catch block. This will prevent WRobot from crashing.
try{ var tram = ObjectManager.GetWoWGameObjectByyId(176082).FirstOrDefault(); if(tram!=null){ var distance = tram.GetDistance(); if(distance<=25){ Logging.Write("Tram is within 25 units"); } else{ Logging.Write("Tram is farther than 25 units"); } } else{ Logging.Write("Tram is null"); } } catch(Exception e){ Logging.Write("Uh oh... something happened:"+ e.ToString()); }