chinajade
Community Developer
- Joined
- Jul 20, 2010
- Messages
- 17,540
- Reaction score
- 172
Greetings Behavior Writers,
This is just an FYI that the argument processing provided by CustomForcedBehavior will be changing over the next couple of drops.
We know that many of you parse things explicitly. But, for those of you that have used the methods provided by CustomForcedBehavior, we'll be moving from an 'old' system (that was error prone, higher maintenance, and failed to address a number of issues) to a 'new' system.
Here's an example of the 'old' system...
With the new argument processing, the code reduces to the following:
Some noteworthy points about the new argument processing system:
So what should you take away from this?
The new system is so much more robust, that the old argument processing system will be removed within the next few Honorbuddy drops. If you wish your behavior to continue working, please convert it to the new argument processing system as soon as possible.
cheers,
chinajade
This is just an FYI that the argument processing provided by CustomForcedBehavior will be changing over the next couple of drops.
We know that many of you parse things explicitly. But, for those of you that have used the methods provided by CustomForcedBehavior, we'll be moving from an 'old' system (that was error prone, higher maintenance, and failed to address a number of issues) to a 'new' system.
Here's an example of the 'old' system...
HTML:
public MyBehaviorConstructor(Dictionary<string, string> args)
: base(args)
{
CheckForUnrecognizedAttributes(new Dictionary<string, object>()
{
{ "Faction", null },
{ "LUATarget", null },
{ "MoveTo", null },
{ "NpcID", null },
{ "NpcId", null },
{ "QuestId", null },
{ "UseCTM", null },
});
int mobId;
int useCTM;
int luatarget;
int usefaction;
int questId;
_isAttributesOkay &= GetAttributeAsInteger("Faction", false, "0", 0, int.MaxValue, out usefaction);
_isAttributesOkay &= GetAttributeAsInteger("NpcID", false, "0", 0, int.MaxValue, out mobId);
_isAttributesOkay &= GetAttributeAsInteger("QuestId", false, "0", 0, int.MaxValue, out questId);
_isAttributesOkay &= GetAttributeAsInteger("LUATarget", false, "0", 0, int.MaxValue, out luatarget);
_isAttributesOkay &= GetAttributeAsInteger("UseCTM", false, "0", 0, int.MaxValue, out useCTM);
// "NpcID" is allowed for legacy purposes --
// If it was not supplied, then its new name "NpcId" is required.
if (mobId == 0)
{ _isAttributesOkay &= GetAttributeAsInteger("NpcId", true, "0", 0, int.MaxValue, out mobId); }
// "UseCTM" is allowed for legacy purposes --
// If it was not supplied, then we need to check its new name "MoveTo", also.
if (useCTM == 0)
{ _isAttributesOkay &= GetAttributeAsInteger("MoveTo", false, "0", 0, int.MaxValue, out useCTM); }
// Weed out Profile Writer sloppiness --
if (_isAttributesOkay)
{
if (mobId == 0)
{
UtilLogMessage("error", "MobId may not be zero");
_isAttributesOkay = false;
}
}
if (_isAttributesOkay)
{
MobId = mobId;
LUATarget = luatarget;
UseCTM = useCTM;
FactionID = usefaction;
QuestId = (uint)questId;
Counter = 0;
}
}
public override void OnStart()
{
if (!_isAttributesOkay)
{
UtilLogMessage("error", "Stopping Honorbuddy. Please repair the profile!");
// *Never* want to stop Honorbuddy (e.g., TreeRoot.Stop()) in the constructor --
// This would defeat the "ProfileDebuggingMode" configurable that builds an instance of each
// used behavior when the profile is loaded.
TreeRoot.Stop();
}
else
{
PlayerQuest quest = StyxWoW.Me.QuestLog.GetQuestById(QuestId);
if (quest != null)
{ TreeRoot.GoalText = "BasicInteractWith - " + quest.Name; }
else
{ TreeRoot.GoalText = "BasicInteractWith: Running"; }
}
}
With the new argument processing, the code reduces to the following:
HTML:
public MyBehaviorConstructor(Dictionary<string, string> args)
: base(args)
{
MobId = GetAttributeAsMobId("MobId", true, new [] { "NpcId", "NpcID" }) ?? 0;
LUATarget = GetAttributeAsInteger("LUATarget", false, null) ?? 0;
UseCTM = GetAttributeAsInteger("MoveTo", false, new [] { "UseCTM" }) ?? 0;
FactionID = GetAttributeAsInteger("FactionId", false, new [] { "Faction" }) ?? 0;
QuestId = (uint?)GetAttributeAsQuestId("QuestId", false, null) ?? 0;
Counter = 0;
}
public override void OnStart()
{
OnStart_HandleAttributeProblem();
if (!IsDone)
{
PlayerQuest quest = StyxWoW.Me.QuestLog.GetQuestById(QuestId);
if (quest != null)
{ TreeRoot.GoalText = "BasicInteractWith - " + quest.Name; }
else
{ TreeRoot.GoalText = "BasicInteractWith: Running"; }
}
}
Some noteworthy points about the new argument processing system:
- Much less code to write for robust behavior
- No more CheckForUnrecognizedAttributes!
Argument names are now auto-discovered, and unrecognized attributes are reported by OnStart_HandleAttributeProblem.
The OnStart_HandleAttributeProblem now informs the Profile Writer of the line number in the profile that is in error. - New system is 'property friendly'
No more temporary local variables are required! - New system automatically handles 'argument aliases'
Very easy to handle backward compatibility when you want to rename arguments.
A Profile writer is informed of an error if he attempts to supply both the argument and one of its aliases as behavior arguments. - The 'default value' is no longer tied to the GetAttribute*() method.
This means your 'default value' does not have to be on the closed interval established by the GetAttribute*() method. - All of the new GetAttribute*() return nullable values.
Allowing 'null' is a popular and very reliable way to know whether or not an argument (or one of its aliases) was provided by the profile writer. - A number of new convenience methods have been supplied.
These methods do additional checking and processing based on usage context.
GetAttributeAsColor()
GetAttributeAsHotbarButton()
GetAttributeAsMobId()
GetAttributeAsQuestId()
GetAttributeAsRange()
GetAttributeAsSpellId()
GetAttributeAsString_NonEmpty()
GetAttributeAsString_SpecificValue() - New methods for processing 'lists' of data (comma or space-separated values)...
double[] GetAttributeAsDoubleArray()
int[] GetAttributeAsIntegerArray()
WoWPoint[] GetAttributeAsWoWPoints() - The new argument processing system has full Visual Studio documentation for these methods in the CustomForcedBehavior class.
So what should you take away from this?
The new system is so much more robust, that the old argument processing system will be removed within the next few Honorbuddy drops. If you wish your behavior to continue working, please convert it to the new argument processing system as soon as possible.
cheers,
chinajade
Last edited: