summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/balancer/blc_distribution.erl59
-rw-r--r--src/balancer/struct/blc_armor.erl134
-rw-r--r--src/shared/struct/shr_attributes.erl10
-rw-r--r--src/shared/util/shr_lists_util.erl30
4 files changed, 228 insertions, 5 deletions
diff --git a/src/balancer/blc_distribution.erl b/src/balancer/blc_distribution.erl
new file mode 100644
index 0000000..2e8a141
--- /dev/null
+++ b/src/balancer/blc_distribution.erl
@@ -0,0 +1,59 @@
+-module(blc_distribution).
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% TYPES %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% EXPORTS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+-export
+(
+ [
+ generate/2
+ ]
+).
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% LOCAL FUNCTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+-spec generate_internals
+ (
+ non_neg_integer(),
+ list(list(0..100)),
+ list(0..100)
+ )
+ -> list(list(0..100)).
+generate_internals (0, CurrentResult, _Sequence) ->
+ CurrentResult;
+generate_internals (N, CurrentResult, Sequence) ->
+ generate_internals
+ (
+ (N - 1),
+ lists:filter
+ (
+ fun (E) -> (lists:sum(E) =< 100) end,
+ shr_lists_util:product
+ (
+ fun (L, E) ->
+ [E|L]
+ end,
+ CurrentResult,
+ Sequence
+ )
+ ),
+ Sequence
+ ).
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%% EXPORTED FUNCTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+-spec generate (non_neg_integer(), 0..100) -> list(list(0..100)).
+generate (0, _Step) -> [];
+generate (Elements, Step) ->
+ Sequence = lists:seq(0, 100, Step),
+ generate_internals
+ (
+ (Elements - 1),
+ lists:map(fun (E) -> [E] end, Sequence),
+ Sequence
+ ).
diff --git a/src/balancer/struct/blc_armor.erl b/src/balancer/struct/blc_armor.erl
index cc23415..0c642e1 100644
--- a/src/balancer/struct/blc_armor.erl
+++ b/src/balancer/struct/blc_armor.erl
@@ -1,6 +1,7 @@
-module(blc_armor).
-include("tacticians/attributes.hrl").
+-include("tacticians/damage_types.hrl").
-define
(
@@ -75,7 +76,8 @@
(
[
new/1,
- get_remaining_points/1
+ get_remaining_points/1,
+ generate/1
]
).
@@ -124,6 +126,17 @@ increase_attribute_by (Attribute, S0Amount, Armor) ->
}
end.
+-spec get_max_attribute_ratio (shr_attributes:meta_enum()) -> float().
+get_max_attribute_ratio (Attribute) ->
+ {AttMin, _AttDef, AttMax, AttCost} = blc_attribute:get_info(Attribute),
+
+ Contrib = (AttCost * (AttMax - AttMin)),
+
+ case (Contrib == 0) of
+ true -> 0.0;
+ false -> (?SPENDABLE_ARMOR_POINTS / Contrib) * 100.0
+ end.
+
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% EXPORTED FUNCTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -313,3 +326,122 @@ increase_defense_score_for (GivenPoints, Armor) ->
-spec get_remaining_points (type()) -> non_neg_integer().
get_remaining_points (Armor) -> Armor#proto_armor.remaining_points.
+
+-spec generate (non_neg_integer()) -> list(type()).
+generate (Step) ->
+ MaxDamageModifier = get_max_attribute_ratio(?ATTRIBUTE_DAMAGE_MODIFIER),
+ MaxDodgeChance = get_max_attribute_ratio(?ATTRIBUTE_DODGE_CHANCE),
+ MaxMovementPoints = get_max_attribute_ratio(?ATTRIBUTE_MOVEMENT_POINTS),
+ MaxHealth = get_max_attribute_ratio(?ATTRIBUTE_HEALTH),
+ MaxDefenseScore = get_max_attribute_ratio(?ATTRIBUTE_DEFENSE_SCORE),
+
+ Distributions = blc_distribution:generate(5, Step),
+ ValidDistributions =
+ lists:filtermap
+ (
+ fun
+ (
+ [
+ DamageModifier,
+ DodgeChance,
+ MovementPoints,
+ Health,
+ DefenseScore
+ ]
+ ) ->
+ if
+ (DamageModifier > MaxDamageModifier) -> false;
+ (DodgeChance > MaxDodgeChance) -> false;
+ (MovementPoints > MaxMovementPoints) -> false;
+ (Health > MaxHealth) -> false;
+ (DefenseScore > MaxDefenseScore) -> false;
+ true ->
+ {
+ true,
+ [
+ {?ATTRIBUTE_DAMAGE_MODIFIER, DamageModifier},
+ {?ATTRIBUTE_DODGE_CHANCE, DodgeChance},
+ {?ATTRIBUTE_MOVEMENT_POINTS, MovementPoints},
+ {?ATTRIBUTE_HEALTH, Health},
+ {?ATTRIBUTE_DEFENSE_SCORE, DefenseScore}%,
+% {
+% extra,
+% (
+% 100
+% -
+% (
+% DamageModifier
+% + DodgeChance
+% + MovementPoints
+% + Health
+% + DefenseScore
+% )
+% )
+% }
+ ]
+ }
+ end
+ end,
+ Distributions
+ ),
+
+ BaseArmorsCoefs = [{?DAMAGE_TYPE_SLASH, 100}],
+
+ BaseArmor = new(BaseArmorsCoefs),
+ BaseArmors =
+ lists:map
+ (
+ fun (Distribution) ->
+ PointsUsed =
+ lists:map
+ (
+ fun ({Attribute, Percent}) ->
+ {
+ Attribute,
+ trunc((?SPENDABLE_ARMOR_POINTS * Percent) / 100)
+ }
+ end,
+ Distribution
+ ),
+
+ FinalArmor =
+ lists:foldl
+ (
+ fun ({Attribute, Points}, Armor) ->
+ case Attribute of
+ ?ATTRIBUTE_DEFENSE_SCORE ->
+ {ok, NewArmor} =
+ increase_defense_score_for(Points, Armor),
+ NewArmor;
+
+ ?ATTRIBUTE_DODGE_CHANCE ->
+ {ok, NewArmor} =
+ increase_dodge_chance_for(Points, Armor),
+ NewArmor;
+
+ ?ATTRIBUTE_HEALTH ->
+ {ok, NewArmor} =
+ increase_health_for(Points, Armor),
+ NewArmor;
+
+ ?ATTRIBUTE_DAMAGE_MODIFIER ->
+ {ok, NewArmor} =
+ increase_damage_modifier_for(Points, Armor),
+ NewArmor;
+
+ ?ATTRIBUTE_MOVEMENT_POINTS ->
+ {ok, NewArmor} =
+ increase_movement_points_for(Points, Armor),
+ NewArmor
+ end
+ end,
+ BaseArmor,
+ PointsUsed
+ ),
+
+ FinalArmor
+ end,
+ ValidDistributions
+ ),
+
+ BaseArmors.
diff --git a/src/shared/struct/shr_attributes.erl b/src/shared/struct/shr_attributes.erl
index 44d2e04..7928862 100644
--- a/src/shared/struct/shr_attributes.erl
+++ b/src/shared/struct/shr_attributes.erl
@@ -98,11 +98,17 @@ mod_accuracy (Mod, Atts) ->
-spec mod_double_hit_chance (integer(), type()) -> type().
mod_double_hit_chance (Mod, Atts) ->
- Atts#attributes{ double_hit_chance = (Atts#attributes.double_hit_chance + Mod) }.
+ Atts#attributes
+ {
+ double_hit_chance = (Atts#attributes.double_hit_chance + Mod)
+ }.
-spec mod_critical_hit_chance (integer(), type()) -> type().
mod_critical_hit_chance (Mod, Atts) ->
- Atts#attributes{ critical_hit_chance = (Atts#attributes.critical_hit_chance + Mod) }.
+ Atts#attributes
+ {
+ critical_hit_chance = (Atts#attributes.critical_hit_chance + Mod)
+ }.
-spec mod_damage_modifier (integer(), type()) -> type().
mod_damage_modifier (Mod, Atts) ->
diff --git a/src/shared/util/shr_lists_util.erl b/src/shared/util/shr_lists_util.erl
index 0568692..348d002 100644
--- a/src/shared/util/shr_lists_util.erl
+++ b/src/shared/util/shr_lists_util.erl
@@ -11,13 +11,35 @@
[
%%% Gentoo hasn't marked Erlang/OTP 21 as stable yet, but I'd like to
%%% use this function.
- %%% TODO: remove once lists:search/2 is available.
- search/2
+ %%% TODO: remove once lists:search/2 is available.
+ search/2,
+ product/3
]
).
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% LOCAL FUNCTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+-spec product_internals
+ (
+ list(A),
+ list(B),
+ fun((A, B) -> C),
+ list(C)
+ )
+ -> list(C).
+product_internals ([], _ListB, _Fun, Result) ->
+ Result;
+product_internals ([A|Next], ListB, Fun, Result) ->
+ product_internals
+ (
+ Next,
+ ListB,
+ Fun,
+ (
+ lists:map(fun (B) -> Fun(A, B) end, ListB)
+ ++ Result
+ )
+ ).
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% EXPORTED FUNCTIONS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
@@ -30,3 +52,7 @@ search (Pred, [Hd|Tail]) ->
end;
search (Pred, []) when is_function(Pred, 1) ->
false.
+
+-spec product (fun((A, B) -> C), list(A), list(B)) -> list(C).
+product (Fun, ListA, ListB) ->
+ product_internals(ListA, ListB, Fun, []).