[+] Added autocast by variable priority (heal the wounded ones, bloodlust for strong ones...)
This commit is contained in:
parent
102a369dcf
commit
82eed1ab1f
3 changed files with 66 additions and 14 deletions
src
|
@ -164,11 +164,17 @@ public:
|
|||
class AutoCastInfo
|
||||
{
|
||||
public:
|
||||
AutoCastInfo() : Range(0), Condition(0), Combat(0) {};
|
||||
// Special flags for priority sorting
|
||||
#define ACP_NOVALUE -1
|
||||
#define ACP_DISTANCE -2
|
||||
AutoCastInfo() : Range(0), Condition(0), Combat(0), PriorytyVar(ACP_NOVALUE), ReverseSort(false) {};
|
||||
~AutoCastInfo() { delete Condition; };
|
||||
/// @todo this below is SQUARE!!!
|
||||
int Range; /// Max range of the target.
|
||||
|
||||
int PriorytyVar; /// Variable to sort autocast targets by priority.
|
||||
bool ReverseSort; /// If true, small values have the highest priority.
|
||||
|
||||
ConditionInfo *Condition; /// Conditions to cast the spell.
|
||||
|
||||
/// Detalied generic conditions (not per-target, where Condition is evaluated.)
|
||||
|
|
|
@ -242,6 +242,30 @@ static void CclSpellAutocast(lua_State *l, AutoCastInfo *autocast)
|
|||
lua_rawgeti(l, -1, j + 1);
|
||||
autocast->Combat = Ccl2Condition(l, LuaToString(l, -1));
|
||||
lua_pop(l, 1);
|
||||
} else if (!strcmp(value, "priority")) {
|
||||
lua_rawgeti(l, -1, j + 1);
|
||||
if (!lua_istable(l, -1) || lua_rawlen(l, -1) != 2) {
|
||||
LuaError(l, "incorrect argument");
|
||||
}
|
||||
lua_rawgeti(l, -1, 1);
|
||||
std::string var = LuaToString(l, -1);
|
||||
int index = UnitTypeVar.VariableNameLookup[var.c_str()];// User variables
|
||||
if (index == -1) {
|
||||
if (!strcmp(var.c_str(), "Distance")) {
|
||||
index = ACP_DISTANCE;
|
||||
} else {
|
||||
fprintf(stderr, "Bad variable name '%s'\n", var.c_str());
|
||||
Exit(1);
|
||||
}
|
||||
}
|
||||
autocast->PriorytyVar = index;
|
||||
lua_pop(l, 1);
|
||||
lua_rawgeti(l, -1, 2);
|
||||
autocast->ReverseSort = LuaToBoolean(l, -1);
|
||||
lua_pop(l, 1);
|
||||
|
||||
lua_pop(l, 1);
|
||||
|
||||
} else if (!strcmp(value, "condition")) {
|
||||
if (!autocast->Condition) {
|
||||
autocast->Condition = new ConditionInfo;
|
||||
|
|
|
@ -187,6 +187,32 @@ static bool PassCondition(const CUnit &caster, const SpellType &spell, const CUn
|
|||
return true;
|
||||
}
|
||||
|
||||
class AutoCastPrioritySort
|
||||
{
|
||||
public:
|
||||
explicit AutoCastPrioritySort(const CUnit &caster, const int var, const bool reverse) :
|
||||
caster(caster), variable(var), reverse(reverse) {}
|
||||
bool operator()(const CUnit *lhs, const CUnit *rhs) const {
|
||||
if (variable == ACP_DISTANCE) {
|
||||
if (reverse) {
|
||||
return lhs->MapDistanceTo(caster) > rhs->MapDistanceTo(caster);
|
||||
} else {
|
||||
return lhs->MapDistanceTo(caster) < rhs->MapDistanceTo(caster);
|
||||
}
|
||||
} else {
|
||||
if (reverse) {
|
||||
return lhs->Variable[variable].Value > rhs->Variable[variable].Value;
|
||||
} else {
|
||||
return lhs->Variable[variable].Value < rhs->Variable[variable].Value;
|
||||
}
|
||||
}
|
||||
}
|
||||
private:
|
||||
const CUnit &caster;
|
||||
const int variable;
|
||||
const bool reverse;
|
||||
};
|
||||
|
||||
/**
|
||||
** Select the target for the autocast.
|
||||
**
|
||||
|
@ -263,21 +289,17 @@ static Target *SelectTargetUnitsOfAutoCast(CUnit &caster, const SpellType &spell
|
|||
}
|
||||
}
|
||||
// Now select the best unit to target.
|
||||
// FIXME: Some really smart way to do this.
|
||||
// FIXME: Heal the unit with the lowest hit-points
|
||||
// FIXME: Bloodlust the unit with the highest hit-point
|
||||
// FIMXE: it will survive more
|
||||
if (n != 0) {
|
||||
#if 0
|
||||
// For the best target???
|
||||
sort(table, n, spell.autocast->f_order);
|
||||
return NewTargetUnit(*table[0]);
|
||||
#else
|
||||
// Best unit, random unit, oh well, same stuff.
|
||||
int index = SyncRand() % n;
|
||||
return NewTargetUnit(*table[index]);
|
||||
#endif
|
||||
}
|
||||
if (autocast->PriorytyVar != ACP_NOVALUE) {
|
||||
std::sort(table.begin(), table.begin() + n,
|
||||
AutoCastPrioritySort(caster, autocast->PriorytyVar, autocast->ReverseSort));
|
||||
return NewTargetUnit(*table[0]);
|
||||
} else { // Use the old behavior
|
||||
return NewTargetUnit(*table[SyncRand() % n]);
|
||||
}
|
||||
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
|
|
Loading…
Add table
Reference in a new issue