This commit is contained in:
SoulliesOfficial
2025-10-23 00:49:44 -04:00
parent 9b1b5ca93f
commit 61a397dd4c
9846 changed files with 2618439 additions and 793547 deletions

View File

@@ -1,10 +1,9 @@
using System;
using Sirenix.OdinInspector;
using System.Collections.Generic;
using TMPro;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.InputSystem;
using UnityEngine.Serialization;
using UnityEngine.UI;
namespace Continentis.MainGame.Card
@@ -21,16 +20,27 @@ namespace Continentis.MainGame.Card
public TMP_Text staminaCostText;
public TMP_Text manaCostText;
public TMP_Text cardTypeText;
public Image cardBackground;
public Image cardImage;
public Image cardRarityMark;
public CardViewKeywordList keywordList;
public Image normalShadow;
public Image hintShadow;
public Image selectShadow;
public string collectionName;
}
public partial class CardViewBase
{
public bool isOccupied;
public bool isHovering;
public bool isSelecting;
public bool isDuringPlaying;
private void Update()
@@ -46,7 +56,11 @@ namespace Continentis.MainGame.Card
if(isDuringPlaying) return;
isHovering = true;
keywordList.Enable(cardInstance.cardLogic.contentSubmodule.keywords);
List<string> allKeywords = new List<string>();
allKeywords.AddRange(cardLogic.contentSubmodule.keywords);
allKeywords.AddRange(cardLogic.contentSubmodule.hintKeywords);
keywordList.Enable(allKeywords);
}
public virtual void OnPointerExit(PointerEventData eventData)
@@ -65,37 +79,41 @@ namespace Continentis.MainGame.Card
cardInstance = card;
}
isOccupied = false;
isHovering = false;
isSelecting = false;
isDuringPlaying = false;
cardNameText.text = cardLogic.contentSubmodule.cardName;
cardDescriptionText.text = cardLogic.contentSubmodule.cardDescription;
cardDescriptionText.text = cardLogic.contentSubmodule.interpretedFunctionText;
cardImage.sprite = cardLogic.contentSubmodule.cardSprite;
if (cardLogic.contentSubmodule.cardRarity != CardRarity.None)
if (cardLogic.contentSubmodule.cardRarity != Rarity.None)
{
cardRarityMark.color = cardLogic.contentSubmodule.cardRarity switch
{
CardRarity.Common => Color.white,
CardRarity.Uncommon => new Color(0.2f, 0.7f, 0.2f), // 绿色
CardRarity.Rare => new Color(0f, 0.5f, 1f), // 蓝色
CardRarity.Epic => new Color(0.6f, 0f, 0.8f), // 紫色
CardRarity.Legendary => new Color(1f, 0.5f, 0f), // 橙色
CardRarity.Divine => new Color(1f, 0.84f, 0f), // 金色
_ => Color.grey
};
cardRarityMark.color = MainGameManager.Instance.basePrefabs.GetRarityColor(cardLogic.contentSubmodule.cardRarity);
}
else
{
cardRarityMark.gameObject.SetActive(false);
}
if (string.IsNullOrEmpty(collectionName)) collectionName = "Basic";
CardViewCollection collection = MainGameManager.Instance.basePrefabs.cardViewCollections[collectionName];
List<string> elementTags = cardLogic.GetElementTags();
string firstElementTag = elementTags.Count > 0 ? elementTags[0] : "Default";
if (!collection.cardViews.ContainsKey(firstElementTag)) firstElementTag = "Default";
cardBackground.sprite = collection.cardViews[firstElementTag].background;
cardTypeText.text = cardLogic.contentSubmodule.cardType.ToString();
staminaCostText.rectTransform.parent.gameObject.SetActive(true);
staminaCostText.text = cardLogic.attributeSubmodule.GetRoundCurrentAttribute("StaminaCost").ToString();
int manaCost = cardLogic.attributeSubmodule.GetRoundCurrentAttribute("ManaCost");
manaCostText.rectTransform.parent.gameObject.SetActive(manaCost > 0);
manaCostText.text = manaCost.ToString();
if (cardLogic.HasTag("Unplayable")) // 如果卡牌不能被打出,则隐藏费用文本
if (cardLogic.HasKeyword("Unplayable")) // 如果卡牌不能被打出,则隐藏费用文本
{
staminaCostText.rectTransform.parent.gameObject.SetActive(false);
manaCostText.rectTransform.parent.gameObject.SetActive(false);

View File

@@ -0,0 +1,23 @@
using System;
using System.Collections.Generic;
using SLSFramework.General;
using UnityEngine;
namespace Continentis.MainGame.Card
{
[CreateAssetMenu(fileName = "CardViewCollection", menuName = "Continentis/MainGame/Card/CardViewCollection")]
public class CardViewCollection : ScriptableObject
{
[KeyWidth(0.25f)]
public SerializableDictionary<string, CardViewParts> cardViews;
}
[Serializable]
public class CardViewParts
{
public Sprite background;
[KeyWidth(0.25f)]
public SerializableDictionary<string, GameObject> customParts;
}
}

View File

@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: d9af8ea1600887d498ff2b813a9aaef8

View File

@@ -0,0 +1,65 @@
using DG.Tweening;
using UnityEngine;
namespace Continentis.MainGame.Card
{
public abstract partial class CardViewBase
{
Tweener hintShadowTweener;
Tweener selectShadowTweener;
public void ClearShadows()
{
hintShadowTweener?.Kill(true);
selectShadowTweener?.Kill(true);
hintShadow.gameObject.SetActive(false);
selectShadow.gameObject.SetActive(false);
}
public void TryDisableAllShadows(bool immediately = false)
{
DisableHintShadow(immediately);
DisableSelectShadow(immediately);
}
public void EnableHintShadow(Color shadowColor)
{
hintShadow.gameObject.SetActive(true);
hintShadow.color = Color.clear;
hintShadowTweener = hintShadow.DOColor(shadowColor, 0.2f).Play();
}
public void DisableHintShadow(bool immediately = false)
{
if (immediately)
{
hintShadowTweener?.Kill(true);
hintShadow.gameObject.SetActive(false);
}
else
{
hintShadowTweener = hintShadow.DOColor(Color.clear, 0.2f).OnComplete(() => { hintShadow.gameObject.SetActive(false); }).Play();
}
}
public void EnableSelectShadow()
{
selectShadow.gameObject.SetActive(true);
selectShadow.color = Color.clear;
selectShadowTweener = selectShadow.DOColor(new Color(0.33f, 0.66f, 1f), 0.2f).Play();
}
public void DisableSelectShadow(bool immediately = false)
{
if (immediately)
{
selectShadowTweener?.Kill(true);
selectShadow.gameObject.SetActive(false);
}
else
{
selectShadowTweener = selectShadow.DOColor(Color.clear, 0.2f).OnComplete(() => { selectShadow.gameObject.SetActive(false); }).Play();
}
}
}
}

View File

@@ -0,0 +1,2 @@
fileFormatVersion: 2
guid: 5352b6ab2496aa34e82a2182052d556c

View File

@@ -1,9 +1,10 @@
using System;
using System.Collections.Generic;
using Continentis.MainGame.Combat;
using Continentis.MainGame.UI;
using DG.Tweening;
using Lean.Pool;
using SoulliesFramework.General;
using SLSFramework.General;
using Unity.VisualScripting;
using UnityEngine;
using UnityEngine.UI;
@@ -27,15 +28,19 @@ namespace Continentis.MainGame.Card
disableTweener = canvasGroup.DOFade(0f, 0.2f).SetEase(Ease.OutQuad).SetAutoKill(false);
}
public void SetUp(List<string> keywords)
public void SetUp(List<string> keys)
{
keywordsContainer.DespawnAllChildren();
foreach (string keyword in keywords)
foreach (string key in keys)
{
string desc = CombatMainManager.Instance.keywordCollection.GetKeywordDescription(keyword);
InformationBox keywordBox = LeanPool.Spawn(MainGameManager.Instance.basePrefabs.informationBox, keywordsContainer).GetComponent<InformationBox>();
keywordBox.Initialize(keyword, desc);
if (MainGameManager.Instance.keywordData.TryGetLocalizedKeyword(key, out string locName, out string locDesc))
{
InformationBox keywordBox = LeanPool.Spawn(MainGameManager.Instance.basePrefabs.informationBox, keywordsContainer)
.GetComponent<InformationBox>();
keywordBox.Initialize(locName, locDesc);
}
}
}

View File

@@ -1,7 +1,8 @@
using System.Collections.Generic;
using Continentis.MainGame.Character;
using Continentis.MainGame.Combat;
using Continentis.MainGame.UI;
using SoulliesFramework.General;
using SLSFramework.General;
using UnityEngine;
using UnityEngine.EventSystems;
@@ -9,6 +10,8 @@ namespace Continentis.MainGame.Card
{
public partial class HandCardView : IBeginDragHandler, IDragHandler, IEndDragHandler, IPointerClickHandler
{
public CombatCharacterViewBase currentTargetingCharacterView;
public List<CharacterBase> validTargets = new List<CharacterBase>();
public List<CharacterBase> conditionNotMetTargets = new List<CharacterBase>();
public List<CharacterBase> invalidTargets = new List<CharacterBase>();
@@ -37,17 +40,30 @@ namespace Continentis.MainGame.Card
public void OnPointerClick(PointerEventData eventData)
{
if (CombatUIManager.Instance.deckPage.handCardSelector.gameObject.activeInHierarchy)
if (CombatUIManager.Instance.combatMainPage.handCardSelector.gameObject.activeInHierarchy)
{
if(isOccupied) return;
if (CombatUIManager.Instance.deckPage.handCardSelector.selectedCards.ContainsKey(cardInstance))
if (CombatUIManager.Instance.combatMainPage.handCardSelector.selectedCards.Contains(cardInstance))
{
CombatUIManager.Instance.deckPage.handCardSelector.Deselect(this);
CombatUIManager.Instance.combatMainPage.handCardSelector.Deselect(this);
}
else
{
CombatUIManager.Instance.deckPage.handCardSelector.Select(this);
CombatUIManager.Instance.combatMainPage.handCardSelector.Select(this);
}
}
else if (CombatUIManager.Instance.combatMainPage.customCardSelector.gameObject.activeInHierarchy)
{
if(isOccupied) return;
if (CombatUIManager.Instance.combatMainPage.customCardSelector.selectedCards.Contains(cardInstance))
{
CombatUIManager.Instance.combatMainPage.customCardSelector.Deselect(this);
}
else
{
CombatUIManager.Instance.combatMainPage.customCardSelector.Select(this);
}
}
}
@@ -58,7 +74,7 @@ namespace Continentis.MainGame.Card
CombatUIManager.Instance.selectingCardView = this;
cardInstance.user = CombatMainManager.Instance.currentCharacter;
cardLogic.SetTargets(out validTargets, out conditionNotMetTargets, out invalidTargets);
cardLogic.DetectTargetsValidity(out validTargets, out conditionNotMetTargets, out invalidTargets);
if (cardLogic.attributeSubmodule.targetCount == 1)
{
@@ -81,19 +97,26 @@ namespace Continentis.MainGame.Card
Camera uiCamera = CombatUIManager.Instance.uiCamera;
Camera worldCamera = CombatUIManager.Instance.combatCamera;
if (CombatUIManager.Instance.hoveringCharacterView != null)
// 先检查悬停的视图是否和当前记录的目标视图发生了变化
if (CombatUIManager.Instance.hoveringCharacterView != currentTargetingCharacterView)
{
cardLogic.Targeting(CombatUIManager.Instance.hoveringCharacterView.character);
Debug.Log("Hovering over " + CombatUIManager.Instance.hoveringCharacterView.character);
}
else
{
cardLogic.Untargeting();
// 如果悬停视图不是空的,说明鼠标移动到了一个新的目标上
if (CombatUIManager.Instance.hoveringCharacterView != null)
{
cardLogic.eventSubmodule.onTargeting(CombatUIManager.Instance.hoveringCharacterView.character);
currentTargetingCharacterView = CombatUIManager.Instance.hoveringCharacterView;
}
else // 悬停视图是空的,说明鼠标离开了之前的目标
{
cardLogic.eventSubmodule.onUntargeting();
currentTargetingCharacterView = null;
}
// 因为目标发生了变化(无论是选中了新的还是取消了),所以统一在这里更新描述
CardTextInterpreter.InterpretText(cardLogic);
cardDescriptionText.text = cardLogic.contentSubmodule.interpretedFunctionText;
}
CardDescriptionInterpreter.InterpretDescription(cardLogic);
cardDescriptionText.text = cardLogic.contentSubmodule.cardDescription;
Vector3 startPosition = cardTransform.position + new Vector3(0, cardTransform.rect.height * cardTransform.lossyScale.y / 2, 0);
Vector3 endPosition = SpaceConverter.ScreenPointToUIPoint(arrowCanvasRect, eventData.position, uiCamera);
PointerArrow mainPointerArrow = CombatUIManager.Instance.arrowsPage.mainPointerArrow;
@@ -203,7 +226,7 @@ namespace Continentis.MainGame.Card
CharacterBase hoveringCharacter = hoveringCharacterView != null ? hoveringCharacterView.character : null;
Camera uiCamera = CombatUIManager.Instance.uiCamera;
CombatUIManager.Instance.arrowsPage.ClearPointerArrows();
if (isSelecting)
{
isSelecting = false;
@@ -211,16 +234,21 @@ namespace Continentis.MainGame.Card
CombatUIManager.Instance.selectingCardView = null;
canvas.overrideSorting = false;
canvas.sortingOrder = 0;
cardLogic.Untargeting();
CardDescriptionInterpreter.InterpretDescription(cardLogic);
cardDescriptionText.text = cardLogic.contentSubmodule.cardDescription;
cardLogic.eventSubmodule.onUntargeting();
CardTextInterpreter.InterpretText(cardLogic);
cardDescriptionText.text = cardLogic.contentSubmodule.interpretedFunctionText;
}
else
{
return;
}
if (cardLogic.HasKeyword("Unplayable")) // 如果有“不能打出”关键词,直接返回
{
return;
}
if (!cardLogic.cardData.functionalTags.Contains("TargetSelf"))
if (!cardLogic.HasTag("TargetSelf"))
{
if (!validTargets.Contains(hoveringCharacter))
{
@@ -236,15 +264,15 @@ namespace Continentis.MainGame.Card
{
if (!cardLogic.Play(new List<CharacterBase>() { CombatUIManager.Instance.hoveringCharacterView.character }))
{
cardLogic.Untargeting();
CardDescriptionInterpreter.InterpretDescription(cardLogic);
cardDescriptionText.text = cardLogic.contentSubmodule.cardDescription;
cardLogic.eventSubmodule.onUntargeting();
CardTextInterpreter.InterpretText(cardLogic);
cardDescriptionText.text = cardLogic.contentSubmodule.interpretedFunctionText;
}
}
}
else
{
RectTransform dropZone = CombatUIManager.Instance.deckPage.dropZone;
RectTransform dropZone = CombatUIManager.Instance.combatMainPage.dropZone;
bool isInDropZone = RectTransformUtility.RectangleContainsScreenPoint(dropZone, eventData.position, uiCamera);
List<CharacterBase> targetList = new List<CharacterBase>();