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

Unity C#农场游戏列表相关作物生长逻辑报错求助

Unity农场游戏作物生长阶段实现方案

1. 核心代码修正与实现

作物数据类定义

明确存储播种时间、位置、当前生长阶段及场景对象引用,避免数据与显示分离导致的逻辑错误:

public class CropsPlanted
{
    // 用游戏运行时间(适合单局游戏,重启后进度重置)
    public float TimeWhenSeeded { get; set; }
    public Vector3 Position { get; set; }
    public int CurrentGrowthStage { get; set; }
    public GameObject CropObject { get; set; }
}

全局作物管理集合

通过单例模式实现全局访问,确保集合已初始化:

public class FarmManager : MonoBehaviour
{
    public static FarmManager Instance;
    public List<CropsPlanted> PlantedCrops = new List<CropsPlanted>();

    void Awake()
    {
        Instance = this;
    }

    // 修正后的CreateObjectSeeded函数
    public void CreateObjectSeeded(Vector3 position, float timeWhenSeeded)
    {
        // 实例化作物预制体(替换为你的预制体路径)
        GameObject cropPrefab = Resources.Load<GameObject>("Prefabs/CropSeed");
        GameObject cropObj = Instantiate(cropPrefab, position, Quaternion.identity);
        
        // 创建作物数据并加入管理集合
        CropsPlanted cropData = new CropsPlanted
        {
            TimeWhenSeeded = timeWhenSeeded,
            Position = position,
            CurrentGrowthStage = 0, // 初始为播种阶段
            CropObject = cropObj
        };
        PlantedCrops.Add(cropData);
    }
}

时间检查与阶段切换逻辑

采用倒序遍历避免集合修改时的索引异常,明确时间差判断规则:

// 可放在FarmManager或单独的生长检测脚本中
void Update()
{
    CheckTimeCrops();
}

void CheckTimeCrops()
{
    var plantedCrops = FarmManager.Instance.PlantedCrops;
    // 倒序遍历,防止删除元素触发索引错误
    for (int i = plantedCrops.Count - 1; i >= 0; i--)
    {
        CropsPlanted crop = plantedCrops[i];
        float timeElapsed = Time.time - crop.TimeWhenSeeded;

        // 替换为你的实际阶段阈值(示例:10秒进入生长阶段,20秒成熟)
        if (timeElapsed >= 20f && crop.CurrentGrowthStage != 2)
        {
            UpdateCropStage(crop, 2); // 切换到成熟阶段
        }
        else if (timeElapsed >= 10f && crop.CurrentGrowthStage != 1)
        {
            UpdateCropStage(crop, 1); // 切换到生长阶段
        }
    }
}

// 单独处理阶段切换,便于扩展显示逻辑
void UpdateCropStage(CropsPlanted crop, int newStage)
{
    crop.CurrentGrowthStage = newStage;
    // 替换作物显示(示例:切换Sprite)
    SpriteRenderer renderer = crop.CropObject.GetComponent<SpriteRenderer>();
    switch (newStage)
    {
        case 1:
            renderer.sprite = Resources.Load<Sprite>("Sprites/CropStage1");
            break;
        case 2:
            renderer.sprite = Resources.Load<Sprite>("Sprites/CropStage2");
            // 成熟后添加采摘交互逻辑
            crop.CropObject.AddComponent<CropHarvest>();
            break;
    }
}

2. 跨会话生长进度保存(可选)

若需关闭游戏后保留生长状态,改用真实时间存储:

// 修改CropsPlanted类的时间属性
public DateTime TimeWhenSeeded { get; set; }

// CreateObjectSeeded中赋值
TimeWhenSeeded = DateTime.Now;

// CheckTimeCrops中计算时间差
TimeSpan timeElapsed = DateTime.Now - crop.TimeWhenSeeded;
float totalSeconds = (float)timeElapsed.TotalSeconds;
// 后续阶段判断逻辑不变

3. 常见报错排查

  • NullReferenceException:检查PlantedCrops是否初始化、FarmManager.Instance是否有效、CropObject是否正确实例化
  • InvalidOperationException:禁止用foreach遍历并修改集合,改用倒序for循环
  • 时间对比无效果:若需不受游戏暂停影响,将Time.time替换为Time.realtimeSinceStartup

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.28 19:53:10