OldBlueWater/BlueWater/Assets/02.Scripts/CozyController.cs

227 lines
8.0 KiB
C#

using System;
using System.Collections.Generic;
using System.Linq;
using DistantLands.Cozy;
using DistantLands.Cozy.Data;
using Sirenix.OdinInspector;
using UnityEngine;
using Random = UnityEngine.Random;
// ReSharper disable once CheckNamespace
namespace BlueWaterProject
{
public enum WeatherType
{
NONE = -1,
SUNNY,
RAIN,
SNOW,
FOG
}
public class CozyController : MonoBehaviour
{
/***********************************************************************
* Definitions
***********************************************************************/
#region Definitions
[Serializable]
public class ForecastProfileRatio
{
[field: SerializeField] public WeatherInfo WeatherInfo { get; set; }
[field: Range(0f, 10f)]
[field: SerializeField] public float Ratio { get; set; }
[field: DisableIf("@true")]
[field: SerializeField] public float Percent { get; set; }
}
[Serializable]
public class WeatherInfo
{
[field: SerializeField] public ForecastProfile ForecastProfile { get; set; }
[field: SerializeField] public WeatherType WeatherType { get; set; }
[field: SerializeField] public Sprite Sprite { get; set; }
public WeatherInfo(ForecastProfile forecastProfile, WeatherType weatherType, Sprite sprite = null)
{
ForecastProfile = forecastProfile;
WeatherType = weatherType;
Sprite = sprite;
}
public WeatherInfo(WeatherInfo weatherInfo)
{
ForecastProfile = weatherInfo.ForecastProfile;
WeatherType = weatherInfo.WeatherType;
Sprite = weatherInfo.Sprite;
}
}
#endregion
/***********************************************************************
* Variables
***********************************************************************/
#region Variables
// 날씨
[TitleGroup("날씨")]
// 기본값
[BoxGroup("날씨/기본값")]
[SerializeField] private ForecastProfileRatio[] forecastProfileRatioRatios;
[BoxGroup("날씨/기본값")]
[SerializeField, Required] private WeatherInfo defaultWeatherInfo;
// 일기예보
[BoxGroup("날씨/일기예보")]
[SerializeField] private int forecastWeatherCount = 7;
[BoxGroup("날씨/일기예보")]
[SerializeField] private List<WeatherInfo> weatherInfoList;
// 실시간 데이터
[TitleGroup("실시간 데이터"), BoxGroup("실시간 데이터/실시간 데이터", false)]
[Tooltip("날씨가 변경되는데 걸리는 시간")]
[SerializeField] private float changeWeatherTime;
public WeatherInfo CurrentWeatherInfo => weatherInfoList[0];
private float totalRatio;
#endregion
/***********************************************************************
* Unity Events
***************************************************************m********/
#region Unity Events
private void Start()
{
InitStart();
}
private void Update()
{
changeWeatherTime = CozyWeather.instance.weatherModule.ecosystem.weatherTimer;
}
#endregion
/***********************************************************************
* Init Methods
***********************************************************************/
#region Init Methods
private void InitStart()
{
if (weatherInfoList != null)
{
weatherInfoList = new List<WeatherInfo>(forecastWeatherCount);
for (var i = 0; i < forecastWeatherCount; i++)
{
var newWeatherInfo = new WeatherInfo(GetWeatherInfo());
weatherInfoList.Add(newWeatherInfo);
}
}
SetForecastProfile(weatherInfoList?[0].ForecastProfile);
}
#endregion
/***********************************************************************
* Methods
***********************************************************************/
#region Methods
[Button("날짜 변경")]
public void SetCurrentDat(int day) => CozyWeather.instance.timeModule.currentDay = day;
[Button("현재 시간 변경")]
public void SetCurrentTime(int hour, int minute)
{
CozyWeather.instance.timeModule.SetHour(hour);
CozyWeather.instance.timeModule.SetMinute(minute);
}
[Button("다음 날로 변경")]
public void SetWeatherAndDate()
{
CozyWeather.instance.timeModule.currentDay += 1;
CozyWeather.instance.timeModule.SetHour(9);
CozyWeather.instance.timeModule.SetMinute(0);
weatherInfoList.RemoveAt(0);
var newWeatherInfo = new WeatherInfo(GetWeatherInfo());
weatherInfoList.Add(newWeatherInfo);
SetForecastProfile(weatherInfoList[0].ForecastProfile);
}
[Button("다음 날씨")]
public void SetNextWeather()
{
var remainWeatherTimer = CozyWeather.instance.weatherModule.ecosystem.weatherTimer;
CozyWeather.instance.weatherModule.ecosystem.SetNextWeather();
CozyWeather.instance.weatherModule.ecosystem.SkipTicks(remainWeatherTimer);
//CozyWeather.instance.weatherModule.ecosystem.SetWeather(CozyWeather.instance.weatherModule.ecosystem.currentWeather, 0f);
//CozyWeather.instance.weatherModule.ecosystem.currentWeather.SetWeatherWeight(0);
}
private void SetForecastProfile(ForecastProfile newForecastProfile)
{
CozyWeather.instance.weatherModule.ecosystem.currentForecast.Clear();
CozyWeather.instance.weatherModule.ecosystem.forecastProfile = newForecastProfile;
foreach (var profile in CozyWeather.instance.weatherModule.ecosystem.forecastProfile.profilesToForecast)
{
foreach (var fx in profile.FX)
fx?.InitializeEffect(CozyWeather.instance);
}
CozyWeather.instance.weatherModule.ecosystem.SetupEcosystem();
//CozyWeather.instance.weatherModule.ecosystem.SetWeather(CozyWeather.instance.weatherModule.ecosystem.currentWeather, 0f);
CozyWeather.instance.weatherModule.ecosystem.currentWeather.SetWeatherWeight(0);
}
[Button("비율 재계산"), GUIColor(0, 1, 0)]
private void CalculateForecastProfileRatio()
{
totalRatio = forecastProfileRatioRatios.Sum(element => element.Ratio);
foreach (var element in forecastProfileRatioRatios)
{
element.Percent = element.Ratio / totalRatio * 100f;
}
}
private WeatherInfo GetWeatherInfo()
{
CalculateForecastProfileRatio();
var randomValue = Random.Range(0f, totalRatio);
var cumulativeRatio = 0f;
foreach (var element in forecastProfileRatioRatios)
{
cumulativeRatio += element.Ratio;
if (randomValue <= cumulativeRatio)
{
return element.WeatherInfo;
}
}
print("미리 설정된 날씨 정보가 없습니다.");
return defaultWeatherInfo;
}
public WeatherType GetCurrentWeatherType() => weatherInfoList[0].WeatherType;
#endregion
}
}