2
0
Fork 0
You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

491 lines
18 KiB
C#

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

using System.Collections.Generic;
using UnityEngine;
using Game.Battle;
namespace Game
{
/// <summary>
/// 实体身上的UI显示均在此管理
/// </summary>
public class PageHeadBar : UIPageBase<ViewHeadBar>
{
private int _targetCache = 0;
private readonly Dictionary<int, UIPoolItem<Viewc_blood>> _hpBarDict =
new Dictionary<int, UIPoolItem<Viewc_blood>>();
private readonly Dictionary<int, List<UIPoolItem<ViewHitNum>>> _hitNumDict =
new Dictionary<int, List<UIPoolItem<ViewHitNum>>>();
private readonly Dictionary<int, List<UIPoolItem<ViewHitBuff>>> _hitBuffDict =
new Dictionary<int, List<UIPoolItem<ViewHitBuff>>>();
private readonly Dictionary<int, UIPoolItem<ViewInteract>> _interactDict =
new Dictionary<int, UIPoolItem<ViewInteract>>();
protected override void OnCreate()
{
CreateUI(false);
}
protected override void OnOpen()
{
//打开时创建所有非主角实体的血条
var entities = Util.GetGroup(GameMatcher.Interact); //怪物、npc、宝箱、传送门...
foreach (var entity in entities)
{
if (entity.iD.Data.IsDestroy)
{
continue;
}
SetHpBar(entity.ID(), true);
SetHitNum(entity.ID(), true);
SetInteract(entity.ID(), true);
}
EventManager.Instance.AddEvent<PEntityAlive>(EEvent.EntityAlive, OnEntityAlive);
EventManager.Instance.AddEvent<PEntityHit>(EEvent.EntityHit, OnEntityHit);
EventManager.Instance.AddEvent<PEntityHitText>(EEvent.EntityHitText, OnEntityHitText);
UpdateHeadBarPos(); //打开时更新位置 避免闪烁
}
protected override void OnClose()
{
foreach (var kvp in _hpBarDict)
{
kvp.Value.Destroy();
}
_hpBarDict.Clear();
EventManager.Instance.RemoveEvent<PEntityAlive>(EEvent.EntityAlive, OnEntityAlive);
EventManager.Instance.RemoveEvent<PEntityHit>(EEvent.EntityHit, OnEntityHit);
EventManager.Instance.RemoveEvent<PEntityHitText>(EEvent.EntityHitText, OnEntityHitText);
}
public override void FixedUpdate()
{
UpdateLock(); //锁定
UpdateHeadBarPos(); //headBar位置更新
UpdateHitNum(); //跳字更新
UpdateHitBuff(); //buff跳字更新
}
private void UpdateLock()
{
var master = Util.GetMaster();
var targetId = master.combo.TargetLock;
var target = Util.GetEntity(targetId);
View.m_showLock.SetSelectedIndex(target == null ? 0 : 1);
if (target == null)
return;
if (targetId != _targetCache)
{
View.m_lock.m_actLock.Play();
_targetCache = targetId;
}
View.m_lock.position = GetScreenPos(Util.EntityViewPos(target));
}
private void UpdateHeadBarPos()
{
foreach (var kvp in _hpBarDict)
{
var entity = Util.GetEntity(kvp.Key);
if (entity != null)
{
var headBarItem = kvp.Value;
var posScreen = GetScreenPos(Util.EntityViewPos(entity));
headBarItem.Component.SetPosition(posScreen.x, posScreen.y - 80, posScreen.z);
}
}
foreach (var kvp in _hitNumDict)
{
var entity = Util.GetEntity(kvp.Key);
if (entity != null)
{
var hitNumList = kvp.Value;
var posScreen = GetScreenPos(Util.EntityViewPos(entity));
foreach (var item in hitNumList)
{
item.Component.SetPosition(posScreen.x, posScreen.y, posScreen.z);
}
}
}
foreach (var kvp in _hitBuffDict)
{
var entity = Util.GetEntity(kvp.Key);
if (entity != null)
{
var hitNumList = kvp.Value;
var posScreen = GetScreenPos(Util.EntityViewPos(entity));
foreach (var item in hitNumList)
{
item.Component.SetPosition(posScreen.x, posScreen.y - 40, posScreen.z);
}
}
}
foreach (var kvp in _interactDict)
{
var entity = Util.GetEntity(kvp.Key);
if (entity != null)
{
var interactItem = kvp.Value;
var posScreen = GetScreenPos(Util.EntityViewPos(entity));
interactItem.Component.SetPosition(posScreen.x, posScreen.y - 80, posScreen.z);
}
}
}
/// <summary>
/// 更新伤害跳字:更新动效等待时间等待时间结束播放2阶段动效 2阶段动效结束删除
/// </summary>
private void UpdateHitNum()
{
foreach (var kvp in _hitNumDict)
{
var hitNumList = kvp.Value;
if (hitNumList.Count == 0)
{
continue;
}
var entity = Util.GetEntity(kvp.Key);
if (entity == null)
{
continue;
}
if (entity.pause.IsPause)
{
continue;
}
var hp = entity.hp;
if (hp.DmgShowTime > 0)
{
hp.DmgShowTime -= Time.deltaTime;
if (hp.DmgShowTime <= 0)
{
hp.DmgShowTime = 0;
var lastItem = hitNumList[hitNumList.Count - 1].Component as ViewHitNum;
lastItem.m_step2.Play();
if (GameRandom.Roll(0.5f))
{
lastItem.m_step3.Play();
}
else
{
lastItem.m_step4.Play();
}
}
}
for (int i = hitNumList.Count - 1; i >= 0; i--)
{
if (i == hitNumList.Count - 1 && hp.DmgShowTime > 0)
{
continue;
}
var item = hitNumList[i];
var hitInfo = hitNumList[i].Component as ViewHitNum;
if (!hitInfo.m_step2.playing)
{
item.Destroy();
hitNumList.RemoveAt(i);
}
}
}
}
private void UpdateHitBuff()
{
foreach (var kvp in _hitBuffDict)
{
var hitNumList = kvp.Value;
if (hitNumList.Count == 0)
{
continue;
}
var entity = Util.GetEntity(kvp.Key);
if (entity == null)
{
continue;
}
if (entity.pause.IsPause)
{
continue;
}
for (int i = hitNumList.Count - 1; i >= 0; i--)
{
var item = hitNumList[i];
var hitInfo = hitNumList[i].Component as ViewHitBuff;
if (entity.pause.IsPause)
{
hitInfo.m_step1.SetPaused(true);
continue;
}
hitInfo.m_step1.SetPaused(false);
if (!hitInfo.m_step1.playing)
{
item.Destroy();
hitNumList.RemoveAt(i);
}
}
}
}
private void OnEntityAlive(PEntityAlive param)
{
var entity = param.Entity;
if (entity == Util.GetMasterID())
{
return;
}
SetHpBar(param.Entity, param.IsAlive);
SetHitNum(param.Entity, param.IsAlive);
SetInteract(param.Entity, param.IsAlive);
}
private void SetInteract(int entityID, bool isAlive = true)
{
var entity = Util.GetEntity(entityID);
if (!entity.hasInteract)
{
return;
}
if (isAlive)
{
if (!_interactDict.ContainsKey(entityID))
{
var interactBar = UIManager.Instance.Creator.CreateUIItem<ViewInteract>(ViewInteract.URL);
_interactDict[entityID] = interactBar;
var interactComp = interactBar.Component;
var interact = entity.interact;
BindData(interact.IsActive,
(_, now) => { interactComp.m_showInteract.selectedIndex = now ? 1 : 0; });
BindData(interact.IsTarget,
(_, now) => { interactComp.m_isTarget.selectedIndex = now ? 1 : 0; });
}
}
else
{
if (_interactDict.ContainsKey(entityID))
{
_interactDict[entityID].Destroy();
_interactDict.Remove(entityID);
var interact = entity.interact;
UnbindData(interact.IsActive);
UnbindData(interact.IsTarget);
}
}
}
private void SetHitNum(int entityID, bool isAlive = true)
{
if (isAlive)
{
if (!_hitNumDict.ContainsKey(entityID))
{
_hitNumDict[entityID] = new List<UIPoolItem<ViewHitNum>>();
_hitBuffDict[entityID] = new List<UIPoolItem<ViewHitBuff>>();
}
}
else
{
if (_hitNumDict.ContainsKey(entityID))
{
foreach (var item in _hitNumDict[entityID])
{
item.Destroy();
}
_hitNumDict.Remove(entityID);
foreach (var item in _hitBuffDict[entityID])
{
item.Destroy();
}
_hitBuffDict.Remove(entityID);
}
}
}
private void SetHpBar(int entityID, bool isAlive = true)
{
var entity = Util.GetEntity(entityID);
if (!entity.hasHp)
{
return;
}
if (isAlive)
{
if (!_hpBarDict.ContainsKey(entityID))
{
//创建血条UI
var hpBar = UIManager.Instance.Creator.CreateUIItem<Viewc_blood>(Viewc_blood.URL);
_hpBarDict[entityID] = hpBar;
var hpComp = hpBar.Component;
if (entity.hasHp)
{
var hp = entity.hp;
var buff = entity.buff;
var ai = entity.aI;
//数据绑定
BindData(hp.IsDamaged, (_, now) =>
{
hpComp.m_showhp.selectedIndex = now ? 1 : 0;
hpComp.m_showshield.selectedIndex = now && (hp.ShieldMax.Value > 0) ? 1 : 0;
//是否显示额外数据
var isShowExtra = now && GameSetting.IsShowExtraHeadBar;
hpComp.m_showExtra.selectedIndex = isShowExtra ? 1 : 0;
});
BindData(hp.HpMax, (_, now) =>
{
hpComp.m_bloodBarEnemy.m_sub.max = now;
hpComp.m_bloodBarEnemy.m_tween.max = now;
//根据hpMax动态调整血条长度
var width = Mathf.Clamp(now, 40, 150);
hpComp.m_bloodBarEnemy.width = width;
hpComp.m_shieldBarEnemy.width = width;
});
BindData(hp.Hp, (_, now) =>
{
hpComp.m_bloodBarEnemy.m_sub.value = now;
hpComp.m_bloodBarEnemy.m_tween.TweenValue(now - 1, 0.5f);
});
BindData(hp.ShieldMax, (_, now) =>
{
hpComp.m_shieldBarEnemy.m_sub.max = now;
hpComp.m_shieldBarEnemy.m_tween.max = now;
hpComp.m_showshield.selectedIndex = hp.IsDamaged.Value && (now > 0) ? 1 : 0;
});
BindData(hp.Shield, (_, now) =>
{
hpComp.m_shieldBarEnemy.m_sub.value = now;
hpComp.m_shieldBarEnemy.m_tween.TweenValue(now - 1, 0.5f);
hpComp.m_showshield.selectedIndex = hp.IsDamaged.Value && (now > 0) ? 1 : 0;
});
BindData(hp.Stun, (_, now) => { hpComp.m_stunBarEnemy.value = now; });
BindData(hp.StunMax, (_, now) => { hpComp.m_stunBarEnemy.max = now; });
BindData(ai.Hungry, (_, now) => { hpComp.m_hungryBarEnemy.value = now; });
BindData(ai.HungryMax, (_, now) => { hpComp.m_hungryBarEnemy.max = now; });
BindData(ai.ModuleType, (_, now) => { hpComp.m_moduleType.selectedIndex = (int)now; });
BindData(ai.IsHungryFull, (_, now) =>
{
if (now)
{
hpComp.m_attackStatus.selectedIndex = 1;
}
});
BindData(ai.AttackPermit, (_, now) =>
{
if (now)
{
hpComp.m_attackStatus.selectedIndex = 2;
}
else
{
hpComp.m_attackStatus.selectedIndex = 0;
}
});
}
}
}
else
{
if (_hpBarDict.ContainsKey(entityID))
{
//销毁血条ui
_hpBarDict[entityID].Destroy();
_hpBarDict.Remove(entityID);
//取消数据绑定
if (entity.hasHp)
{
var hp = entity.hp;
var ai = entity.aI;
var buff = entity.buff;
UnbindData(hp.HpMax);
UnbindData(hp.Hp);
UnbindData(hp.ShieldMax);
UnbindData(hp.Shield);
UnbindData(hp.StunMax);
UnbindData(hp.Stun);
UnbindData(ai.HungryMax);
UnbindData(ai.Hungry);
UnbindData(ai.ModuleType);
UnbindData(ai.IsHungryFull);
UnbindData(ai.AttackPermit);
}
}
}
}
private void OnEntityHit(PEntityHit param)
{
AddHitNum(param.Target, param.Dmg);
}
private void OnEntityHitText(PEntityHitText param)
{
AddHitText(param.Target, param.Text);
}
private void AddHitNum(int entityID, int dmg)
{
if (!_hitNumDict.ContainsKey(entityID))
{
return;
}
var hitList = _hitNumDict[entityID];
var hp = Util.GetEntity(entityID).hp;
ViewHitNum targetItem = null;
if (hp.DmgShowTime == 0)
{
hp.LastDmg = dmg;
var hitNum = UIManager.Instance.Creator.CreateUIItem<ViewHitNum>(ViewHitNum.URL);
var item = hitNum.Component as ViewHitNum;
hitList.Add(hitNum);
targetItem = item;
}
else
{
hp.LastDmg += dmg;
targetItem = hitList[hitList.Count - 1].Component as ViewHitNum;
}
targetItem.m_num.text = $"{hp.LastDmg}";
targetItem.m_step1.Play();
hp.DmgShowTime = GameConst.HitNumTerm;
}
private void AddHitText(int entityID, string text)
{
if (!_hitBuffDict.ContainsKey(entityID))
{
return;
}
var hitList = _hitBuffDict[entityID];
var hitNum = UIManager.Instance.Creator.CreateUIItem<ViewHitBuff>(ViewHitBuff.URL);
hitList.Add(hitNum);
var item = hitNum.Component as ViewHitBuff;
item.m_name.text = text;
item.m_step1.Play();
}
}
}