diff --git a/src/main/java/uno/mloluyu/characters/Fighter.java b/src/main/java/uno/mloluyu/characters/Fighter.java index 9cc7e6b..06d9a86 100644 --- a/src/main/java/uno/mloluyu/characters/Fighter.java +++ b/src/main/java/uno/mloluyu/characters/Fighter.java @@ -15,7 +15,7 @@ public abstract class Fighter implements Disposable { // 动作类型枚举 - 所有角色共用的基础动作 public enum Action { IDLE, WALK, JUMP, FALL, - ATTACK1, ATTACK2, ATTACK3, + ATTACK1, ATTACK2, ATTACK3,ATTACK4, HIT, DEFEND, SPECIAL1, SPECIAL2, DEATH diff --git a/src/main/java/uno/mloluyu/desktop/GameCore.java b/src/main/java/uno/mloluyu/desktop/GameCore.java index ce02cd9..e6c73ef 100644 --- a/src/main/java/uno/mloluyu/desktop/GameCore.java +++ b/src/main/java/uno/mloluyu/desktop/GameCore.java @@ -5,18 +5,20 @@ import com.badlogic.gdx.Gdx; import com.badlogic.gdx.graphics.GL20; import com.badlogic.gdx.graphics.Texture; import com.badlogic.gdx.graphics.g2d.SpriteBatch; +import com.badlogic.gdx.graphics.g2d.TextureAtlas; import uno.mloluyu.desktop.character.Alice; public class GameCore implements ApplicationListener { private SpriteBatch batch; - private Texture img; - private Alice alice1 = new Alice(); + private TextureAtlas atlas; + private Alice alice1; + @Override public void create() { - alice1.create(); - + atlas = new TextureAtlas(Gdx.files.internal("characters/alice.atlas")); + alice1= new Alice(); } @@ -25,8 +27,10 @@ public class GameCore implements ApplicationListener { Gdx.gl.glClearColor(150, 150, 150, 1); Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT); + alice1.update(Gdx.graphics.getDeltaTime()); - alice1.render(); + batch.begin(); + alice1.render(batch); } @Override diff --git a/src/main/java/uno/mloluyu/desktop/character/Alice.java b/src/main/java/uno/mloluyu/desktop/character/Alice.java index a88613c..05cce69 100644 --- a/src/main/java/uno/mloluyu/desktop/character/Alice.java +++ b/src/main/java/uno/mloluyu/desktop/character/Alice.java @@ -1,179 +1,57 @@ package uno.mloluyu.desktop.character; +import uno.mloluyu.characters.Fighter; +import com.badlogic.gdx.graphics.g2d.TextureAtlas; -import uno.mloluyu.util.SimpleFormatter; +/** + * 角色类,继承自Fighter父类 + */ +public class Alice extends Fighter { -import com.badlogic.gdx.Gdx; -import com.badlogic.gdx.Input; -import com.badlogic.gdx.graphics.Texture; -import com.badlogic.gdx.graphics.g2d.Animation; -import com.badlogic.gdx.graphics.g2d.SpriteBatch; -import com.badlogic.gdx.graphics.g2d.TextureRegion; -import com.badlogic.gdx.math.Vector2; -import com.badlogic.gdx.utils.Array; - -public class Alice { - private SpriteBatch batch; - private Animation walkAnimation; // 行走动画 - private Animation idleAnimation; // idle动画 - private TextureRegion currentFrame; // 当前显示的帧 - private float stateTime; // 动画播放时间 - - private String path = "character/alice/"; - private final float MOVEMENT_SPEED = 200f; - private Vector2 position; - private float width; // 角色宽度 - private float height; // 角色高度 - private boolean isMoving = false; // 是否在移动 - private boolean isFacingRight = true; // 是否面朝右 - - public void create() { - batch = new SpriteBatch(); - position = new Vector2(); - - // 加载动画帧 - loadAnimations(); - - // 初始化位置(屏幕中心) - setToCenter(); + public Alice(TextureAtlas atlas) { + super(atlas); + speed = 350f; // 速度更快 + maxHealth = 90; // 生命值较低 + health = maxHealth; + attackPower = 12; // 攻击力中等 } + + @Override + protected void loadAnimations() { + loadAnimationFromAtlas(Action.IDLE, "stand", 15, true); + loadAnimationFromAtlas(Action.WALK, "walkFront", 9, true); + loadAnimationFromAtlas(Action.JUMP, "jump", 8, false); + loadAnimationFromAtlas(Action.FALL, "hitSpin", 5, false); + loadAnimationFromAtlas(Action.ATTACK1, "attackAa", 6, false); + loadAnimationFromAtlas(Action.ATTACK2, "attackAb", 6, false); + loadAnimationFromAtlas(Action.ATTACK3, "attackAc", 6, false); + loadAnimationFromAtlas(Action.ATTACK4, "attackAd", 6, false); - /** - * 加载动画帧序列 - */ - private void loadAnimations() { - try { - // 1. 加载静止动画 - Array idleFrames = new Array<>(); - for (int i = 0; i < 16; i++) { - Texture texture = new Texture(Gdx.files.internal(path + "stand" + SimpleFormatter.addLeadingZeros(i,3) + ".png")); //文件路径 - System.out.println(texture); - idleFrames.add(new TextureRegion(texture)); - } - - idleAnimation = new Animation<>(0.1f, idleFrames, Animation.PlayMode.LOOP); // 每帧时间 - - // 2. 加载行走动画 - Array walkFrames = new Array<>(); - for (int i = 0; i < 5; i++) { - Texture texture = new Texture(Gdx.files.internal(path + "walkFront" + SimpleFormatter.addLeadingZeros(i,3) + ".png")); - System.out.println("调试代码"+texture); - walkFrames.add(new TextureRegion(texture)); - } - walkAnimation = new Animation<>(0.1f, walkFrames, Animation.PlayMode.LOOP); - - // 设置角色尺寸 - width = idleFrames.get(0).getRegionWidth(); - height = idleFrames.get(0).getRegionHeight(); - - Gdx.app.log("Alice", "动画加载成功"); - - } catch (Exception e) { - Gdx.app.error("Alice", "动画加载失败: " + e.getMessage()); - e.printStackTrace(); - } + loadAnimationFromAtlas(Action.HIT, "hitSpin", 5, false); + + // 为忍者特定动作设置帧间隔 + setFrameDuration(Action.WALK, 0.08f); // 行走更快 + setFrameDuration(Action.ATTACK1, 0.07f); // 攻击更快 + setFrameDuration(Action.SPECIAL2, 0.06f); // 特殊技能2非常快 } - - /** - * 设置角色到屏幕中心 - */ - private void setToCenter() { - float x = (Gdx.graphics.getWidth() - width) / 2f; - float y = (Gdx.graphics.getHeight() - height) / 2f; - position.set(x, y); - } - - /** - * 更新逻辑和动画 - */ - public void update(float deltaTime) { - if (idleAnimation == null) return; - - stateTime += deltaTime; - - handleMovement(deltaTime); - - if (isMoving) { - currentFrame = walkAnimation.getKeyFrame(stateTime); - } else { - currentFrame = idleAnimation.getKeyFrame(stateTime); - } - - if ((isFacingRight && currentFrame.isFlipX()) || - (!isFacingRight && !currentFrame.isFlipX())) { - currentFrame.flip(true, false); - } - } - - /** - * 处理移动逻辑 - */ - private void handleMovement(float deltaTime) { - float moveX = 0; - float moveY = 0; - isMoving = false; - - // 方向键控制 - if (Gdx.input.isKeyPressed(Input.Keys.UP)) { - moveY += MOVEMENT_SPEED * deltaTime; - isMoving = true; - } - if (Gdx.input.isKeyPressed(Input.Keys.DOWN)) { - moveY -= MOVEMENT_SPEED * deltaTime; - isMoving = true; - } - if (Gdx.input.isKeyPressed(Input.Keys.RIGHT)) { - moveX += MOVEMENT_SPEED * deltaTime; - isMoving = true; - isFacingRight = true; // 朝右 - } - if (Gdx.input.isKeyPressed(Input.Keys.LEFT)) { - moveX -= MOVEMENT_SPEED * deltaTime; - isMoving = true; - isFacingRight = false; // 朝左 - } - - // 更新位置并限制在屏幕内 - position.add(moveX, moveY); - clampPosition(); - } - - /** - * 限制在屏幕范围内 - */ - private void clampPosition() { - float maxX = Gdx.graphics.getWidth() - width; - float maxY = Gdx.graphics.getHeight() - height; - position.x = Math.max(0, Math.min(position.x, maxX)); - position.y = Math.max(0, Math.min(position.y, maxY)); - } - - /** - * 渲染角色和动画 - */ - public void render() { - if (batch == null || currentFrame == null) return; - batch.begin(); - batch.draw(currentFrame, position.x, position.y); - batch.end(); - } - - /** - * 释放资源 - */ - public void dispose() { - if (batch != null) { - batch.dispose(); - batch = null; - } - if (idleAnimation != null) { - for (TextureRegion region : idleAnimation.getKeyFrames()) { - region.getTexture().dispose(); - } - } - if (walkAnimation != null) { - for (TextureRegion region : walkAnimation.getKeyFrames()) { - region.getTexture().dispose(); + + // 忍者特定的移动状态处理 + @Override + protected void handleMoveState() { + // 忍者在跳跃时也能移动 + if (currentAction != Action.ATTACK1 && currentAction != Action.ATTACK2 && + currentAction != Action.ATTACK3 && currentAction != Action.SPECIAL1 && + currentAction != Action.SPECIAL2 && currentAction != Action.DEFEND) { + + if (currentAction != Action.JUMP && currentAction != Action.FALL) { + changeAction(Action.WALK); } } } + + // 忍者可以在空中攻击 + @Override + protected boolean canAttack() { + return super.canAttack() || currentAction == Action.JUMP || currentAction == Action.FALL; + } } + \ No newline at end of file diff --git a/target/classes/uno/mloluyu/characters/Fighter$Action.class b/target/classes/uno/mloluyu/characters/Fighter$Action.class index d6471bf..7f5b853 100644 Binary files a/target/classes/uno/mloluyu/characters/Fighter$Action.class and b/target/classes/uno/mloluyu/characters/Fighter$Action.class differ diff --git a/target/classes/uno/mloluyu/characters/Fighter.class b/target/classes/uno/mloluyu/characters/Fighter.class index 21b6e04..363f772 100644 Binary files a/target/classes/uno/mloluyu/characters/Fighter.class and b/target/classes/uno/mloluyu/characters/Fighter.class differ diff --git a/target/classes/uno/mloluyu/desktop/GameCore.class b/target/classes/uno/mloluyu/desktop/GameCore.class index 67bd962..2d615a1 100644 Binary files a/target/classes/uno/mloluyu/desktop/GameCore.class and b/target/classes/uno/mloluyu/desktop/GameCore.class differ diff --git a/target/classes/uno/mloluyu/desktop/character/Alice.class b/target/classes/uno/mloluyu/desktop/character/Alice.class index 353d489..5fa4ba2 100644 Binary files a/target/classes/uno/mloluyu/desktop/character/Alice.class and b/target/classes/uno/mloluyu/desktop/character/Alice.class differ