C# Unity 游戏中实现行动点消耗影响饥饿和健康值
C# Unity 游戏中实现行动点消耗影响饥饿和健康值
本文介绍如何在C# Unity游戏中实现一个功能:每次消耗行动点后,角色饥饿值下降,当饥饿值低于一定阈值时,角色健康值开始下降。
代码示例:
namespace QFramework.Escape
{
[Serializable]
// 玩家Model属性
public class PlayerModel : AbstractModel
{
public int maxHealth = 100;
public int maxHungry = 100;
public int maxActionPoint = 5;
public int health = 100;
public int hungry = 100;
public int actionPoint = 5;
public float speed = 3;
public int hungryThreshold = 40;
public int Health
{
get => health; set
{
health = Mathf.Clamp(value, 0, maxHealth);
}
}
public int Hungry
{
get => hungry; set
{
hungry = Mathf.Clamp(value, 0, maxHungry);
}
}
public int ActionPoint
{
get => actionPoint; set
{
actionPoint = Mathf.Clamp(value, 0, maxActionPoint);
}
}
public float Speed { get => speed; set => speed = value; }
protected override void OnInit()
{
}
}
public partial class Player : ViewController
{
private static Player mInstance;
// Model
[SerializeField]
public PlayerModel playerData;
// 固定的Y轴偏移
public float YOffset = -2.5f;
public Animator animator;
// 是否锁定(对话时)
public bool Blocking = false;
// 单例
public static Player Instance
{
get
{
if (mInstance == null)
{
mInstance = FindObjectOfType<Player>();
}
return mInstance;
}
}
private void Awake()
{
// 初始化组件
animator = Sprite.gameObject.GetComponent<Animator>();
}
void Start()
{
if (mInstance == null)
{
mInstance = this;
}
// 创建行动点
for (int i = 0; i < this.playerData.maxActionPoint; i++)
{
Instantiate(Player.Instance.UIActionPointItem, this.PointPanel.transform);
}
// 初始化UI
RefreshView();
}
private void Update()
{
HandleMove();
if (playerData.ActionPoint > 0)
{
playerData.ActionPoint--;
playerData.Hungry -= 5;
if (playerData.Hungry <= playerData.hungryThreshold)
{
playerData.Health -= 10;
}
}
}
/// <summary>
/// 处理移动逻辑
/// </summary>
private void HandleMove()
{
float horizontalInput = Input.GetAxis("Horizontal");
if (Blocking)
{
horizontalInput = 0;
}
// 使用物理速度移动
//this.transform.Translate(Vector3.right * horizontalInput * this.playerData.Speed * Time.deltaTime);
this.Rigbody.velocity = new Vector2(horizontalInput * this.playerData.Speed, 0);
// 触发动画
{
animator.SetFloat("HorizontalInput", horizontalInput);
animator.SetBool("Moving", horizontalInput != 0);
}
}
/// <summary>
/// 进入房间,重置摄像机和玩家的位置
/// </summary>
/// <param name="room"></param>
public void IntoRoom(Room room, GameObject door)
{
if (this.Blocking)
{
return;
}
// 进入房间后,修改摄像机和玩家的位置
IntoRoom(room);
if (door)
{
this.transform.position = door.transform.position;
}
// 进入其他房间时,关闭所有UI
UIKit.CloseAllPanel();
// 限制X轴小于5.8大于-5.8,固定玩家的Y轴
this.transform.position = new Vector3(Mathf.Clamp(this.transform.position.x, room.transform.position.x - 5.8f, room.transform.position.x + 5.8f), YOffset, this.transform.position.z);
}
/// <summary>
/// 进入房间,重置摄像机和玩家的位置
/// </summary>
/// <param name="room"></param>
public void IntoRoom(Room room)
{
// 进入房间后,修改摄像机和玩家的位置
this.transform.position = room.GetPlayerSpawnPos();
this.Camera.transform.position = room.GetCameraPos();
// 弹出房间名称
GameHandle.PopMsg(room.RoomName);
}
public void ApplyPlayerInfluence(PlayerInfluence inf)
{
if (inf.AddHealth != 0 || inf.SetHealth >= 0)
{
this.AddHealth(inf.AddHealth);
if (inf.SetHealth >= 0)
{
this.SetHealth(inf.SetHealth);
}
}
// 以同样的方式处理饥饿值
if (inf.AddHungry != 0 || inf.SetHungry >= 0)
{
this.AddHungry(inf.AddHungry);
if (inf.SetHungry >= 0)
{
this.SetHungry(inf.SetHungry);
}
}
// 以同样的方式处理行动点
if (inf.AddActionPoint != 0 || inf.SetActionPoint >= 0)
{
this.AddActionPoint(inf.AddActionPoint);
if (inf.SetActionPoint >= 0)
{
this.SetActionPoint(inf.SetActionPoint);
}
}
}
private void RefreshView()
{
RefreshHealthBar();
RefreshHungryBar();
UpdateActionPointView();
}
private void RefreshHealthBar()
{
// 刷新血条
this.HealthBar.value = ((float)this.playerData.Health / (float)this.playerData.maxHealth);
}
private void RefreshHungryBar()
{
// 刷新饥饿值
this.HungryBar.value = ((float)this.playerData.Hungry / (float)this.playerData.maxHungry);
}
public void SetHealth(int health)
{
this.playerData.Health = health;
RefreshHealthBar();
}
public void AddHealth(int health)
{
this.playerData.Health += health;
RefreshHealthBar();
}
public void SetHungry(int hungry)
{
this.playerData.Hungry = hungry;
RefreshHungryBar();
}
public void AddHungry(int hungry)
{
this.playerData.Hungry += hungry;
if (this.playerData.Hungry <= this.playerData.hungryThreshold)
{
this.playerData.Health -= 10;
}
RefreshHungryBar();
}
public void SetActionPoint(int point)
{
this.playerData.ActionPoint = point;
UpdateActionPointView();
}
public void AddActionPoint(int point)
{
this.playerData.ActionPoint += point;
UpdateActionPointView();
}
public void UpdateActionPointView()
{
// 清空原有的行动点显示
foreach (Transform child in this.PointPanel.transform)
{
child.gameObject.SetActive(false);
}
// 显示新的行动点
for (int i = 0; i < this.playerData.ActionPoint; i++)
{
this.PointPanel.transform.GetChild(i).gameObject.SetActive(true);
}
}
}
}
代码解释:
- 在
PlayerModel类中添加一个新的属性hungryThreshold,用于存储饥饿下降阈值。 - 在
Player类的Update方法中,在行动点消耗后处理饥饿下降和健康下降逻辑。如果当前行动点大于0,则消耗一个行动点,饥饿值下降 5 点,如果饥饿值低于阈值,则健康值下降 10 点。 - 修改
ApplyPlayerInfluence方法,将修改饥饿值和行动点的逻辑移动到AddHungry和AddActionPoint方法中,并在AddHungry方法中添加饥饿值低于阈值时健康值下降的逻辑。
改进建议:
- 可以考虑添加UI提示,例如在饥饿值低于阈值时,在屏幕上显示警告提示。
- 可以考虑添加恢复饥饿值的功能,例如通过吃食物来恢复饥饿值。
- 可以考虑添加其他属性,例如体力值,并使其受到饥饿值的影响。
注意事项:
- 此代码仅供参考,具体实现需要根据您的游戏需求进行调整。
- 确保代码逻辑清晰易懂,便于维护和扩展。
- 定期测试代码,确保功能正常运行。
结语:
通过以上代码示例和改进建议,您应该能够在C# Unity游戏中实现行动点消耗影响饥饿和健康值的功能。希望本文能对您有所帮助。
原文地址: https://www.cveoy.top/t/topic/pcUg 著作权归作者所有。请勿转载和采集!