스킬 시스템 구현
- 애니메이션 이벤트 기반 스킬 시스템 추가 - SkillData: 스킬 데이터 (클립, 쿨타임, 효과 목록) - SkillController: 스킬 실행 및 애니메이션 제어 - AnimatorOverrideController로 단일 State에서 다양한 스킬 재생 - 스킬 효과 시스템 - DamageEffect, HealEffect, BuffEffect - KnockbackEffect, SoundEffect, SpawnEffect - 범위 공격 및 팀 구분 지원 - Team 컴포넌트로 아군/적 구분 - 스킬 중 이동 제한 - IsPlayingAnimation으로 애니메이션 종료까지 이동 불가 - OnSkillEnd 호출 시 다음 스킬 시전 가능 - 입력 시스템에 스킬 슬롯 6개 추가 - 애니메이션 에셋 추가 및 정리 - AnimationSwordCombat 패키지 추가 (검 공격 애니메이션) - PlayerAnimationController에 Skill 상태 추가 - External_Used 폴더 구조 정리 Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
134
Assets/Scripts/Skills/SkillEffect.cs
Normal file
134
Assets/Scripts/Skills/SkillEffect.cs
Normal file
@@ -0,0 +1,134 @@
|
||||
using UnityEngine;
|
||||
using Colosseum;
|
||||
|
||||
namespace Colosseum.Skills
|
||||
{
|
||||
/// <summary>
|
||||
/// 스킬 효과의 기본 클래스.
|
||||
/// 모든 효과는 이 클래스를 상속받아 구현합니다.
|
||||
/// 효과 발동 타이밍은 애니메이션 이벤트(OnEffect)로 제어합니다.
|
||||
/// </summary>
|
||||
public abstract class SkillEffect : ScriptableObject
|
||||
{
|
||||
[Header("대상 설정")]
|
||||
[Tooltip("Self: 시전자, Area: 범위 내 대상")]
|
||||
[SerializeField] protected TargetType targetType = TargetType.Self;
|
||||
|
||||
[Header("Area Settings (TargetType이 Area일 때)")]
|
||||
[Tooltip("범위 내에서 공격할 대상 필터")]
|
||||
[SerializeField] protected TargetTeam targetTeam = TargetTeam.Enemy;
|
||||
[SerializeField] protected AreaCenterType areaCenter = AreaCenterType.Caster;
|
||||
[Min(0.1f)] [SerializeField] protected float areaRadius = 3f;
|
||||
[SerializeField] protected LayerMask targetLayers;
|
||||
|
||||
// Properties
|
||||
public TargetType TargetType => targetType;
|
||||
public TargetTeam TargetTeam => targetTeam;
|
||||
|
||||
/// <summary>
|
||||
/// 스킬 시전 시 호출
|
||||
/// </summary>
|
||||
public void ExecuteOnCast(GameObject caster)
|
||||
{
|
||||
switch (targetType)
|
||||
{
|
||||
case TargetType.Self:
|
||||
ApplyEffect(caster, caster);
|
||||
break;
|
||||
|
||||
case TargetType.Area:
|
||||
ExecuteArea(caster);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 투사체 충돌 시 호출
|
||||
/// </summary>
|
||||
public void ExecuteOnHit(GameObject caster, GameObject hitTarget)
|
||||
{
|
||||
if (IsValidTarget(caster, hitTarget))
|
||||
{
|
||||
ApplyEffect(caster, hitTarget);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 실제 효과 적용 (상속받은 클래스에서 구현)
|
||||
/// </summary>
|
||||
protected abstract void ApplyEffect(GameObject caster, GameObject target);
|
||||
|
||||
/// <summary>
|
||||
/// 충돌한 대상이 유효한 타겟인지 확인
|
||||
/// </summary>
|
||||
public bool IsValidTarget(GameObject caster, GameObject target)
|
||||
{
|
||||
if (target == null) return false;
|
||||
|
||||
// 레이어 체크
|
||||
if (targetLayers.value != 0 && (targetLayers.value & (1 << target.layer)) == 0)
|
||||
return false;
|
||||
|
||||
// 팀 체크
|
||||
return IsCorrectTeam(caster, target);
|
||||
}
|
||||
|
||||
private bool IsCorrectTeam(GameObject caster, GameObject target)
|
||||
{
|
||||
bool isSameTeam = Team.IsSameTeam(caster, target);
|
||||
|
||||
return targetTeam switch
|
||||
{
|
||||
TargetTeam.Enemy => !isSameTeam,
|
||||
TargetTeam.Ally => isSameTeam,
|
||||
TargetTeam.All => true,
|
||||
_ => true
|
||||
};
|
||||
}
|
||||
|
||||
private void ExecuteArea(GameObject caster)
|
||||
{
|
||||
Vector3 center = GetAreaCenter(caster);
|
||||
Collider[] hits = Physics.OverlapSphere(center, areaRadius, targetLayers);
|
||||
|
||||
foreach (var hit in hits)
|
||||
{
|
||||
if (hit.gameObject == caster) continue;
|
||||
if (!IsCorrectTeam(caster, hit.gameObject)) continue;
|
||||
|
||||
ApplyEffect(caster, hit.gameObject);
|
||||
}
|
||||
}
|
||||
|
||||
private Vector3 GetAreaCenter(GameObject caster)
|
||||
{
|
||||
if (caster == null) return Vector3.zero;
|
||||
|
||||
return areaCenter switch
|
||||
{
|
||||
AreaCenterType.Caster => caster.transform.position,
|
||||
AreaCenterType.CasterForward => caster.transform.position + caster.transform.forward * areaRadius,
|
||||
_ => caster.transform.position
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
public enum TargetType
|
||||
{
|
||||
Self,
|
||||
Area
|
||||
}
|
||||
|
||||
public enum TargetTeam
|
||||
{
|
||||
Enemy,
|
||||
Ally,
|
||||
All
|
||||
}
|
||||
|
||||
public enum AreaCenterType
|
||||
{
|
||||
Caster,
|
||||
CasterForward
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user