CharacterUIController.cs 8.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304
  1. using UnityEngine;
  2. using UnityEngine.UI;
  3. using DamageNumbersPro;
  4. using System.Collections;
  5. public class CharacterUIController : MonoBehaviour
  6. {
  7. public Slider hpSlider;
  8. public Slider fatigueSlider;
  9. public Slider expSlider;
  10. public GameObject skillPanel;
  11. public Transform skillListContainer;
  12. public GameObject skillButtonPrefab;
  13. public GameObject inventoryPanel; // Panel displaying character inventory
  14. public InventoryUIController inventoryUIController; // Reference to inventory UI controller
  15. public Image characterIcon;
  16. public Button attackButton;
  17. public Button repeatActionButton;
  18. public Button openSkillsButton;
  19. public Button openInventoryButton; // Button to open character inventory
  20. public Image cooldownOverlay;
  21. public FirstPersonWeapon assignedWeapon;
  22. public CharacterInGroup character;
  23. public CharacterInGroup Character => character;
  24. public DamageNumber damageUIPrefab; // à assigner dans l’inspector (UI)
  25. public RectTransform damageSpawnPoint;
  26. public void Setup(CharacterInGroup chara, FirstPersonWeapon weapon)
  27. {
  28. character = chara;
  29. assignedWeapon = weapon;
  30. // Initialisation des sliders
  31. if (hpSlider != null)
  32. {
  33. hpSlider.maxValue = character.maxHP;
  34. hpSlider.value = character.currentHP;
  35. }
  36. if (fatigueSlider != null)
  37. {
  38. fatigueSlider.maxValue = character.maxFatigue;
  39. fatigueSlider.value = character.currentFatigue;
  40. }
  41. if (expSlider != null)
  42. {
  43. expSlider.maxValue = 100;
  44. expSlider.value = character.experience;
  45. }
  46. if (attackButton != null)
  47. attackButton.onClick.AddListener(OnAttack);
  48. if (repeatActionButton != null)
  49. repeatActionButton.onClick.AddListener(OnRepeat);
  50. if (openSkillsButton != null)
  51. openSkillsButton.onClick.AddListener(ToggleSkillPanel);
  52. if (openInventoryButton != null)
  53. openInventoryButton.onClick.AddListener(OnOpenInventory);
  54. UIUpdater.Instance?.Register(character, this);
  55. PopulateSkillList();
  56. if (cooldownOverlay != null)
  57. {
  58. cooldownOverlay.gameObject.SetActive(false);
  59. }
  60. }
  61. public void ShowDamageOnCard(int amount)
  62. {
  63. if (damageUIPrefab != null && damageSpawnPoint != null)
  64. {
  65. damageUIPrefab.SpawnGUI(damageSpawnPoint, Vector2.zero, amount);
  66. }
  67. }
  68. void PopulateSkillList()
  69. {
  70. foreach (Transform child in skillListContainer)
  71. Destroy(child.gameObject);
  72. foreach (var skill in character.learnedSkills)
  73. {
  74. SkillData data = skill.GetData();
  75. if (data == null) continue;
  76. var btnObj = Instantiate(skillButtonPrefab, skillListContainer);
  77. btnObj.transform.Find("Image").GetComponent<Image>().sprite = data.icon;
  78. Button btn = btnObj.GetComponent<Button>();
  79. if (btn != null)
  80. {
  81. // Capture la compétence associée
  82. SkillData capturedSkill = data;
  83. btn.onClick.AddListener(() => OnSkillButtonClicked(capturedSkill));
  84. }
  85. }
  86. }
  87. void OnAttack()
  88. {
  89. if (character.currentFatigue <= 0)
  90. {
  91. if (Random.value < 0.8f)
  92. {
  93. DisableButtonsTemporarily(5f);
  94. return;
  95. }
  96. }
  97. if (Random.value < 0.3f && character.currentFatigue > 0)
  98. {
  99. character.currentFatigue = Mathf.Max(0, character.currentFatigue - 5);
  100. UIUpdater.Instance?.UpdateCharacterFatigue(character);
  101. }
  102. character.lastAction = ActionType.Attack;
  103. assignedWeapon?.TriggerAttack();
  104. DisableButtonsTemporarily(5f);
  105. }
  106. void OnSkillButtonClicked(SkillData skillData)
  107. {
  108. int staminaCost = 15;
  109. if (character.currentFatigue < staminaCost)
  110. {
  111. return;
  112. }
  113. character.currentFatigue = Mathf.Max(0, character.currentFatigue - staminaCost);
  114. UIUpdater.Instance?.UpdateCharacterFatigue(character);
  115. if (skillData.skillName == "Boule de Feu")
  116. {
  117. FindFirstObjectByType<SpellCastingManager>()?.StartFireballCasting(skillData.icon.texture);
  118. character.lastAction = ActionType.UseSkill;
  119. character.lastSkillName = skillData.skillName;
  120. }
  121. DisableButtonsTemporarily(5f);
  122. }
  123. void OnRepeat()
  124. {
  125. switch (character.lastAction)
  126. {
  127. case ActionType.Attack:
  128. OnAttack();
  129. return;
  130. case ActionType.UseSkill:
  131. var learnedSkill = character.learnedSkills.Find(s => s.GetData()?.skillName == character.lastSkillName);
  132. if (learnedSkill != null)
  133. {
  134. var skillData = learnedSkill.GetData();
  135. if (skillData != null)
  136. {
  137. OnSkillButtonClicked(skillData);
  138. return;
  139. }
  140. }
  141. break;
  142. case ActionType.Heal:
  143. break;
  144. default:
  145. break;
  146. }
  147. DisableButtonsTemporarily(5f);
  148. }
  149. void ToggleSkillPanel()
  150. {
  151. if (skillPanel != null)
  152. skillPanel.SetActive(!skillPanel.activeSelf);
  153. }
  154. void OnOpenInventory()
  155. {
  156. if (inventoryPanel != null)
  157. {
  158. inventoryPanel.SetActive(!inventoryPanel.activeSelf);
  159. if (inventoryPanel.activeSelf && inventoryUIController != null)
  160. {
  161. inventoryUIController.Bind(character);
  162. }
  163. }
  164. }
  165. public void UpdateHPBar()
  166. {
  167. if (hpSlider == null || character == null) return;
  168. hpSlider.maxValue = character.maxHP;
  169. hpSlider.value = character.currentHP;
  170. UnityEngine.UI.LayoutRebuilder.ForceRebuildLayoutImmediate(hpSlider.GetComponent<RectTransform>());
  171. }
  172. public void UpdateFatigueBar()
  173. {
  174. if (fatigueSlider == null || character == null) return;
  175. fatigueSlider.maxValue = character.maxFatigue;
  176. fatigueSlider.value = character.currentFatigue;
  177. UnityEngine.UI.LayoutRebuilder.ForceRebuildLayoutImmediate(fatigueSlider.GetComponent<RectTransform>());
  178. }
  179. public void UpdateExpBar()
  180. {
  181. if (expSlider == null || character == null) return;
  182. expSlider.value = character.experience;
  183. UnityEngine.UI.LayoutRebuilder.ForceRebuildLayoutImmediate(expSlider.GetComponent<RectTransform>());
  184. }
  185. public void DisableButtonsTemporarily(float duration)
  186. {
  187. StartCoroutine(CooldownRoutine(duration));
  188. }
  189. private IEnumerator CooldownRoutine(float duration)
  190. {
  191. cooldownOverlay.gameObject.SetActive(true);
  192. SetButtonsInteractable(false);
  193. if (cooldownOverlay) cooldownOverlay.fillAmount = 1f;
  194. float elapsed = 0f;
  195. while (elapsed < duration)
  196. {
  197. elapsed += Time.deltaTime;
  198. float fill = Mathf.Clamp01(1f - elapsed / duration);
  199. if (cooldownOverlay) cooldownOverlay.fillAmount = fill;
  200. yield return null;
  201. }
  202. SetButtonsInteractable(true);
  203. if (cooldownOverlay) cooldownOverlay.fillAmount = 0f;
  204. }
  205. private void SetButtonsInteractable(bool interactable)
  206. {
  207. if (attackButton != null)
  208. attackButton.interactable = interactable;
  209. if (repeatActionButton != null)
  210. repeatActionButton.interactable = interactable;
  211. if (openSkillsButton != null)
  212. openSkillsButton.interactable = interactable;
  213. // Note: Inventory button should remain accessible during cooldown
  214. var fadedColor = interactable ? Color.white : new Color(1f, 1f, 1f, 0.5f);
  215. if (attackButton != null)
  216. attackButton.image.color = fadedColor;
  217. if (repeatActionButton != null)
  218. repeatActionButton.image.color = fadedColor;
  219. if (openSkillsButton != null)
  220. openSkillsButton.image.color = fadedColor;
  221. }
  222. public void HandleCharacterDeath()
  223. {
  224. string characterName = character.characterName;
  225. TeamCohesionManager cohesionManager = FindFirstObjectByType<TeamCohesionManager>();
  226. if (cohesionManager != null)
  227. {
  228. cohesionManager.groupMembers.Remove(character);
  229. }
  230. UIUpdater.Instance?.Unregister(characterName);
  231. Destroy(gameObject);
  232. if (cohesionManager != null && cohesionManager.groupMembers.Count == 0)
  233. {
  234. var gameManagerObj = GameObject.Find("GameManager");
  235. if (gameManagerObj != null)
  236. {
  237. gameManagerObj.SendMessage("OnPartyWiped", SendMessageOptions.DontRequireReceiver);
  238. }
  239. }
  240. }
  241. }