2025-01-25 04:38:09 +08:00

385 lines
11 KiB
C#

using System;
using System.Collections.Generic;
using System.IO;
using UnityEngine;
using PathUtils = UnityEngine.Gonbest.MagicCube.PathUtils;
using CoroutinePool = UnityEngine.Gonbest.MagicCube.CoroutinePool;
using StringUtils = UnityEngine.Gonbest.MagicCube.StringUtils;
using FFileReader = UnityEngine.Gonbest.MagicCube.FFileReader;
namespace Thousandto.Cinematic
{
[Serializable]
public abstract class ICinematic
{
[NonSerialized]
private Stream _fStream;
[NonSerialized]
private BinaryWriter _bWriter;
[NonSerialized]
private BinaryReader _bReader;
protected static string _rootPath;
protected static string _extension = ".bytes";
public Dictionary<string, object> Serialize()
{
Dictionary<string, object> dict = new Dictionary<string, object>();
var fields = GetType().GetFields();
for (int i = 0; i < fields.Length; ++i)
{
if (fields[i].Name == "" || fields[i].Name == "") continue;
var value = fields[i].GetValue(this);
if (Attribute.IsDefined(fields[i], typeof(NonSerializedAttribute))) continue;
if (value is List<CinematicObj> && value != null)
{
value = ToObj((List<CinematicObj>)value);
}
if (value is List<CinematicKeyframe> && value != null)
{
value = ToObj((List<CinematicKeyframe>)value);
}
if (value is List<CinematicEventData> && value != null)
{
value = ToObj((List<CinematicEventData>)value);
}
if (value is CinematicEventData && value != null)
{
value = ((CinematicEventData)value).Serialize();
}
if (value is CinematicKeyframe && value != null)
{
value = ((CinematicKeyframe)value).Serialize();
}
if (value is KeyFrameEvent)
{
dict.Add(fields[i].Name, (int)value);
}
else
{
if (value != null)
dict.Add(fields[i].Name, value);
}
}
return dict;
}
public virtual object Deserialize(object dictObj)
{
Dictionary<string, object> dict = dictObj as Dictionary<string, object>;
if (dict == null) return null;
var fields = GetType().GetFields();
for (int i = 0; i < fields.Length; ++i)
{
var type = fields[i].FieldType;
object value;
if (dict.TryGetValue(fields[i].Name, out value))
{
if (type == typeof(List<CinematicObj>) && value != null)
{
value = ToClass<CinematicObj>(value);
}
if (type == typeof(List<CinematicKeyframe>) && value != null)
{
value = ToClass<CinematicKeyframe>(value);
}
else if (type == typeof(List<CinematicEventData>))
{
value = ToClass<CinematicEventData>(value);
}
else if (type == typeof(CinematicEventData) && value != null)
{
value = new CinematicEventData().Deserialize(value);
}
else if (type == typeof(CinematicKeyframe) && value != null)
{
value = new CinematicKeyframe().Deserialize(value);
}
fields[i].SetValue(this, value);
}
}
return this;
}
public object ToObj<T>(List<T> listData) where T : ICinematic
{
List<Dictionary<string, object>> ret = new List<Dictionary<string, object>>();
for (int i = 0; i < listData.Count; ++i)
{
Dictionary<string, object> value = null;
if (listData[i] is T && listData[i] != null)
{
value = ((T)listData[i]).Serialize();
}
else
value = null;
ret.Add(value);
}
return ret;
}
public List<T> ToClass<T>(object listDataObj) where T : ICinematic
{
var listData = listDataObj as List<Dictionary<string, object>>;
List<T> ret = new List<T>();
for (int i = 0; i < listData.Count; ++i)
{
object value = null;
if (listData[i] != null)
{
var ins1 = typeof(T).Assembly.CreateInstance(typeof(T).FullName);
var ins2 = typeof(T).Assembly.CreateInstance(typeof(T).FullName, true);
if (ins1 == null) ins1 = ins2;
var instance = ins1 as T;
value = instance.Deserialize(listData[i]);
}
else
value = listData[i];
ret.Add((T)value);
}
return ret;
}
public virtual ICinematic newInstance() { return null; }
public virtual void WriteAll(BinaryWriter bw) { }
public virtual void ReadAll(BinaryReader rd) { }
static ICinematic() { InitRootPath(); }
public static string InitRootPath()
{
_rootPath = PathUtils.GetStreamingRootPath("/Cinematics");
if (!Directory.Exists(_rootPath))
Directory.CreateDirectory(_rootPath);
return _rootPath;
}
public static string GetExtension()
{
return _extension;
}
public string GetFullPath(string clipName)
{
return _rootPath + "/" + clipName + _extension;
}
public void PrepareWrite(string clipName)
{
if (_bWriter != null) _bWriter.Close();
if (_fStream != null) _fStream.Close();
_fStream = new FileStream(GetFullPath(clipName), FileMode.Create);
_bWriter = new BinaryWriter(_fStream);
}
public void EndWrite()
{
if (_bWriter != null) _bWriter.Close();
if (_fStream != null) _fStream.Close();
}
public void PrepareWriter(BinaryWriter bw)
{
_bWriter = bw;
}
public void PrepareReader(BinaryReader br)
{
_bReader = br;
}
public void PrepareRead(string clipName)
{
if (_bReader != null) _bReader.Close();
if (_fStream != null) _fStream.Close();
UnityEngine.Debug.Log("Load cinematic file: " + clipName);
//if (!File.Exists(GetFullPath(clipName)))
// _rootPath = Application.streamingAssetsPath + "/Cinematics";
//string fullPath = GetFullPath(clipName);
//_fStream = new FileStream(fullPath, FileMode.Open, FileAccess.Read);
FFileReader.ReadBytesAsync(GetFullPath(clipName),x=> {
_fStream = new MemoryStream(x);
_bReader = new BinaryReader(_fStream);
});
}
public void EndRead()
{
if (_bReader != null) _bReader.Close();
if (_fStream != null) _fStream.Close();
}
public void WriteInt(int value)
{
_bWriter.Write(value);
}
public int ReadInt()
{
return _bReader.ReadInt32();
}
public void WriteFloat(float value)
{
_bWriter.Write(value);
}
public float ReadFloat()
{
return _bReader.ReadSingle();
}
public void WriteString(string value)
{
_bWriter.Write(value);
}
public string ReadString()
{
return _bReader.ReadString();
}
public void WriteBool(bool value)
{
_bWriter.Write(value);
}
public bool ReadBool()
{
return _bReader.ReadBoolean();
}
public void WriteVector3(float[] vale)
{
for (int i = 0; i < vale.Length; ++i)
{
WriteFloat(vale[i]);
}
}
public float[] ReadVector3()
{
float[] ret = new float[3];
for (int i = 0; i < ret.Length; ++i)
{
ret[i] = ReadFloat();
}
return ret;
}
public void WriteList<T>(List<T> list) where T : ICinematic
{
int count = list.Count;
_bWriter.Write(count);
for (int i = 0; i < count; ++i)
{
list[i].WriteAll(_bWriter);
}
}
public List<T> ReadList<T>() where T : ICinematic, new()
{
List<T> ret = new List<T>();
int count = _bReader.ReadInt32();
for (int i = 0; i < count; ++i)
{
T obj = new T();
obj.ReadAll(_bReader);
ret.Add(obj);
}
return ret;
}
public void WriteListV3(List<float[]> posList)
{
int count = posList.Count;
WriteInt(count);
for (int i = 0; i < count; ++i)
{
WriteFloat(posList[i][0]);
WriteFloat(posList[i][1]);
WriteFloat(posList[i][2]);
}
}
public List<float[]> ReadListV3()
{
List<float[]> ret = new List<float[]>();
int count = _bReader.ReadInt32();
for (int i = 0; i < count; ++i)
{
float[] v3 = new float[3];
v3[0] = ReadFloat();
v3[1] = ReadFloat();
v3[2] = ReadFloat();
ret.Add(v3);
}
return ret;
}
public void WriteV3Array(Vector3[] posList)
{
int count = posList.Length;
WriteInt(count);
for (int i = 0; i < count; ++i)
{
WriteFloat(posList[i].x);
WriteFloat(posList[i].y);
WriteFloat(posList[i].z);
}
}
public Vector3[] ReadV3Array()
{
int count = _bReader.ReadInt32();
Vector3[] ret = new Vector3[count];
for (int i = 0; i < count; ++i)
{
Vector3 v3 = new Vector3();
v3.x = ReadFloat();
v3.y = ReadFloat();
v3.z = ReadFloat();
ret[i] = v3;
}
return ret;
}
public Vector3[] ToV3Array(float[][] array)
{
Vector3[] v3Array = new Vector3[array.Length];
for (int i = 0; i < v3Array.Length; ++i)
{
v3Array[i].x = array[i][0];
v3Array[i].y = array[i][1];
v3Array[i].z = array[i][2];
}
return v3Array;
}
}
}