You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

OpenGL 2D Survival Shooter项目如何实现定时生成且不销毁现有敌人的生成器

实现多敌人定时生成方案

核心逻辑说明

你当前的问题核心是没有存储所有敌人的独立状态,也没有新增计时触发生成的逻辑,按照以下步骤修改即可实现需求:

第一步:定义敌人数据结构与类成员变量

首先在Tema1类的头文件中新增敌人结构体和相关控制变量,存储所有敌人的独立属性:

// 敌人属性结构体,每个敌人独有一套位置、速度参数
struct Enemy {
    float posX;
    float posY;
    float speed;
    // 后续可扩展血量、敌人类型等属性
};

// 在Tema1类中新增以下成员变量
private:
    std::vector<Enemy> enemies; // 存储所有存活敌人的列表
    float spawnTimer = 0.0f; // 生成计时变量
    const float SPAWN_INTERVAL = 5.0f; // 生成间隔,这里设为5秒,可自行修改

第二步:在Update方法中添加定时生成逻辑

每帧累加计时,达到间隔阈值就生成新敌人加入列表,不会影响已存在的敌人:

void Tema1::Update(float deltaTime) {
    // 累加生成计时器
    spawnTimer += deltaTime;

    // 达到生成间隔时触发新敌人生成
    if (spawnTimer >= SPAWN_INTERVAL) {
        spawnTimer = 0.0f; // 重置计时器
        Enemy newEnemy;

        // --------------------------
        // 以下是生成位置逻辑,二选一即可
        // 方案1:随机边界生成(地图外出生,避免突然出现在视野内)
        int spawnSide = rand() % 4; // 0-3对应上、右、下、左四个地图边界
        float mapWidth = 1920; // 替换为你的实际地图宽度
        float mapHeight = 1080; // 替换为你的实际地图高度
        switch(spawnSide) {
            case 0: // 上边界
                newEnemy.posX = rand() % (int)mapWidth;
                newEnemy.posY = mapHeight + 50;
                break;
            case 1: // 右边界
                newEnemy.posX = mapWidth + 50;
                newEnemy.posY = rand() % (int)mapHeight;
                break;
            case 2: // 下边界
                newEnemy.posX = rand() % (int)mapWidth;
                newEnemy.posY = -50;
                break;
            case 3: // 左边界
                newEnemy.posX = -50;
                newEnemy.posY = rand() % (int)mapHeight;
                break;
        }

        // 方案2:固定点位随机生成,提前定义好生成点数组即可
        // float spawnPoints[3][2] = {{100, 100}, {1820, 100}, {1820, 980}};
        // int selectIdx = rand() % 3;
        // newEnemy.posX = spawnPoints[selectIdx][0];
        // newEnemy.posY = spawnPoints[selectIdx][1];
        // --------------------------

        newEnemy.speed = 100.0f; // 可固定也可设为随机速度
        enemies.push_back(newEnemy); // 新敌人加入列表,原有敌人不受影响
    }

    // 遍历所有敌人,调用你的绘制方法更新位置+渲染
    glm::mat3 visMatrix = GetVisMatrix(); // 替换为你实际获取visMatrix的代码
    for (auto& enemy : enemies) {
        SpawnEnemy(visMatrix, deltaTime, &enemy.posX, &enemy.posY, enemy.speed);
    }

    // 后续可在此处添加敌人死亡/出界的移除逻辑,避免列表无限膨胀
}

第三步:原有SpawnEnemy方法适配

你现有的SpawnEnemy方法不需要做任何修改,遍历调用时每个敌人会传入自己的位置指针,独立更新位置、独立渲染,不会互相覆盖,已存在的敌人也不会被销毁。


补充注意点

  • 随机生成逻辑可以换成C++11的<random>库替代rand(),避免生成结果不均匀的问题
  • 如果需要限制场上最大敌人数量,加一个判断enemies.size() < MAX_ENEMY_COUNT再触发生成即可
  • 敌人死亡或者跑出地图后记得调用enemies.erase()移除对应元素,优化性能

内容的提问来源于stack exchange,提问作者Catalin Ursu

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.26 03:57:03