Для управления сложными взаимодействиями, такими как несколько фаз боя с разными состояниями монстра, лучший подход — использовать шаблон проектирования "Состояние" (State Pattern). + t+ D8 o- [0 |
0 n2 }- T# g5 g
Этот шаблон позволяет разделить логику поведения объекта на разные состояния и управлять ими более гибко, избегая перегрузки основного класса монстра.
# R" H& o0 D2 ]+ J& V
9 h) v c; O. f7 h1 AШаг 1: Создание интерфейса для состояний монстраПервый шаг — создать интерфейс, который будет представлять разные состояния монстра. Этот интерфейс определяет метод, который будет вызываться в зависимости от текущего состояния.9 L2 i6 a3 X0 [
3 H/ y4 C, S# ]# D! U5 G
- // Пакет для состояний монстра
n+ `0 h* `# [ - package org.l2jmobius.gameserver.model.actor.state;" d& d& E2 M4 V
3 `/ F8 q/ U8 c" e. p- // Интерфейс, представляющий состояния монстра
; @( u5 U/ t' F( i. K' T - public interface MonsterState {
4 H! v5 c( q! ?5 @2 B/ _ - void handleState(Monster monster);& _* ?, G0 b* ~% f/ u3 z
- }
- S) _; c$ Y* @+ J I
Скопировать код # I# o! V1 [# H1 f
Шаг 2: Реализация различных состоянийТеперь создадим классы для каждого состояния: например, InitialState, AggressiveState и FinalState. + b" K. g0 g$ o
) o( j8 `4 \ ?8 u+ \) t& k
Эти состояния будут реализовывать интерфейс MonsterState и определять поведение монстра на разных этапах боя.
! A& q# ~, d9 r% }7 x2 p5 \9 B" N/ t+ g1 X& b4 ~7 l
Класс для начального состояния монстра:; A% R1 P! u" b9 j2 F; Q4 {% e# n
- // Пакет org.l2jmobius.gameserver.model.actor.state. [% P1 J3 X- Y. j5 i" V" l
- package org.l2jmobius.gameserver.model.actor.state;7 _: Z* e+ t" s+ p. ]* x& A
6 p( f' G$ {# `4 g- s- import org.l2jmobius.gameserver.model.actor.Monster;/ c, [1 ?% g+ M# i8 Y% ]+ ?% T# \* u
- 6 _& d# m! V/ b& @$ t" v
- public class InitialState implements MonsterState {
& L+ s9 g& _# S$ D) @ - @Override3 d4 a5 M+ R1 n5 [/ a$ l3 {; x
- public void handleState(Monster monster) {
' Q+ s I; V5 v0 g) C! M - // Начальная фаза боя5 q. @3 w/ J+ P
- System.out.println(monster.getName() + " начинает бой с обычной атакой.");( ]* c0 i6 ?7 p1 F* { Y
- }4 V: y, t+ w; d% Z
- }
6 {0 T; D- N; w0 {
Скопировать код Класс для агрессивного состояния монстра:
9 B6 } G7 k4 Z( ]- // Пакет org.l2jmobius.gameserver.model.actor.state& y9 Y! w; q, N A+ v
- package org.l2jmobius.gameserver.model.actor.state;: K. t5 I; O* H9 I! d
- . m& j: P' _8 ?) g3 c( Q
- import org.l2jmobius.gameserver.model.actor.Monster;9 a0 B1 ^: I/ E, S0 Z
- 7 A* n& d, h; T9 L0 {3 w
- public class AggressiveState implements MonsterState {
& t& e# D4 F+ J/ [1 @! _7 r - @Override, k! s/ q* c7 w
- public void handleState(Monster monster) {
7 K) Q# k( G2 \; E' D! ? - // Агрессивная фаза боя
7 v' ^8 x* E6 x R" q - System.out.println(monster.getName() + " становится агрессивным! Атаки усиливаются.");3 @( c% r- O2 N( V" I/ J
- monster.setAttackPower(monster.getAttackPower() * 1.5); // Увеличиваем силу атаки
+ u4 p. M) W. y4 S7 S* O7 K - }" `' B+ [9 v6 h, v* I* T6 a' h
- }
- d, J( P( G7 M5 V* l: t8 m: D
Скопировать код Класс для финального состояния монстра:
& k4 K0 F) V3 ^- // Пакет org.l2jmobius.gameserver.model.actor.state5 L* _7 F! O8 u6 q
- package org.l2jmobius.gameserver.model.actor.state;0 F* B) P: O( z+ h, g( ^5 }$ y
! t& D* @. o# J- import org.l2jmobius.gameserver.model.actor.Monster;
! Q! N$ p" C0 c0 B! o9 ~+ T! ]' X9 H
5 T5 f1 _8 K! ^4 Y6 o- public class FinalState implements MonsterState {# }# ?; h: J. n% L# o
- @Override _( y' y( O) c* ^2 Y& i5 X j, B7 I4 `) A
- public void handleState(Monster monster) {% W9 t( e8 F, c; I5 q
- // Финальная фаза боя% `2 A9 Q9 ]" A
- System.out.println(monster.getName() + " готовится к финальной атаке!"); ?5 } ?3 |9 n: \& A
- monster.setAttackPower(monster.getAttackPower() * 2); // Максимальная сила атаки# g6 ^8 h4 x- ?
- }
; ` H1 p% ?3 M) M& ]; T0 z- [ - }# @& [, H( L3 _- k! c/ t
Скопировать код 5 {3 \7 t- T4 T/ r' M
Шаг 3: Изменение класса MonsterЧтобы монстр мог переключаться между состояниями, нам нужно обновить класс Monster. В этой сборке L2J_Mobius, классы для игровых объектов, таких как монстры, находятся в пакете org.l2jmobius.gameserver.model.actor.
) O t$ s6 a# \ N* X/ R% ?- // Пакет org.l2jmobius.gameserver.model.actor
/ f4 s7 m: U# [8 v6 k. g9 Q* q8 r - package org.l2jmobius.gameserver.model.actor;( \7 l i( p. d! `% F
- + o6 ]* A; |, d- ]& P. h
- import org.l2jmobius.gameserver.model.actor.state.MonsterState;3 E/ R$ b, q3 x1 N
- import org.l2jmobius.gameserver.model.actor.state.InitialState;
6 ?6 a2 x7 o. L, | - 1 e5 }& Z& m* n3 i( `
- public class Monster extends Creature {
* b% z( L( q, S1 W% a - private String name;2 M5 a1 P6 B: R: {
- private double attackPower;: e- i0 p( R& Y& G6 I
- private MonsterState state; // Текущее состояние монстра! F( B/ g2 X6 o% l6 x6 r
2 \4 c- a; f, z& @+ u% a- // Конструктор монстра- v4 }$ P3 C g9 r) L
- public Monster(String name, double attackPower) {
6 i* o/ b5 {- o/ F* y - this.name = name;
; t2 U5 n1 t# m6 g2 ~' k9 @& x - this.attackPower = attackPower;
7 U! `/ \7 F5 G% Y# S% D+ [' i - this.state = new InitialState(); // Устанавливаем начальное состояние
$ K) H$ J8 P& G4 N% j - }
0 W: J5 H3 x9 I
7 l+ _/ n7 A3 V- // Метод для смены состояния
4 ~, J9 d; _4 d$ f& b - public void setState(MonsterState newState) {6 L c, E5 d) y. S' D0 V
- this.state = newState;1 |, c& Z) l9 C- m$ ? `/ n X$ n7 ]
- }8 [0 M X3 F2 l) O* y7 a
1 ] i2 J4 F: ?/ g! R/ ?- // Выполнение действий на основе текущего состояния
4 s* J! ] _+ T# v* u# X# j - public void executeState() {
P2 W4 A; O" A$ s - state.handleState(this);7 t) H s" a6 j! t% s
- }# _8 W4 n% {- `6 {& T1 \& U" N+ n/ ~+ \
: ^" W5 c1 C8 U! M9 R& |- // Геттеры и сеттеры8 w' X! b% b$ \) g
- public String getName() {
{, d7 [4 w0 i7 W4 I" S( V& V - return name;. [* n+ }# u* B
- }
' s+ u" V0 M! q: f) S/ M8 e7 f( l
2 ~' K6 |6 g, \; i9 Q/ f8 a9 w- public double getAttackPower() {0 y) G$ ^7 O) R7 R3 ~# d
- return attackPower;
7 G: a& ~$ k8 r$ e5 s6 F/ m - }
. ~, {6 I7 M7 |/ M1 d
4 ?3 N8 R! J( q8 D' k1 O \$ S2 W- public void setAttackPower(double attackPower) {$ n$ h# `( P; S* ^: V9 A
- this.attackPower = attackPower;
3 e. s& P4 Y- G$ X6 | - }
. D' j( z; c8 }0 ~ f - }
) z% d/ x+ O+ {4 ?0 A( t. @
Скопировать код ( i8 x C! R; i+ l3 t% D9 |) O# ~% |
Шаг 4: Симуляция боя с фазамиТеперь мы можем протестировать логику боя с переключением состояний монстра.
/ h. b5 o$ c& [% u5 h, i
% S7 I, U& A0 d/ V9 r% _1 `- // Пакет org.l2jmobius.gameserver.model.battle; |7 \/ J# z6 X+ O# q
- package org.l2jmobius.gameserver.model.battle;
3 O! i7 X+ O, ]8 z4 H0 Q" j
* e1 s3 |3 V. v+ i- import org.l2jmobius.gameserver.model.actor.Monster;9 a1 L; x: Y6 R/ Z
- import org.l2jmobius.gameserver.model.actor.state.AggressiveState;
0 p* P2 ^' X& h+ p2 b- x% u - import org.l2jmobius.gameserver.model.actor.state.FinalState;0 `% A w6 W' h# {: t
* H' ~ r/ n% E' E0 F+ k, V- public class BattleSimulation {
, f, u! Z9 d2 H2 D% ]4 v9 m - public static void main(String[] args) {
: o$ R% X5 s' ^0 U- d$ D& s - // Создаем монстра с начальной атакой0 z" r8 V! p" k% ~- y
- Monster monster = new Monster("Дракон", 100);
1 n6 a I) N' Y, C) x7 f
1 J6 {+ Z) d/ f$ L$ R% |- // Начальная фаза) a" m. B& o( G" W9 B* Z
- monster.executeState();, D) R% [, k$ V0 O
1 Y3 |$ K( @0 o/ D- // Переход в агрессивную фазу
# E% f/ I2 P8 c1 \$ b4 c% L - monster.setState(new AggressiveState());
0 e: n% B8 a/ a - monster.executeState();; i% J6 l/ d. N9 x2 v# {$ Z$ ^' p
- " m& U% w$ y6 A$ C; i: ]+ Q8 L$ ?
- // Финальная фаза
" U, v$ X' |! z' p, P( X: i& ^- C - monster.setState(new FinalState());' `. ^" m0 [; k
- monster.executeState();
4 O9 D; T) H5 d2 o. G3 ]0 ]' ^ - }
N* @9 E0 B2 ?8 c' ?$ \ - }! l# v; D, z5 ?
Скопировать код
5 N: _& v) R+ R- f/ ^6 q& SКомментарии по структуре пакетов и классов:
# d# g+ g! Q3 S" Z- Пакет org.l2jmobius.gameserver.model.actor: содержит основные игровые сущности, такие как Monster.
- Пакет org.l2jmobius.gameserver.model.actor.state: отвечает за реализацию состояний для объектов, таких как монстры.
- Пакет org.l2jmobius.gameserver.model.battle: может содержать примеры взаимодействий, такие как симуляция боевых сценариев.$ r. i4 z3 ^; D: Z+ [
ЗаключениеШаблон "Состояние" позволяет легко управлять фазами боя и не перегружать основной класс монстра. Это делает логику боевых сценариев более гибкой и масштабируемой. В будущем, если появятся новые фазы или состояния, их можно будет легко добавить, не изменяя основной код., H, [9 K1 o4 B* }5 i
Если появятся дополнительные вопросы по реализации или структуре классов, буду рада помочь!
$ d, ^! l B0 o' w! X+ E7 @8 T! ]; J* x0 _
( i+ ?" N+ i6 |$ j
; |% w; v- h# P8 P+ ^
( P! k$ F2 s. `$ o* ~. L, y4 V0 ^- L2 g" u
) b3 |$ [6 a2 b+ V( w& G( t: R
0 n, |% O6 `- Y/ [, d1 f; f
# C4 f$ h7 j/ A" K: l
( ?/ ^9 R' M: q* {& U6 X; _9 A
# n* M5 I4 q: G" Q( v% b" o6 P. T- z1 D3 L9 X
) M9 f) p* ^% H! E0 {% G* g; A6 B2 t# F/ {9 h; R
6 H5 P% T- m+ D8 }- N: q" O' m1 z |