障碍物不能持续出现,怎样修改


package main;

import java.awt.Graphics;
import java.awt.image.BufferedImage;

import util.Constant;
import util.Gameutil;

public class Barrier {
    
    //障碍物移动速度
    private int speed = 3;
    
    //定义障碍物需要的两个图片
    private static BufferedImage[] imgs;//定义一个数组来存放图片**imgs
    
    //在静态代码块中初始化一些参数
    static {
        final int COUNT = 3;//先定义一个常量
        //类加载的时候将三个图片初始化
        imgs = new BufferedImage[COUNT];
        for (int i = 0; i < COUNT; i++) {
            imgs[i] = Gameutil.loadBufferedImage(Constant.BARRIER_IMG_PATH[i]);
        }//把图片加载进去
    }
    
    //障碍物的位置
    private int x,y;
    //障碍物的宽度和高度
    private int width,height;
    //障碍物的类型
    private int type;
    public static final int TYPE_TOP_NORMAL = 0;
    public static final int TYPE_BOTTOM_NORMAL = 2;
    public static final int TYPE_HOVER_NORMAL = 4;
    
    //获得障碍物的宽度和高度
    public static final int BARRIRE_WIDTH = imgs[0].getWidth();
    public static final int BARRIRE_HEIGHT = imgs[0].getHeight();
    public static final int BARRIRE_HEAD_WIDTH = imgs[1].getWidth();
    public static final int BARRIRE_HEAD_HEIGHT = imgs[1].getHeight();
    
    //定义一个构造器
    public Barrier() {}
    
    public Barrier(int x,int y,int height,int type) {
        this.x = x;
        this.y = y;
        this.height = height;
        this.type = type;
        this.width = BARRIRE_WIDTH;
    }
    
    //根据不同的类型绘制障碍物
    public void draw(Graphics g) {
        switch(type){
            case TYPE_TOP_NORMAL:
                 drawTopMormal(g);
                 break;
            case TYPE_BOTTOM_NORMAL:
                 drawNomalTop(g);
                 break;
        }
        
    }
    
    //绘制从上向下的障碍物
    private void drawTopMormal(Graphics g) {
        
        //求出所需要的障碍物的块数
        int count = (height-BARRIRE_HEAD_HEIGHT)/BARRIRE_HEIGHT+1;
        //for循环绘制障碍物
        for (int i = 0; i < count; i++) {
            g.drawImage(imgs[0], x, y+i*BARRIRE_HEIGHT, null);
        }
        //绘制头
        int y = height-BARRIRE_HEAD_HEIGHT;
        g.drawImage(imgs[2], x-(BARRIRE_HEAD_WIDTH-BARRIRE_WIDTH)/2, y,null);
        x-=speed;
    }
    
    //绘制从下向上的障碍物
    private void drawNomalTop(Graphics g) {
        //求出所需要的障碍物的块数
        int count = height/BARRIRE_HEIGHT+1;
        //for循环绘制障碍物
        for (int i = 0; i < count; i++) {
            g.drawImage(imgs[0], x, Constant.FRAM_HEIGNT-i*BARRIRE_HEIGHT, null);
        }
        
        //绘制头
        int y = Constant.FRAM_HEIGNT-height;
        g.drawImage(imgs[1], x-(BARRIRE_HEAD_WIDTH-BARRIRE_WIDTH)/2, y, null);
        x-=speed;
        
    }
    
    //判断什么时候绘制下一组障碍物
    public boolean isInFrame () {return 600-x>150;}
    //
    public int getX() {
        return x;
    }
    
    public void setX(int x) {
        this.x = x;
    }
    
    public int getY() {
        return y;
    }
    
    public void setY(int y) {
        this.y = y;
    }
    
    public int getHeight() {
        return height;
    }
    
    public void setHeight(int height) {
        this.height = height;
    }
    
    public int getType() {
        return type;
    }
    
    public void setType(int type) {
        this.type = type;
    }
}

package main;

import java.awt.Graphics;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;

public class GameBarrierLayer {
    
    //用于生成随机数的函数
    private Random random = new Random();
    
    //定一个数组来存放障碍物
    private List<Barrier> barriers;
    
    //定义一个构造器
    public GameBarrierLayer() {
        barriers = new ArrayList<>();
    }
    
    //绘制障碍物
    public void draw(Graphics g) {
        Barrier barrier = new Barrier(200,0,200,0);
        barriers.add(barrier);
        barriers.get(0).draw(g);
        Barrier barrier1 = new Barrier(300,0,300,2);
        barriers.add(barrier1);
        barriers.get(1).draw(g);
    }
    
    //生成随机障碍物
    public void logic() {
        if (barriers.size()==0) {
            ran();
            //Barrier top = new Barrier(800,0,numberTop,0);
            //barriers.add(top);
            //Barrier down = new Barrier(800,500-numberDown,numberDown,2);
            //barriers.add(down);
            insert(600, 0, numberTop, 0);
            insert(600, 500-numberDown, numberTop, 2);
        }else {
            //判断最后一个障碍物是否完全进入屏幕内
            Barrier last = barriers.get(barriers.size()-1);
            if (last.isInFrame()) {
                ran();
                //Barrier top = new Barrier(800,0,numberTop,0);
                //barriers.add(top);
                //Barrier down = new Barrier(800,500-numberDown,numberDown,2);
                //barriers.add(down);
                insert(600, 0, numberTop, 0);
                insert(600, 500-numberDown, numberTop, 2);
            }
        }
    }
    
    //用于从池中获取对象,并把参数封装成barrier,存入barrier数组
    public void insert(int x,int y,int num,int type) {
        Barrier top = Barrierpool.getPool();
        top.setX(x);
        top.setY(y);
        top.setHeight(num);
        top.setType(type);
        barriers.add(top);
    }
    
    //上方障碍物高度
    private int numberTop;
    //下方障碍物高度
    private int numberDown;
    //产生两个100~500之间的随机高度
    public void ran() {
        numberTop = random.nextInt(400)+100;
        numberDown = random.nextInt(400)+100;
        //如果管道重合,则重新随机
        if (numberTop+numberDown>450) {
            ran();
        }
    }

}


package main;

import java.util.ArrayList;
import java.util.List;

public class Barrierpool {
    
    //用于管理池中所有对象的容量
    private static List<Barrier>pool = new ArrayList<>();
    
    //池中初始的对象个数
    public static final int initCount = 16;
    
    //对象池中最大个数
    public static final int maxCount = 20;
    
    //静态代码块
    static {
        //初始化池中对象
        for (int i = 0; i < initCount; i++) {
            pool.add(new Barrier());
        }
    }
    
    //从池中获取一个对象的方法
    public static Barrier getPool() {
        int size = pool.size();
        //如果池中有对象才可以拿
        if (size>0) {
            //移除并返回对象
            System.out.println("拿走一个");
            return pool.remove(size-1);
        }else {
            //池中没有对象了,只能new
            System.out.println("新的对象");
            return new Barrier();
        }
    }
    
    //把对象归还给容器
    public static void setPool(Barrier barrier) {
        if (pool.size()<maxCount) {
            pool.add(barrier);
            System.out.println("容器归还了");
        }
    }

}

请问在哪里出了问题,障碍物不能持续出现(用java写飞翔的小鸟小游戏)

引用 皆我百晓生 小程序回复内容作答:
GameBarrierLayer类的insert方法中,调用了静态方法Barrierpool.getPool()从对象池中获取一个对象,但在使用完这个对象后,没有将其归还给对象池。这导致当对象池中的对象都被取出时,无法再生成新的障碍物对象。为了解决这个问题,可以在调用完Barrier对象后,使用Barrierpool.setPool(Barrier barrier)方法将对象归还给对象池。

具体修改代码如下:

// 生成随机障碍物
public void logic() {
    if (barriers.size() == 0) {
        ran();
        insert(600, 0, numberTop, 0);
        insert(600, 500 - numberDown, numberTop, 2);
    } else {
        // 判断最后一个障碍物是否完全进入屏幕内
        Barrier last = barriers.get(barriers.size() - 1);
        if (last.isInFrame()) {
            ran();
            insert(600, 0, numberTop, 0);
            insert(600, 500 - numberDown, numberTop, 2);
        }
    }
}

// 用于从池中获取对象,并把参数封装成barrier,存入barrier数组
public void insert(int x, int y, int num, int type) {
    Barrier top = Barrierpool.getPool();
    top.setX(x);
    top.setY(y);
    top.setHeight(num);
    top.setType(type);
    barriers.add(top);
}

// 绘制障碍物
public void draw(Graphics g) {
    for (int i = 0; i < barriers.size(); i++) {
        barriers.get(i).draw(g);
        // 判断障碍物是否超出屏幕范围,是则归还给对象池
        if (!barriers.get(i).isInFrame()) {
            Barrierpool.setPool(barriers.get(i));
            barriers.remove(i);
            i--;
        }
    }
}

这样,在绘制障碍物时,如果障碍物超出屏幕范围,就会将该障碍物归还给对象池,然后从障碍物数组中移除。这样就可以实现障碍物的持续出现。

【以下回答由 GPT 生成】

问题中的代码只展示了障碍物的定义和初始化部分,并未包含障碍物生成和销毁的逻辑。要实现障碍物不会持续出现的功能,需要进行以下修改和添加:

  1. 修改Barrier类的构造方法,在构造障碍物对象时增加一个随机生成障碍物类型的逻辑。在构造方法中添加以下代码:
public Barrier() {
    // 生成随机的障碍物类型
    Random random = new Random();
    type = random.nextInt(3) * 2;
    // 初始化障碍物的位置
    x = Constant.FRAME_WIDTH;
    y = random.nextInt(Constant.FRAME_HEIGHT - BARRIRE_HEIGHT);
    // 初始化障碍物的宽度和高度
    width = BARRIRE_WIDTH;
    height = BARRIRE_HEIGHT;
}
  1. 修改Game类中的绘制和更新逻辑。在Game类中,将障碍物存储在一个List集合中,并在更新游戏状态时进行障碍物的生成和销毁逻辑。在Game类中的相应位置添加以下代码:
// 声明一个障碍物集合
private List<Barrier> barriers = new ArrayList<>();

// 在update方法中添加障碍物的生成和销毁逻辑
public void update() {
    // 生成障碍物
    if (barriers.isEmpty() || barriers.get(barriers.size() - 1).getX() < Constant.FRAME_WIDTH - 200) {
        Barrier barrier = new Barrier();
        barriers.add(barrier);
    }
    // 销毁超出边界的障碍物
    for (int i = 0; i < barriers.size(); i++) {
        Barrier barrier = barriers.get(i);
        if (barrier.getX() < -barrier.getWidth()) {
            barriers.remove(barrier);
            i--;
        }
    }
    // 更新障碍物的位置
    for (Barrier barrier : barriers) {
        barrier.move();
    }
}

// 在paint方法中添加绘制障碍物的逻辑
public void paint(Graphics g) {
    // 绘制障碍物
    for (Barrier barrier : barriers) {
        g.drawImage(Barrier.imgs[barrier.getType()], barrier.getX(), barrier.getY(), null);
    }
    // 其他绘制逻辑...
}

通过以上修改和添加,可以实现障碍物不会持续出现的功能。障碍物的生成和销毁逻辑会在游戏更新状态时进行判断和处理。每当障碍物超出游戏窗口边界时,会被销毁,同时会生成新的障碍物,保持障碍物的数量在合理的范围内。



【相关推荐】



如果你已经解决了该问题, 非常希望你能够分享一下解决方案, 写成博客, 将相关链接放在评论区, 以帮助更多的人 ^-^