Java编程进阶:智能仿真无人机项目4.0

一、项目前期准备

V4 版本在 V3 "双向对抗" 基础上,新增定点任务处理、鼠标交互、多线程协作、状态机管理四大核心功能,新手需在 V3 基础(集合、线程通信、扫描攻击)上,额外掌握以下知识点:

1. 鼠标事件监听(MouseListener

  • 作用:捕捉鼠标操作(点击、按压、释放等),实现 "鼠标点击生成任务" 的交互;
  • 核心接口:MouseListener,需重写 5 个方法(重点用mousePressed:鼠标按压时触发);
  • 关键步骤:给窗口注册鼠标监听器→重写mousePressed方法→获取鼠标点击坐标。

2. 距离计算(勾股定理)

  • 作用:找到 "离任务点最近的无人机",实现任务分配逻辑;

  • 公式:两点(无人机坐标(x1,y1)、任务坐标(x2,y2))距离 dis =

  • 代码实现:

    java 复制代码
    (int) Math.sqrt((t.x - d.x)*(t.x - d.x) + (t.y - d.y)*(t.y - d.y));

3.多线程协作

  • 新增TaskProThread(任务处理线程),与原有DroneThread(无人机线程)协同工作;
  • 核心:通过共享droneListtaskList,实现 "任务生成→分配→执行→完成" 的闭环。

4. 状态机管理

  • 无人机新增 3 种状态:0(巡逻)、1(跟随入侵者)、2(处理任务);
  • 核心:状态决定行为(如巡逻时随机运动,处理任务时飞向任务点),状态切换通过修改state属性实现。

5. 坐标与速度适配

  • 任务点导向速度:通过计算无人机与任务点的坐标差,调整runSpeedxrunSpeedy,让无人机飞向任务点。

二、项目结构解析

V4 版本的核心变化是新增 "任务体系",实现 "鼠标点击生成任务→系统分配给最近无人机→无人机完成任务后回归巡逻" 的完整流程,同时保留 V3 的双向对抗功能,形成 "任务处理 + 敌对对抗" 的复合场景。

1.项目结构分析

类名 作用 核心新增技术点
Task 任务实体类(存储任务坐标、状态、生命值) 任务可视化绘制、状态管理(未分配 / 已分配 / 完成)
TaskProThread 任务处理线程(分配任务、监控任务进度) 距离计算、最近无人机匹配、速度调整
Drone 无人机实体类(新增状态、任务相关属性) 多状态管理、状态可视化(颜色区分)、速度适配
DroneListener 监听器(新增鼠标监听,生成任务) MouseListener、鼠标坐标获取
DroneThread 核心线程(保留对抗 + 新增任务绘制) 状态判断、任务与对抗逻辑兼容
DroneUI 界面搭建(新增任务集合、鼠标监听器注册) 多集合共享、鼠标监听器绑定
Intruder 入侵者实体类(优化边界、新增生命值显示) 边界调整、生命值可视化

2.项目核心逻辑流程

  1. **任务生成:**用户鼠标点击窗口→监听器捕捉坐标→创建Task对象→存入taskList;
  2. **任务分配:**TaskProThread遍历taskList→找到未分配任务→计算所有无人机到任务点的距离→分配给最近的空闲无人机(state=0)→无人机状态改为2(处理任务);
  3. **任务执行:**无人机线程根据state=2→调整速度飞向任务点→到达后扣除任务生命值;
  4. **任务完成:**任务生命值≤0→状态改为2(已完成)→无人机状态重置为0(巡逻);
  5. **并行对抗:**任务执行过程中,无人机与入侵者的双向扫描攻击正常进行。

三、核心模块详细讲解

1:新增实体类 ------Task(任务类)

Task类是 "定点任务" 的载体,封装了任务的核心信息,支持可视化绘制和状态管理。

(1)关键代码解析
java 复制代码
import java.awt.Graphics;
import java.awt.Color;

public class Task {
    int x; // 任务点x坐标(鼠标点击位置)
    int y; // 任务点y坐标
    int state; // 任务状态:0=未分配,1=已分配,2=已完成
    int blood; // 任务生命值(需无人机攻击多次完成)

    // 构造方法:创建任务时初始化坐标和状态
    public Task(int x, int y, int state) {
        this.x = x;
        this.y = y;
        this.state = state;
        this.blood = 10; // 初始生命值10(需攻击10次完成)
    }

    // 绘制任务点(可视化,新手能直观看到任务位置)
    public void draw(Graphics g) {
        if (blood <= 0) {
            state = 2; // 生命值为0,标记为已完成
            return;
        }
        g.setColor(Color.BLACK);
        // 绘制任务点:黑色矩形(左上角(x,y),宽80,高80)
        g.fillRect(x, y, 80, 80);
    }

    // Getter/Setter方法:获取/修改坐标、状态(供其他类访问)
    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 getState() { return state; }
    public void setState(int state) { this.state = state; }
}
(2)理解要点
  • 任务状态设计:0-1-2的状态流转,确保任务不会重复分配,符合 "生成→分配→完成" 的逻辑;
  • 任务生命值:blood = 10 意味着无人机需要到达任务点附近 10 次(每次扣 1 血)才能完成任务,模拟 "持续处理任务" 的场景;
  • 可视化绘制:fillRect 绘制黑色矩形,新手能直接在窗口看到鼠标点击生成的任务点。

2.新增线程 ------TaskProThread(任务处理线程)

这是 V4 版本的核心新增线程,负责 "任务分配" 和 "任务进度监控",是连接 "任务生成" 和 "无人机执行" 的桥梁。

(1)关键代码解析
java 复制代码
import java.util.ArrayList;

public class TaskProThread extends Thread {
    ArrayList<Drone> droneList; // 共享无人机集合
    ArrayList<Task> taskList; // 共享任务集合

    public void run() {
        while (true) { // 死循环:持续监控任务
            try {
                Thread.sleep(30); // 每30毫秒检查一次,避免频繁计算
            } catch (InterruptedException e) {
                throw new RuntimeException(e);
            }

            // 遍历所有任务,寻找未分配的任务(state=0)
            for (int i = 0; i < taskList.size(); i++) {
                Task t = taskList.get(i);
                if (t.state == 0) { // 找到未分配的任务
                    int minDis = 1000; // 初始化最小距离(足够大即可)
                    int targetDroneIndex = 0; // 最近无人机的索引

                    // 遍历所有无人机,找到距离任务点最近的空闲无人机(state=0:巡逻中)
                    for (int j = 0; j < droneList.size(); j++) {
                        Drone d = droneList.get(j);
                        // 跳过正在跟随入侵者(state=1)或处理其他任务(state=2)的无人机
                        if (d.state == 1 || d.state == 2) {
                            continue;
                        }

                        // 勾股定理计算无人机到任务点的距离
                        int dis = (int) Math.sqrt(
                            (t.x - d.x) * (t.x - d.x) + (t.y - d.y) * (t.y - d.y)
                        );

                        // 更新最小距离和对应的无人机索引
                        if (dis < minDis) {
                            minDis = dis;
                            targetDroneIndex = j;
                        }
                    }

                    // 给最近的无人机分配任务
                    Drone targetDrone = droneList.get(targetDroneIndex);
                    // 计算无人机到任务点的坐标差(用于调整速度方向)
                    int dx = t.x - targetDrone.x; // x方向差值(任务点 - 无人机x)
                    int dy = t.y - targetDrone.y; // y方向差值(任务点 - 无人机y)

                    // 记录任务索引(无人机执行时需对应任务)
                    targetDrone.tindex = i;
                    // 基础速度(取无人机原有速度的绝对值,保证速度大小不变)
                    int baseSpeedX = Math.abs(targetDrone.speedx);
                    int baseSpeedY = Math.abs(targetDrone.speedy);

                    // 调整x方向速度:无人机在任务点左边(dx>0)则向右飞(+baseSpeedX),否则向左(-baseSpeedX)
                    targetDrone.runSpeedx = dx > 0 ? baseSpeedX : -baseSpeedX;
                    // 调整y方向速度:同理,确保飞向任务点
                    targetDrone.runSpeedy = dy > 0 ? baseSpeedY : -baseSpeedY;

                    // 更新状态:任务改为"已分配"(state=1),无人机改为"处理任务"(state=2)
                    t.state = 1;
                    targetDrone.state = 2;
                }
            }

            // 监控任务执行进度:无人机到达任务点后,扣除任务生命值
            if (taskList.size() > 0) {
                for (int i = 0; i < droneList.size(); i++) {
                    Drone d = droneList.get(i);
                    if (d.state == 2) { // 只处理正在执行任务的无人机
                        Task t = taskList.get(d.tindex); // 获取对应的任务

                        // 判断无人机是否到达任务点(无人机中心+120像素,覆盖任务矩形范围)
                        if (d.x + 120 >= t.x && d.x + 120 <= t.x + 80 
                            && d.y + 120 >= t.y && d.y + 120 <= t.y + 80) {
                            d.runSpeedx = 0; // 到达后停止移动
                            d.runSpeedy = 0;
                            t.blood--; // 扣除任务生命值(完成一次处理)
                        }

                        // 任务完成(生命值≤0):重置无人机和任务状态
                        if (t.blood <= 0) {
                            d.state = 0; // 无人机回归巡逻状态
                            d.tindex = 0; // 清空任务索引
                            t.state = 2; // 任务标记为已完成
                        }
                    }
                }
            }
        }
    }
}
(2)理解要点

任务分配流程

  1. 遍历任务集合,筛选出 "未分配"(state=0)的任务;
  2. 遍历无人机集合,跳过忙碌的无人机(state=1/2),计算空闲无人机到任务点的距离;
  3. 选中距离最近的无人机,根据坐标差调整速度方向(确保飞向任务点);
  4. 更新任务和无人机的状态,完成分配。

距离计算的意义

  • 用勾股定理计算 "直线距离",确保分配的是 "最近" 的无人机,符合 "高效任务处理" 的逻辑;
  • 新手无需深入理解数学原理,直接复用Math.sqrt的代码即可,重点关注 "距离对比" 的逻辑。

速度调整逻辑

  • 核心:通过 dx(x 方向差值)判断无人机在任务点的左 / 右,通过 dy判断上 / 下;
  • 示例:若 dx>0(任务点在无人机右边),则runSpeedx=baseSpeedX(向右飞),反之向左飞,确保无人机精准飞向任务点。

3.实体类优化 ------Drone(多状态管理)

V4 版本的Drone类新增了状态、任务索引、运行速度等属性,支持 "巡逻→跟随→任务" 的状态切换,且状态通过颜色可视化。

(1)关键代码解析
java 复制代码
import java.awt.Graphics;
import java.awt.Color;

public class Drone {
    // 原有属性(坐标、速度、尺寸等)
    int x, y, speedx, speedy, size;
    // 新增属性:任务相关
    int tindex; // 绑定的任务索引(对应taskList中的位置)
    int state; // 状态:0=巡逻,1=跟随入侵者,2=处理任务
    // 新增属性:速度控制(runSpeedx/y是实际运行速度,可动态调整)
    int runSpeedx, runSpeedy;
    // 原有属性(雷达范围、状态灯尺寸)
    int stateSize;
    int scanSize;

    // 构造方法:初始化属性,默认状态为0(巡逻)
    public Drone(int x, int y, int state, int speedx, int speedy) {
        this.x = x;
        this.y = y;
        this.state = state; // 初始状态:巡逻(0)
        this.size = 30;
        this.stateSize = 15;
        this.scanSize = 100;
        this.speedx = speedx;
        this.speedy = speedy;
        this.runSpeedx = speedx; // 初始运行速度=默认速度
        this.runSpeedy = speedy;
    }

    // 绘制无人机(新增状态颜色区分,可视化关键)
    public void drawDrone(Graphics bg) {
        // 1. 绘制雷达范围(蓝色半透明椭圆,与V3一致)
        Color color1 = new Color(0, 0, 255, 60);
        bg.setColor(color1);
        bg.fillOval(x, y, scanSize, scanSize);

        // 2. 绘制无人机主体(绿色椭圆,与V3一致)
        Color color2 = new Color(64, 195, 66);
        bg.setColor(color2);
        bg.fillOval(x + 35, y + 35, size, size);

        // 3. 绘制状态灯(根据状态改变颜色,新手直观区分)
        Color color3;
        if (state == 0) { // 巡逻状态:红色
            color3 = new Color(255, 0, 0);
        } else { // 跟随(1)或处理任务(2):黄色
            color3 = new Color(255, 255, 0);
        }
        bg.setColor(color3);
        bg.fillOval(x + 42, y + 42, stateSize, stateSize);
    }

    // 移动方法(根据状态调整速度,核心逻辑)
    public void move() {
        // 巡逻状态(state=0):使用默认速度,随机运动
        if (state == 0) {
            runSpeedx = speedx;
            runSpeedy = speedy;
        }

        // 边界检测(与V3类似,优化反弹逻辑)
        // 水平边界:左200,右800(防守区范围)
        if (x > 300 + 600 || x < 200) {
            if (x < 200) {
                runSpeedx = -runSpeedx; // 反弹
                speedx = -speedx;
                x += size; // 避免卡在边界
            } else {
                runSpeedx = -runSpeedx;
                speedx = -speedx;
                x -= size;
            }
        }

        // 垂直边界:上175,下675(防守区范围)
        if (y > 175 + 500 || y < 175) {
            if (y < 175) {
                runSpeedy = -runSpeedy;
                speedy = -speedy;
                y += size;
            } else {
                runSpeedy = -runSpeedy;
                speedy = -speedy;
                y -= size;
            }
        }

        // 更新坐标(使用runSpeedx/y,支持动态速度调整)
        x += runSpeedx;
        y += runSpeedy;
    }
}
(2)理解要点

状态管理与可视化:

  • 状态切换:通过修改state属性实现(如任务分配时设为 2,任务完成后设为 0);
  • 颜色区分:巡逻(红色灯)、跟随 / 任务(黄色灯),新手无需看代码,直接观察窗口即可判断无人机状态;
  • 速度分离:speedx/y是默认速度(巡逻时用),runSpeedx/y是实际运行速度(跟随 / 任务时动态调整),避免速度冲突。

4..交互核心升级 ------DroneListener(新增鼠标监听)

监听器同时实现ActionListener(按钮监听)和MouseListener(鼠标监听),支持 "生产无人机 / 入侵者" 和 "鼠标点击生成任务" 两种交互。

(1)关键代码解析
java 复制代码
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.util.ArrayList;
import java.util.Random;

public class DroneListener implements ActionListener, MouseListener {
    // 共享集合:无人机、入侵者、任务(与UI线程、其他线程共用)
    ArrayList<Drone> droneList;
    ArrayList<Intruder> intruderList;
    ArrayList<Task> taskList;
    Random random = new Random();

    // 按钮监听逻辑(与V3一致,生产无人机/入侵者)
    public void actionPerformed(ActionEvent e) {
        String ac = e.getActionCommand();
        if (ac.equals("生产无人机")) {
            int x = random.nextInt(700) + 200;
            int y = random.nextInt(500) + 175;
            int speedx = random.nextInt(5) - 2;
            int speedy = random.nextInt(5) - 2;
            droneList.add(new Drone(x, y, 0, speedx, speedy)); // 初始状态0:巡逻
        } else if (ac.equals("生产入侵者")) {
            int x = random.nextInt(1200 - 205) + 60;
            int y = random.nextInt(950 - 205) + 60;
            // 确保入侵者初始在防守区外
            while (true) {
                if (x < 200 || x > 900 || y < 175 || y > 675) {
                    break;
                }
                x = random.nextInt(1200 - 205) + 60;
                y = random.nextInt(950 - 205) + 60;
            }
            int speedx = random.nextInt(5) - 2;
            int speedy = random.nextInt(5) - 2;
            intruderList.add(new Intruder(x, y, speedx, speedy, 45));
        }
    }

    // 新增:鼠标按压时触发(生成任务)
    public void mousePressed(MouseEvent e) {
        // 获取鼠标点击的坐标(e.getX()=x,e.getY()=y)
        int x = e.getX();
        int y = e.getY();
        // 创建任务对象(状态0:未分配)
        Task task = new Task(x, y, 0);
        taskList.add(task); // 存入任务集合
        System.out.println("生成任务,坐标:(" + x + "," + y + ")");
    }

    // 以下4个方法是MouseListener接口必须重写的,无需实现逻辑,留空即可
    public void mouseClicked(MouseEvent e) {}

    public void mouseReleased(MouseEvent e) {}

    public void mouseEntered(MouseEvent e) {}

    public void mouseExited(MouseEvent e) {}
}
(2)理解要点

鼠标监听使用:

  • 接口实现:必须同时重写MouseListener的 5 个方法,即使不用也不能删除(否则编译报错);
  • 坐标获取:e.getX()e.getY()获取的是鼠标在窗口内的坐标,直接用于创建任务点,精准对应点击位置;
  • 注册监听:需在DroneUI中调用addMouseListener(droneL),否则鼠标点击无反应。

5.界面与线程协同 ------DroneUI(新增任务集合与线程)

DroneUI类新增任务集合(taskList)和任务处理线程(TaskProThread),并注册鼠标监听器,是整个项目的 "中枢调度中心"。

(1)关键代码解析
java 复制代码
import javax.swing.*;
import java.awt.*;
import java.util.ArrayList;

public class DroneUI extends JFrame {
    // 原有集合:无人机、入侵者
    ArrayList<Drone> droneList = new ArrayList<>();
    ArrayList<Intruder> intruderList = new ArrayList<>();
    // 新增集合:任务
    ArrayList<Task> taskList = new ArrayList<>();

    public DroneUI() {
        // 窗口基础设置(与V3一致)
        setTitle("智能无人机平台");
        setSize(1200, 1000);
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        setLocationRelativeTo(null);

        // 按钮面板(与V3一致)
        JPanel btnPanel = new JPanel();
        btnPanel.setBackground(Color.LIGHT_GRAY);
        JButton btn = new JButton("生产无人机");
        JButton btn1 = new JButton("生产入侵者");
        btnPanel.add(btn);
        btnPanel.add(btn1);
        add(btnPanel, BorderLayout.SOUTH);
        setVisible(true);

        // 初始化绘图工具、监听器、线程
        Graphics g = this.getGraphics();
        DroneThread dt = new DroneThread(g); // 无人机线程
        DroneListener droneL = new DroneListener(); // 监听器(按钮+鼠标)
        TaskProThread tpt = new TaskProThread(); // 新增:任务处理线程

        // 注册监听
        btn.addActionListener(droneL);
        btn1.addActionListener(droneL);
        addMouseListener(droneL); // 新增:注册鼠标监听器

        // 共享集合传递(关键!所有线程共用同一个集合)
        droneL.droneList = droneList;
        droneL.intruderList = intruderList;
        droneL.taskList = taskList; // 监听器获取任务集合
        dt.droneList = droneList;
        dt.intruderList = intruderList;
        dt.taskList = taskList; // 无人机线程获取任务集合
        tpt.droneList = droneList; // 任务线程获取无人机集合
        tpt.taskList = taskList; // 任务线程获取任务集合

        // 启动线程(两个线程并行工作)
        dt.start();
        tpt.start(); // 新增:启动任务处理线程
    }

    // 重写paint方法
    public void paint(Graphics g) {
        super.paint(g);
    }

    public static void main(String[] args) {
        new DroneUI();
    }
}
(2)理解要点

多线程协同:

  • 两个线程并行:DroneThread负责绘制和对抗,TaskProThread负责任务分配,通过共享集合通信,互不干扰;
  • 集合传递:必须将taskList传递给监听器(生成任务)、无人机线程(绘制任务)、任务线程(分配任务),否则功能失效。

6.敌对实体类优化------Intruder(边界调整 + 生命值可视化)

V4 版本的Intruder类优化了边界判断,新增生命值可视化(新手能看到入侵者剩余血量)。

(1)关键代码解析
java 复制代码
import java.awt.Graphics;
import java.awt.Color;
 
public class Intruder {
    // 入侵者属性
    int x, y; // 坐标
    int speedx, speedy; // 速度
    int size; // 尺寸
    int blood; // 生命值
 
    // 构造方法:初始化坐标、速度、尺寸、生命值
    public Intruder(int x, int y, int speedx, int speedy, int size) {
        this.x = x;
        this.y = y;
        this.speedx = speedx;
        this.speedy = speedy;
        this.size = size;
        this.blood = 100; // 初始生命值100
    }
 
    // 行为1:绘制入侵者
    public void drawIntruder(Graphics g) {
        if (blood <= 0) { // 生命值≤0时,不绘制
            return;
        }
        g.setColor(Color.BLACK); // 主体黑色
        g.fillOval(x, y, size, size); // 绘制黑色椭圆
        g.setColor(Color.RED); // 边框红色
        g.drawOval(x - 1, y - 1, size + 2, size + 2); // 绘制红色边框
    }
 
    // 行为2:入侵者移动
    public void move() {
        if (blood <= 0) {
            return;
        }
        // 边界调整:左60,右1200-145,上60,下950-145(扩大运动范围,预留安全距离)
        if (x > 1200 - 145 || x < 60) {
            speedx = -speedx;
        }
        if (y > 950 - 145 || y < 60) {
            speedy = -speedy;
        } 
        x += speedx;
        y += speedy;
    }

    // 生命值可视化(在DroneThread的入侵者扫描逻辑中添加)
    g.setColor(Color.BLACK);
    // 绘制生命值背景框(入侵者上方)
    g.drawRect(intruder.x, intruder.y - 22, 20, 10);
    g.setColor(Color.GREEN);
    // 绘制当前生命值(按比例填充绿色)
    g.fillRect(intruder.x + 1, intruder.y - 21, (int)(intruder.blood / 100.0 * 20), 8);
    g.setColor(Color.RED);
    // 绘制生命值数字(直观显示)
    g.drawString("" + intruder.blood, intruder.x + 18, intruder.y);
}
(2)理解要点

生命值可视化:

  • 背景框 + 填充条:黑色边框是生命值满格的宽度(20 像素),绿色填充条长度随blood比例变化(如 blood=50 时,填充 10 像素);
  • 数字显示:直接绘制blood值,新手无需计算,一眼就能看到入侵者剩余血量。

四、常见问题与注意事项(新手避坑)

1. 鼠标点击不生成任务

  • 原因 1:未给窗口注册鼠标监听器(忘记addMouseListener(droneL));
  • 原因 2:mousePressed方法名写错(如写成mousePress);
  • 解决:检查监听器注册代码和方法名拼写,确保MouseListener的 5 个方法都重写。

2. 任务分配给忙碌的无人机

  • 原因:任务分配时未过滤状态(if (d.state == 1 || d.state == 2)),导致分配给正在跟随 / 处理任务的无人机;
  • 解决:确保遍历无人机时,跳过state=1state=2的无人机,只选择state=0的空闲无人机。

3. 无人机不飞向任务点

  • 原因 1:速度调整逻辑错误(如dx>0时设为-baseSpeedX,方向相反);
  • 原因 2:runSpeedx/y未正确赋值,仍使用默认速度;
  • 解决:检查速度调整代码,确保dx>0runSpeedx=baseSpeedXdx<0时为-baseSpeedX

4. 任务完成后无人机不回归巡逻

  • 原因:任务生命值≤0 时,未将无人机state重置为 0;
  • 解决:在TaskProThread的任务监控逻辑中,添加d.state = 0(任务完成后重置状态)。

5. 数组下标越界(任务集合)

  • 原因:任务完成后未判断taskList是否为空,直接调用taskList.get(d.tindex)
  • 解决:在遍历无人机处理任务前,添加if (taskList.size() == 0) continue;,避免空集合访问。

五、拓展巩固

1. 实现补给仓功能(文档提到的电量 / 弹药补给)

  • 需求:添加 "补给仓" 按钮,点击生成补给点,无人机靠近后恢复电量 / 弹药;
  • 步骤:
    1. 新增Supply类(属性:x、y、type,方法:draw);
    2. 监听器添加 "生成补给仓" 按钮逻辑,创建Supply对象存入supplyList
    3. 无人机线程中,遍历supplyList,无人机靠近补给点时,恢复电量 / 弹药;
    4. 补给点被使用后,从supplyList中移除。

2. 任务优先级设置

  • 需求:给任务添加优先级(1~3 级),高优先级任务优先分配无人机;
  • 思路:
    1. Task类新增priority属性(1 = 低,2 = 中,3 = 高);
    2. 鼠标点击时,按快捷键区分优先级(如按住 Ctrl 点击生成 3 级任务);
    3. TaskProThread中,先遍历高优先级任务,再处理中、低优先级。

3. 多任务并行处理

  • 需求:支持同时分配多个任务,每个任务分配一个空闲无人机;
  • 思路:修改TaskProThread的任务分配逻辑,遍历所有未分配任务,为每个任务分别匹配最近的空闲无人机(避免一个无人机同时处理多个任务)。

4. 任务超时机制

  • 需求:任务生成后 30 秒未完成,自动标记为 "失败" 并重置;
  • 思路:Task类新增createTime属性(记录生成时间),TaskProThread中判断当前时间与createTime的差值,超过 30 秒则重置任务状态。

六、总结

V4 版本完成了从 "单纯对抗" 到 "任务 + 对抗" 的复合场景升级,核心收获如下:

  1. 交互能力升级 :掌握MouseListener实现鼠标交互,理解 "用户操作→事件触发→逻辑执行" 的完整链路;
  2. 多线程协作:学会多个线程(无人机线程 + 任务线程)通过共享集合通信,避免线程冲突;
  3. 状态机思维:理解 "状态决定行为" 的设计模式,能通过状态切换实现复杂功能(巡逻→跟随→任务);
  4. 数学逻辑落地:将勾股定理等数学知识应用到距离计算中,明白 "代码解决实际问题" 的思路;
  5. 可视化优化:通过颜色、图形、数字直观展示状态和数据(如无人机状态灯、入侵者生命值),提升项目可读性。

对于 Java 新手,V4 版本的学习重点是 "模块拆分" 和 "逻辑协同"------ 复杂项目并非一蹴而就,而是将 "任务生成""任务分配""状态管理""对抗逻辑" 拆分为多个模块,每个模块负责单一功能,再通过共享数据和线程协作整合。通过本项目,你不仅巩固了多线程、集合、Swing 等基础,还培养了 "需求拆解→代码实现→优化迭代" 的编程思维,为后续开发更复杂的 Java 应用(如管理系统、小游戏)奠定了坚实基础。

相关推荐
Remember_9932 小时前
MySQL 索引详解:从原理到实战优化
java·数据库·mysql·spring·http·adb·面试
牵牛老人2 小时前
Qt中集成 MQTT 来实现物联网通信:从原理到实战全解析
开发语言·qt·物联网
micro_xx2 小时前
借助Matlab有限元工具pde进行静态结构有限元分析
开发语言·matlab
代码无bug抓狂人2 小时前
C语言之可分解的正整数(蓝桥杯省B)
c语言·开发语言·算法
Cher ~2 小时前
常见C++编译器套件
开发语言·c++
上海合宙LuatOS2 小时前
LuatOS ——Modbus RTU 通信模式
java·linux·服务器·开发语言·网络·嵌入式硬件·物联网
xyq20242 小时前
《jEasyUI 启用行内编辑》
开发语言
野生技术架构师2 小时前
Java 21虚拟线程 vs Kotlin协程:高并发编程模型的终极对决与选型思考
java·开发语言·kotlin
言之。2 小时前
Kotlin快速入门
android·开发语言·kotlin