Для управления сложными взаимодействиями, такими как несколько фаз боя с разными состояниями монстра, лучший подход — использовать шаблон проектирования "Состояние" (State Pattern). + ~: T1 q! l1 m' Y; P- {
; L7 a ~7 q2 ~3 k. O" e9 B
Этот шаблон позволяет разделить логику поведения объекта на разные состояния и управлять ими более гибко, избегая перегрузки основного класса монстра.
- V9 ^( H! B/ }2 a0 L$ Q+ Z
9 ^' I9 d( i2 W- ^Шаг 1: Создание интерфейса для состояний монстраПервый шаг — создать интерфейс, который будет представлять разные состояния монстра. Этот интерфейс определяет метод, который будет вызываться в зависимости от текущего состояния.$ u& U; J/ o1 }7 B
6 o f( l* N4 }- // Пакет для состояний монстра! k3 {# r+ g2 l$ u p3 {
- package org.l2jmobius.gameserver.model.actor.state;
/ h* E5 B0 s0 b0 i5 D7 x {+ a7 ^
, l) l" ?) E- O& m9 j. h- // Интерфейс, представляющий состояния монстра, X# K4 R) h. z: r. P) w `/ @+ G
- public interface MonsterState {& b4 l2 n" B" F ~/ z& g# S* Y
- void handleState(Monster monster);
& Q/ s- [+ X8 Q9 @. A - }
2 \6 U& b1 n+ v1 {7 |- G p; c
Скопировать код
+ F% j' p1 U$ _* I& nШаг 2: Реализация различных состоянийТеперь создадим классы для каждого состояния: например, InitialState, AggressiveState и FinalState. ) k% K, i; k6 `
5 e: r, ]: c, Z, K" W Z" GЭти состояния будут реализовывать интерфейс MonsterState и определять поведение монстра на разных этапах боя.
4 X# ~: i. b6 E5 e& }
& m1 |, ~, f% i( K: NКласс для начального состояния монстра:+ c3 J% I4 J' z* b( @( ^
- // Пакет org.l2jmobius.gameserver.model.actor.state
$ I+ h6 L( p/ j/ r. T - package org.l2jmobius.gameserver.model.actor.state;
8 \& D) [! `9 p) \( \. x
) \7 }/ k, B9 `& ?# G: O- import org.l2jmobius.gameserver.model.actor.Monster;
) d! ]5 x( F" T$ l; O% f1 R
. B9 ]3 ~+ c. I5 S- public class InitialState implements MonsterState {5 K' \: s8 E9 Z. b5 P
- @Override
) o7 b; I. Y# j1 X' v5 I - public void handleState(Monster monster) {2 C9 g& i/ A) ~) ^
- // Начальная фаза боя, k1 R3 |; L& s- G4 h1 r; }
- System.out.println(monster.getName() + " начинает бой с обычной атакой.");+ H8 n: P3 ?' m
- }2 x: g6 y6 _6 |- t
- }# O5 g( D# k# A
Скопировать код Класс для агрессивного состояния монстра:
) k8 L3 ]6 J3 v, D9 ]- // Пакет org.l2jmobius.gameserver.model.actor.state
6 N7 d- {7 q+ i- D7 D+ D: k; u - package org.l2jmobius.gameserver.model.actor.state;! G: W1 A% E5 r) ~' D8 A4 p
- ' Q( E" P) `4 Y$ S/ L
- import org.l2jmobius.gameserver.model.actor.Monster;
4 c4 B2 S- x- ~$ S4 B2 d
. Z8 q1 ~' Z0 |7 h0 c& Y- public class AggressiveState implements MonsterState {. X0 m" i6 V- R" C
- @Override6 X" M# Y2 O' t8 F7 q; [ h
- public void handleState(Monster monster) {
' P v& G, c/ ~/ s0 f: g7 K - // Агрессивная фаза боя+ S" M' Q( j; r: p& a/ G4 R
- System.out.println(monster.getName() + " становится агрессивным! Атаки усиливаются.");
3 ^% J* H7 G* _) r2 P6 K) r4 I - monster.setAttackPower(monster.getAttackPower() * 1.5); // Увеличиваем силу атаки
2 C3 p; ]% z+ l - }9 S- k( h8 Z2 `" O, N: n
- }- x$ V# S+ s1 G* c, p+ [( H* G1 [" I
Скопировать код Класс для финального состояния монстра:
& v/ c4 }$ c. N7 F9 k- // Пакет org.l2jmobius.gameserver.model.actor.state
% H) H5 K0 L! u3 j, |: S - package org.l2jmobius.gameserver.model.actor.state;
$ O( X9 o% V" N7 {: ~$ B
3 ^# p% ~* j7 K$ S. }- import org.l2jmobius.gameserver.model.actor.Monster;6 u8 y& y- R$ i9 T$ J9 |
|7 v( k3 A9 I0 l+ g- public class FinalState implements MonsterState {
: B" V% g& a0 Q - @Override" x u S/ t$ k/ e+ b
- public void handleState(Monster monster) {9 l- @* u K5 f a& F* t
- // Финальная фаза боя9 G: F" Y6 V+ U! A" U/ k
- System.out.println(monster.getName() + " готовится к финальной атаке!");# A7 L0 q0 {( q& {" [0 C& R, K
- monster.setAttackPower(monster.getAttackPower() * 2); // Максимальная сила атаки2 @. N l# W( e9 v, j, J
- }
& q" G) Z6 d3 F) [) F6 { - }; T8 h. X5 Y) _# {1 O7 Y
Скопировать код
5 t+ X& k# m! X2 R, I; YШаг 3: Изменение класса MonsterЧтобы монстр мог переключаться между состояниями, нам нужно обновить класс Monster. В этой сборке L2J_Mobius, классы для игровых объектов, таких как монстры, находятся в пакете org.l2jmobius.gameserver.model.actor.: B4 g) a$ e' s- l2 Q
- // Пакет org.l2jmobius.gameserver.model.actor
7 L, N+ T7 _$ |9 b8 K - package org.l2jmobius.gameserver.model.actor;# y" ~2 r i; M7 b$ w
- & ?& t8 g7 ~1 D' s
- import org.l2jmobius.gameserver.model.actor.state.MonsterState;$ A) I; T! W1 n2 |# s- n
- import org.l2jmobius.gameserver.model.actor.state.InitialState;
p$ i$ W: X5 Y, c6 B: V+ m - 7 j8 ~3 g1 L2 f; [2 z
- public class Monster extends Creature {& w5 P4 @1 ^! J n L1 H/ n1 K1 q
- private String name;
% `$ l) Z0 x" M( Q - private double attackPower;$ H& i8 P5 D* A6 l) P
- private MonsterState state; // Текущее состояние монстра; Z0 H% Q: b4 u# I4 F# b# O- M
, ~. Y! X- k0 g; t- c6 A: \- // Конструктор монстра
, r. L) e) D2 W9 x. } s3 s3 U - public Monster(String name, double attackPower) {
9 h* E- l3 K: O+ E - this.name = name;
2 i! g6 A& I5 c6 B$ C7 ]. y - this.attackPower = attackPower;
& h, B& P c8 a8 l - this.state = new InitialState(); // Устанавливаем начальное состояние7 ~3 P' T9 n0 w3 |
- }: W; A4 T$ m* M' G j% ]( J- P
- 7 O$ E, K! `" x
- // Метод для смены состояния
4 u% C n- k/ ^. x6 K' J( D( W; j - public void setState(MonsterState newState) {" b9 G0 O: z: r7 _0 g& t
- this.state = newState;
) |4 D! k7 g$ j3 ?( G - }; I" V/ l4 S& h
+ M& | |* O1 }3 H- // Выполнение действий на основе текущего состояния" j# `$ L! ?5 T
- public void executeState() {: M' z, G' S i/ x% h
- state.handleState(this);, G" b, N- e# M
- }: O9 F3 _% D( X- T
- % [: l$ @. Y: ?! _
- // Геттеры и сеттеры3 U1 I m `6 ` x+ Z' q9 c
- public String getName() { b6 e9 x1 g$ x
- return name;
K6 }; v& p: y - }
9 Q8 I/ d; L X1 h
7 z2 ^2 x! V; W0 p- public double getAttackPower() {$ Q5 w* @* k% d0 O
- return attackPower;
, n7 X1 v, {/ V) r - }
! E S* A8 e. {2 Z" h - % u K4 L0 N3 T ?9 X
- public void setAttackPower(double attackPower) {
0 e9 W1 G9 h) C e' F, @ - this.attackPower = attackPower;
* C( ^5 z4 D& r8 r - }! _+ k8 D) b$ H+ ]8 W! ]& n' S7 E5 v
- }# L, o% D; @& C( {' R8 z
Скопировать код
2 v# e3 o' P# K/ x( o7 YШаг 4: Симуляция боя с фазамиТеперь мы можем протестировать логику боя с переключением состояний монстра.; d: b9 d; m5 j7 f
# }/ i% }4 h% n5 I- // Пакет org.l2jmobius.gameserver.model.battle
. y8 {7 B! F1 |% b" T& k% v0 y - package org.l2jmobius.gameserver.model.battle;4 B2 P8 [! W- J! W; a* T
- K) c% X9 z' O- b$ ^& n5 r- import org.l2jmobius.gameserver.model.actor.Monster;3 I' M4 y8 G( ^0 b- p% q
- import org.l2jmobius.gameserver.model.actor.state.AggressiveState;+ b4 a* X! j, A0 L6 o) q% b% C5 H
- import org.l2jmobius.gameserver.model.actor.state.FinalState;
p. Q5 q+ l9 F7 I. w$ N - $ b$ |6 i( @: ~! n7 h- H
- public class BattleSimulation {
- e9 S) x9 ~; p5 D' z! r9 `: \ - public static void main(String[] args) {
" C3 {/ ]% P. f$ V4 T5 J - // Создаем монстра с начальной атакой
$ Z1 v+ e! `1 r0 ^3 ]1 D - Monster monster = new Monster("Дракон", 100);& W* a# O0 K$ O7 `' [1 w- E: Z
; J. B, w5 O3 K3 [2 D9 p- A! N- // Начальная фаза) G$ @+ n# C6 s" g# Y
- monster.executeState();
5 ?1 s4 z5 y) L. @2 `
' D/ b. M' k8 r! u/ t& {4 j8 o- // Переход в агрессивную фазу7 y) F9 }$ k7 \* N& k( ]. p, @4 }
- monster.setState(new AggressiveState());
' f( D9 |8 W0 w+ s5 y* T+ [0 J - monster.executeState();5 j" J7 \9 e6 J. t a8 k# ~
* P' i# Q" h u/ F6 X1 B& T6 M- // Финальная фаза$ @+ |* ^) B/ x s H% U" u
- monster.setState(new FinalState());
6 e' X1 p- |0 M5 J5 ~ - monster.executeState();- x7 N5 Q& @( w# p J1 F A
- }
8 X% Y) G9 w9 |. U - }
9 i) M) P( g7 G8 k4 N) j _2 S
Скопировать код 8 C; g# p4 \; ]6 q4 O
Комментарии по структуре пакетов и классов:& b& j+ o; V7 Z& \6 ^+ J
- Пакет org.l2jmobius.gameserver.model.actor: содержит основные игровые сущности, такие как Monster.
- Пакет org.l2jmobius.gameserver.model.actor.state: отвечает за реализацию состояний для объектов, таких как монстры.
- Пакет org.l2jmobius.gameserver.model.battle: может содержать примеры взаимодействий, такие как симуляция боевых сценариев.
; ]( O1 r h6 `5 I: w3 x5 H4 i+ h+ c5 h ЗаключениеШаблон "Состояние" позволяет легко управлять фазами боя и не перегружать основной класс монстра. Это делает логику боевых сценариев более гибкой и масштабируемой. В будущем, если появятся новые фазы или состояния, их можно будет легко добавить, не изменяя основной код.( P) h4 z) P' o" H4 k6 j1 S
Если появятся дополнительные вопросы по реализации или структуре классов, буду рада помочь!
* x% X' p0 [& N) w2 I% M' ^( x' L
4 l( R& J) `' F8 r0 L% K
( G' T4 s2 N6 T* f' X g" K9 u/ R4 R) K- P2 y0 Y# K
: G1 D# L& e! }9 U# H5 h" J& Z6 n' n7 h) c! `7 E$ g
* o: K8 I' m" A' ?1 h8 A! q
$ K0 c1 D; c) l) Z
# Q8 i, b! b4 }0 D- z5 U: a5 b6 b
e1 f6 H% r% n3 E0 Q
4 w* \9 i' M' V0 g3 R l9 ^. F5 d/ ~/ e6 ~
8 [ H& p7 e/ g- p9 a2 I% O3 W9 B1 j
|