//----------------------------------------------------------------- /// <summary> /// 세션 로드 /// </summary> /// <param name="filepath"></param> /// <returns></returns> public static FSNSession Load(string filepath) { var newsession = new FSNSession(); var rawdata = FSNUtils.LoadTextData(filepath); JSONObject json = JSONObject.Create(rawdata); if (json != null) { // Script 관련 newsession.ScriptName = json[c_field_scriptName].str; newsession.ScriptHashKey = json[c_field_scriptHash].str; newsession.SnapshotIndex = (int)json[c_field_snapshotIndex].n; // 플래그 테이블 var flagtable = json[c_field_flagTable]; foreach (var key in flagtable.keys) { newsession.SetFlagValue(key, flagtable[key].b, true); } // 값 테이블 var valuetable = json[c_field_valueTable]; foreach (var key in valuetable.keys) { newsession.SetNumberValue(key, valuetable[key].n, true); } } else { Debug.LogErrorFormat("[FSNSession] error loading session file : {0}", filepath); } return(newsession); }
/// <summary> /// 세션 저장 /// </summary> /// <param name="session"></param> /// <param name="filepath"></param> public static void Save(FSNSession session, string filepath, string saveTitle = "") { { var json = new JSONObject(JSONObject.Type.OBJECT); // Script 관련 json.AddField(c_field_scriptName, session.ScriptName); json.AddField(c_field_scriptHash, session.ScriptHashKey); json.AddField(c_field_snapshotIndex, session.SnapshotIndex); // 세이브 정보 json.AddField(c_field_saveDateTime, FSNUtils.GenerateCurrentDateAndTimeString()); json.AddField(c_field_saveTitle, saveTitle); // 플래그 테이블 var flagtable = new JSONObject(JSONObject.Type.OBJECT); json.AddField(c_field_flagTable, flagtable); foreach (var pair in session.m_flagTable) { flagtable.AddField(pair.Key, pair.Value); } // 값 테이블 var valuetable = new JSONObject(JSONObject.Type.OBJECT); json.AddField(c_field_valueTable, valuetable); foreach (var pair in session.m_valueTable) { valuetable.AddField(pair.Key, pair.Value); } FSNUtils.SaveTextData(filepath, json.Print()); } }
/// <summary> /// 속성 이름 별명을 원래 속성명으로 변환 /// </summary> /// <param name="aliasname"></param> /// <returns></returns> public static string ConvertPropertyNameAlias(string aliasname) { string realname = aliasname; string spaceRemoved = FSNUtils.RemoveAllWhiteSpaces(aliasname); // 공백 모두 제거 return(s_propNameAlias.TryGetValue(spaceRemoved, out realname)? realname : aliasname); // 이름을 검색하지 못했다면 원래 이름을 그대로 반환한다 }
public Config(string configPath) { //Debug.Log("Config file read : " + configPath); var data = AssetDatabase.LoadAssetAtPath <TextAsset>(configPath).text; var json = new JSONObject(data); // 설정파일을 읽는다. outputPath = json[c_jsonfield_outputPath].str; var pair = json[c_jsonfield_targetDimension].list; outputWidth = (int)pair[0].n; outputHeight = (int)pair[1].n; // 설정파일과 같은 경로에 있는 텍스쳐들을 검색 string dir, filename; FSNUtils.StripPathAndName(configPath, out dir, out filename); var textureGUIDs = AssetDatabase.FindAssets("t:Texture2D", new string[] { dir }); var texcount = textureGUIDs.Length; var texturePaths = new string[texcount]; for (int i = 0; i < texcount; i++) { texturePaths[i] = AssetDatabase.GUIDToAssetPath(textureGUIDs[i]); } spritePathList = texturePaths; }
/// <summary> /// Persistent 데이터 세이브 /// </summary> public static void Save(bool force = false) { if (IsDirty || force) // 변경점이 있을 때만 저장, force가 올라가있다면 무조건 { FSNUtils.SaveTextData(c_persistent_filename, m_persData.Print()); IsDirty = false; // dirty 플래그 내리기 } }
/// <summary> /// 해당 이름으로 스크립트에서 읽어온 parameter를 세팅한다 /// </summary> /// <param name="name"></param> /// <param name="param"></param> public void SetPropertyFromScriptParams(string name, string param) { var realname = ConvertAliasPropertyName(FSNUtils.RemoveAllWhiteSpaces(name)); // 공백을 제거해서 별명 변환 시도 if (SetPropertyImpl(realname, param)) // 파라미터 값을 적용했다면 setFlag 리스트에 추가 { AddPropertySetFlag(name); } }
/// <summary> /// 파라미터 문자열을 변수명으로 해서 세션 변수값을 가져오거나, 세션 변수값이 아닌 것 같은 경우 리터럴로 처리 /// </summary> /// <param name="param"></param> /// <returns></returns> static float GetValueOrLiteral(string param) { if (engine.ScriptValueIsDeclared(param)) { return(engine.GetScriptValue(param)); } else { return(FSNUtils.StringToValue <float>(param)); } }
// Util funcs /// <summary> /// 파라미터 문자열을 변수명으로 해서 세션 플래그값을 가져오거나, 세션 플래그값이 아닌 것 같은 경우 리터럴로 처리 /// </summary> /// <param name="param"></param> /// <returns></returns> static bool GetFlagOrLiteral(string param) { if (engine.ScriptFlagIsDeclared(param)) { return(engine.GetScriptFlag(param)); } else { return(FSNUtils.StringToValue <bool>(param)); } }
public void OnBtn_Quit() { CloseSelf(); var msgbox = FSNOverlayUI.Instance.GetDialog <FSNOverlayMessageDialog>(); msgbox.SetupDialogTexts("앱을 종료할 시 진행 사항을 따로 저장하지 않으면 모두 소실됩니다.\n\n정말로 종료할까요?", "예", "아니오"); msgbox.SetupCallbacks(() => { FSNUtils.QuitApp(); }); FSNOverlayUI.Instance.OpenDialog <FSNOverlayMessageDialog>(); }
//--------------------------------------------------------------------------------------- /// <summary> /// 헤더 정보 먼저 처리 /// </summary> /// <param name="scriptData"></param> /// <param name="session"></param> static void ProcessHeaders(string scriptData, FSNScriptSequence sequence, FSNSession session) { var strstream = new System.IO.StringReader(scriptData); string line = null; int linenumber = 0; // 줄 번호 while ((line = strstream.ReadLine()) != null) // 줄 단위로 읽는다. { linenumber++; FSNDebug.currentProcessingScriptLine = linenumber; // 디버깅 정보 설정 if (line.Length > 0 && line.Substring(0, 1) == c_token_PreProcessor) // 프리프로세서 기호에만 반응한다 { var commandAndParam = line.Substring(1).Split(c_whiteSpaceArray, 2); // 명령어 파라미터 구분 var command = commandAndParam[0]; var paramStr = commandAndParam.Length > 1? commandAndParam[1] : ""; // 아직까지는 header 커맨드밖에 없으므로 간단하게 if로만 체크한다. 더 늘어나면 리팩토링이 필요해질듯... if (command == "헤더" || command == "header") { sequence.Header.FromAsset(paramStr.Trim()); } else { Debug.LogErrorFormat("[FSNSequence] line {0} : unknown preprocessor command {1}", linenumber, command); } } } // 읽어들인 헤더 정보를 바탕으로 플래그/변수 기본값들 세팅하기 (선언되어있지 않은 경우에만) foreach (var pair in sequence.Header.FlagDeclarations) // 플래그 선언 { if (!session.FlagIsDeclared(pair.Key)) // 아직 선언되지 않은 경우만 세팅 { bool value = string.IsNullOrEmpty(pair.Value)? false : FSNUtils.StringToValue <bool>(pair.Value); // 초기값까지 선언한 경우 값 해독, 아니면 기본값 false session.SetFlagValue(pair.Key, value, true); } } foreach (var pair in sequence.Header.ValueDeclarations) // 값 선언 { if (!session.ValueIsDeclared(pair.Key)) // 아직 선언되지 않은 경우만 세팅 { float value = string.IsNullOrEmpty(pair.Value)? 0 : FSNUtils.StringToValue <float>(pair.Value); // 초기값까지 선언한 경우 값 해독, 아니면 기본값 false session.SetNumberValue(pair.Key, value, true); } } }
public void SetPropertyByString(string propName, string strval) { var propInfo = typeof(Chain).GetProperty(propName); if (propInfo == null) { Debug.LogError("Cannot find a property named " + propName); } else { object value = FSNUtils.StringToValue(propInfo.PropertyType, strval); propInfo.SetValue(this, value, null); } }
/// <summary> /// 세이브 파일 정보 가져오기 /// </summary> /// <param name="filepath"></param> /// <returns></returns> public static SaveInfo GetSaveFileInfo(string filepath) { var info = new SaveInfo(); var rawdata = FSNUtils.LoadTextData(filepath); JSONObject json = JSONObject.Create(rawdata); if (json != null) { info.saveDateTime = json[c_field_saveDateTime].str; info.title = json[c_field_saveTitle].str; } return(info); }
/// <summary> /// 타겟 경로가 유효하도록, 필요할 경우 폴더를 생성한다. /// </summary> /// <param name="targetpath"></param> public static void MakeTargetDirectory(string targetdir) { if (!string.IsNullOrEmpty(targetdir) && !AssetDatabase.IsValidFolder(targetdir)) { string parent, current; FSNUtils.StripPathAndName(targetdir, out parent, out current); MakeTargetDirectory(parent); if (!string.IsNullOrEmpty(current)) { AssetDatabase.CreateFolder(parent, current); //Debug.LogFormat("making dir : {0}, {1}", parent, current); } } }
public static void __fsnengine_SetValues(params string [] param) { int count = param.Length; string varname = null; for (int i = 0; i < count; i++) { if (i % 2 == 0) // 홀수번째 파라미터는 플래그 이름 { varname = param[i]; } else { // 짝수번째는 변수값. 바로 이전에 얻은 변수 이름으로 세팅한다 engine.SetScriptValue(varname, FSNUtils.StringToValue <float>(param[i])); varname = null; } } }
/// <summary> /// Persistent 데이터 로딩 /// </summary> public static void Load() { if (FSNUtils.CheckTextFileExists(c_persistent_filename)) // 파일이 존재하는 경우엔 단순 로드 { m_persData = JSONObject.Create(FSNUtils.LoadTextData(c_persistent_filename)); } else { // 파일이 없을 시엔 새롭게 JSONObject 생성 m_persData = new JSONObject(JSONObject.Type.OBJECT); var scriptVars = new JSONObject(JSONObject.Type.OBJECT); m_persData.AddField(c_field_scriptVars, scriptVars); scriptVars.AddField(c_field_flagTable, new JSONObject(JSONObject.Type.OBJECT)); scriptVars.AddField(c_field_valueTable, new JSONObject(JSONObject.Type.OBJECT)); IsDirty = true; // dirty 플래그 세우기 } }
/// <summary> /// 다른 Layer와 비교해서 두 레이어에 모두 포함되는 Element와 그렇지 않은 Element를 찾아내 리턴한다 /// </summary> /// <param name="other"></param> /// <param name="matching"></param> /// <param name="notmatching"></param> public Match CompareAndReturnElements(Layer other) { Match result; HashSet <int> inThis = new HashSet <int>(m_elements.Keys); HashSet <int> inOther = new HashSet <int>(other.m_elements.Keys); HashSet <int> matching = new HashSet <int>(inThis); matching.IntersectWith(inOther); // 두 Layer에 모두 포함되는 것들 inThis.ExceptWith(matching); // 각각 교집합 부분을 모두 소거한다 (각자에게만 있는 것만 남음) inOther.ExceptWith(matching); result.Matching = FSNUtils.MakeArray <int>(matching); result.OnlyInThis = FSNUtils.MakeArray <int>(inThis); result.OnlyInOther = FSNUtils.MakeArray <int>(inOther); return(result); }
protected override bool SetPropertyImpl(string name, string param) { // 기존 속성들은 사용하지 않음 //return base.SetPropertyImpl(name, param); bool success = false; switch (name) { case c_property_clipPath: clipPath = param; success = true; break; case c_property_volume: volume = float.Parse(param); success = true; break; case c_property_panning: panning = float.Parse(param); success = true; break; case c_property_looping: looping = FSNUtils.StringToValue <bool>(param); success = true; break; case c_property_Transition: transition = float.Parse(param); success = true; break; default: Debug.LogErrorFormat("[Segments.Sound] Wrong property name {0}", name); success = false; break; } return(success); }
protected override bool SetPropertyImpl(string name, string param) { switch (name) { case c_property_TexturePath: texturePath = param; return(true); case c_property_Pivot: pivot = FSNUtils.StringToValue <PivotPreset>(param); return(true); case c_property_CombImgPath: combinedImgPath = param; return(true); case c_property_AdaptToPerspective: adaptToPerspective = FSNUtils.StringToValue <bool>(param); return(true); } return(base.SetPropertyImpl(name, param)); }
/// <summary> /// 조합 이미지 하나를 빌드한다. /// </summary> /// <param name="config"></param> /// <returns></returns> static bool BuildCombinedImage(Config config) { var packer = new FSNSpritePacker(); packer.outputPath = config.outputPath; var paths = config.spritePathList; var count = paths.Length; for (int i = 0; i < count; i++) // 각 텍스쳐 경로에 대해 실행 { EnsureSourceTextureImportSetting(paths[i]); // 소스 텍스쳐 임포트 세팅 맞추기 var origpath = paths[i]; string path, name; FSNUtils.StripPathAndName(origpath, out path, out name); var texture = AssetDatabase.LoadAssetAtPath <Texture2D>(origpath); var data = new FSNSpritePackerData(texture, FSNUtils.RemoveFileExt(name)); packer.PushData(data); // 팩커에 텍스쳐 하나씩 밀어넣기 } return(packer.Pack(config.outputWidth, config.outputHeight)); }
/// <summary> /// 특정 경로에 있는 텍스쳐들을 검색해서 premultiplied alpha를 적용하여 빌드한다. /// </summary> /// <param name="searchPath"></param> public static void ConvertWithinPath(string searchPath, string destPath) { var guids = AssetDatabase.FindAssets("t:Texture2D", new string[] { searchPath }); var count = guids.Length; var processed = 0; for (var i = 0; i < count; i++) { var path = AssetDatabase.GUIDToAssetPath(guids[i]); string dir, name; FSNUtils.StripPathAndName(path, out dir, out name); // 텍스쳐 경로, 이름 분리 var subdir = searchPath.Length == dir.Length? "" : dir.Substring(searchPath.Length + 1); // 검색 경로의 하위 경로를 뽑아낸다. var importer = AssetImporter.GetAtPath(path) as TextureImporter; // 텍스쳐 타입을 제대로 설정한다. importer.npotScale = TextureImporterNPOTScale.None; importer.textureFormat = TextureImporterFormat.AutomaticTruecolor; importer.isReadable = true; importer.SaveAndReimport(); var completeDestPath = destPath; if (subdir.Length > 0 && subdir[0] != '/') { subdir = "/" + subdir; } completeDestPath += subdir; //Debug.Log("completeDestPath : " + completeDestPath); Convert(path, name, completeDestPath); processed++; } AssetDatabase.Refresh(); Debug.LogFormat("Premultiplied Alpha 텍스쳐 생성 완료. 총 {0} 개 처리했습니다.", processed); }
protected override void OnSuccess(int width, int height, Output[] output) { var outtex = new Texture2D(width, height, TextureFormat.ARGB32, false); var pixels = outtex.GetPixels32(); // 텍스쳐를 0으로 채우기 var pixcnt = pixels.Length; var zeroCol = new Color32(0, 0, 0, 0); for (int i = 0; i < pixcnt; i++) { pixels[i] = zeroCol; } outtex.SetPixels32(pixels); int count = output.Length; for (int i = 0; i < count; i++) // 텍스쳐를 조립한다. { var entry = output[i]; var texture = entry.data.texture; outtex.SetPixels32(entry.xMin, entry.yMin, texture.width, texture.height, texture.GetPixels32()); } //var textureOutAssetPath = "Resources/" + outputPath + ".png"; // 실제 출력할 텍스쳐 경로 (asset) var textureOutAssetPath = outputPath + ".png"; var textureOutRealPath = Application.dataPath + "/" + textureOutAssetPath; // 실제 출력할 텍스쳐 경로 (절대경로) string outPath, outName; FSNUtils.StripPathAndName(textureOutAssetPath, out outPath, out outName); FSNEditorUtils.MakeTargetDirectory("Assets/" + outPath); // 타겟 디렉토리 확보 System.IO.File.WriteAllBytes(textureOutRealPath, outtex.EncodeToPNG()); // 텍스쳐를 파일로 기록한다. AssetDatabase.Refresh(); var importer = AssetImporter.GetAtPath("Assets/" + textureOutAssetPath) as TextureImporter; var settings = new TextureImporterSettings(); importer.ReadTextureSettings(settings); settings.ApplyTextureType(TextureImporterType.Sprite, false); settings.spriteMeshType = SpriteMeshType.FullRect; settings.spriteExtrude = 0; settings.rgbm = TextureImporterRGBMMode.Off; importer.SetTextureSettings(settings); importer.textureType = TextureImporterType.Advanced; // 출력한 텍스쳐의 임포트 옵션 설정 importer.anisoLevel = 0; importer.filterMode = FilterMode.Bilinear; importer.mipmapEnabled = false; importer.npotScale = TextureImporterNPOTScale.None; importer.isReadable = true; importer.spriteImportMode = SpriteImportMode.Single; // 어떤 경우, Single로 바꾼 다음 다시 Multi로 바꿔야한다. importer.textureFormat = TextureImporterFormat.AutomaticTruecolor; importer.linearTexture = true; var spritesheet = new List <SpriteMetaData>(); // 스프라이트 시트 생성 (각 스프라이트 영역 구분) for (int i = 0; i < count; i++) { var entry = output[i]; spritesheet.Add(new SpriteMetaData() { pivot = new Vector2(0.5f, 0.5f), alignment = 0, name = entry.data.spriteName, rect = new Rect(entry.xMin, entry.yMin, entry.data.width, entry.data.height) }); } importer.spriteImportMode = SpriteImportMode.Multiple; importer.spritesheet = spritesheet.ToArray(); importer.SaveAndReimport(); }
/// <summary> /// /// </summary> /// <param name="name">변환된 프로퍼티 이름</param> /// <param name="param">스크립트에서 읽어온 파라미터</param> /// <returns>세팅 성공시 true, 실패시 false</returns> protected virtual bool SetPropertyImpl(string name, string param) { bool success; switch (name) { case c_property_Position: // * 위치 { var splitparams = FSNScriptSequence.Parser.ParseParameters(param); switch (splitparams.Length) { case 2: position.x = float.Parse(splitparams[0]); position.y = float.Parse(splitparams[1]); success = true; break; case 3: position.x = float.Parse(splitparams[0]); position.y = float.Parse(splitparams[1]); position.z = float.Parse(splitparams[2]); success = true; break; default: Debug.LogError("Position property needs at least 2 parameters."); success = false; break; } } break; case c_property_Scale: // * 스케일 { var splitparams = FSNScriptSequence.Parser.ParseParameters(param); switch (splitparams.Length) { case 1: scale = Vector3.one * float.Parse(splitparams[0]); success = true; break; case 2: scale.x = float.Parse(splitparams[0]); scale.y = float.Parse(splitparams[1]); success = true; break; case 3: scale.x = float.Parse(splitparams[0]); scale.y = float.Parse(splitparams[1]); scale.z = float.Parse(splitparams[2]); success = true; break; default: Debug.LogError("Scale property needs from 1 to 3 parameters."); success = false; break; } } break; case c_property_Rotation: // * 로테이션 { var splitparams = FSNScriptSequence.Parser.ParseParameters(param); switch (splitparams.Length) { case 1: rotation.z = float.Parse(splitparams[0]); success = true; break; case 3: rotation.x = float.Parse(splitparams[0]); rotation.y = float.Parse(splitparams[1]); rotation.z = float.Parse(splitparams[2]); success = true; break; default: Debug.LogError("Position property needs 1 or 3 parameters."); success = false; break; } } break; case c_property_Color: // * Color { var splitparams = FSNScriptSequence.Parser.ParseParameters(param); switch (splitparams.Length) { case 1: color = FSNUtils.ConvertHexCodeToColor(splitparams[0]); success = true; break; case 3: color.r = float.Parse(splitparams[0]); color.g = float.Parse(splitparams[1]); color.b = float.Parse(splitparams[2]); success = true; break; case 4: color.r = float.Parse(splitparams[0]); color.g = float.Parse(splitparams[1]); color.b = float.Parse(splitparams[2]); color.a = float.Parse(splitparams[3]); success = true; break; default: Debug.LogError("Position property needs 1 or 3 parameters."); success = false; break; } } break; case c_property_Alpha: alpha = float.Parse(param); success = true; break; case c_property_Transition: transition = float.Parse(param); success = true; break; case c_property_Component: if (componentName != null) // 이미 지정된 상태에서는 컴포넌트 이름을 또 지정할 수는 없다 { Debug.LogError("[Segments.Object] Cannot change componentName after applied once"); success = false; } else { componentName = param.Trim(); success = true; } break; case c_property_CompParam: componentParameter = param.Trim(); success = true; break; default: Debug.LogErrorFormat("[Segments.Object] Wrong property name {0}", name); success = false; break; } return(success); }
/// <summary> /// 프로퍼티가 설정되었음을 나타내는 플래그 추가 /// </summary> public void AddPropertySetFlag(string name) { var realname = ConvertAliasPropertyName(FSNUtils.RemoveAllWhiteSpaces(name)); // 공백을 제거해서 별명 변환 시도 PropertySetList.Add(realname); }