EasyCastleUNITY

유니티 GUI 미션 (데이터 연동 및 저장, 저장한 데이터 불러오기) 본문

유니티 심화

유니티 GUI 미션 (데이터 연동 및 저장, 저장한 데이터 불러오기)

EasyCastleT 2023. 9. 10. 23:49

DataManager

using Newtonsoft.Json;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;

public class DataManager 
{
    
    public static readonly DataManager instance = new DataManager(); //싱글톤 
    //상자 정보를 저장할 사전 
    private Dictionary<int, ChestData> chestDataDics = new Dictionary<int, ChestData>();
    //미션 정보를 저장할 사전
    private Dictionary<int, MissionData> missionDataDic = new Dictionary<int, MissionData>();
    //골드 정보를 저장할 사전 
    private Dictionary<int, GoldData> goldDataDic = new Dictionary<int, GoldData>();
    //젬 정보를 저장할 사전 
    private Dictionary<int, GemData> gemDataDic = new Dictionary<int, GemData>();

    private List<UIMissionCell> missions = new List<UIMissionCell>();
    //생성자
    private DataManager()
    {

    }

    public void SaveMissionCell(UIMissionCell mission)
    {
        this.missions.Add(mission);
    }

    public MissionData GetMissionCell(int id)
    {
        return this.missionDataDic[id];
    }

    public List<UIMissionCell> GetMissionsCell()
    {
        return this.missions;
    }
    public void LoadChestDatas()
    {
        TextAsset aseet = Resources.Load<TextAsset>("chest_data"); //json은 안 붙임

        //역직렬화
        ChestData[] chestDatas = JsonConvert.DeserializeObject<ChestData[]>(aseet.text);
        foreach(var chestData in chestDatas)
        {
            this.chestDataDics.Add(chestData.id, chestData);
        }
        Debug.Log("상자 로드 완료");
    }

    public void LoadMissionDatas()
    {
        TextAsset asset = Resources.Load<TextAsset>("mission_data");
        //역직렬화 
        MissionData[] missionDatas = JsonConvert.DeserializeObject<MissionData[]>(asset.text);
        //사전 등록
        foreach(var missionData in missionDatas)
        {
            this.missionDataDic.Add(missionData.id, missionData);
        }
        Debug.Log("미션 로드 완료");
    }

    public void LoadGoldDatas()
    {
        TextAsset asset = Resources.Load<TextAsset>("gold_data");
        //역직렬화
        GoldData[] goldDatas = JsonConvert.DeserializeObject<GoldData[]>(asset.text);
        //사전 등록
        foreach(var goldData in goldDatas)
        {
            this.goldDataDic.Add(goldData.id, goldData);
        }
        Debug.LogFormat("<color=yellow>Gold Count: {0}</color>",this.goldDataDic.Count);
        Debug.Log("골드 로드 완료");
    }

    public void LoadGemDatas()
    {
        TextAsset asset = Resources.Load<TextAsset>("gem_data");
        //역직렬화
        GemData[] gemDatas = JsonConvert.DeserializeObject<GemData[]>(asset.text);
        //사전 등록
        foreach(var gemData in gemDatas)
        {
            this.gemDataDic.Add(gemData.id, gemData);
        }
        Debug.LogFormat("<color=yellow>Gem Count: {0}</color>", this.gemDataDic.Count);
        Debug.Log("젬 로드 완료");
    }
    public List<ChestData> GetChestDatas()
    {
        return this.chestDataDics.Values.ToList();
    }

    public List<MissionData> GetMissionDatas()
    {
        return this.missionDataDic.Values.ToList();
    }

    public List<GoldData> GetGoldDatas()
    {
        return this.goldDataDic.Values.ToList();
    }

    public List<GemData> GetGemDatas()
    {
        return this.gemDataDic.Values.ToList();
    }
}

MissionData -> 매핑 클래스 

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class MissionData 
{
    //   id   name    desc  goal    icon_name   mission_icon_width  mission_icon_height reward_amount   reward_icon_name reward_icon_width   reward_icon_height
    //    int string  string int      string     int                 int                 int             string           int                 int

    public int id;
    public string name;
    public string desc;
    public int goal;
    public string icon_name;
    public int mission_icon_width;
    public int mission_icon_height;
    public int reward_amount;
    public string reward_icon_name;
    public int reward_icon_width;
    public int reward_icon_height;

}

InfoManager

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class InfoManager
{
    public static readonly InfoManager instance = new InfoManager();
    List<MissionInfo> missions = new List<MissionInfo>(); //info 저장하는 리스트 


    private InfoManager()
    {

    }

    public void SaveMissionInfos(MissionInfo info)
    {
        missions.Add(info);
    }

    public void ClearMissionInfos()
    {
        this.missions.Clear();
    }
    
    public List<MissionInfo> LoadMissionInfos()
    {
        //foreach(var info in missions)
        //{
        //    Debug.LogFormat("Id:{0} Count:{1} State:{2}", info.id, info.count, info.stateNum);
        //}
        return this.missions;
    }
}

MissionInfo -> 매핑 클래스, 변하는 정보들을 저장 

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class MissionInfo 
{
    
    public int id;
    public int count;
    public int stateNum;

    public MissionInfo(int id, int count , int stateNum)
    {
        this.id = id;
        this.count = count;
        this.stateNum = stateNum; 
    }
}

Test06UIMain

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using Newtonsoft.Json;
using System.IO;

public class Test06UIMain : MonoBehaviour
{
    [SerializeField]
    private UIPageMission uiPageMission;

    [SerializeField]
    private Button saveButton;

    

    // Start is called before the first frame update
    void Start()
    {
        DataManager.instance.LoadMissionDatas();
        List<MissionData> missionDatas = DataManager.instance.GetMissionDatas();
        

        string filepath = string.Format("{0}/mission_info.json", Application.persistentDataPath);

        this.uiPageMission.onChangeCount = (id, count,state) => {
            //Debug.LogFormat("id:{0}, count:{1} state:{2}", id, count,state);
        };

        this.uiPageMission.onSaveButtonClick = () =>{
            List<MissionInfo> missionInfos = InfoManager.instance.LoadMissionInfos();
            string json = JsonConvert.SerializeObject(missionInfos);
            Debug.Log(json);

            File.WriteAllText(filepath, json);
        };

        if (File.Exists(filepath)) //기존 유저 
        {
            Debug.Log("<color=yellow>기존유저</color>");
            string json = File.ReadAllText(filepath);
            MissionInfo[] missionInfos = JsonConvert.DeserializeObject<MissionInfo[]>(json);
            this.uiPageMission.Init(missionInfos);
        }
        else
        {
            Debug.Log("<color=yellow>신규유저</color>");
            this.uiPageMission.Init(missionDatas);
        }
    }

}

UIPageMission

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class UIPageMission : MonoBehaviour
{
    [SerializeField]
    private UIMissionScrollView missionScrollView;

    public System.Action<int, float,int> onChangeCount;
    public System.Action onSaveButtonClick;

    public void Init(List<MissionData> missionDatas)
    {
        foreach (MissionData data in missionDatas)
        {
            Debug.LogFormat("<color=yellow>{0},{1},{2},{3},{4},{5},{6},{7},{8},{9},{10}</color>",
                data.id,data.name,data.desc,data.goal,data.icon_name,data.mission_icon_width,data.mission_icon_height
                ,data.reward_amount,data.reward_icon_name,data.reward_icon_width,data.reward_icon_height);
            this.missionScrollView.Init(data);    
        }

        this.missionScrollView.SaveMissionInfos();

        this.missionScrollView.onChangeCount = (id, count, state) => {
            this.onChangeCount(id, count, state);
        };

        this.missionScrollView.onSaveButtonClick = () => {
            this.onSaveButtonClick();
        };
    }

    public void Init(MissionInfo[] missionInfos)
    {
        foreach(MissionInfo info in missionInfos)
        {
            Debug.LogFormat("<color=red>{0},{1},{2} </color>",info.id,info.count,info.stateNum);
            this.missionScrollView.Init(info);
        }

        this.missionScrollView.SaveMissionInfos();

        this.missionScrollView.onChangeCount = (id, count, state) => {
            this.onChangeCount(id, count, state);
        };

        this.missionScrollView.onSaveButtonClick = () => {
            this.onSaveButtonClick();
        };
    }
}

UIMissionScrollView

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.U2D;
using UnityEngine.UI;

public class UIMissionScrollView : MonoBehaviour
{
    public System.Action<int,float,int> onChangeCount;
    public System.Action onSaveButtonClick;
    [SerializeField]
    private GameObject missionCellPrefab;
    [SerializeField]
    private SpriteAtlas rewardIconAtlas;
    [SerializeField]
    private SpriteAtlas missionIconAtlas;

    [SerializeField] private Button btnSave;

    //신규 일 때
    public void Init(MissionData data)
    {
        //인스턴스화 
        GameObject context = GameObject.FindGameObjectWithTag("Content");
        GameObject go = Instantiate(this.missionCellPrefab, context.transform);
        UIMissionCell mission = go.GetComponent<UIMissionCell>();
        this.SetMissionCellData(mission, data);
        mission.Init();

        DataManager.instance.SaveMissionCell(mission); //처음 만들 때, Cell들을 저장 
        

        mission.onChangeCount = (count,state) => {
            this.onChangeCount(data.id,count,state);
        };
    }
    //기존 일때 
    public void Init(MissionInfo info)
    {
        //인스턴스화 
        GameObject context = GameObject.FindGameObjectWithTag("Content");
        GameObject go = Instantiate(this.missionCellPrefab, context.transform);
        UIMissionCell mission = go.GetComponent<UIMissionCell>();
        this.SetMissionCellInfo(mission, info);
        mission.Init();

        DataManager.instance.SaveMissionCell(mission);

        mission.onChangeCount = (count, state) => {
            this.onChangeCount(info.id, count, state);
        };
    }

    public void SaveMissionInfos()
    {
        this.btnSave.onClick.AddListener(() => {

            List<UIMissionCell> missionCells = DataManager.instance.GetMissionsCell(); //저장한 cell들 불러오기 
            Debug.LogFormat("<color=yellow>missionCells Count:{0}</color>", missionCells.Count);
            InfoManager.instance.ClearMissionInfos(); //그냥 계속 저장하면 정보가 쌓이니, 저장하기 전에 클리어 
            foreach (var missionCell in missionCells)
            {
                MissionInfo missionInfo = missionCell.GetMissionInfo(); //cell들의 info를 받아오고 
                InfoManager.instance.SaveMissionInfos(missionInfo); //InfoManager의 리스트에 저장 
            }
            this.onSaveButtonClick();
        });
    }
    //처음 할 때 cell 정보 세팅 
    private void SetMissionCellData(UIMissionCell cell, MissionData data)
    {
        cell.Id = data.id; 
        cell.Name = data.name;
        cell.Goal = data.goal;
        cell.Icon_name = data.icon_name;
        cell.Desc = data.desc;
        cell.Mission_icon_height = data.mission_icon_height;
        cell.Mission_icon_width = data.mission_icon_width;
        cell.MissionIcanSprite = this.missionIconAtlas.GetSprite(data.icon_name);
        cell.Reward_amount = data.reward_amount;
        cell.Reward_icon_name = data.reward_icon_name;
        cell.RewardIconSprite = this.rewardIconAtlas.GetSprite(data.reward_icon_name);
        cell.Reward_icon_width = data.reward_icon_width;
        cell.Reward_icon_height = data.reward_icon_height;
    }
    //기존 유저일 경우 cell 정보 세팅 
    private void SetMissionCellInfo(UIMissionCell cell, MissionInfo info)
    {
        cell.Id = info.id;
        cell.Count = info.count;
        cell.State = (UIMissionCell.eState)info.stateNum;

        MissionData data = DataManager.instance.GetMissionCell(info.id);

        cell.Goal = data.goal;
        cell.Icon_name = data.icon_name;
        cell.Desc = data.desc;
        cell.Mission_icon_height = data.mission_icon_height;
        cell.Mission_icon_width = data.mission_icon_width;
        cell.MissionIcanSprite = this.missionIconAtlas.GetSprite(data.icon_name);
        cell.Reward_amount = data.reward_amount;
        cell.Reward_icon_name = data.reward_icon_name;
        cell.RewardIconSprite = this.rewardIconAtlas.GetSprite(data.reward_icon_name);
        cell.Reward_icon_width = data.reward_icon_width;
        cell.Reward_icon_height = data.reward_icon_height;

    }
}

UIMissionCell

using System.Collections;
using System.Collections.Generic;
using TMPro;
using UnityEngine;
using UnityEngine.UI;

public class UIMissionCell : MonoBehaviour
{
    #region info
    private int id;
    private new string name;
    private string desc;
    private int goal;
    private string icon_name;
    private int mission_icon_width;
    private int mission_icon_height;
    private int reward_amount;
    private string reward_icon_name;
    private int reward_icon_width;
    private int reward_icon_height;

    public int Id { get => id; set => id = value; }
    public string Name { get => name; set => name = value; }
    public string Desc { get => desc; set => desc = value; }
    public int Goal { get => goal; set => goal = value; }
    public string Icon_name { get => icon_name; set => icon_name = value; }
    public int Mission_icon_width { get => mission_icon_width; set => mission_icon_width = value; }
    public int Mission_icon_height { get => mission_icon_height; set => mission_icon_height = value; }
    public int Reward_amount { get => reward_amount; set => reward_amount = value; }
    public string Reward_icon_name { get => reward_icon_name; set => reward_icon_name = value; }
    public int Reward_icon_width { get => reward_icon_width; set => reward_icon_width = value; }
    public int Reward_icon_height { get => reward_icon_height; set => reward_icon_height = value; }
    #endregion
    #region CellChangeInfo
    [SerializeField]
    private TMP_Text txtName;
    [SerializeField]
    private TMP_Text txtDesc;
    [SerializeField]
    private TMP_Text txtRewardAmount;

    [SerializeField]
    private Image missonIconImage;

    [SerializeField]
    private Image rewardIconImage;

    private Sprite missionIconSprite;
    public Sprite MissionIcanSprite
    {
        get { return missionIconSprite; }
        set { missionIconSprite = value; }
    }

    private Sprite rewardIconSprite;
    public Sprite RewardIconSprite
    {
        get { return rewardIconSprite; }
        set { rewardIconSprite = value; }
    }

    [SerializeField]
    private Slider slider;

    [SerializeField]
    private TMP_Text sliderCount;
    #endregion
    public enum eState
    {
        Doing, Done, Complete
    }
    private eState state;

    public eState State { get => state; set => state = value; }

    private int count;
    public int Count { get => count; set => count = value; }
    
    public System.Action<float,int> onChangeCount;
    public System.Action onButtonClick;

    private MissionInfo missionInfo = new MissionInfo(0,0,0);
    public void Init()
    {
        this.txtName.text = this.name;
        this.txtDesc.text = string.Format(this.desc, this.goal);
        this.txtRewardAmount.text = this.reward_amount.ToString();
        this.SetSlider(0, this.goal);
        this.SetImage(missonIconImage, missionIconSprite,mission_icon_width,mission_icon_height);
        this.SetImage(rewardIconImage,rewardIconSprite,reward_icon_width,reward_icon_height);

    }

    private void SetImage(Image image, Sprite sprite , int width, int height)
    {
        image.sprite = sprite;
        image.SetNativeSize();
        //이미지 사이즈 변경
        image.rectTransform.sizeDelta = new Vector2(width, height);
    }

    private void SetSlider(int min, int max)
    {
        this.slider.minValue = min;
        this.slider.maxValue = max;
        this.slider.value = this.count;
        this.sliderCount.text = this.count.ToString();

        this.slider.onValueChanged.AddListener((val) => {
            this.sliderCount.text = val.ToString();
            if (val == max) this.state = eState.Done;
            else this.state = eState.Doing;
            this.onChangeCount(val,(int)this.state);
            this.count = (int)val;

            this.missionInfo.id = this.id;
            this.missionInfo.count = this.count;
            this.missionInfo.stateNum = (int)this.state;

            //Debug.LogFormat("<color=yellow>Id:{0} Count:{1} State:{2}</color>", 
            //    this.missionInfo.id, this.missionInfo.count, this.missionInfo.stateNum);
        });
    }

    public MissionInfo GetMissionInfo()
    {
        return this.missionInfo; 
    }
}

신규 유저 일 때 시연영상

기존유저 일때 시연영상

 

'유니티 심화' 카테고리의 다른 글

유니티 GUI 애니메이션  (0) 2023.09.12
보석 상점 GUI  (0) 2023.09.09
골드 상점 GUI  (0) 2023.09.09
유니티 GUI (스크롤 뷰 및 셀) 및 데이터 연동  (0) 2023.09.07
유니티 GUI 3 (Stage UI)  (0) 2023.09.06