Work on AI.

This commit is contained in:
Relintai 2019-10-31 01:35:29 +01:00
parent 056791b313
commit 90e7e0064d
16 changed files with 393 additions and 54 deletions

3
SCsub
View File

@ -111,7 +111,10 @@ module_env.add_source_files(env.modules_sources,"ai/ai_action.cpp")
module_env.add_source_files(env.modules_sources,"ai/ai_spell_action.cpp")
module_env.add_source_files(env.modules_sources,"ai/ai_action_container.cpp")
module_env.add_source_files(env.modules_sources,"ai/ai_spell_action_container.cpp")
module_env.add_source_files(env.modules_sources,"ai/ai_fsm_action.cpp")
module_env.add_source_files(env.modules_sources,"ai/ai_spec_action.cpp")
module_env.add_source_files(env.modules_sources,"formations/ai_formation.cpp")
env.add_source_files(env.modules_sources,"profile_manager/input/input_profile_modifier.cpp")
env.add_source_files(env.modules_sources,"profile_manager/input/input_profile_modifier_entry.cpp")

56
ai/ai_fsm_action.cpp Normal file
View File

@ -0,0 +1,56 @@
#include "ai_fsm_action.h"
EntityEnums::AIStates AIFSMAction::get_state() {
return _state;
}
void AIFSMAction::set_state(EntityEnums::AIStates state) {
_state = state;
}
EntityEnums::AIStates AIFSMAction::get_force_state() {
return _force_state;
}
void AIFSMAction::set_force_state(EntityEnums::AIStates state) {
_force_state = state;
}
Ref<AIAction> AIFSMAction::get_action(const EntityEnums::AIStates index) {
return _states[index];
}
void AIFSMAction::set_action(const EntityEnums::AIStates index, Ref<AIAction> action) {
_states[index] = action;
}
AIFSMAction::AIFSMAction() {
_state = EntityEnums::AI_STATE_OFF;
_force_state = EntityEnums::AI_STATE_OFF;
}
AIFSMAction::~AIFSMAction() {
for (int i = 0; i < EntityEnums::AI_STATE_MAX; ++i) {
_states[i].unref();
}
}
void AIFSMAction::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_state"), &AIFSMAction::get_state);
ClassDB::bind_method(D_METHOD("set_state", "state"), &AIFSMAction::set_state);
ADD_PROPERTY(PropertyInfo(Variant::INT, "state", PROPERTY_HINT_ENUM, "SpellCastInfo"), "set_state", "get_state");
ClassDB::bind_method(D_METHOD("get_force_state"), &AIFSMAction::get_force_state);
ClassDB::bind_method(D_METHOD("set_force_state", "state"), &AIFSMAction::set_force_state);
ADD_PROPERTY(PropertyInfo(Variant::INT, "force_state", PROPERTY_HINT_ENUM, "SpellCastInfo"), "set_force_state", "get_force_state");
ClassDB::bind_method(D_METHOD("get_action", "index"), &AIFSMAction::get_action);
ClassDB::bind_method(D_METHOD("set_action", "index", "action"), &AIFSMAction::set_action);
ADD_PROPERTYI(PropertyInfo(Variant::OBJECT, "action_off", PROPERTY_HINT_RESOURCE_TYPE, "AIAction"), "set_action", "get_action", EntityEnums::AI_STATE_OFF);
ADD_PROPERTYI(PropertyInfo(Variant::OBJECT, "action_rest", PROPERTY_HINT_RESOURCE_TYPE, "AIAction"), "set_action", "get_action", EntityEnums::AI_STATE_REST);
ADD_PROPERTYI(PropertyInfo(Variant::OBJECT, "action_patrol", PROPERTY_HINT_RESOURCE_TYPE, "AIAction"), "set_action", "get_action", EntityEnums::AI_STATE_PATROL);
ADD_PROPERTYI(PropertyInfo(Variant::OBJECT, "action_follow_path", PROPERTY_HINT_RESOURCE_TYPE, "AIAction"), "set_action", "get_action", EntityEnums::AI_STATE_FOLLOW_PATH);
ADD_PROPERTYI(PropertyInfo(Variant::OBJECT, "action_regenerate", PROPERTY_HINT_RESOURCE_TYPE, "AIAction"), "set_action", "get_action", EntityEnums::AI_STATE_REGENERATE);
ADD_PROPERTYI(PropertyInfo(Variant::OBJECT, "action_attack", PROPERTY_HINT_RESOURCE_TYPE, "AIAction"), "set_action", "get_action", EntityEnums::AI_STATE_ATTACK);
ADD_PROPERTYI(PropertyInfo(Variant::OBJECT, "action_pet_follow", PROPERTY_HINT_RESOURCE_TYPE, "AIAction"), "set_action", "get_action", EntityEnums::AI_STATE_PET_FOLLOW);
ADD_PROPERTYI(PropertyInfo(Variant::OBJECT, "action_pet_stop", PROPERTY_HINT_RESOURCE_TYPE, "AIAction"), "set_action", "get_action", EntityEnums::AI_STATE_PET_STOP);
ADD_PROPERTYI(PropertyInfo(Variant::OBJECT, "action_pet_attack", PROPERTY_HINT_RESOURCE_TYPE, "AIAction"), "set_action", "get_action", EntityEnums::AI_STATE_PET_ATTACK);
}

34
ai/ai_fsm_action.h Normal file
View File

@ -0,0 +1,34 @@
#ifndef AI_FSM_ACTION_H
#define AI_FSM_ACTION_H
#include "ai_action.h"
#include "../entity_enums.h"
class AIFSMAction : public AIAction {
GDCLASS(AIFSMAction, AIAction);
public:
EntityEnums::AIStates get_state();
void set_state(EntityEnums::AIStates state);
EntityEnums::AIStates get_force_state();
void set_force_state(EntityEnums::AIStates state);
Ref<AIAction> get_action(const EntityEnums::AIStates index);
void set_action(const EntityEnums::AIStates index, Ref<AIAction> action);
AIFSMAction();
~AIFSMAction();
protected:
static void _bind_methods();
private:
EntityEnums::AIStates _state;
EntityEnums::AIStates _force_state;
Ref<AIAction> _states[EntityEnums::AI_STATE_MAX];
};
#endif

45
ai/ai_spec_action.cpp Normal file
View File

@ -0,0 +1,45 @@
#include "ai_spec_action.h"
Vector<int> AISpecAction::get_spec_distribution() {
return _spec_distribution;
}
void AISpecAction::set_spec_distribution(Vector<int> data) {
_spec_distribution = data;
}
int AISpecAction::get_variance() {
return _variance;
}
void AISpecAction::set_variance(int value) {
_variance = value;
}
Ref<AIAction> AISpecAction::get_action() {
return _action;
}
void AISpecAction::set_action(Ref<AIAction> action) {
_action = action;
}
AISpecAction::AISpecAction() {
_variance = 0;
}
AISpecAction::~AISpecAction() {
_spec_distribution.clear();
_action.unref();
}
void AISpecAction::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_spec_distribution"), &AISpecAction::get_spec_distribution);
ClassDB::bind_method(D_METHOD("set_spec_distribution", "value"), &AISpecAction::set_spec_distribution);
ADD_PROPERTY(PropertyInfo(Variant::ARRAY, "spec_distribution"), "set_spec_distribution", "get_spec_distribution");
ClassDB::bind_method(D_METHOD("get_variance"), &AISpecAction::get_variance);
ClassDB::bind_method(D_METHOD("set_variance", "value"), &AISpecAction::set_variance);
ADD_PROPERTY(PropertyInfo(Variant::INT, "variance"), "set_variance", "get_variance");
ClassDB::bind_method(D_METHOD("get_action"), &AISpecAction::get_action);
ClassDB::bind_method(D_METHOD("set_action", "value"), &AISpecAction::set_action);
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "action", PROPERTY_HINT_RESOURCE_TYPE, "AIAction"), "set_action", "get_action");
}

33
ai/ai_spec_action.h Normal file
View File

@ -0,0 +1,33 @@
#ifndef AI_SPEC_ACTION_H
#define AI_SPEC_ACTION_H
#include "ai_action.h"
#include "core/vector.h"
class AISpecAction : public AIAction {
GDCLASS(AISpecAction, AIAction);
public:
Vector<int> get_spec_distribution();
void set_spec_distribution(Vector<int> data);
int get_variance();
void set_variance(int value);
Ref<AIAction> get_action();
void set_action(Ref<AIAction> action);
AISpecAction();
~AISpecAction();
protected:
static void _bind_methods();
private:
Vector<int> _spec_distribution;
int _variance;
Ref<AIAction> _action;
};
#endif

View File

@ -1,6 +1,6 @@
#include "entity_class_data.h"
#include "../../ai/ai_action.h"
#include "../../ai/ai_spec_action.h"
#include "../../data/aura.h"
#include "../../data/spell.h"
#include "../../data/item_instance.h"
@ -269,16 +269,16 @@ void EntityClassData::set_num_ai_actions(int value) {
_ai_actions.resize(value);
}
Ref<AIAction> EntityClassData::get_ai_action(int index) {
Ref<AISpecAction> EntityClassData::get_ai_action(int index) {
if (_ai_actions.size() == 0 && _inherits.is_valid()) {
return _inherits->get_ai_action(index);
}
ERR_FAIL_INDEX_V(index, _ai_actions.size(), Ref<AIAction>());
ERR_FAIL_INDEX_V(index, _ai_actions.size(), Ref<AISpecAction>());
return _ai_actions[index];
}
void EntityClassData::set_ai_action(int index, Ref<AIAction> ai_action) {
void EntityClassData::set_ai_action(int index, Ref<AISpecAction> ai_action) {
ERR_FAIL_INDEX(index, _ai_actions.size());
_ai_actions.set(index, ai_action);
@ -294,7 +294,7 @@ Vector<Variant> EntityClassData::get_ai_actions() {
void EntityClassData::set_ai_actions(const Vector<Variant> &ai_actions) {
_ai_actions.clear();
for (int i = 0; i < ai_actions.size(); i++) {
Ref<AIAction> ai_action = Ref<AIAction>(ai_actions[i]);
Ref<AISpecAction> ai_action = Ref<AISpecAction>(ai_actions[i]);
_ai_actions.push_back(ai_action);
}
@ -1135,5 +1135,5 @@ void EntityClassData::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_ai_actions"), &EntityClassData::get_ai_actions);
ClassDB::bind_method(D_METHOD("set_ai_actions", "auras"), &EntityClassData::set_ai_actions);
ADD_PROPERTY(PropertyInfo(Variant::ARRAY, "ai_actions", PROPERTY_HINT_NONE, "17/17:AIAction", PROPERTY_USAGE_DEFAULT, "AIAction"), "set_ai_actions", "get_ai_actions");
ADD_PROPERTY(PropertyInfo(Variant::ARRAY, "ai_actions", PROPERTY_HINT_NONE, "17/17:AISpecAction", PROPERTY_USAGE_DEFAULT, "AISpecAction"), "set_ai_actions", "get_ai_actions");
}

View File

@ -24,7 +24,7 @@ class ItemInstance;
class CharacterSpec;
class Entity;
class SpellCastInfo;
class AIAction;
class AISpecAction;
class EntityClassData : public Resource {
GDCLASS(EntityClassData, Resource);
@ -101,8 +101,8 @@ public:
int get_num_ai_actions();
void set_num_ai_actions(int value);
Ref<AIAction> get_ai_action(int index);
void set_ai_action(int index, Ref<AIAction> aura);
Ref<AISpecAction> get_ai_action(int index);
void set_ai_action(int index, Ref<AISpecAction> aura);
Vector<Variant> get_ai_actions();
void set_ai_actions(const Vector<Variant> &ai_actions);
@ -246,7 +246,7 @@ private:
Vector<Ref<Spell> > _start_spells;
Vector<Ref<CharacterSpec> > _specs;
Vector<Ref<Aura> > _auras;
Vector<Ref<AIAction> > _ai_actions;
Vector<Ref<AISpecAction> > _ai_actions;
};
#endif

View File

@ -108,6 +108,20 @@ void EntityData::set_equipment_data(Ref<EquipmentData> data) {
_equipment_data = data;
}
Ref<AIFSMAction> EntityData::get_fsm() const {
return _fsm;
}
void EntityData::set_fsm(const Ref<AIFSMAction> fsm) {
_fsm = fsm;
}
Ref<AIFormation> EntityData::get_formation() const {
return _formation;
}
void EntityData::set_formation(const Ref<AIFormation> data) {
_formation = data;
}
Ref<LootDataBase> EntityData::get_loot_db() const {
return _lootdb;
}
@ -1198,6 +1212,15 @@ void EntityData::_bind_methods() {
ClassDB::bind_method(D_METHOD("set_equipment_data", "value"), &EntityData::set_equipment_data);
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "equipment_data", PROPERTY_HINT_RESOURCE_TYPE, "EquipmentData"), "set_equipment_data", "get_equipment_data");
//AI
ClassDB::bind_method(D_METHOD("get_fsm"), &EntityData::get_fsm);
ClassDB::bind_method(D_METHOD("set_fsm", "value"), &EntityData::set_fsm);
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "fsm", PROPERTY_HINT_RESOURCE_TYPE, "AIFSMAction"), "set_fsm", "get_fsm");
ClassDB::bind_method(D_METHOD("get_formation"), &EntityData::get_formation);
ClassDB::bind_method(D_METHOD("set_formation", "value"), &EntityData::set_formation);
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "formation", PROPERTY_HINT_RESOURCE_TYPE, "AIFormation"), "set_formation", "get_formation");
// Loot DB
ClassDB::bind_method(D_METHOD("get_loot_db"), &EntityData::get_loot_db);
ClassDB::bind_method(D_METHOD("set_loot_db", "value"), &EntityData::set_loot_db);

View File

@ -25,6 +25,9 @@
#include "../../skeleton/entity_species_data.h"
#include "../../ai/ai_fsm_action.h"
#include "../../formations/ai_formation.h"
class Aura;
class Spell;
class Entity;
@ -81,6 +84,12 @@ public:
Ref<EquipmentData> get_equipment_data();
void set_equipment_data(Ref<EquipmentData> data);
Ref<AIFSMAction> get_fsm() const;
void set_fsm(const Ref<AIFSMAction> fsm);
Ref<AIFormation> get_formation() const;
void set_formation(const Ref<AIFormation> data);
Ref<LootDataBase> get_loot_db() const;
void set_loot_db(const Ref<LootDataBase> data);
@ -99,19 +108,6 @@ public:
Vector<Variant> get_craft_recipes();
void set_craft_recipes(const Vector<Variant> &recipe);
/*
Vector<int> get_mob_party_ids();
void set_mob_party_ids(Vector<int> ids);
Vector<int> get_mob_dislike_ids();
void set_mob_dislike_ids(Vector<int> ids);
*/
//MobSpellData *getMobSpellData();
//void setMobSpellData(MobSpellData *value);
//int get_inspector_max_spells();
//void set_inspector_max_spells(int value);
String generate_name();
//Setup
@ -261,15 +257,13 @@ private:
Ref<EntitySpeciesData> _entity_species_data;
Ref<EquipmentData> _equipment_data;
Ref<AIFSMAction> _fsm;
Ref<AIFormation> _formation;
Ref<LootDataBase> _lootdb;
Ref<VendorItemData> _vendor_item_data;
Ref<ItemContainerData> _item_container_data;
Vector<Ref<CraftRecipe> > _craft_recipes;
//Vector<int> _mob_party_ids;
//Vector<int> _mob_dislike_ids;
//MobSpellData *_mob_spell_data;
};
#endif

View File

@ -339,6 +339,23 @@ void Entity::_setup() {
set_process(_s_entity_data.is_valid());
}
// AI
int Entity::get_formation_index() {
return _formation_index;
}
void Entity::set_formation_index(int value) {
_formation_index = value;
}
Ref<AIFSMAction> Entity::get_ai() {
return _ai;
}
void Entity::set_ai(Ref<AIFSMAction> value) {
_ai = value;
}
//// Serialization ////
bool Entity::is_deserialized() {
@ -804,11 +821,11 @@ void Entity::initialize(Ref<EntityCreateInfo> info) {
////// Stat System //////
bool Entity::gets_is_dead() {
return sIsDead;
return _s_is_dead;
}
bool Entity::getc_is_dead() {
return sIsDead;
return _c_is_dead;
}
bool Entity::getc_has_global_cooldown() {
@ -4343,12 +4360,12 @@ Entity::Entity() {
_s_state = PlayerStates::STATE_NORMAL;
_c_state = PlayerStates::STATE_NORMAL;
sIsDead = false;
cIsDead = false;
_s_gcd = 0;
_c_gcd = 0;
_s_is_dead = 0;
_c_is_dead = 0;
_s_interaction_type = EntityEnums::ENITIY_INTERACTION_TYPE_NORMAL;
_c_interaction_type = EntityEnums::ENITIY_INTERACTION_TYPE_NORMAL;
@ -4359,9 +4376,6 @@ Entity::Entity() {
_s_state = 0;
_c_state = 0;
sRezTimer = 0;
cRezTimer = 0;
_s_active_category_cooldowns = 0;
_c_active_category_cooldowns = 0;
@ -4393,6 +4407,8 @@ Entity::Entity() {
_stats[i] = s;
}
_formation_index = 0;
/*
get_stat_enum(Stat::STAT_ID_HEALTH)->set_base(10000);
get_stat_enum(Stat::STAT_ID_MANA)->set_base(100);
@ -4625,6 +4641,8 @@ Entity::~Entity() {
_s_sees.clear();
_s_seen_by.clear();
_ai.unref();
}
void Entity::_notification(int p_what) {
@ -5441,6 +5459,16 @@ void Entity::_bind_methods() {
ClassDB::bind_method(D_METHOD("get_action_bar_profile"), &Entity::get_action_bar_profile);
// AI
ClassDB::bind_method(D_METHOD("get_formation_index"), &Entity::get_formation_index);
ClassDB::bind_method(D_METHOD("set_formation_index", "value"), &Entity::set_formation_index);
ADD_PROPERTY(PropertyInfo(Variant::INT, "formation_index"), "set_formation_index", "get_formation_index");
ClassDB::bind_method(D_METHOD("get_ai"), &Entity::get_ai);
ClassDB::bind_method(D_METHOD("set_ai", "value"), &Entity::set_ai);
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "ai", PROPERTY_HINT_RESOURCE_TYPE, "AIFSMAction"), "set_ai", "get_ai");
//Serialization
BIND_VMETHOD(MethodInfo("_from_dict", PropertyInfo(Variant::DICTIONARY, "dict")));
BIND_VMETHOD(MethodInfo(PropertyInfo(Variant::DICTIONARY, "dict"), "_to_dict"));

View File

@ -36,6 +36,8 @@
#include "../profile_manager/actionbar/action_bar_profile.h"
#include "../ai/ai_fsm_action.h"
class EntityData;
class AuraData;
class Spell;
@ -725,6 +727,15 @@ public:
void setup();
virtual void _setup();
//// AI ////
int get_formation_index();
void set_formation_index(int value);
Ref<AIFSMAction> get_ai();
void set_ai(Ref<AIFSMAction> value);
//// Serialization ////
bool is_deserialized();
@ -735,7 +746,7 @@ public:
virtual Dictionary _to_dict();
virtual void _from_dict(const Dictionary &dict);
//Networking
// Networking
Entity *gets_sees(int index);
void removes_sees_index(int index);
void removes_sees(Entity *entity);
@ -808,6 +819,9 @@ private:
EntityEnums::EntityInteractionType _s_interaction_type;
EntityEnums::EntityInteractionType _c_interaction_type;
int _s_is_dead;
int _c_is_dead;
//// Stats ////
Ref<Stat> _stats[Stat::STAT_ID_TOTAL_STATS];
@ -822,16 +836,6 @@ private:
Vector<Ref<EntityResource> > _s_resources;
Vector<Ref<EntityResource> > _c_resources;
//old
bool sIsDead;
bool cIsDead;
bool localClient;
bool s;
bool c;
float sRezTimer;
float cRezTimer;
//// GCD ////
float _s_gcd;
@ -932,7 +936,13 @@ private:
Ref<Bag> _s_target_bag;
Ref<Bag> _c_target_bag;
//AI
int _formation_index;
Ref<AIFSMAction> _ai;
//Networking
Vector<Entity *> _s_sees;
Vector<Entity *> _s_seen_by;
};

View File

@ -7,7 +7,7 @@ const String EntityEnums::BINDING_STRING_ENTITY_CONTOLLER = "None,Player,AI,Mob"
const String EntityEnums::BINDING_STRING_ENTITY_FLAGS = "Untargetable,Hidden,Interactable,Hostile";
const String EntityEnums::BINDING_STRING_ENTITY_STATE_TYPES = "None,Stun,Root,Frozen,Silenced,Disoriented,Feared,Burning,Cold,Cursed,Pacified";
const String EntityEnums::BINDING_STRING_CHARCATER_SKELETON_POINTS = "Root,Pelvis,Spine,Spine 1,Spine 2,Neck,Head,Left Clavicle,Left upper Arm,Left Forearm,Left Hand,Left Thumb Base,Left Thumb End,Left Fingers Base,Left Fingers End,Right Clavicle,Right upper Arm,Right Forearm,Right Hand,Right Thumb Base,Right Thumb End,Right Fingers Base,Right Fingers End,Left Thigh,Left Calf,Left Foot,Right Thigh,Right Calf,Right Foot";
const String EntityEnums::BINDING_STRING_AI_STATES = "Off,Rest,Patrol,Follow Path,Regenerate,Attack";
const String EntityEnums::BINDING_STRING_AI_STATES = "Off,Rest,Patrol,Follow Path,Regenerate,Attack,Pet Follow,Pet Stop,Pet Attack";
const String EntityEnums::BINDING_STRING_ENTITY_IMMUNITY_FLAGS = "Stun,Root,Freeze,Silence,Disorient,Fear,Burning,Cold,Pacify,Magic,Poison,Physical,Curse,Bleed,Melee,Holy,Shadow,Nature,Fire,Frost,Lightning,Chaos,Slow,Crit,AOE,Damage,Fall Damage,Projectile,Debuff,Attacks";
const String EntityEnums::BINDING_STRING_ENTITY_INTERACTION_TYPE = "Normal,Speak,Loot,Use,None";
const String EntityEnums::BINDING_STRING_ENTITY_PLAYSTYLE_TYPE = "Melee,Spell,Hybrid,None";
@ -121,6 +121,7 @@ void EntityEnums::_bind_methods() {
BIND_ENUM_CONSTANT(AI_STATE_FOLLOW_PATH);
BIND_ENUM_CONSTANT(AI_STATE_REGENERATE);
BIND_ENUM_CONSTANT(AI_STATE_ATTACK);
BIND_ENUM_CONSTANT(AI_STATE_MAX);
BIND_ENUM_CONSTANT(ENTITY_IMMUNITY_FLAG_NONE);

View File

@ -192,12 +192,18 @@ public:
};
enum AIStates {
AI_STATE_OFF,
AI_STATE_REST,
AI_STATE_PATROL,
AI_STATE_FOLLOW_PATH,
AI_STATE_REGENERATE,
AI_STATE_ATTACK,
AI_STATE_OFF = 0,
AI_STATE_REST = 1,
AI_STATE_PATROL = 2,
AI_STATE_FOLLOW_PATH = 3,
AI_STATE_REGENERATE = 4,
AI_STATE_ATTACK = 5,
AI_STATE_PET_FOLLOW = 6,
AI_STATE_PET_STOP = 7,
AI_STATE_PET_ATTACK = 8,
AI_STATE_MAX = 9,
};
enum EntityInteractionType {

View File

@ -0,0 +1,67 @@
#include "ai_formation.h"
#include "../entities/entity.h"
void AIFormation::set_owner(Entity *entity) {
_owner = entity;
call("_on_set_owner");
}
void AIFormation::set_owner_bind(Node *entity) {
if (!entity) {
return;
}
Entity *e = cast_to<Entity>(entity);
if (!e) {
return;
}
return set_owner(e);
}
Entity *AIFormation::get_owner() {
return _owner;
}
void AIFormation::set_editor_description(const String &p_editor_description) {
set_meta("_editor_description_", p_editor_description);
}
String AIFormation::get_editor_description() const {
if (has_meta("_editor_description_")) {
return get_meta("_editor_description_");
} else {
return "";
}
}
Vector3 AIFormation::get_position(int slot_index) {
ERR_FAIL_COND_V(!ObjectDB::instance_validate(_owner), Vector3());
if (has_method("_get_position"))
return call("_get_position", slot_index);
return Vector3();
}
AIFormation::AIFormation() {
_owner = NULL;
}
void AIFormation::_bind_methods() {
BIND_VMETHOD(MethodInfo("_on_set_owner"));
BIND_VMETHOD(MethodInfo(PropertyInfo(Variant::VECTOR3, "pos"), "_get_position", PropertyInfo(Variant::INT, "slot_index")));
ClassDB::bind_method(D_METHOD("get_owner"), &AIFormation::get_owner);
ClassDB::bind_method(D_METHOD("set_owner", "entity"), &AIFormation::set_owner_bind);
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "owner", PROPERTY_HINT_RESOURCE_TYPE, "Entity", 0), "set_owner", "get_owner");
ClassDB::bind_method(D_METHOD("get_position", "slot_index"), &AIFormation::get_position);
ClassDB::bind_method(D_METHOD("_set_editor_description", "editor_description"), &AIFormation::set_editor_description);
ClassDB::bind_method(D_METHOD("_get_editor_description"), &AIFormation::get_editor_description);
ADD_PROPERTY(PropertyInfo(Variant::STRING, "editor_description", PROPERTY_HINT_MULTILINE_TEXT, "", PROPERTY_USAGE_EDITOR | PROPERTY_USAGE_INTERNAL), "_set_editor_description", "_get_editor_description");
}

31
formations/ai_formation.h Normal file
View File

@ -0,0 +1,31 @@
#ifndef AI_FORMATION_H
#define AI_FORMATION_H
#include "core/resource.h"
#include "scene/main/node.h"
class Entity;
class AIFormation : public Resource {
GDCLASS(AIFormation, Resource);
public:
void set_owner(Entity *entity);
void set_owner_bind(Node *entity);
Entity *get_owner();
void set_editor_description(const String &p_editor_description);
String get_editor_description() const;
Vector3 get_position(int slot_index);
AIFormation();
protected:
static void _bind_methods();
private:
Entity *_owner;
};
#endif

View File

@ -102,6 +102,10 @@
#include "ai/ai_spell_action.h"
#include "ai/ai_action_container.h"
#include "ai/ai_spell_action_container.h"
#include "ai/ai_fsm_action.h"
#include "ai/ai_spec_action.h"
#include "formations/ai_formation.h"
#include "profile_manager/input/input_profile_modifier.h"
#include "profile_manager/input/input_profile_modifier_entry.h"
@ -235,6 +239,10 @@ void register_entity_spell_system_types() {
ClassDB::register_class<AISpellAction>();
ClassDB::register_class<AIActionContainer>();
ClassDB::register_class<AISpellActionContainer>();
ClassDB::register_class<AIFSMAction>();
ClassDB::register_class<AISpecAction>();
ClassDB::register_class<AIFormation>();
//meshes
ClassDB::register_class<MeshDataResource>();