오늘는 스파르타 코딩 클럽 unity 게임 개발 과정 36일차(코드카타 문제 풀이와 팀 프로젝트 아이템매니저)
2023. 12. 19. 09:16ㆍ스파르타코딩클럽 게임개발
반응형
코드카타
0부터 9까지의 숫자 중 일부가 들어있는 정수 배열 numbers가 매개변수로 주어집니다. numbers에서 찾을 수 없는 0부터 9까지의 숫자를 모두 찾아 더한 수를 return 하도록 solution 함수를 완성해주세요.
간단한 문제였다.
0부터 10까지 하나하나 numbers에 없는지 확인하고 없는 값을 더하면 되는 간단한 문제 였다.
public int 없는숫자더하기(int[] numbers)
{
int result = 0;
for (int i = 0; i < 10; i++)
{
if (numbers.Contains(i)) result += i;
}
return result;
}
이렇게 링큐를 사용하면 간단하게 문제가 끝난다.
링큐를 사용하지 않으면 어떻게 할까?
public int 없는숫자더하기(int[] numbers)
{
int result = 0;
for (int i = 0; i < 10; i++)
{
if (!Check(i,numbers)) result += i;
}
return result;
}
public bool Check(int x, int[] ints)
{
foreach (var item in ints)
{
if (item == x) return true;
}
return false;
}
이렇게 메서드를 하나 만들어 체크하는 방식으로 링큐를 대신해 보았다.
어렵지 않은 문제였다.
다음은 아이템 매니저를 팀프로젝트에서 이용하기 위해 스크립트로 작성해 보았다.
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using Scripts.Utility;
using UnityEngine;
#region Item Class
/// <summary>
/// 게임 내의 개별 아이템을 표현하는 클래스입니다.
/// </summary>
public class Item : MonoBehaviour
{
#region Field
private string \_id; // 아이디
private string \_name; //이름
private string \_category; //속성
private string \_description; // 설명
private bool \_isActive; // 활성상태
private float \_power; // 아이템이 주는 효과
private float \_duration; // 아이템 지속시간
#endregion
#region Initialization
public void Initialize(string id, string name, string category, string description, float power, float duration)
{
\_id = id;
\_name = name;
\_category = category;
\_description = description;
\_power = power;
\_duration = duration;
\_isActive = false; // 기본적으로 아이템은 비활성 상태로 시작
}
#endregion
#region Property
/// <summary>
/// 아이템의 고유 식별자를 반환합니다.
/// </summary>
public string Id => \_id;
/// <summary>
/// 아이템의 이름을 반환합니다.
/// </summary>
public string Name => \_name;
/// <summary>
/// 아이템의 카테고리를 반환합니다.
/// </summary>
public string Category => \_category;
/// <summary>
/// 아이템에 대한 설명을 반환합니다.
/// </summary>
public string Description => \_description;
/// <summary>
/// 아이템이 주는 효과를 반환합니다.
/// </summary>
public float Power => \_power;
/// <summary>
/// 아이템의 효과가 지속되는 시간입니다.
/// </summary>
/// <returns></returns>
public float Duration
{
get => \_duration;
set
{
\_duration = value;
}
}
/// <summary>
/// 아이템의 활성상태를 반환합니다.
/// </summary>
public bool IsActivate
{
get => \_isActive;
set
{
\_isActive = value;
}
}
#endregion
}
#endregion
#region ItemManager Class
/// <summary>
/// 아이템을 관리하는 매니저 클래스입니다.
/// </summary>
public class ItemManager : MonoBehaviour
{
#region Field
/// <summary>
/// 아이템의 목록을 저장하는 딕셔너리입니다.
/// </summary>
private Dictionary<string, Item> \_items = new Dictionary<string, Item>();
#endregion
#region Item management methods
// 아이템의 효과를 플레이어에 적용하거나 제거하는 메서드
// apply가 true이면 효과를 적용하고, false이면 효과를 제거합니다.
private void UpdatePlayerWithItemEffect(Item item, bool apply)
{
float factor = apply ? item.Power : 1 / item.Power;
switch (item.Id)
{
case "0":
// Main.Controller.SetMoveSpeed(\_player.GetSpeed() \* factor);
break;
case "1":
// Main.PlayerController.SetJumpForce(\_player.GetJumpForc() \* factor);
break;
}
}
// 아이템의 효과를 플레이어에게 적용하는 메서드
private void ApplyItemsEffectToPlayer(Item item)
{
UpdatePlayerWithItemEffect(item, true);
}
// 아이템의 효과를 원래대로 되돌리는 메서드
private void RemoveItemsEffectFromPlayer(Item item)
{
UpdatePlayerWithItemEffect(item, false);
}
public IEnumerator ActivateItem(Item item)
{
// 아이템을 활성화합니다.
item.IsActivate = true;
ApplyItemsEffectToPlayer(item);
Debug.Log($"{item.Name} 아이템이 활성화되었습니다.");
// 아이템의 지속 시간만큼 대기합니다.
yield return new WaitForSeconds(item.Duration);
// 아이템을 비활성화합니다.
item.IsActivate = false;
Debug.Log($"{item.Name} 아이템이 비활성화되었습니다.");
// 아이템을 목록에서 제거합니다.
RemoveItem(item);
}
/// <summary>
/// 아이템을 추가하는 메서드입니다.
/// </summary>
public void AddItem(Item item)
{
if (\_items.ContainsKey(item.Id))
{
// 기존 아이템의 활성 상태를 업데이트합니다.
\_items\[item.Id\].Duration += \_items\[item.Id\].Duration;
}
else
{
foreach (var hadItem in \_items)
{
if (hadItem.Value.IsActivate)
{
RemoveItem(hadItem.Value);
}
}
\_items.Add(item.Id, item);
\_items\[item.Id\].IsActivate = true;
}
// 아이템을 추가하고 활성화 코루틴을 시작합니다.
StartCoroutine(ActivateItem(item));
}
/// <summary>
/// 아이템을 제거하는 메서드입니다.
/// </summary>
public void RemoveItem(Item item)
{
if (\_items.ContainsKey(item.Id))
{
item.IsActivate = false;
\_items.Remove(item.Id);
RemoveItemsEffectFromPlayer(item);
}
else
{
System.Console.WriteLine($"아이템을 찾을 수 없습니다: {item.Id}");
}
}
public Item LoadAndCreateItems(string jsonFilePath,Transform transform)
{
// JSON 파일의 내용을 읽어옵니다.
string jsonText = Syste[http://m.IO.File.ReadAllText(jsonFilePath);](http://m.IO.File.ReadAllText(jsonFilePath);)
// JSON 데이터를 직접 파싱합니다.
var json = JsonUtility.FromJson<Dictionary<string, object>>(jsonText);
// InstantiatePrefab 함수를 이용하여 프리팹을 인스턴스화하고, 인스턴스화된 게임 오브젝트에 Item 컴포넌트를 추가합니다.
// TODO : 제이슨 데이터 완성시에 키값 조정 필요
GameObject itemObject = Main.Resource.InstantiatePrefab(json\["\_name"\].ToString(),transform);
// 아이템 객체를 초기화합니다.
Item item = SceneUtility.GetAddComponent<Item>(itemObject);
item.Initialize(
id: json\["\_id"\].ToString(),
name: json\["\_name"\].ToString(),
category: json\["\_category"\].ToString(),
description: json\["\_description"\].ToString(),
power: float.Parse(json\["\_power"\].ToString()),
duration: float.Parse(json\["\_duration"\].ToString())
);
return item;
}
#endregion
}
#endregion
아이템을 습득하면 효과가 적용되고 효과는 지속시간만큼 코루티을 통해 지속되며 그것이 끝나면 아이템이
삭제되어 효과가 사라지는 것을 볼 수있다.
하지만 아직 아이템을 생성하는 부분에서는 정확한 방향성을 잡지 못했으며 수정이 필요할 것 같다.'
어드레서블을 사용하여 인스턴스화 시킨것을 반환 하는것
데이터를 제이슨으로 불러오는 것 두가지의 메서드로 나누어 구현해도 좋을 듯 싶다.
반응형
'스파르타코딩클럽 게임개발' 카테고리의 다른 글
오늘는 스파르타 코딩 클럽 unity 게임 개발 과정 40일차(파티클에 대해 ) (0) | 2023.12.27 |
---|---|
오늘는 스파르타 코딩 클럽 unity 게임 개발 과정 37일차(아이템 매니저 추가 구현 ) (0) | 2023.12.20 |
오늘은 스파르타 코딩 클럽 unity 게임 개발 과정 34 & 35일차 땜빵( Addressable을 이용하여 리소스매니저 만들기) (1) | 2023.12.18 |
오늘는 스파르타 코딩 클럽 unity 게임 개발 과정 33일차(리포지토리 클론을 사용할 때 주의할 점) (0) | 2023.12.13 |
어제는 스파르타 코딩 클럽 unity 게임 개발 과정 32일차(스크롤 뷰 사용하기 ) (0) | 2023.12.13 |