-데이터 저장, 불러오기 연습을 하기위해 이전 포스팅 씬을 수정하려 한다.
먼저 구현해야 할 내용을 정리해보자.
- 신규 유저인지 기존 유저인지 확인한다.
-신규 유저라면, missionData.json에 있는 값의 진행 정도는 다 0으로 비워져야한다 : 초기화하자.
-기존 유저의 유저의 정보를 불러오도록 한다. 유저마다 진행 정도가 다를 것이다.
=> 유저의 정보를 담을 info.json가 있어야 한다. info.json이 없다면 생성하도록 코드 작성.
유저의 미션상태 정보는 다음과 같이 저장된다.
상태
0 : Doing (진행중)
1 : Done (완료 했지만 보상 아직 안받음)
2 : Complete (완료 했고 보상도 받음)
이를 테스트하기 위해서 다음과 같이 수정했다.
-저장하기 버튼을 생성하고, slider 위에 텍스트로 value를 나타내도록 한다. 마우스로 value를 설정할 수 있다.
-------------------------------------------------------------------------------------------------------------------------------------------------------
ㅋㅋ 다 마무리하고 포스팅 끝낸 줄 알았는데 reward text안바꿔서 코드 수정을 좀 했다..한줄.
물론 rewardText는 넣어줘야한다. serializefield로 넣어줬다.
-------------------------------------------------------------------------------------------------------------------------------------------------------
-main을 다음과 같이 작성했다. start에서 액션을 불러오므로 UIMain에서 start함수를 awake로 변경하고 코드를 수정했다.(start는 바로 호출되므로 start에서 알려주기 전에 awake에서 익명 메서드를 갖고있어야 참조할 수 있게 되기 때문이다.)
=> 뭔가 말이 안깔끔한데 뭐라고 써야될지 모르겠다...
-인포를 가져와 슬라이더에 나타내도록 값을 수정한다.
데이터 저장
cell에 멤버변수로 missionInfo를 선언해서 세이브 버튼을 누르면 onclick이벤트로 cell의 멤버 변수를 받으려고 했더니 못받아서 onclick한 걸 이벤트로 cell에 알려주도록 대리자를 새로 작성했다.
-json이 잘 바뀌는지도 확인 완료했다.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System.IO;
using Newtonsoft.Json;
using System.Linq;
public class InfoManager
{
public static readonly InfoManager instance = new InfoManager();
private Dictionary<int, MissionInfo> dicMissionInfos = new Dictionary<int, MissionInfo>();
public bool LoadMissionInfo(){
if (File.Exists("./Assets/Resources/mission_info.json"))//파일 존재여부 확인
{
string json = File.ReadAllText("./Assets/Resources/mission_info.json");
Debug.Log("기존 유저 입니다. 정보를 로드합니다.");// 존재한다면 기존유저
//missionInfo를 가져온다.
MissionInfo[] missionInfos = JsonConvert.DeserializeObject<MissionInfo[]>(json);//MissionInfo에 json 가져옴
this.dicMissionInfos = missionInfos.ToDictionary(x => x.id);
return true;
}
else
{//파일 생성
Debug.Log("유저 정보가 없습니다. 신규 유저의 새로운 미션 정보를 등록합니다.");
//새로운 missionInfo 생성
return false;
}
}
public List<MissionInfo> GetMissionInfo()
{
return this.dicMissionInfos.Values.ToList();
}
public void SaveMissionInfo(MissionInfo info)
{
List<MissionInfo> missionInfoList = this.dicMissionInfos.Values.ToList();
for(int i=0; i<missionInfoList.Count;i++)
{
if (missionInfoList[i].id == info.id)
{
Debug.Log(info.id);
missionInfoList.RemoveAt(i);
//missionInfoList.Add(info);
missionInfoList.Insert(i,info);
}
}
//직렬화
string json = JsonConvert.SerializeObject(missionInfoList);
File.WriteAllText("./Assets/Resources/mission_info.json", json);
Debug.Log("Info 저장");
}
}
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using TMPro;
public class Test06UIMissionCell : MonoBehaviour
{
[SerializeField] TextMeshProUGUI missionText;
[SerializeField] TextMeshProUGUI descText;
[SerializeField] TextMeshProUGUI rewardText;
[SerializeField] Image cellIconImage;
[SerializeField] Image rewardIconImage;
[SerializeField] Button getRewardButton;
[SerializeField] GameObject doingGo;
[SerializeField] GameObject completeGo;
[SerializeField] Slider sliderValue;
public MissionInfo missionInfo = new MissionInfo();
public int id;
private Test06UIMain uiMain;
private float value;
// Start is called before the first frame update
void Awake()
{
this.uiMain = FindAnyObjectByType<Test06UIMain>();
this.getRewardButton.onClick.AddListener(() => {
//doing 일때 미션을 모두 완료하면 reward icon 에서 버튼 생성
//complete상태에서 버튼을 클릭하면 보상 아이템 획득
// Debug.LogFormat("{0} clicked!",button);
Debug.Log("보상을 획득하였습니다.");
this.missionInfo.state = 2;
});
}
public void Init(MissionData data,MissionInfo info)
{//기존유저
this.sliderValue.onValueChanged.AddListener((val) => {
if (val == this.sliderValue.maxValue)
{
Debug.Log("missionCompleted!");
this.doingGo.SetActive(false);
this.completeGo.SetActive(true);
this.missionInfo.state = 1;
}
this.missionInfo.count = (int)val;
if (val != this.value)//데이터 로드했을 때 값이랑 다르면
{
this.uiMain.onSaveButtonClicked = () => {
this.missionInfo.id = info.id;
//Debug.LogFormat("id:{0},count:{1},state:{2}",this.missionInfo.id,this.missionInfo.count,this.missionInfo.state);
InfoManager.instance.SaveMissionInfo(this.missionInfo);
};
}
else
{
Debug.Log("value not changed");
}
});
this.missionText.text = data.name;
this.descText.text = string.Format(data.desc, data.goal);
var atlas = AtlasManager.instance.GetAtlas("icon");
//icon 이미지 변경
this.cellIconImage.sprite = atlas.GetSprite(data.icon_name);
this.cellIconImage.SetNativeSize();
Vector2 vector = new Vector2(data.width, data.height);
this.cellIconImage.rectTransform.sizeDelta = vector;
//보상 아이콘 이미지 변경
this.rewardIconImage.sprite = atlas.GetSprite(data.reward_icon_name);
this.rewardIconImage.SetNativeSize();
this.rewardIconImage.rectTransform.sizeDelta = new Vector2(data.reward_icon_width, data.reward_icon_height);
this.rewardText.text = data.reward_amount.ToString();
//기존 유저이므로 인포를 가져온다.
this.sliderValue.maxValue = data.goal;
this.value = info.count;
this.sliderValue.value = value;
// Debug.LogFormat("data: {0},value: {1} /maxValue: {2}", data.name,this.sliderValue.value,this.sliderValue.maxValue);
}
public void newInit(MissionData data)
{
this.missionText.text = data.name;
// Debug.Log(data.icon_name);
this.descText.text = string.Format(data.desc, data.goal);
var atlas = AtlasManager.instance.GetAtlas("icon");
//icon 이미지 변경
this.cellIconImage.sprite = atlas.GetSprite(data.icon_name);
this.cellIconImage.SetNativeSize();
Vector2 vector = new Vector2(data.width, data.height);
this.cellIconImage.rectTransform.sizeDelta = vector;
//보상 아이콘 이미지 변경
this.rewardIconImage.sprite = atlas.GetSprite(data.reward_icon_name);
this.rewardIconImage.SetNativeSize();
this.rewardIconImage.rectTransform.sizeDelta = new Vector2(data.reward_icon_width, data.reward_icon_height);
this.rewardText.text = data.reward_amount.ToString();
}
}
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Test06Main : MonoBehaviour
{
private bool isInfoExist;
public System.Action onLoadExistInfo;
public System.Action onLoadNewInfo;
// Start is called before the first frame update
void Start()
{
this.isInfoExist = InfoManager.instance.LoadMissionInfo();
if (this.isInfoExist)
{//기존 유저라면
//데이터 로드
this.onLoadExistInfo();
}
else
{//신규 유저라면
//데이터 초기화
this.onLoadNewInfo();
}
}
// Update is called once per frame
void Update()
{
}
}
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Test06UIScrollView : MonoBehaviour
{
[SerializeField] GameObject uiMissionCellGo;
[SerializeField] GameObject contentGo;
private List<Test06UIMissionCell> uiCellList = new List<Test06UIMissionCell>();
// private List<MissionData> data = new List<MissionData>();
// Start is called before the first frame update
void Start()
{
for(int i = 0; i<uiCellList.Count; i++)
{
//uiCellList[i].onButtonClick = () =>
//{
// Debug.LogFormat("{0} Clicked!", uiCellList[i]);
//};
}
}
public void Init()
{
List<MissionData> data = DataManager.instance.GetMissionDatas();
List<MissionInfo> missionInfo = InfoManager.instance.GetMissionInfo();//기존 유저이므로 인포를 가져옴
for (int i=0;i<data.Count; i++)
{
GameObject go = Instantiate<GameObject>(this.uiMissionCellGo, this.contentGo.transform);
//cell프리팹 생성. content오브젝트의 자식으로 넣는다.
this.uiCellList.Add(go.GetComponent<Test06UIMissionCell>());
// Debug.Log(missionInfo[i].id);
this.uiCellList[i].Init(data[i],missionInfo[i]);//매개변수를 통해 데이터 전달, 미션 정보 전달
}
}
public void newInit()
{
List<MissionData> data = DataManager.instance.GetMissionDatas();
for (int i = 0; i < data.Count; i++)
{
GameObject go = Instantiate<GameObject>(this.uiMissionCellGo, this.contentGo.transform);
//cell프리팹 생성. content오브젝트의 자식으로 넣는다.
this.uiCellList.Add(go.GetComponent<Test06UIMissionCell>());
this.uiCellList[i].newInit(data[i]);//매개변수를 통해 데이터 전달
}
}
}
using Newtonsoft.Json;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.U2D;
public class Test06UIMain : MonoBehaviour
{
[SerializeField] Test06UIMissionCell missionCell;
[SerializeField] Test06UIScrollView scrollView;
[SerializeField] Test06Main main;
public Button saveDataButton;
public System.Action onSaveButtonClicked;
MissionInfo info;
// Start is called before the first frame update
void Awake()
{
AtlasManager.instance.LoadAtlases();
this.main.onLoadExistInfo = () => {
DataManager.instance.LoadMissionData();
this.scrollView.Init();
};
this.main.onLoadNewInfo = () =>
{
DataManager.instance.LoadMissionData();
this.scrollView.newInit();
//초기화하도록 수정
};
this.saveDataButton.onClick.AddListener(() =>
{
this.onSaveButtonClicked();//cell에 알려줌
});
// SpriteAtlas atlas = AtlasManager.instance.GetAtlas("icon");
//Sprite[] arr = new Sprite[atlas.spriteCount];
//var cnt = atlas.GetSprites(arr);
//Debug.LogFormat("cnt : {0}", cnt);
//for (int i = 0; i < arr.Length; i++)
//{
// var sp = arr[i];
// Debug.LogFormat("i: {0} , sp -> {1}", i, sp);
// var a = sp.name.Replace("(Clone)", "");
// if (a == "icon_coins_pouch") {
// Debug.LogFormat("<color=lime>==> {0}</color>", a);
// }
//}
//var sp1 = atlas.GetSprite("icon_coins_pouch");
//Debug.LogFormat("=============> <color=yellow>{0}</color>", sp1);
//var json = Resources.Load<TextAsset>("mission_data").text;
//Debug.LogFormat("==> {0}", json);
//var con = json.Contains("icon_coins_pouch");
//Debug.LogFormat("===========> {0}", con);
////---------------------- 여기부터 문제 생김 -----------------------------
//var arr1 = JsonConvert.DeserializeObject<MissionData[]>(json);
////----------------------------------------------------------------------
////foreach (var aa in arr1)
////{
//// Debug.LogFormat("<color=cyan>=====> {0}, {1}, {2}</color>", aa.icon_name, aa.icon_name.Equals("icon_coins_pouch"), aa.icon_name == "icon_coins_pouch");
////}
//string iconName = arr1[0].icon_name;
//Debug.LogFormat(iconName);
//Debug.LogFormat("icon_coins_pouch");
//Debug.LogFormat("{0}", iconName.TrimStart() == "icon_coins_pouch");
//for (int i = 0; i < iconName.Length; i++)
//{
// char c = iconName[i];
// Debug.LogFormat("====>>>>> {0}, {1}", iconName[i], (int)c);
//}
//var dic = arr1.ToDictionary(x => x.id);
//var data = dic[1000];
//Debug.LogFormat("===> {0}, ==> {1}", data.icon_name, data.icon_name == "icon_coins_pouch");
}
}
'유니티 심화' 카테고리의 다른 글
[UGUI 연습] UI 연출2 (0) | 2023.09.12 |
---|---|
[UGUI연습] UI 연출 (0) | 2023.09.12 |
[UGUI연습] 미션(동적 스크롤뷰 활용) (0) | 2023.09.08 |
[UGUI연습]-동적 스크롤 뷰, json연결 (0) | 2023.09.07 |
[UGUI연습]스크롤 뷰 생성(정적 스크롤뷰) (0) | 2023.09.07 |