228 lines
6.8 KiB
C#
228 lines
6.8 KiB
C#
using UnityEngine;
|
|
|
|
/// <summary>
|
|
/// 바닥에 떨어진 화살 아이템 (아이템 전용 — 발사체 기능 제거됨)
|
|
/// 습득 시 PlayerAttack에 파티클 프리팹 + 속성 정보를 전달합니다.
|
|
/// </summary>
|
|
public class ArrowPickup : MonoBehaviour
|
|
{
|
|
[Header("--- 화살 아이템 정보 ---")]
|
|
[SerializeField] private string arrowName = "기본 화살";
|
|
[SerializeField] private ArrowElementType elementType = ArrowElementType.None;
|
|
|
|
[Header("--- 스탯 ---")]
|
|
[SerializeField] private float baseDamage = 15f;
|
|
[SerializeField] private float elementDamage = 5f;
|
|
[SerializeField] private float elementDuration = 3f;
|
|
|
|
[Header("--- 발사체 파티클 ---")]
|
|
[Tooltip("이 화살이 장착될 때 발사할 파티클 프리팹")]
|
|
[SerializeField] private GameObject projectilePrefab;
|
|
|
|
[Header("--- 비주얼 (필드 아이템) ---")]
|
|
[SerializeField] private GameObject visualModel;
|
|
|
|
[Header("--- UI 표시 ---")]
|
|
[SerializeField] private GameObject pickupUI;
|
|
[SerializeField] private float uiDisplayRange = 3f;
|
|
|
|
[Header("--- Collider 설정 (자동 탐지) ---")]
|
|
[Tooltip("아이템 습득용 Sphere Collider (Trigger)")]
|
|
[SerializeField] private Collider pickupCollider;
|
|
[Tooltip("바닥 충돌용 Box Collider (물리)")]
|
|
[SerializeField] private Collider physicsCollider;
|
|
|
|
private Transform playerTransform;
|
|
private Rigidbody rb;
|
|
|
|
/// <summary>
|
|
/// [NEW] ArrowData 구조체로 정보 패키징
|
|
/// </summary>
|
|
public ArrowData GetArrowData()
|
|
{
|
|
return new ArrowData
|
|
{
|
|
arrowName = this.arrowName,
|
|
elementType = this.elementType,
|
|
baseDamage = this.baseDamage,
|
|
elementDamage = this.elementDamage,
|
|
elementDuration = this.elementDuration,
|
|
projectilePrefab = this.projectilePrefab
|
|
};
|
|
}
|
|
|
|
private void Awake()
|
|
{
|
|
rb = GetComponent<Rigidbody>();
|
|
|
|
if (pickupCollider == null || physicsCollider == null)
|
|
{
|
|
AutoDetectColliders();
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Collider 자동 탐지 (기존 로직 유지)
|
|
/// </summary>
|
|
private void AutoDetectColliders()
|
|
{
|
|
Collider[] allColliders = GetComponents<Collider>();
|
|
|
|
foreach (Collider col in allColliders)
|
|
{
|
|
if (col is SphereCollider && pickupCollider == null)
|
|
{
|
|
pickupCollider = col;
|
|
Debug.Log($"습득용 Collider: {col.GetType().Name}");
|
|
}
|
|
else if (col is BoxCollider && physicsCollider == null)
|
|
{
|
|
physicsCollider = col;
|
|
Debug.Log($"물리용 Collider: {col.GetType().Name}");
|
|
}
|
|
}
|
|
}
|
|
|
|
private void Start()
|
|
{
|
|
SetupAsItem();
|
|
}
|
|
|
|
/// <summary>
|
|
/// 아이템 모드 설정 (기존 로직 유지 + 단순화)
|
|
/// </summary>
|
|
private void SetupAsItem()
|
|
{
|
|
GameObject player = GameObject.FindGameObjectWithTag("Player");
|
|
if (player != null)
|
|
{
|
|
playerTransform = player.transform;
|
|
}
|
|
|
|
if (pickupUI != null) pickupUI.SetActive(false);
|
|
|
|
// Collider 설정
|
|
if (pickupCollider != null)
|
|
{
|
|
pickupCollider.enabled = true;
|
|
pickupCollider.isTrigger = true;
|
|
}
|
|
|
|
if (physicsCollider != null)
|
|
{
|
|
physicsCollider.enabled = true;
|
|
physicsCollider.isTrigger = false;
|
|
}
|
|
|
|
// 물리 설정
|
|
if (rb != null)
|
|
{
|
|
rb.useGravity = true;
|
|
rb.isKinematic = false;
|
|
rb.collisionDetectionMode = CollisionDetectionMode.ContinuousDynamic;
|
|
}
|
|
}
|
|
|
|
private void Update()
|
|
{
|
|
if (playerTransform == null || pickupUI == null) return;
|
|
|
|
float distance = Vector3.Distance(transform.position, playerTransform.position);
|
|
pickupUI.SetActive(distance <= uiDisplayRange);
|
|
}
|
|
|
|
/// <summary>
|
|
/// [MODIFIED] PlayerInteraction에서 'E' 키를 눌렀을 때 호출
|
|
/// 기존: SwapArrow(gameObject) → 변경: SetCurrentArrow(ArrowData)
|
|
/// </summary>
|
|
public void Pickup(PlayerAttack playerAttack)
|
|
{
|
|
if (playerAttack == null) return;
|
|
|
|
// ArrowData를 패키징하여 PlayerAttack에 전달
|
|
ArrowData data = GetArrowData();
|
|
playerAttack.SetCurrentArrow(data);
|
|
|
|
Debug.Log($"[{arrowName}] 화살 습득! 속성: {elementType}");
|
|
|
|
// 아이템 제거
|
|
Destroy(gameObject);
|
|
}
|
|
|
|
/// <summary>
|
|
/// 몬스터 드롭 시 화살 정보 설정 (기존 함수 유지)
|
|
/// </summary>
|
|
public void SetArrowData(string name, float dmg, float spd, float rng)
|
|
{
|
|
arrowName = name;
|
|
baseDamage = dmg;
|
|
}
|
|
|
|
/// <summary>
|
|
/// [NEW] 속성 정보까지 포함한 전체 세팅 함수
|
|
/// </summary>
|
|
public void SetArrowDataFull(
|
|
string name,
|
|
ArrowElementType element,
|
|
float baseDmg,
|
|
float elemDmg,
|
|
float elemDur,
|
|
GameObject particlePrefab)
|
|
{
|
|
arrowName = name;
|
|
elementType = element;
|
|
baseDamage = baseDmg;
|
|
elementDamage = elemDmg;
|
|
elementDuration = elemDur;
|
|
projectilePrefab = particlePrefab;
|
|
}
|
|
|
|
/// <summary>
|
|
/// 바닥 충돌 시 속도 감쇠 (기존 로직 유지)
|
|
/// </summary>
|
|
private void OnCollisionEnter(Collision collision)
|
|
{
|
|
if (rb != null && collision.gameObject.CompareTag("Ground"))
|
|
{
|
|
rb.velocity *= 0.5f;
|
|
rb.angularVelocity *= 0.5f;
|
|
}
|
|
}
|
|
|
|
#region 디버그 시각화
|
|
|
|
private void OnDrawGizmosSelected()
|
|
{
|
|
if (pickupCollider != null && pickupCollider.enabled)
|
|
{
|
|
Gizmos.color = Color.green;
|
|
if (pickupCollider is SphereCollider sphere)
|
|
{
|
|
Gizmos.DrawWireSphere(transform.position + sphere.center, sphere.radius);
|
|
}
|
|
}
|
|
|
|
if (physicsCollider != null && physicsCollider.enabled)
|
|
{
|
|
Gizmos.color = Color.blue;
|
|
if (physicsCollider is BoxCollider box)
|
|
{
|
|
Gizmos.matrix = transform.localToWorldMatrix;
|
|
Gizmos.DrawWireCube(box.center, box.size);
|
|
}
|
|
}
|
|
|
|
// [NEW] 속성 색상 표시
|
|
switch (elementType)
|
|
{
|
|
case ArrowElementType.Fire: Gizmos.color = Color.red; break;
|
|
case ArrowElementType.Ice: Gizmos.color = Color.cyan; break;
|
|
case ArrowElementType.Poison: Gizmos.color = new Color(0.5f, 1f, 0f); break;
|
|
case ArrowElementType.Lightning: Gizmos.color = Color.yellow; break;
|
|
default: Gizmos.color = Color.white; break;
|
|
}
|
|
Gizmos.DrawWireSphere(transform.position, 0.3f);
|
|
}
|
|
|
|
#endregion
|
|
} |