Skip to content

Commit

Permalink
feat(ai): Add giver percent life simulator
Browse files Browse the repository at this point in the history
  • Loading branch information
vincent4vx committed Dec 2, 2023
1 parent fd73c80 commit 3009136
Show file tree
Hide file tree
Showing 3 changed files with 157 additions and 0 deletions.
2 changes: 2 additions & 0 deletions src/main/java/fr/quatrevieux/araknemu/game/GameModule.java
Original file line number Diff line number Diff line change
Expand Up @@ -148,6 +148,7 @@
import fr.quatrevieux.araknemu.game.fight.ai.simulation.effect.ArmorSimulator;
import fr.quatrevieux.araknemu.game.fight.ai.simulation.effect.DamageSimulator;
import fr.quatrevieux.araknemu.game.fight.ai.simulation.effect.FixedCasterDamage;
import fr.quatrevieux.araknemu.game.fight.ai.simulation.effect.GivePercentLifeSimulator;
import fr.quatrevieux.araknemu.game.fight.ai.simulation.effect.HealOrMultiplyDamageSimulator;
import fr.quatrevieux.araknemu.game.fight.ai.simulation.effect.HealSimulator;
import fr.quatrevieux.araknemu.game.fight.ai.simulation.effect.InvokeDoubleSimulator;
Expand Down Expand Up @@ -968,6 +969,7 @@ private void configureServices(ContainerConfigurator configurator) {

// Heal
simulator.register(108, new HealSimulator());
simulator.register(90, new GivePercentLifeSimulator());

// Misc
simulator.register(950, new SetStateSimulator()
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
/*
* This file is part of Araknemu.
*
* Araknemu is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Araknemu is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Araknemu. If not, see <https://www.gnu.org/licenses/>.
*
* Copyright (c) 2017-2023 Vincent Quatrevieux
*/

package fr.quatrevieux.araknemu.game.fight.ai.simulation.effect;

import fr.arakne.utils.value.Interval;
import fr.quatrevieux.araknemu.game.fight.ai.AI;
import fr.quatrevieux.araknemu.game.fight.ai.simulation.CastSimulation;
import fr.quatrevieux.araknemu.game.fight.castable.CastScope;
import fr.quatrevieux.araknemu.game.fight.castable.effect.EffectValue;
import fr.quatrevieux.araknemu.game.fight.fighter.FighterData;
import fr.quatrevieux.araknemu.game.fight.map.BattlefieldCell;

/**
* Simulate the "give percent life" effect
* The simulator will compute the damage to the caster, and add the heal to the targets
*
* @see fr.quatrevieux.araknemu.game.fight.castable.effect.handler.heal.GivePercentLifeHandler The simulated effect
*/
public final class GivePercentLifeSimulator implements EffectSimulator {
@Override
public void simulate(CastSimulation simulation, AI ai, CastScope.EffectScope<? extends FighterData, ? extends BattlefieldCell> effect) {
final FighterData caster = ai.fighter();
final int heal = EffectValue.create(effect.effect(), caster, caster).value() * caster.life().current() / 100;

simulation.addDamage(Interval.of(heal), caster);

for (FighterData target : effect.targets()) {
if (!target.equals(caster)) {
simulation.addHeal(Interval.of(heal), target);
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
/*
* This file is part of Araknemu.
*
* Araknemu is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Araknemu is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with Araknemu. If not, see <https://www.gnu.org/licenses/>.
*
* Copyright (c) 2017-2023 Vincent Quatrevieux
*/

package fr.quatrevieux.araknemu.game.fight.ai.simulation.effect;

import fr.quatrevieux.araknemu.data.value.EffectArea;
import fr.quatrevieux.araknemu.game.fight.Fight;
import fr.quatrevieux.araknemu.game.fight.FightBaseCase;
import fr.quatrevieux.araknemu.game.fight.ai.FighterAI;
import fr.quatrevieux.araknemu.game.fight.ai.action.logic.NullGenerator;
import fr.quatrevieux.araknemu.game.fight.ai.simulation.CastSimulation;
import fr.quatrevieux.araknemu.game.fight.castable.CastScope;
import fr.quatrevieux.araknemu.game.fight.castable.effect.Element;
import fr.quatrevieux.araknemu.game.fight.fighter.Fighter;
import fr.quatrevieux.araknemu.game.fight.fighter.player.PlayerFighter;
import fr.quatrevieux.araknemu.game.fight.map.FightCell;
import fr.quatrevieux.araknemu.game.spell.Spell;
import fr.quatrevieux.araknemu.game.spell.SpellConstraints;
import fr.quatrevieux.araknemu.game.spell.effect.SpellEffect;
import fr.quatrevieux.araknemu.game.spell.effect.area.CellArea;
import fr.quatrevieux.araknemu.game.spell.effect.area.CircleArea;
import fr.quatrevieux.araknemu.game.spell.effect.target.SpellEffectTarget;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.mockito.Mockito;

import static org.junit.jupiter.api.Assertions.*;

class GivePercentLifeSimulatorTest extends FightBaseCase {
private Fight fight;
private PlayerFighter fighter;
private Fighter target;
private FighterAI ai;

@Override
@BeforeEach
public void setUp() throws Exception {
super.setUp();

fight = createFight();
fighter = player.fighter();
target = other.fighter();

fighter.init();
target.init();

target.life().alter(target, -30);

ai = new FighterAI(fighter, fight, new NullGenerator());
}

@Test
void simulateWithoutTarget() {
CastSimulation simulation = simulate();

assertEquals(0, simulation.enemiesLife());
assertEquals(-29, simulation.selfLife());
}

@Test
void simulateWithTarget() {
fighter.move(fight.map().get(182));
target.move(fight.map().get(196));

CastSimulation simulation = simulate();

assertEquals(29, simulation.enemiesLife());
assertEquals(-29, simulation.selfLife());
}

private CastSimulation simulate() {
SpellEffect effect = Mockito.mock(SpellEffect.class);
Spell spell = Mockito.mock(Spell.class);
SpellConstraints constraints = Mockito.mock(SpellConstraints.class);

Mockito.when(effect.min()).thenReturn(10);
Mockito.when(effect.area()).thenReturn(new CircleArea(new EffectArea(EffectArea.Type.CIRCLE, 1)));
Mockito.when(effect.target()).thenReturn(SpellEffectTarget.DEFAULT);
Mockito.when(spell.constraints()).thenReturn(constraints);
Mockito.when(constraints.freeCell()).thenReturn(false);

CastSimulation simulation = new CastSimulation(spell, fighter, fighter.cell());

CastScope<Fighter, FightCell> scope = makeCastScope(fighter, spell, effect, fighter.cell());
new GivePercentLifeSimulator().simulate(simulation, ai, scope.effects().get(0));

return simulation;
}
}

0 comments on commit 3009136

Please sign in to comment.