From 2df0db54d42a54fe5bec35bdf9996376164c23e7 Mon Sep 17 00:00:00 2001 From: Nathanael Sensfelder Date: Fri, 11 Oct 2019 23:39:11 +0200 Subject: ... --- src/battle/mechanic/action/btl_action_attack.erl | 136 +++++++++++++---- src/battle/mechanic/condition/blt_cond_heal.erl | 187 ----------------------- src/battle/mechanic/condition/btl_cond_heal.erl | 125 +++++++++++++++ src/battle/struct/btl_character.erl | 46 ++++-- src/battle/struct/btl_condition.erl | 131 ++++++++++++---- 5 files changed, 365 insertions(+), 260 deletions(-) delete mode 100644 src/battle/mechanic/condition/blt_cond_heal.erl create mode 100644 src/battle/mechanic/condition/btl_cond_heal.erl diff --git a/src/battle/mechanic/action/btl_action_attack.erl b/src/battle/mechanic/action/btl_action_attack.erl index b9b3eea..0cc0718 100644 --- a/src/battle/mechanic/action/btl_action_attack.erl +++ b/src/battle/mechanic/action/btl_action_attack.erl @@ -24,22 +24,40 @@ btl_character:type(), btl_character_turn_update:type() ) - -> {shr_condition:context(A, B), btl_character_turn_update:type()}. + -> + { + shr_condition:context(A, B), + btl_character:type(), + ataxic:basic(), + btl_character_turn_update:type() + }. apply_conditions ( Context = {Trigger, _ReadOnlyContext, _VolatileContext}, - Actor, + S0Actor, S0Update ) -> - {LastContext, S1Update} = + {LastContext, S1Update, ConditionUpdates} = btl_condition:recursive_apply ( - btl_character:get_conditions_on(Trigger, Actor), + btl_character:get_conditions_on(Trigger, S0Actor), Context, S0Update ), - {LastContext, S1Update}. + S0AllConditions = btl_character:get_conditions(S0Actor), + {S1AllConditions, AllConditionsAtaxiaUpdate} = + btl_condition:ataxia_apply_updates(ConditionUpdates, S0AllConditions), + + {S1Actor, ActorAtaxiaUpdate} = + btl_character:ataxia_set_conditions + ( + S1AllConditions, + AllConditionsAtaxiaUpdate, + S0Actor + ), + + {LastContext, S1Actor, ActorAtaxiaUpdate, S1Update}. -spec roll_for_precision ( @@ -215,38 +233,64 @@ apply_mirror_conditions {ReadOnlyContext, S0VolatileContext}, S0Update ) -> - CharacterIX = btl_action:get_actor_index(Action), + ActorIX = btl_action:get_actor_index(Action), S0Battle = btl_character_turn_update:get_battle(S0Update), - {Character, S1Battle} = - btl_battle:get_resolved_character(CharacterIX, S0Battle), - + {S0Actor, S1Battle} = btl_battle:get_resolved_character(ActorIX, S0Battle), S1Update = btl_character_turn_update:set_battle(S1Battle, S0Update), - {{_TriggerName, _ReadOnlyContext, S1VolatileContext}, S2Update} = + { + {_TriggerName, _ReadOnlyContext, S1VolatileContext}, + S1Actor, + ActorAtaxiaUpdate, + S2Update + } = apply_conditions ( {OwnTriggerName, ReadOnlyContext, S0VolatileContext}, - Character, + S0Actor, S1Update ), - TargetCharacterIX = btl_action:get_target_index(Action), + TargetIX = btl_action:get_target_index(Action), S2Battle = btl_character_turn_update:get_battle(S2Update), + S3Battle = + btl_battle:ataxia_set_character + ( + ActorIX, + S1Actor, + ActorAtaxiaUpdate, + S2Battle + ), - {TargetCharacter, S3Battle} = - btl_battle:get_resolved_character(TargetCharacterIX, S2Battle), - - S3Update = btl_character_turn_update:set_battle(S3Battle, S2Update), + {Target, S4Battle} = btl_battle:get_resolved_character(TargetIX, S3Battle), + S3Update = btl_character_turn_update:set_battle(S4Battle, S2Update), - {{_TriggerName, _ReadOnlyContext, S2VolatileContext}, S4Update} = + { + {_TriggerName, _ReadOnlyContext, S2VolatileContext}, + S1Target, + TargetAtaxiaUpdate, + S4Update + } = apply_conditions ( {OtherTriggerName, ReadOnlyContext, S1VolatileContext}, - TargetCharacter, + Target, S3Update ), - {S2VolatileContext, S4Update}; + S5Battle = btl_character_turn_update:get_battle(S4Update), + S6Battle = + btl_battle:ataxia_set_character + ( + TargetIX, + S1Target, + TargetAtaxiaUpdate, + S5Battle + ), + + S5Update = btl_character_turn_update:set_battle(S6Battle, S4Update), + + {S2VolatileContext, S5Update}; apply_mirror_conditions ( true, @@ -256,38 +300,68 @@ apply_mirror_conditions {ReadOnlyContext, S0VolatileContext}, S0Update ) -> - TargetCharacterIX = btl_action:get_target_index(Action), + TargetIX = btl_action:get_target_index(Action), S0Battle = btl_character_turn_update:get_battle(S0Update), - {TargetCharacter, S1Battle} = - btl_battle:get_resolved_character(TargetCharacterIX, S0Battle), + {S0Target, S1Battle} = + btl_battle:get_resolved_character(TargetIX, S0Battle), S1Update = btl_character_turn_update:set_battle(S1Battle, S0Update), - {{_TriggerName, _ReadOnlyContext, S1VolatileContext}, S2Update} = + { + {_TriggerName, _ReadOnlyContext, S1VolatileContext}, + S1Target, + TargetAtaxiaUpdate, + S2Update + } = apply_conditions ( {OwnTriggerName, ReadOnlyContext, S0VolatileContext}, - TargetCharacter, + S0Target, S1Update ), - CharacterIX = btl_action:get_actor_index(Action), + ActorIX = btl_action:get_actor_index(Action), S2Battle = btl_character_turn_update:get_battle(S2Update), - {Character, S3Battle} = - btl_battle:get_resolved_character(CharacterIX, S2Battle), + {S0Actor, S3Battle} = btl_battle:get_resolved_character(ActorIX, S2Battle), + + S4Battle = + btl_battle:ataxia_set_character + ( + TargetIX, + S1Target, + TargetAtaxiaUpdate, + S3Battle + ), - S3Update = btl_character_turn_update:set_battle(S3Battle, S2Update), + S3Update = btl_character_turn_update:set_battle(S4Battle, S2Update), - {{_TriggerName, _ReadOnlyContext, S2VolatileContext}, S4Update} = + { + {_TriggerName, _ReadOnlyContext, S2VolatileContext}, + S1Actor, + ActorAtaxiaUpdate, + S4Update + } = apply_conditions ( {OtherTriggerName, ReadOnlyContext, S1VolatileContext}, - Character, + S0Actor, S3Update ), - {S2VolatileContext, S4Update}. + S5Battle = btl_character_turn_update:get_battle(S4Update), + S6Battle = + btl_battle:ataxia_set_character + ( + ActorIX, + S1Actor, + ActorAtaxiaUpdate, + S5Battle + ), + + S5Update = btl_character_turn_update:set_battle(S6Battle, S4Update), + + {S2VolatileContext, S5Update}. -spec handle_start_of_attack ( diff --git a/src/battle/mechanic/condition/blt_cond_heal.erl b/src/battle/mechanic/condition/blt_cond_heal.erl deleted file mode 100644 index 021739f..0000000 --- a/src/battle/mechanic/condition/blt_cond_heal.erl +++ /dev/null @@ -1,187 +0,0 @@ --module(btl_cond_heal). - -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -%% TYPES %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% --include("tacticians/conditions.hrl"). - -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -%% EXPORTS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% --export -( - [ - apply/3 - ] -). - -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -%% LOCAL FUNCTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% --spec apply_to_character - ( - btl_condition:type(), - btl_character:type() - ) - -> - { - btl_condition:type(), - btl_condition:update_action(), - [{btl_character:type(), ataxic:basic()}] - }. -apply_to_character (Condition, S0Character) -> - {_TargetIX, Amount} = btl_condition:get_parameters(Condition), - - case btl_character:get_is_alive(S0Character) of - false -> {Condition, none, []}; - true -> - RemainingUses = btl_condition:get_remaining_uses(Condition), - CurrentHealth = btl_character:get_current_health(S0Character), - MaxHealth = - shr_attributes:get_health - ( - shr_character:get_attributes - ( - btl_character:get_base_character(S0Character) - ) - ), - - UpdatedHealth = min(MaxHealth, (CurrentHealth + Amount)), - UpdatedRemainingUses = - - {S1Character, CharacterUpdate} = - btl_character:ataxia_set_current_health(UpdatedHealth, S0Character), - - if - (RemainingUses == -1) -> - { - Condition, - do_nothing, - [{S1Character, CharacterUpdate}] - }; - - (RemainingUses == 1) -> - { - btl_condition:set_remaining_uses - ( - UpdatedRemainingUses, - Condition - ), - remove, - [{S1Character, CharacterUpdate}] - }; - - (RemainingUses == 0) -> - { - Condition, - remove, - [{S1Character, CharacterUpdate}] - }; - - true -> - {UpdatedCondition, ConditionUpdate} = - btl_condition:ataxia_set_remaining_uses - ( - UpdatedRemainingUses, - Condition - ), - { - UpdatedCondition, - {update, ConditionUpdate}, - [{S1Character, CharacterUpdate}] - } - end - end. - --spec handle_trigger - ( - btl_condition:trigger(), - btl_condition:type() - ) - -> btl_condition:trigger(). -handle_trigger ({TriggerType, S0TriggerData}, Condition) -> - {TargetIX, _Amount} = btl_condition:get_parameters(Condition), - - case - ( - (TriggerType == ?CONDITION_TRIGGER_START_OF_OWN_ATTACK) - or (TriggerType == ?CONDITION_TRIGGER_END_OF_OWN_ATTACK) - or (TriggerType == ?CONDITION_TRIGGER_START_OF_OWN_HIT) - or (TriggerType == ?CONDITION_TRIGGER_END_OF_OWN_HIT) - or (TriggerType == ?CONDITION_TRIGGER_OWN_DODGE) - or (TriggerType == ?CONDITION_TRIGGER_OWN_CRITICAL) - or (TriggerType == ?CONDITION_TRIGGER_OWN_DOUBLE_HIT) - or (TriggerType == ?CONDITION_TRIGGER_OWN_DAMAGE) - or (TriggerType == ?CONDITION_TRIGGER_START_OF_TARGET_ATTACK) - or (TriggerType == ?CONDITION_TRIGGER_END_OF_TARGET_ATTACK) - or (TriggerType == ?CONDITION_TRIGGER_START_OF_TARGET_HIT) - or (TriggerType == ?CONDITION_TRIGGER_END_OF_TARGET_HIT) - or (TriggerType == ?CONDITION_TRIGGER_TARGET_DODGE) - or (TriggerType == ?CONDITION_TRIGGER_TARGET_CRITICAL) - or (TriggerType == ?CONDITION_TRIGGER_TARGET_DOUBLE_HIT) - or (TriggerType == ?CONDITION_TRIGGER_TARGET_DAMAGE) - ) - of - false -> {TriggerType, S0TriggerData}; - true -> - {Char0IX, Char0, Char1IX, Char1} = TriggerData, - if - (Char0IX == TargetIX) -> - {_UpdatedCondition, _UpdateOrder, UpdatedChar} = - apply_to_character(Condition, Char0), - - { - TriggerType, - { - Char0IX - UpdatedChar, - Char1IX, - Char1 - } - }; - - (Char1IX == TargetIX) -> - {_UpdatedCondition, _UpdateOrder, UpdatedChar} = - apply_to_character(Condition, Char0), - - { - TriggerType, - { - Char0IX - Char0, - Char1IX, - UpdatedChar - } - }; - - true -> {TriggerType, S0TriggerData} - end - end. - -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -%% EXPORTED FUNCTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% --spec apply - ( - btl_condition:trigger(), - btl_condition:type(), - btl_character_turn_update:type() - ) -> - { - btl_condition:type(), - btl_condition:update_action(), - btl_condition:trigger(), - btl_character_turn_update:type() - }. -apply (S0Trigger, Condition, Update) -> - S1Trigger = handle_trigger(S0Trigger, Condition), - - Parameters, - Condition, - Update) -> - {TargetIX, Amount} = - case btl_condition:get_parameters(Condition) of - {StoredTargetIX, StoredAmount} -> {StoredTargetIX, StoredAmount}; - Other -> error({condition, parameter, Other}) - end, - {[{Condition, []}], Update}. diff --git a/src/battle/mechanic/condition/btl_cond_heal.erl b/src/battle/mechanic/condition/btl_cond_heal.erl new file mode 100644 index 0000000..bbbbc96 --- /dev/null +++ b/src/battle/mechanic/condition/btl_cond_heal.erl @@ -0,0 +1,125 @@ +-module(btl_cond_heal). + +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +%% TYPES %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +-include("tacticians/conditions.hrl"). + +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +%% EXPORTS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +-export +( + [ + apply/3 + ] +). + +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +%% LOCAL FUNCTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +-spec apply_to_character + ( + btl_condition:type(), + btl_character:type() + ) + -> + { + btl_condition:type(), + btl_condition:update_action(), + [{btl_character:type(), ataxic:basic()}] + }. +apply_to_character (Condition, S0Character) -> + {_TargetIX, Amount} = btl_condition:get_parameters(Condition), + + case btl_character:get_is_alive(S0Character) of + false -> {Condition, none, []}; + true -> + RemainingUses = btl_condition:get_remaining_uses(Condition), + CurrentHealth = btl_character:get_current_health(S0Character), + MaxHealth = + shr_attributes:get_health + ( + shr_character:get_attributes + ( + btl_character:get_base_character(S0Character) + ) + ), + + UpdatedHealth = min(MaxHealth, (CurrentHealth + Amount)), + UpdatedRemainingUses = + + {S1Character, CharacterUpdate} = + btl_character:ataxia_set_current_health(UpdatedHealth, S0Character), + + if + (RemainingUses == -1) -> + { + Condition, + none, + [{S1Character, CharacterUpdate}] + }; + + (RemainingUses == 1) -> + { + btl_condition:set_remaining_uses + ( + UpdatedRemainingUses, + Condition + ), + remove, + [{S1Character, CharacterUpdate}] + }; + + (RemainingUses == 0) -> + { + Condition, + remove, + [{S1Character, CharacterUpdate}] + }; + + true -> + {UpdatedCondition, ConditionUpdate} = + btl_condition:ataxia_set_remaining_uses + ( + UpdatedRemainingUses, + Condition + ), + { + UpdatedCondition, + {update, ConditionUpdate}, + [{S1Character, CharacterUpdate}] + } + end + end. + +-spec handle_context + ( + shr_condition:context(), + btl_condition:type() + ) + -> shr_condition:context(). +handle_context ({Trigger, ReadOnly, VolatileData}, Condition) -> + {_TargetIX, _Amount} = btl_condition:get_parameters(Condition), + {Trigger, ReadOnly, VolatileData}. + +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +%% EXPORTED FUNCTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +-spec apply + ( + shr_condition:context(), + btl_condition:type(), + btl_character_turn_update:type() + ) -> + { + shr_condition:context(), + btl_character_turn_update:type(), + btl_condition:update_action() + }. +apply (S0Context, S0Condition, S0Update) -> + S1Context = handle_context(S0Context, S0Condition), + + {TargetIX, Amount} = btl_condition:get_parameters(S0Condition), + + {S1Context, S0Update, none}. diff --git a/src/battle/struct/btl_character.erl b/src/battle/struct/btl_character.erl index 6dffd6b..7771b1a 100644 --- a/src/battle/struct/btl_character.erl +++ b/src/battle/struct/btl_character.erl @@ -7,7 +7,7 @@ -define(IS_ACTIVE_FIELD, <<"ena">>). -define(IS_DEFEATED_FIELD, <<"dea">>). -define(BASE_CHAR_FIELD, <<"bas">>). --define(CONDITION_FIELD, <<"con">>). +-define(CONDITIONS_FIELD, <<"con">>). %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %% TYPES %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% @@ -25,7 +25,7 @@ is_active :: boolean(), is_defeated :: boolean(), base :: shr_character:unresolved(), - conditions :: list(btl_condition:type()) + conditions :: orddict:orddict(non_neg_integer(), btl_condition:type()) } ). @@ -40,7 +40,7 @@ is_active :: boolean(), is_defeated :: boolean(), base :: shr_character:type(), - conditions :: list(btl_condition:type()) + conditions :: orddict:orddict(non_neg_integer(), btl_condition:type()) } ). @@ -105,7 +105,7 @@ -export ( [ - new/4, + new/5, resolve/2, is_unresolved/1, to_unresolved/1, @@ -194,8 +194,8 @@ get_base_character (#btl_char{ base = R }) -> R; get_base_character (#btl_char_ref{ base = R }) -> R. -spec get_conditions - (type()) -> list(btl_condition:type()); - (unresolved()) -> list(btl_conditions:type()). + (type()) -> orddict:orddict(non_neg_integer(), btl_condition:type()); + (unresolved()) -> orddict:orddict(non_neg_integer(), btl_conditions:type()). get_conditions (#btl_char{ conditions = R }) -> R; get_conditions (#btl_char_ref{ conditions = R }) -> R. @@ -204,11 +204,11 @@ get_conditions (#btl_char_ref{ conditions = R }) -> R. shr_condition:trigger(), either() ) - -> list(btl_condition:type()). + -> orddict:orddict(non_neg_integer(), btl_condition:type()). get_conditions_on (Trigger, Char) -> - lists:filter + orddict:filter ( - fun (Condition) -> + fun (_IX, Condition) -> btl_condition:triggers_on(Trigger, Condition) end, get_conditions(Char) @@ -448,8 +448,16 @@ ataxia_set_base_character (NewBaseCharacter, Char) -> ). -spec set_conditions - (list(btl_condition:type()), type()) -> type(); - (list(btl_condition:type()), unresolved()) -> unresolved(). + ( + orddict:orddict(non_neg_integer(), btl_condition:type()), + type() + ) + -> type(); + ( + orddict:orddict(non_neg_integer(), btl_condition:type()), + unresolved() + ) + -> unresolved(). set_conditions (Conditions, Char) when is_record(Char, btl_char) -> Char#btl_char{ conditions = Conditions }; set_conditions (Conditions, Char) when is_record(Char, btl_char_ref) -> @@ -458,13 +466,13 @@ set_conditions (Conditions, Char) when is_record(Char, btl_char_ref) -> -spec ataxia_set_conditions ( - list(btl_condition:type()), + orddict:orddict(non_neg_integer(), btl_condition:type()), ataxic:basic(), type() ) -> {type(), ataxic:basic()}; ( - list(btl_condition:type()), + orddict:orddict(non_neg_integer(), btl_condition:type()), ataxic:basic(), unresolved() ) -> {unresolved(), ataxic:basic()}. @@ -479,8 +487,16 @@ ataxia_set_conditions (Conditions, Update, Char) -> }. -spec ataxia_set_conditions - (list(btl_condition:type()), type()) -> {type(), ataxic:basic()}; - (list(btl_condition:type()), unresolved()) -> {unresolved(), ataxic:basic()}. + ( + orddict:orddict(non_neg_integer(), btl_condition:type()), + type() + ) + -> {type(), ataxic:basic()}; + ( + orddict:orddict(non_neg_integer(), btl_condition:type()), + unresolved() + ) + -> {unresolved(), ataxic:basic()}. ataxia_set_conditions (Conditions, Char) -> ataxia_set_conditions ( diff --git a/src/battle/struct/btl_condition.erl b/src/battle/struct/btl_condition.erl index 24ef084..fee7279 100644 --- a/src/battle/struct/btl_condition.erl +++ b/src/battle/struct/btl_condition.erl @@ -5,7 +5,12 @@ %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -include("tacticians/conditions.hrl"). --type update_action() :: (none, remove, {update, ataxic:basic()}). +-type update_action() :: + ( + none + | remove + | {update, type(), ataxic:basic()} + ). -record ( @@ -61,7 +66,9 @@ [ triggers_on/2, apply/3, - recursive_apply/3 + recursive_apply/3, + apply_updates/2, + ataxia_apply_updates/2 ] ). @@ -234,47 +241,117 @@ get_parameters_field () -> #btl_cond.parameters. shr_condition:context(), btl_character_turn_update:type() ) - -> {shr_condition:context(), btl_character_turn_update:type()}. -apply (S0Condition, S0Context, S0Update) -> - Module = shr_condition_selector:get_module(get_category(S0Condition)), - - {S1Condition, UpdateAction, S1Context, S1Update} = - erlang:apply(Module, apply, [S0Context, S0Condition, S0Update]), + -> + { + shr_condition:context(), + btl_character_turn_update:type(), + update_action() + }. +apply (Condition, S0Context, S0Update) -> + Module = shr_condition_selector:get_module(get_category(Condition)), - case UpdateAction of - none -> {S1Context, S1Update}; - remove -> - % TODO - {S1Context, S1Update}; + {S1Context, S1Update, UpdateAction} = + erlang:apply(Module, apply, [S0Context, Condition, S0Update]), - {update, ConditionUpdate} -> - % TODO - {S1Context, S1Update} + {S1Context, S1Update, UpdateAction}. - end. -spec recursive_apply ( - list(type()), + orddict:orddict(IndexType, type()), shr_condition:context(), btl_character_turn_update:type() ) - -> {shr_condition:context(), btl_character_turn_update:type()}. + -> + { + shr_condition:context(), + btl_character_turn_update:type(), + list({IndexType, update_action()}) + }. recursive_apply (Conditions, S0Context, S0Update) -> - [LastContext, LastUpdate] = - lists:foldl + {[LastContext, LastUpdate], AllUpdateActions} = + orddict:fold ( - fun (Condition, Parameters) -> - {NextContext, NextUpdate} = + fun (IX, Condition, {Parameters, UpdateActions}) -> + {NextContext, NextUpdate, UpdateAction} = erlang:apply(btl_condition, apply, [Condition|Parameters]), - [NextContext, NextUpdate] + { + [NextContext, NextUpdate], + case UpdateAction of + none -> UpdateActions; + _ -> [{IX, UpdateAction}|UpdateActions] + end + } end, - [S0Context, S0Update], + [S0Context, S0Update, []], Conditions ), - {LastContext, LastUpdate}. + {LastContext, LastUpdate, AllUpdateActions}. + +-spec apply_updates + ( + list({IndexType, update_action()}), + orddict:orddict(IndexType, type()) + ) + -> orddict:orddict(IndexType, type()). +apply_updates (Updates, Conditions) -> + lists:foldl + ( + fun ({IX, Update}, CurrentConditions) -> + case Update of + none -> CurrentConditions; + remove -> orddict:erase(IX, CurrentConditions); + {update, Val, _Ataxic} -> orddict:store(IX, Val, CurrentConditions) + end + end, + Conditions, + Updates + ). + +-spec ataxia_apply_updates + ( + list({IndexType, update_action()}), + orddict:orddict(IndexType, type()) + ) + -> {orddict:orddict(IndexType, type()), ataxic:basic()}. +ataxia_apply_updates (Updates, Conditions) -> + {FinalConditions, AtaxicSequence} = + lists:foldl + ( + fun ({IX, Update}, {CurrentConditions, AtaxicUpdates}) -> + case Update of + none -> {CurrentConditions, AtaxicUpdates}; + remove -> + { + orddict:erase(IX, CurrentConditions), + [ + ataxic:apply_function + ( + orddict, + erase, + [ataxic:constant(IX), ataxic:current_value()] + ) + |AtaxicUpdates + ] + }; + + {update, Val, Ataxic} -> + { + orddict:store(IX, Val, CurrentConditions), + [ + ataxic_sugar:update_orddict_element(IX, Ataxic) + |AtaxicUpdates + ] + } + end + end, + Conditions, + Updates + ), + + {FinalConditions, ataxic:sequence(AtaxicSequence)}. -spec encode (type()) -> {list({binary(), any()})}. -encode (Condition) -> {[]} % TODO. +encode (Condition) -> {[]}. % TODO -- cgit v1.2.3-70-g09d2