Compare commits

...

12 Commits

Author SHA1 Message Date
8942aceef2 version 0.4 2016-09-22 02:19:15 +07:00
7057cd71a8 clear code 2016-09-22 02:14:58 +07:00
1d402eb91e clip groups 2016-09-21 23:36:32 +07:00
2ce9897d60 compress asset data 2016-09-21 01:16:12 +07:00
63fea79f49 able move containers and assets 2016-09-20 15:19:39 +07:00
5d29da73c7 tint color for clips 2016-09-16 05:08:06 +07:00
0c4efc0111 flash tools log prefix 2016-09-16 04:50:07 +07:00
6474828774 open settings menu button 2016-09-16 04:36:47 +07:00
78758786e6 'reimport all' menu button 2016-09-16 03:25:44 +07:00
7a0940b6a1 pause, resume and rate scale for manger 2016-09-16 03:03:33 +07:00
3d688d1ac2 controller API improvements 2016-09-16 02:33:48 +07:00
6d69b46c2f Added tag versions/0.3 for changeset d2d05072620c 2016-09-14 22:30:25 +07:00
28 changed files with 878 additions and 514 deletions

View File

@@ -1,3 +1,12 @@
-----------------
-- Version 0.4 --
-----------------
Clip groups
Fix move assets bug
Tint color for clips
Animation API improvements
-----------------
-- Version 0.3 --
-----------------

View File

@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 075eada96ece147de8eeee4710c5ab0f
timeCreated: 1474360714
licenseType: Free
DefaultImporter:
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -145,7 +145,7 @@ Camera:
far clip plane: 1000
field of view: 60
orthographic: 1
orthographic size: 5
orthographic size: 23
m_Depth: 0
m_CullingMask:
serializedVersion: 2

View File

@@ -1,6 +1,7 @@
Shader "FlashTools/SwfMasked" {
Properties {
[PerRendererData] _MainTex("Main Texture", 2D) = "white" {}
[PerRendererData] _MainTex("Main Texture", 2D ) = "white" {}
[PerRendererData] _Color ("Tint" , Color) = (1,1,1,1)
_StencilID ("Stencil ID", Int) = 0
}
@@ -42,11 +43,13 @@ Shader "FlashTools/SwfMasked" {
fixed4 addcolor : TEXCOORD1;
};
fixed4 _Color;
v2f vert(appdata_t IN) {
v2f OUT;
OUT.vertex = mul(UNITY_MATRIX_MVP, IN.vertex);
OUT.uv = IN.uv;
OUT.mulcolor = IN.mulcolor;
OUT.mulcolor = IN.mulcolor * _Color;
OUT.addcolor = IN.addcolor;
return OUT;
}

View File

@@ -1,6 +1,7 @@
Shader "FlashTools/SwfSimple" {
Properties {
[PerRendererData] _MainTex("Main Texture", 2D) = "white" {}
[PerRendererData] _MainTex("Main Texture", 2D ) = "white" {}
[PerRendererData] _Color ("Tint" , Color) = (1,1,1,1)
}
SubShader {
@@ -37,11 +38,13 @@ Shader "FlashTools/SwfSimple" {
fixed4 addcolor : TEXCOORD1;
};
fixed4 _Color;
v2f vert(appdata_t IN) {
v2f OUT;
OUT.vertex = mul(UNITY_MATRIX_MVP, IN.vertex);
OUT.uv = IN.uv;
OUT.mulcolor = IN.mulcolor;
OUT.mulcolor = IN.mulcolor * _Color;
OUT.addcolor = IN.addcolor;
return OUT;
}

View File

@@ -8,27 +8,12 @@ using System.Collections.Generic;
namespace FlashTools.Internal {
[CustomEditor(typeof(SwfAsset)), CanEditMultipleObjects]
public class SwfAssetEditor : Editor {
List<SwfAsset> _assets = new List<SwfAsset>();
bool _clipsFoldout = false;
bool _settingsFoldout = false;
List<SwfAsset> _assets = new List<SwfAsset>();
//
//
//
static string GetAssetPath(SwfAsset asset) {
return asset
? AssetDatabase.GetAssetPath(asset)
: string.Empty;
}
static string GetSwfPath(SwfAsset asset) {
var asset_path = GetAssetPath(asset);
return string.IsNullOrEmpty(asset_path)
? string.Empty
: Path.ChangeExtension(asset_path, ".swf");
}
static SwfSettings _defaultSettingsCache = null;
static SwfSettings GetDefaultSettings() {
if ( !_defaultSettingsCache ) {
@@ -50,19 +35,14 @@ namespace FlashTools.Internal {
}
static void ApplyOverriddenSettings(SwfAsset asset) {
if ( File.Exists(GetSwfPath(asset)) ) {
asset.Settings = asset.Overridden;
ReconvertAsset(asset);
} else {
Debug.LogErrorFormat(
"Swf source for asset not found: '{0}'",
GetSwfPath(asset));
RevertOverriddenSettings(asset);
}
asset.Settings = asset.Overridden;
ReconvertAsset(asset);
}
static void ReconvertAsset(SwfAsset asset) {
AssetDatabase.ImportAsset(GetSwfPath(asset));
asset.Converting = new SwfAsset.ConvertingState();
AssetDatabase.ImportAsset(
AssetDatabase.GetAssetPath(asset));
}
//
@@ -113,81 +93,28 @@ namespace FlashTools.Internal {
}
}
void DrawGUIDefaultSettings() {
SwfEditorUtils.DoWithEnabledGUI(false, () => {
EditorGUILayout.ObjectField(
"Default Settings",
GetDefaultSettings(),
typeof(SwfSettings),
false);
});
}
void DrawGUIClips() {
var asset = _assets.Count == 1 ? _assets.First() : null;
if ( asset && asset.Clips != null && asset.Clips.Count > 0 ) {
_clipsFoldout = EditorGUILayout.Foldout(_clipsFoldout, "Clips");
if ( _clipsFoldout ) {
SwfEditorUtils.DoWithEnabledGUI(false, () => {
var clip_count = Mathf.Min(asset.Data.Symbols.Count, asset.Clips.Count);
for ( var i = 0; i < clip_count; ++i ) {
EditorGUILayout.ObjectField(
asset.Data.Symbols[i].Name,
asset.Clips[i],
typeof(SwfClipAsset),
false);
}
});
DrawGUIClipsControls();
}
}
}
void DrawGUIClipsControls() {
GUILayout.BeginHorizontal();
GUILayout.FlexibleSpace();
{
if ( GUILayout.Button("Reimport all") ) {
RevertAllOverriddenSettings();
ApplyAllOverriddenSettings();
}
}
GUILayout.EndHorizontal();
}
void DrawGUISettings() {
_settingsFoldout = EditorGUILayout.Foldout(_settingsFoldout, "Settings");
if ( _settingsFoldout ) {
var it = SwfEditorUtils.GetPropertyByName(serializedObject, "Overridden");
while ( it.Next(true) ) {
EditorGUILayout.PropertyField(it, true);
}
DrawGUISettingsControls();
}
}
void DrawGUISettingsControls() {
GUILayout.BeginHorizontal();
GUILayout.FlexibleSpace();
{
var default_settings = GetDefaultSettings().Settings;
SwfEditorUtils.DoWithEnabledGUI(
_assets.Any(p => !p.Overridden.CheckEquals(default_settings)), () => {
if ( GUILayout.Button("Default") ) {
AllOverriddenSettingsToDefault();
}
});
SwfEditorUtils.DoWithEnabledGUI(
_assets.Any(p => !p.Overridden.CheckEquals(p.Settings)), () => {
if ( GUILayout.Button("Revert") ) {
RevertAllOverriddenSettings();
}
if ( GUILayout.Button("Apply") ) {
ApplyAllOverriddenSettings();
}
});
var prop = SwfEditorUtils.GetPropertyByName(serializedObject, "Overridden");
if ( prop.isExpanded ) {
SwfEditorUtils.DoRightHorizontalGUI(() => {
var default_settings = GetDefaultSettings().Settings;
SwfEditorUtils.DoWithEnabledGUI(
_assets.Any(p => !p.Overridden.CheckEquals(default_settings)), () => {
if ( GUILayout.Button("Default") ) {
AllOverriddenSettingsToDefault();
}
});
SwfEditorUtils.DoWithEnabledGUI(
_assets.Any(p => !p.Overridden.CheckEquals(p.Settings)), () => {
if ( GUILayout.Button("Revert") ) {
RevertAllOverriddenSettings();
}
if ( GUILayout.Button("Apply") ) {
ApplyAllOverriddenSettings();
}
});
});
}
GUILayout.EndHorizontal();
}
// ---------------------------------------------------------------------
@@ -197,9 +124,7 @@ namespace FlashTools.Internal {
// ---------------------------------------------------------------------
void OnEnable() {
_assets = targets.OfType<SwfAsset>().ToList();
_clipsFoldout = false;
_settingsFoldout = true;
_assets = targets.OfType<SwfAsset>().ToList();
}
void OnDisable() {
@@ -209,9 +134,7 @@ namespace FlashTools.Internal {
public override void OnInspectorGUI() {
serializedObject.Update();
DrawDefaultInspector();
DrawGUIDefaultSettings();
DrawGUIClips();
DrawGUISettings();
DrawGUISettingsControls();
if ( GUI.changed ) {
serializedObject.ApplyModifiedProperties();
}

View File

@@ -120,16 +120,14 @@ namespace FlashTools.Internal {
}
void DrawGUIControls() {
GUILayout.BeginHorizontal();
{
SwfEditorUtils.DoHorizontalGUI(() => {
if ( GUILayout.Button("Create prefab") ) {
CreateAllClipsPrefabs();
}
if ( GUILayout.Button("Instance to scene") ) {
CreateAllClipsOnScene();
}
}
GUILayout.EndHorizontal();
});
}
// ---------------------------------------------------------------------

View File

@@ -16,20 +16,14 @@ namespace FlashTools.Internal {
}
void DrawClipControls() {
GUILayout.BeginHorizontal();
GUILayout.FlexibleSpace();
{
if ( GUILayout.Button("Rewind") ) {
AllControllersForeach(p => p.Rewind());
}
SwfEditorUtils.DoRightHorizontalGUI(() => {
if ( GUILayout.Button("Stop") ) {
AllControllersForeach(p => p.Stop());
AllControllersForeach(ctrl => ctrl.Stop(ctrl.isStopped));
}
if ( GUILayout.Button("Play") ) {
AllControllersForeach(p => p.Play());
AllControllersForeach(ctrl => ctrl.Play(ctrl.isPlaying));
}
}
GUILayout.EndHorizontal();
});
}
// ---------------------------------------------------------------------

View File

@@ -109,9 +109,7 @@ namespace FlashTools.Internal {
void DrawClipControls() {
EditorGUILayout.Space();
GUILayout.BeginHorizontal();
GUILayout.FlexibleSpace();
{
SwfEditorUtils.DoCenterHorizontalGUI(() => {
if ( GUILayout.Button(new GUIContent("<<", "to begin frame")) ) {
AllClipsForeachWithUndo(p => p.ToBeginFrame());
}
@@ -127,9 +125,7 @@ namespace FlashTools.Internal {
if ( GUILayout.Button(new GUIContent(">>", "to end frame")) ) {
AllClipsForeachWithUndo(p => p.ToEndFrame());
}
}
GUILayout.FlexibleSpace();
GUILayout.EndHorizontal();
});
}
void HideMaterials() {

View File

@@ -1,19 +1,76 @@
using UnityEngine;
using UnityEditor;
using System.Collections.Generic;
namespace FlashTools.Internal {
[CustomEditor(typeof(SwfManager))]
public class SwfManagerEditor : Editor {
SwfManager _manager = null;
SwfManager _manager = null;
SwfList<SwfClipController> _controllers = new SwfList<SwfClipController>();
bool _groupsFoldout = true;
void DrawAnimationCount() {
void DrawCounts() {
SwfEditorUtils.DoWithEnabledGUI(false, () => {
EditorGUILayout.IntField(
"Clip count",
_manager.AllClipCount);
_manager.clipCount);
EditorGUILayout.IntField(
"Controller count",
_manager.controllerCount);
});
}
void DrawControls() {
SwfEditorUtils.DoRightHorizontalGUI(() => {
if ( _manager.isPaused && GUILayout.Button("Resume") ) {
_manager.Resume();
}
if ( _manager.isPlaying && GUILayout.Button("Pause") ) {
_manager.Pause();
}
});
}
void DrawGroupControls() {
var group_names = GetAllGroupNames();
if ( group_names.Count > 0 ) {
_groupsFoldout = EditorGUILayout.Foldout(_groupsFoldout, "Groups");
if ( _groupsFoldout ) {
foreach ( var group_name in group_names ) {
SwfEditorUtils.DoWithEnabledGUI(false, () => {
EditorGUILayout.TextField("Name", group_name);
});
EditorGUI.BeginChangeCheck();
var new_rate_scale = EditorGUILayout.FloatField(
"Rate Scale", _manager.GetGroupRateScale(group_name));
if ( EditorGUI.EndChangeCheck() ) {
_manager.SetGroupRateScale(group_name, new_rate_scale);
}
SwfEditorUtils.DoRightHorizontalGUI(() => {
if ( _manager.IsGroupPaused(group_name) && GUILayout.Button("Resume") ) {
_manager.ResumeGroup(group_name);
}
if ( _manager.IsGroupPlaying(group_name) && GUILayout.Button("Pause") ) {
_manager.PauseGroup(group_name);
}
});
}
}
}
}
HashSet<string> GetAllGroupNames() {
var result = new HashSet<string>();
for ( int i = 0, e = _controllers.Count; i < e; ++i ) {
var ctrl = _controllers[i];
if ( !string.IsNullOrEmpty(ctrl.groupName) ) {
result.Add(ctrl.groupName);
}
}
return result;
}
// ---------------------------------------------------------------------
//
// Messages
@@ -22,11 +79,20 @@ namespace FlashTools.Internal {
void OnEnable() {
_manager = target as SwfManager;
_manager.GetAllControllers(_controllers);
}
public override void OnInspectorGUI() {
serializedObject.Update();
DrawDefaultInspector();
DrawAnimationCount();
DrawCounts();
if ( Application.isPlaying ) {
DrawControls();
DrawGroupControls();
}
if ( GUI.changed ) {
serializedObject.ApplyModifiedProperties();
}
}
}
}

View File

@@ -26,26 +26,157 @@ namespace FlashTools.Internal {
static void SwfAssetProcess(SwfAsset asset) {
try {
var atlas_asset = LoadAtlasAsset(asset);
if ( atlas_asset != asset.Atlas ) {
asset.Atlas = atlas_asset;
ConfigureAtlas(asset);
ConfigureClips(asset);
if ( asset.Converting.Stage == 0 ) {
var new_data = ConfigureBitmaps(
asset,
SwfEditorUtils.DecompressAsset<SwfAssetData>(asset.Data));
asset.Data = SwfEditorUtils.CompressAsset(new_data);
++asset.Converting.Stage;
EditorUtility.SetDirty(asset);
AssetDatabase.SaveAssets();
AssetDatabase.ImportAsset(AssetDatabase.GetAssetPath(asset));
} else if ( asset.Converting.Stage == 1 ) {
asset.Atlas = LoadAssetAtlas(asset);
if ( asset.Atlas ) {
ConfigureAtlas(asset);
ConfigureClips(
asset,
SwfEditorUtils.DecompressAsset<SwfAssetData>(asset.Data));
}
++asset.Converting.Stage;
EditorUtility.SetDirty(asset);
AssetDatabase.ImportAsset(AssetDatabase.GetAssetPath(asset));
}
ConfigureAssetClips(asset);
} catch ( Exception e ) {
Debug.LogErrorFormat(
"Postprocess swf asset error: {0}",
"<b>[FlashTools]</b> Postprocess swf asset error: {0}",
e.Message);
SwfEditorUtils.DeleteAssetWithDepends(asset);
AssetDatabase.DeleteAsset(AssetDatabase.GetAssetPath(asset));
} finally {
if ( asset ) {
UpdateAssetClips(asset);
}
}
}
static Texture2D LoadAtlasAsset(SwfAsset asset) {
static Texture2D LoadAssetAtlas(SwfAsset asset) {
return AssetDatabase.LoadAssetAtPath<Texture2D>(
SwfEditorUtils.GetAtlasPathFromAsset(asset));
GetAtlasPath(asset));
}
static string GetAtlasPath(SwfAsset asset) {
if ( asset.Atlas ) {
return AssetDatabase.GetAssetPath(asset.Atlas);
} else {
var asset_path = AssetDatabase.GetAssetPath(asset);
return Path.ChangeExtension(asset_path, "._Atlas_.png");
}
}
// ---------------------------------------------------------------------
//
// ConfigureBitmaps
//
// ---------------------------------------------------------------------
static SwfAssetData ConfigureBitmaps(SwfAsset asset, SwfAssetData data) {
var textures = data.Bitmaps
.Where (p => p.Redirect == 0)
.Select (p => new KeyValuePair<ushort, Texture2D>(
p.Id,
LoadTextureFromData(p)))
.ToList();
var rects = PackAndSaveBitmapsAtlas(
GetAtlasPath(asset),
textures.Select(p => p.Value).ToArray(),
asset.Settings);
for ( var i = 0; i < data.Bitmaps.Count; ++i ) {
var bitmap = data.Bitmaps[i];
var texture_key = bitmap.Redirect > 0 ? bitmap.Redirect : bitmap.Id;
bitmap.SourceRect = SwfRectData.FromURect(
rects[textures.FindIndex(p => p.Key == texture_key)]);
}
return data;
}
static Texture2D LoadTextureFromData(SwfBitmapData bitmap) {
var texture = new Texture2D(
bitmap.RealWidth, bitmap.RealHeight,
TextureFormat.ARGB32, false);
texture.LoadRawTextureData(bitmap.ARGB32);
return texture;
}
struct BitmapsAtlasInfo {
public Texture2D Atlas;
public Rect[] Rects;
}
static Rect[] PackAndSaveBitmapsAtlas(
string atlas_path, Texture2D[] textures, SwfSettingsData settings)
{
var atlas_info = PackBitmapsAtlas(textures, settings);
RevertTexturePremultipliedAlpha(atlas_info.Atlas);
File.WriteAllBytes(atlas_path, atlas_info.Atlas.EncodeToPNG());
GameObject.DestroyImmediate(atlas_info.Atlas, true);
AssetDatabase.ImportAsset(atlas_path);
return atlas_info.Rects;
}
static BitmapsAtlasInfo PackBitmapsAtlas(
Texture2D[] textures, SwfSettingsData settings)
{
var atlas_padding = Mathf.Max(0, settings.AtlasPadding);
var max_atlas_size = Mathf.Max(32, settings.AtlasPowerOfTwo
? Mathf.ClosestPowerOfTwo(settings.MaxAtlasSize)
: settings.MaxAtlasSize);
var atlas = new Texture2D(0, 0);
var rects = atlas.PackTextures(textures, atlas_padding, max_atlas_size);
while ( rects == null ) {
max_atlas_size = Mathf.NextPowerOfTwo(max_atlas_size + 1);
rects = atlas.PackTextures(textures, atlas_padding, max_atlas_size);
}
return settings.AtlasForceSquare && atlas.width != atlas.height
? BitmapsAtlasToSquare(atlas, rects)
: new BitmapsAtlasInfo{Atlas = atlas, Rects = rects};
}
static BitmapsAtlasInfo BitmapsAtlasToSquare(Texture2D atlas, Rect[] rects) {
var atlas_size = Mathf.Max(atlas.width, atlas.height);
var atlas_scale = new Vector2(atlas.width, atlas.height) / atlas_size;
var new_atlas = new Texture2D(atlas_size, atlas_size, TextureFormat.ARGB32, false);
for ( var i = 0; i < rects.Length; ++i ) {
var new_position = rects[i].position;
new_position.Scale(atlas_scale);
var new_size = rects[i].size;
new_size.Scale(atlas_scale);
rects[i] = new Rect(new_position, new_size);
}
var fill_pixels = new Color32[atlas_size * atlas_size];
for ( var i = 0; i < atlas_size * atlas_size; ++i ) {
fill_pixels[i] = new Color(1,1,1,0);
}
new_atlas.SetPixels32(fill_pixels);
new_atlas.SetPixels32(0, 0, atlas.width, atlas.height, atlas.GetPixels32());
new_atlas.Apply();
GameObject.DestroyImmediate(atlas, true);
return new BitmapsAtlasInfo{
Atlas = new_atlas,
Rects = rects};
}
static void RevertTexturePremultipliedAlpha(Texture2D texture) {
var pixels = texture.GetPixels();
for ( var i = 0; i < pixels.Length; ++i ) {
var c = pixels[i];
if ( c.a > 0 ) {
c.r /= c.a;
c.g /= c.a;
c.b /= c.a;
}
pixels[i] = c;
}
texture.SetPixels(pixels);
texture.Apply();
}
// ---------------------------------------------------------------------
@@ -55,28 +186,21 @@ namespace FlashTools.Internal {
// ---------------------------------------------------------------------
static void ConfigureAtlas(SwfAsset asset) {
var atlas_importer = GetBitmapsAtlasImporter(asset);
var atlas_importer_size = GetSizeFromTextureImporter(atlas_importer);
atlas_importer.spritesheet = asset.Data.Bitmaps
.Select(bitmap => new SpriteMetaData{
name = bitmap.Id.ToString(),
rect = new Rect(
bitmap.SourceRect.xMin * atlas_importer_size.x,
bitmap.SourceRect.yMin * atlas_importer_size.y,
bitmap.SourceRect.width * atlas_importer_size.x,
bitmap.SourceRect.height * atlas_importer_size.y)})
.ToArray();
var atlas_path = AssetDatabase.GetAssetPath(asset.Atlas);
var atlas_importer = GetBitmapsAtlasImporter(asset);
atlas_importer.spritesheet = new SpriteMetaData[0];
atlas_importer.textureType = TextureImporterType.Sprite;
atlas_importer.spriteImportMode = SpriteImportMode.Multiple;
atlas_importer.spritePixelsPerUnit = asset.Settings.PixelsPerUnit;
atlas_importer.mipmapEnabled = asset.Settings.GenerateMipMaps;
atlas_importer.filterMode = SwfAtlasFilterToImporterFilter(asset.Settings.AtlasTextureFilter);
atlas_importer.textureFormat = SwfAtlasFormatToImporterFormat(asset.Settings.AtlasTextureFormat);
AssetDatabase.ImportAsset(SwfEditorUtils.GetAtlasPathFromAsset(asset));
AssetDatabase.WriteImportSettingsIfDirty(atlas_path);
AssetDatabase.ImportAsset(atlas_path);
}
static TextureImporter GetBitmapsAtlasImporter(SwfAsset asset) {
var atlas_path = SwfEditorUtils.GetAtlasPathFromAsset(asset);
var atlas_path = AssetDatabase.GetAssetPath(asset.Atlas);
var atlas_importer = AssetImporter.GetAtPath(atlas_path) as TextureImporter;
if ( !atlas_importer ) {
throw new UnityException(string.Format(
@@ -86,14 +210,6 @@ namespace FlashTools.Internal {
return atlas_importer;
}
static Vector2 GetSizeFromTextureImporter(TextureImporter importer) {
var method_args = new object[2]{0,0};
typeof(TextureImporter)
.GetMethod("GetWidthAndHeight", BindingFlags.NonPublic | BindingFlags.Instance)
.Invoke(importer, method_args);
return new Vector2((int)method_args[0], (int)method_args[1]);
}
static FilterMode SwfAtlasFilterToImporterFilter(
SwfSettingsData.AtlasFilter filter)
{
@@ -136,32 +252,45 @@ namespace FlashTools.Internal {
//
// ---------------------------------------------------------------------
static void ConfigureClips(SwfAsset asset) {
asset.Clips.Clear();
foreach ( var symbol in asset.Data.Symbols ) {
ConfigureClip(asset, symbol);
static SwfAssetData ConfigureClips(SwfAsset asset, SwfAssetData data) {
asset.Clips = asset.Clips.Where(p => !!p).ToList();
foreach ( var symbol in data.Symbols ) {
ConfigureClip(asset, data, symbol);
}
return data;
}
static void ConfigureClip(SwfAsset asset, SwfAssetData data, SwfSymbolData symbol) {
var clip_asset = asset.Clips.FirstOrDefault(p => p.Name == symbol.Name);
if ( clip_asset ) {
ConfigureClipAsset(clip_asset, asset, data, symbol);
AssetDatabase.ImportAsset(AssetDatabase.GetAssetPath(clip_asset));
} else {
var asset_path = AssetDatabase.GetAssetPath(asset);
var clip_asset_path = Path.ChangeExtension(asset_path, symbol.Name + ".asset");
SwfEditorUtils.LoadOrCreateAsset<SwfClipAsset>(clip_asset_path, new_clip_asset => {
ConfigureClipAsset(new_clip_asset, asset, data, symbol);
asset.Clips.Add(new_clip_asset);
});
}
}
static void ConfigureClip(SwfAsset asset, SwfSymbolData symbol) {
var asset_path = AssetDatabase.GetAssetPath(asset);
var clip_asset_path = Path.ChangeExtension(asset_path, symbol.Name + ".asset");
var clip_asset = SwfEditorUtils.LoadOrCreateAsset<SwfClipAsset>(clip_asset_path);
static void ConfigureClipAsset(
SwfClipAsset clip_asset, SwfAsset asset, SwfAssetData data, SwfSymbolData symbol)
{
clip_asset.Name = symbol.Name;
clip_asset.Atlas = asset.Atlas;
clip_asset.Container = AssetDatabase.AssetPathToGUID(asset_path);
clip_asset.FrameRate = asset.Data.FrameRate;
clip_asset.Sequences = LoadClipSequences(asset, symbol);
EditorUtility.SetDirty(clip_asset);
asset.Clips.Add(clip_asset);
clip_asset.FrameRate = data.FrameRate;
clip_asset.Sequences = LoadClipSequences(asset, data, symbol);
}
static List<SwfClipAsset.Sequence> LoadClipSequences(
SwfAsset asset, SwfSymbolData symbol)
SwfAsset asset, SwfAssetData data, SwfSymbolData symbol)
{
var sequences = new List<SwfClipAsset.Sequence>();
if ( IsValidAssetsForFrame(asset, symbol) ) {
foreach ( var frame in symbol.Frames ) {
var baked_frame = BakeClipFrame(asset, frame);
var baked_frame = BakeClipFrame(asset, data, frame);
if ( !string.IsNullOrEmpty(frame.Name) &&
(sequences.Count < 1 || sequences.Last().Name != frame.Name) )
{
@@ -192,7 +321,7 @@ namespace FlashTools.Internal {
}
static SwfClipAsset.Frame BakeClipFrame(
SwfAsset asset, SwfFrameData frame)
SwfAsset asset, SwfAssetData data, SwfFrameData frame)
{
List<uint> baked_uvs = new List<uint>();
List<uint> baked_mulcolors = new List<uint>();
@@ -203,11 +332,11 @@ namespace FlashTools.Internal {
foreach ( var inst in frame.Instances ) {
var bitmap = inst != null
? FindBitmapFromAssetData(asset.Data, inst.Bitmap)
? FindBitmapFromAssetData(data, inst.Bitmap)
: null;
if ( bitmap != null && IsVisibleInstance(inst) ) {
var width = bitmap.RealSize.x / 20.0f;
var height = bitmap.RealSize.y / 20.0f;
var width = bitmap.RealWidth / 20.0f;
var height = bitmap.RealHeight / 20.0f;
var v0 = new Vector2( 0, 0);
var v1 = new Vector2(width, 0);
@@ -231,14 +360,14 @@ namespace FlashTools.Internal {
uint mul_pack0, mul_pack1;
SwfUtils.PackFColorToUInts(
inst.ColorTrans.Mul,
inst.ColorTrans.mulColor,
out mul_pack0, out mul_pack1);
baked_mulcolors.Add(mul_pack0);
baked_mulcolors.Add(mul_pack1);
uint add_pack0, add_pack1;
SwfUtils.PackFColorToUInts(
inst.ColorTrans.Add,
inst.ColorTrans.addColor,
out add_pack0, out add_pack1);
baked_addcolors.Add(add_pack0);
baked_addcolors.Add(add_pack1);
@@ -323,12 +452,12 @@ namespace FlashTools.Internal {
// ---------------------------------------------------------------------
//
// ConfigureAssetClips
// UpdateAssetClips
//
// ---------------------------------------------------------------------
static void ConfigureAssetClips(SwfAsset asset) {
var clips = GameObject.FindObjectsOfType<SwfClip>();
static void UpdateAssetClips(SwfAsset asset) {
var clips = Resources.FindObjectsOfTypeAll<SwfClip>();
foreach ( var clip in clips ) {
if ( clip && clip.clip && asset.Clips.Contains(clip.clip) ) {
clip.UpdateAllProperties();

View File

@@ -26,42 +26,38 @@ namespace FlashTools.Internal {
static void SwfFileProcess(string swf_path) {
var swf_asset_path = Path.ChangeExtension(swf_path, ".asset");
var swf_asset = SwfEditorUtils.LoadOrCreateAsset<SwfAsset>(swf_asset_path);
if ( LoadSwfAsset(swf_path, swf_asset) ) {
EditorUtility.SetDirty(swf_asset);
AssetDatabase.SaveAssets();
} else {
SwfEditorUtils.DeleteAssetWithDepends(swf_asset);
}
SwfEditorUtils.LoadOrCreateAsset<SwfAsset>(swf_asset_path, swf_asset => {
SafeLoadSwfAsset(swf_path, swf_asset);
});
}
static bool LoadSwfAsset(string swf_path, SwfAsset swf_asset) {
static void SafeLoadSwfAsset(string swf_path, SwfAsset swf_asset) {
try {
if ( swf_asset.Atlas ) {
AssetDatabase.DeleteAsset(
AssetDatabase.GetAssetPath(swf_asset.Atlas));
swf_asset.Atlas = null;
}
swf_asset.Data = LoadSwfAssetData(
swf_asset,
new SwfDecoder(swf_path));
return true;
var new_data = LoadSwfAssetData(swf_path);
swf_asset.Data = SwfEditorUtils.CompressAsset(new_data);
swf_asset.Converting = new SwfAsset.ConvertingState();
} catch ( Exception e ) {
Debug.LogErrorFormat("Parsing swf error: {0}", e.Message);
return false;
Debug.LogErrorFormat(
"<b>[FlashTools]</b> Parsing swf error: {0}",
e.Message);
}
}
static SwfAssetData LoadSwfAssetData(
SwfAsset swf_asset, SwfDecoder swf_decoder)
{
static SwfAssetData LoadSwfAssetData(string swf_path) {
var library = new SwfLibrary();
var decoder = new SwfDecoder(swf_path);
return new SwfAssetData{
FrameRate = swf_decoder.UncompressedHeader.FrameRate,
Symbols = LoadSymbols(library, swf_decoder),
Bitmaps = LoadBitmaps(library, swf_asset)};
FrameRate = decoder.UncompressedHeader.FrameRate,
Symbols = LoadSymbols(library, decoder),
Bitmaps = LoadBitmaps(library)};
}
// ---------------------------------------------------------------------
//
// LoadSymbols
//
// ---------------------------------------------------------------------
static List<SwfSymbolData> LoadSymbols(
SwfLibrary library, SwfDecoder decoder)
{
@@ -176,7 +172,7 @@ namespace FlashTools.Internal {
break;
default:
throw new UnityException(string.Format(
"Unsupported SwfDisplayInstanceType: {0}", inst.Type));
"unsupported SwfDisplayInstanceType: {0}", inst.Type));
}
}
CheckSelfMasks(self_masks, ushort.MaxValue, frame);
@@ -199,105 +195,23 @@ namespace FlashTools.Internal {
masks.RemoveAll(p => p.ClipDepth < depth);
}
static List<SwfBitmapData> LoadBitmaps(
SwfLibrary library, SwfAsset asset)
{
var bitmap_defines = library.Defines
// ---------------------------------------------------------------------
//
// LoadBitmaps
//
// ---------------------------------------------------------------------
static List<SwfBitmapData> LoadBitmaps(SwfLibrary library) {
return library.Defines
.Where (p => p.Value.Type == SwfLibraryDefineType.Bitmap)
.ToDictionary(p => p.Key, p => p.Value as SwfLibraryBitmapDefine);
var textures = bitmap_defines
.Where (p => p.Value.Redirect == 0)
.Select (p => new KeyValuePair<int, Texture2D>(
p.Key, LoadTextureFromBitmapDefine(p.Value)))
.ToDictionary(p => p.Key, p => p.Value as SwfLibraryBitmapDefine)
.Select (p => new SwfBitmapData{
Id = p.Key,
ARGB32 = p.Value.ARGB32,
Redirect = p.Value.Redirect,
RealWidth = p.Value.Width,
RealHeight = p.Value.Height})
.ToList();
var rects = PackAndSaveBitmapsAtlas(asset, textures.Select(p => p.Value).ToArray());
var bitmaps = new List<SwfBitmapData>(bitmap_defines.Count);
foreach ( var bitmap_define in bitmap_defines ) {
var texture_key = bitmap_define.Value.Redirect > 0
? bitmap_define.Value.Redirect
: bitmap_define.Key;
var bitmap_data = new SwfBitmapData{
Id = bitmap_define.Key,
RealSize = new Vector2(bitmap_define.Value.Width, bitmap_define.Value.Height),
SourceRect = rects[textures.FindIndex(p => p.Key == texture_key)]};
bitmaps.Add(bitmap_data);
}
return bitmaps;
}
static Texture2D LoadTextureFromBitmapDefine(SwfLibraryBitmapDefine bitmap) {
var texture = new Texture2D(
bitmap.Width, bitmap.Height,
TextureFormat.ARGB32, false);
texture.LoadRawTextureData(bitmap.ARGB32);
RevertTexturePremultipliedAlpha(texture);
return texture;
}
static void RevertTexturePremultipliedAlpha(Texture2D texture) {
for ( int y = 0; y < texture.height; ++y ) {
for ( int x = 0; x < texture.width; ++x ) {
var c = texture.GetPixel(x, y);
if ( c.a > 0 ) {
c.r /= c.a;
c.g /= c.a;
c.b /= c.a;
}
texture.SetPixel(x, y, c);
}
}
texture.Apply();
}
struct BitmapsAtlasInfo {
public Texture2D Atlas;
public Rect[] Rects;
}
static Rect[] PackAndSaveBitmapsAtlas(SwfAsset asset, Texture2D[] textures) {
var atlas_info = PackBitmapsAtlas(textures, asset.Settings);
var atlas_path = SwfEditorUtils.GetAtlasPathFromAsset(asset);
File.WriteAllBytes(atlas_path, atlas_info.Atlas.EncodeToPNG());
GameObject.DestroyImmediate(atlas_info.Atlas, true);
AssetDatabase.ImportAsset(atlas_path);
return atlas_info.Rects;
}
static BitmapsAtlasInfo PackBitmapsAtlas(Texture2D[] textures, SwfSettingsData settings) {
var atlas_padding = Mathf.Max(0, settings.AtlasPadding);
var max_atlas_size = Mathf.Max(32, settings.AtlasPowerOfTwo
? Mathf.ClosestPowerOfTwo(settings.MaxAtlasSize)
: settings.MaxAtlasSize);
var atlas = new Texture2D(0, 0);
var rects = atlas.PackTextures(textures, atlas_padding, max_atlas_size);
if ( rects == null ) {
throw new UnityException("Pack textures to atlas error");
}
return settings.AtlasForceSquare && atlas.width != atlas.height
? BitmapsAtlasToSquare(atlas, rects)
: new BitmapsAtlasInfo{Atlas = atlas, Rects = rects};
}
static BitmapsAtlasInfo BitmapsAtlasToSquare(Texture2D atlas, Rect[] rects) {
var atlas_size = Mathf.Max(atlas.width, atlas.height);
var atlas_scale = new Vector2(atlas.width, atlas.height) / atlas_size;
var new_atlas = new Texture2D(atlas_size, atlas_size, TextureFormat.ARGB32, false);
for ( var i = 0; i < rects.Length; ++i ) {
var new_position = rects[i].position;
new_position.Scale(atlas_scale);
var new_size = rects[i].size;
new_size.Scale(atlas_scale);
rects[i] = new Rect(new_position, new_size);
}
var fill_pixels = new Color32[atlas_size * atlas_size];
for ( var i = 0; i < atlas_size * atlas_size; ++i ) {
fill_pixels[i] = new Color(1,1,1,0);
}
new_atlas.SetPixels32(fill_pixels);
new_atlas.SetPixels32(0, 0, atlas.width, atlas.height, atlas.GetPixels32());
new_atlas.Apply();
GameObject.DestroyImmediate(atlas, true);
return new BitmapsAtlasInfo{Atlas = new_atlas, Rects = rects};
}
}
}

View File

@@ -2,10 +2,21 @@
using UnityEditor;
using System.IO;
using System.Linq;
using System.Collections.Generic;
using System.Runtime.Serialization.Formatters.Binary;
using Ionic.Zlib;
namespace FlashTools.Internal {
public static class SwfEditorUtils {
// ---------------------------------------------------------------------
//
// Functions
//
// ---------------------------------------------------------------------
public static void DoWithMixedValue(bool mixed, System.Action act) {
var last_show_mixed_value = EditorGUI.showMixedValue;
EditorGUI.showMixedValue = mixed;
@@ -17,12 +28,41 @@ namespace FlashTools.Internal {
}
public static void DoWithEnabledGUI(bool enabled, System.Action act) {
var last_gui_enabled = GUI.enabled;
GUI.enabled = enabled;
EditorGUI.BeginDisabledGroup(true);
try {
act();
} finally {
GUI.enabled = last_gui_enabled;
EditorGUI.EndDisabledGroup();
}
}
public static void DoHorizontalGUI(System.Action act) {
GUILayout.BeginHorizontal();
try {
act();
} finally {
GUILayout.EndHorizontal();
}
}
public static void DoRightHorizontalGUI(System.Action act) {
GUILayout.BeginHorizontal();
GUILayout.FlexibleSpace();
try {
act();
} finally {
GUILayout.EndHorizontal();
}
}
public static void DoCenterHorizontalGUI(System.Action act) {
GUILayout.BeginHorizontal();
GUILayout.FlexibleSpace();
try {
act();
} finally {
GUILayout.FlexibleSpace();
GUILayout.EndHorizontal();
}
}
@@ -36,17 +76,6 @@ namespace FlashTools.Internal {
return prop;
}
public static void DeleteAssetWithDepends(SwfAsset asset) {
if ( asset ) {
if ( asset.Atlas ) {
AssetDatabase.DeleteAsset(
AssetDatabase.GetAssetPath(asset.Atlas));
}
AssetDatabase.DeleteAsset(
AssetDatabase.GetAssetPath(asset));
}
}
public static void RemoveAllSubAssets(string asset_path) {
var assets = AssetDatabase.LoadAllAssetsAtPath(asset_path);
foreach ( var asset in assets ) {
@@ -56,18 +85,76 @@ namespace FlashTools.Internal {
}
}
public static T LoadOrCreateAsset<T>(string asset_path) where T : ScriptableObject {
public static T LoadOrCreateAsset<T>(string asset_path, System.Action<T> act) where T : ScriptableObject {
var asset = AssetDatabase.LoadAssetAtPath<T>(asset_path);
if ( !asset ) {
if ( asset ) {
act(asset);
} else {
asset = ScriptableObject.CreateInstance<T>();
act(asset);
AssetDatabase.CreateAsset(asset, asset_path);
}
AssetDatabase.ImportAsset(asset_path);
return asset;
}
public static string GetAtlasPathFromAsset(SwfAsset asset) {
var asset_path = AssetDatabase.GetAssetPath(asset);
return Path.ChangeExtension(asset_path, "._Atlas_.png");
public static byte[] CompressAsset<T>(T asset) {
var bytes = AssetToBytes(asset);
var result = ZlibStream.CompressBuffer(bytes);
return result;
}
public static T DecompressAsset<T>(byte[] data) {
var bytes = ZlibStream.UncompressBuffer(data);
var result = BytesToAsset<T>(bytes);
return result;
}
static byte[] AssetToBytes<T>(T asset) {
var formatter = new BinaryFormatter();
using ( var stream = new MemoryStream() ) {
formatter.Serialize(stream, asset);
return stream.ToArray();
}
}
static T BytesToAsset<T>(byte[] bytes) {
var formatter = new BinaryFormatter();
using ( var stream = new MemoryStream(bytes) ) {
return (T)formatter.Deserialize(stream);
}
}
// ---------------------------------------------------------------------
//
// Internal
//
// ---------------------------------------------------------------------
[MenuItem("Tools/FlashTools/Open settings...")]
static void Tools_FlashTools_OpenSettings() {
var settings_holder = SwfSettings.GetHolder();
Selection.objects = new Object[]{settings_holder};
}
[MenuItem("Tools/FlashTools/Reimport all swf files")]
static void Tools_FlashTools_ReimportAllSwfFiles() {
var swf_paths = GetAllSwfFilePaths();
var title = "Reimport";
var message = string.Format(
"Do you really want to reimport all ({0}) swf files?",
swf_paths.Length);
if ( EditorUtility.DisplayDialog(title, message, "Ok", "Cancel") ) {
foreach ( var swf_path in swf_paths ) {
AssetDatabase.ImportAsset(swf_path);
}
}
}
static string[] GetAllSwfFilePaths() {
return AssetDatabase.GetAllAssetPaths()
.Where(p => Path.GetExtension(p).ToLower().Equals(".swf"))
.ToArray();
}
}
}

View File

@@ -4,7 +4,7 @@ using UnityEditor;
using System.Linq;
using System.Collections.Generic;
namespace FlashTools.Internal.SwfEditorTools {
namespace FlashTools.Internal {
//
// SwfIntRange
@@ -271,4 +271,23 @@ namespace FlashTools.Internal.SwfEditorTools {
}
}
}
//
// SwfDisplayNameDrawer
//
[CustomPropertyDrawer(typeof(SwfDisplayNameAttribute))]
public class SwfDisplayNameDrawer : PropertyDrawer {
public override void OnGUI(
Rect position, SerializedProperty property, GUIContent label)
{
var new_label = new GUIContent(label);
new_label.text = (attribute as SwfDisplayNameAttribute).DisplayName;
if ( EditorGUI.PropertyField(position, property, new_label) ) {
foreach ( SerializedProperty child in property ) {
EditorGUILayout.PropertyField(child);
}
}
}
}
}

View File

@@ -364,7 +364,9 @@ namespace FlashTools.Internal.SwfTools {
void TagToDebugLog(SwfTagBase tag) {
if ( tag is UnsupportedTag || tag is UnknownTag ) {
Debug.LogWarningFormat("SwfContextExecuter. {0}", tag);
Debug.LogWarningFormat(
"<b>[FlashTools]</b> SwfContextExecuter. {0}",
tag);
}
}
}

View File

@@ -62,14 +62,14 @@ namespace FlashTools.Internal.SwfTools.SwfTypes {
public SwfColorTransData ToColorTransData() {
var trans = SwfColorTransData.identity;
if ( HasAdd ) {
trans.Add = new Vector4(
trans.addColor = new SwfVec4Data(
RAdd / 256.0f,
GAdd / 256.0f,
BAdd / 256.0f,
AAdd / 256.0f);
}
if ( HasMul ) {
trans.Mul = new Vector4(
trans.mulColor = new SwfVec4Data(
RMul / 256.0f,
GMul / 256.0f,
BMul / 256.0f,

View File

@@ -114,7 +114,7 @@ namespace FlashTools.Internal.SwfTools.SwfTypes {
fill_style.BitmapMatrix = SwfMatrix.Read(reader, true);
} else {
Debug.LogError(
"imported .swf file contains vector graphics. " +
"<b>[FlashTools]</b> Imported .swf file contains vector graphics. " +
"You should use Tools/FlashExport.jsfl script for prepare .fla file");
}
return fill_style;

View File

@@ -9,12 +9,6 @@ namespace FlashTools.Internal.Tests {
Assert.AreEqual(v0.y, v1.y, delta);
}
static void AssertAreEqualVectors(Vector3 v0, Vector3 v1, float delta) {
Assert.AreEqual(v0.x, v1.x, delta);
Assert.AreEqual(v0.y, v1.y, delta);
Assert.AreEqual(v0.z, v1.z, delta);
}
static void AssertAreEqualVectors(Vector4 v0, Vector4 v1, float delta) {
Assert.AreEqual(v0.x, v1.x, delta);
Assert.AreEqual(v0.y, v1.y, delta);
@@ -26,23 +20,6 @@ namespace FlashTools.Internal.Tests {
//
//
[Test]
public static void PackBytesToUIntTests() {
byte b0 = 1, b1 = 10, b2 = 100, b3 = 255;
byte bb0, bb1, bb2, bb3;
SwfUtils.UnpackBytesFromUInt(
SwfUtils.PackBytesToUInt(b0, b1, b2, b3),
out bb0, out bb1, out bb2, out bb3);
Assert.AreEqual(b0, bb0);
Assert.AreEqual(b1, bb1);
Assert.AreEqual(b2, bb2);
Assert.AreEqual(b3, bb3);
}
//
//
//
[Test]
public static void PackUShortsToUIntTests() {
ushort v0 = 11, v1 = 99;
@@ -64,17 +41,17 @@ namespace FlashTools.Internal.Tests {
public static void PackUVTests() {
var v0 = new Vector2(0.9999f, 0.1111f);
float u0, u1;
SwfUtils.UnpackUV(SwfUtils.PackUV(v0), out u0, out u1);
SwfUtils.UnpackUV(SwfUtils.PackUV(v0.x, v0.y), out u0, out u1);
AssertAreEqualVectors(v0, new Vector2(u0, u1), SwfUtils.UVPrecision);
var v1 = new Vector2(0.0987f, 0.0123f);
float u2, u3;
SwfUtils.UnpackUV(SwfUtils.PackUV(v1), out u2, out u3);
SwfUtils.UnpackUV(SwfUtils.PackUV(v1.x, v1.y), out u2, out u3);
AssertAreEqualVectors(v1, new Vector2(u2, u3), SwfUtils.UVPrecision);
var v2 = new Vector2(1.0f, 0.0f);
float u4, u5;
SwfUtils.UnpackUV(SwfUtils.PackUV(v2), out u4, out u5);
SwfUtils.UnpackUV(SwfUtils.PackUV(v2.x, v2.y), out u4, out u5);
AssertAreEqualVectors(v2, new Vector2(u4, u5), SwfUtils.UVPrecision);
}

View File

@@ -42,4 +42,11 @@ namespace FlashTools.Internal {
ReadOnly = read_only;
}
}
public class SwfDisplayNameAttribute : PropertyAttribute {
public string DisplayName;
public SwfDisplayNameAttribute(string display_name) {
DisplayName = display_name;
}
}
}

View File

@@ -73,7 +73,7 @@ namespace FlashTools.Internal {
// ---------------------------------------------------------------------
//
// Private
// Internal
//
// ---------------------------------------------------------------------

View File

@@ -13,30 +13,6 @@ namespace FlashTools.Internal {
//
//
public static uint PackBytesToUInt(
byte b0, byte b1, byte b2, byte b3)
{
var bb0 = (uint)b0;
var bb1 = (uint)b1;
var bb2 = (uint)b2;
var bb3 = (uint)b3;
return (bb0 << 24) + (bb1 << 16) + (bb2 << 8) + bb3;
}
public static void UnpackBytesFromUInt(
uint pack,
out byte b0, out byte b1, out byte b2, out byte b3)
{
b0 = (byte)((pack >> 24) & 0xFF);
b1 = (byte)((pack >> 16) & 0xFF);
b2 = (byte)((pack >> 8) & 0xFF);
b3 = (byte)((pack ) & 0xFF);
}
//
//
//
public static uint PackUShortsToUInt(ushort x, ushort y) {
var xx = (uint)x;
var yy = (uint)y;
@@ -54,9 +30,6 @@ namespace FlashTools.Internal {
//
//
//
public static uint PackUV(Vector2 uv) {
return PackUV(uv.x, uv.y);
}
public static uint PackUV(float u, float v) {
var uu = (uint)(Mathf.Clamp01(u) * UShortMax);
@@ -96,7 +69,7 @@ namespace FlashTools.Internal {
}
public static void PackFColorToUInts(
Vector4 v,
SwfVec4Data v,
out uint pack0, out uint pack1)
{
PackFColorToUInts(v.x, v.y, v.z, v.w, out pack0, out pack1);

View File

@@ -3,58 +3,126 @@ using FlashTools.Internal;
using System.Collections.Generic;
namespace FlashTools {
[System.Serializable]
public struct SwfVec2Data {
public float x;
public float y;
public SwfVec2Data(float x, float y) {
this.x = x;
this.y = y;
}
public static SwfVec2Data one {
get { return new SwfVec2Data(1.0f, 1.0f); }
}
public static SwfVec2Data zero {
get { return new SwfVec2Data(0.0f, 0.0f); }
}
}
[System.Serializable]
public struct SwfVec4Data {
public float x;
public float y;
public float z;
public float w;
public SwfVec4Data(float x, float y, float z, float w) {
this.x = x;
this.y = y;
this.z = z;
this.w = w;
}
public static SwfVec4Data one {
get { return new SwfVec4Data(1.0f, 1.0f, 1.0f, 1.0f); }
}
public static SwfVec4Data zero {
get { return new SwfVec4Data(0.0f, 0.0f, 0.0f, 0.0f); }
}
}
[System.Serializable]
public struct SwfRectData {
public float xMin;
public float xMax;
public float yMin;
public float yMax;
public static SwfRectData identity {
get {
return new SwfRectData{
xMin = 0.0f,
xMax = 0.0f,
yMin = 0.0f,
yMax = 0.0f};
}
}
public static SwfRectData FromURect(Rect rect) {
return new SwfRectData{
xMin = rect.xMin,
xMax = rect.xMax,
yMin = rect.yMin,
yMax = rect.yMax};
}
}
[System.Serializable]
public struct SwfMatrixData {
public Vector2 Sc;
public Vector2 Sk;
public Vector2 Tr;
public SwfVec2Data sc;
public SwfVec2Data sk;
public SwfVec2Data tr;
public static SwfMatrixData identity {
get {
return new SwfMatrixData{
Sc = Vector2.one,
Sk = Vector2.zero,
Tr = Vector2.zero};
sc = SwfVec2Data.one,
sk = SwfVec2Data.zero,
tr = SwfVec2Data.zero};
}
}
public Matrix4x4 ToUMatrix() {
var mat = Matrix4x4.identity;
mat.m00 = Sc.x;
mat.m11 = Sc.y;
mat.m10 = Sk.x;
mat.m01 = Sk.y;
mat.m03 = Tr.x;
mat.m13 = Tr.y;
mat.m00 = sc.x;
mat.m11 = sc.y;
mat.m10 = sk.x;
mat.m01 = sk.y;
mat.m03 = tr.x;
mat.m13 = tr.y;
return mat;
}
public static SwfMatrixData FromUMatrix(Matrix4x4 mat) {
return new SwfMatrixData{
Sc = new Vector2(mat.m00, mat.m11),
Sk = new Vector2(mat.m10, mat.m01),
Tr = new Vector2(mat.m03, mat.m13)};
sc = new SwfVec2Data(mat.m00, mat.m11),
sk = new SwfVec2Data(mat.m10, mat.m01),
tr = new SwfVec2Data(mat.m03, mat.m13)};
}
}
[System.Serializable]
public struct SwfColorTransData {
public Vector4 Mul;
public Vector4 Add;
public SwfVec4Data mulColor;
public SwfVec4Data addColor;
public Color ApplyToColor(Color color) {
return new Color(
Mathf.Clamp01(color.r * Mul.x + Add.x),
Mathf.Clamp01(color.g * Mul.y + Add.y),
Mathf.Clamp01(color.b * Mul.z + Add.z),
Mathf.Clamp01(color.a * Mul.w + Add.w));
Mathf.Clamp01(color.r * mulColor.x + addColor.x),
Mathf.Clamp01(color.g * mulColor.y + addColor.y),
Mathf.Clamp01(color.b * mulColor.z + addColor.z),
Mathf.Clamp01(color.a * mulColor.w + addColor.w));
}
public static SwfColorTransData identity {
get {
return new SwfColorTransData{
Mul = Vector4.one,
Add = Vector4.zero};
mulColor = SwfVec4Data.one,
addColor = SwfVec4Data.zero};
}
}
@@ -62,16 +130,16 @@ namespace FlashTools {
SwfColorTransData a, SwfColorTransData b)
{
return new SwfColorTransData{
Mul = new Vector4(
b.Mul.x * a.Mul.x,
b.Mul.y * a.Mul.y,
b.Mul.z * a.Mul.z,
b.Mul.w * a.Mul.w),
Add = new Vector4(
b.Add.x * a.Mul.x + a.Add.x,
b.Add.y * a.Mul.y + a.Add.y,
b.Add.z * a.Mul.z + a.Add.z,
b.Add.w * a.Mul.w + a.Add.w)};
mulColor = new SwfVec4Data(
b.mulColor.x * a.mulColor.x,
b.mulColor.y * a.mulColor.y,
b.mulColor.z * a.mulColor.z,
b.mulColor.w * a.mulColor.w),
addColor = new SwfVec4Data(
b.addColor.x * a.mulColor.x + a.addColor.x,
b.addColor.y * a.mulColor.y + a.addColor.y,
b.addColor.z * a.mulColor.z + a.addColor.z,
b.addColor.w * a.mulColor.w + a.addColor.w)};
}
}
@@ -104,9 +172,12 @@ namespace FlashTools {
[System.Serializable]
public class SwfBitmapData {
public int Id = 0;
public Vector2 RealSize = Vector2.zero;
public Rect SourceRect = new Rect();
public ushort Id = 0;
public byte[] ARGB32 = new byte[0];
public ushort Redirect = 0;
public int RealWidth = 0;
public int RealHeight = 0;
public SwfRectData SourceRect = SwfRectData.identity;
}
[System.Serializable]
@@ -117,24 +188,31 @@ namespace FlashTools {
}
public class SwfAsset : ScriptableObject {
[System.Serializable]
public struct ConvertingState {
public int Stage;
}
[HideInInspector]
public SwfAssetData Data;
public byte[] Data;
[SwfReadOnly]
public Texture2D Atlas;
[HideInInspector]
public List<SwfClipAsset> Clips;
[HideInInspector]
public SwfSettingsData Settings;
[HideInInspector]
[SwfDisplayName("Settings")]
public SwfSettingsData Overridden;
[HideInInspector]
public ConvertingState Converting;
#if UNITY_EDITOR
void Reset() {
Data = new SwfAssetData();
Data = new byte[0];
Atlas = null;
Clips = new List<SwfClipAsset>();
Settings = SwfSettings.GetDefault();
Overridden = SwfSettings.GetDefault();
Converting = new ConvertingState();
}
#endif
}

View File

@@ -25,7 +25,7 @@ namespace FlashTools {
[Header("Sorting")]
[SerializeField][SwfSortingLayer]
public string _sortingLayer = "Default";
public string _sortingLayer = string.Empty;
public string sortingLayer {
get { return _sortingLayer; }
set {
@@ -45,22 +45,35 @@ namespace FlashTools {
}
[Header("Animation")]
[SerializeField]
Color _tint = Color.white;
public Color tint {
get { return _tint; }
set {
_tint = value;
ChangeTint();
}
}
[SerializeField]
SwfClipAsset _clip = null;
public SwfClipAsset clip {
get { return _clip; }
set {
_clip = value;
_clip = value;
_sequence = string.Empty;
_currentFrame = 0;
ChangeClip();
}
}
[SerializeField][HideInInspector]
string _sequence = "Default";
string _sequence = string.Empty;
public string sequence {
get { return _sequence; }
set {
_sequence = value;
_sequence = value;
_currentFrame = 0;
ChangeSequence();
}
}
@@ -85,7 +98,9 @@ namespace FlashTools {
public float frameRate {
get {
return clip ? clip.FrameRate : 1.0f;
return clip
? clip.FrameRate
: 1.0f;
}
}
@@ -100,7 +115,9 @@ namespace FlashTools {
}
public void ToEndFrame() {
currentFrame = frameCount - 1;
currentFrame = frameCount > 0
? frameCount - 1
: 0;
}
public bool ToPrevFrame() {
@@ -129,10 +146,10 @@ namespace FlashTools {
if ( _meshFilter && _meshRenderer && _dirtyMesh ) {
var baked_frame = GetCurrentBakedFrame();
if ( baked_frame != null ) {
_meshFilter.sharedMesh = baked_frame.CachedMesh;
_meshFilter .sharedMesh = baked_frame.CachedMesh;
_meshRenderer.sharedMaterials = baked_frame.Materials;
} else {
_meshFilter.sharedMesh = null;
_meshFilter .sharedMesh = null;
_meshRenderer.sharedMaterials = new Material[0];
}
}
@@ -140,11 +157,11 @@ namespace FlashTools {
public void UpdateAllProperties() {
ClearCache();
clip = _clip;
sequence = _sequence;
currentFrame = _currentFrame;
sortingLayer = _sortingLayer;
sortingOrder = _sortingOrder;
ChangeTint();
ChangeClip();
ChangeSequence();
ChangeCurrentFrame();
ChangeSortingProperties();
}
void ClearCache() {
@@ -155,11 +172,8 @@ namespace FlashTools {
_curPropBlock = null;
}
void ChangeSortingProperties() {
if ( _meshRenderer ) {
_meshRenderer.sortingOrder = sortingOrder;
_meshRenderer.sortingLayerName = sortingLayer;
}
void ChangeTint() {
UpdatePropBlock();
}
void ChangeClip() {
@@ -173,11 +187,18 @@ namespace FlashTools {
void ChangeSequence() {
_curSequence = null;
if ( clip && clip.Sequences != null ) {
for ( int i = 0, e = clip.Sequences.Count; i < e; ++i ) {
var clip_sequence = clip.Sequences[i];
if ( clip_sequence != null && clip_sequence.Name == sequence ) {
_curSequence = clip_sequence;
break;
if ( !string.IsNullOrEmpty(sequence) ) {
for ( int i = 0, e = clip.Sequences.Count; i < e; ++i ) {
var clip_sequence = clip.Sequences[i];
if ( clip_sequence != null && clip_sequence.Name == sequence ) {
_curSequence = clip_sequence;
break;
}
}
if ( _curSequence == null ) {
Debug.LogWarningFormat(this,
"<b>[FlashTools]</b> Sequence '{0}' not found",
sequence);
}
}
if ( _curSequence == null ) {
@@ -201,12 +222,22 @@ namespace FlashTools {
SetDirtyCurrentMesh();
}
void ChangeSortingProperties() {
if ( _meshRenderer ) {
_meshRenderer.sortingOrder = sortingOrder;
_meshRenderer.sortingLayerName = sortingLayer;
}
}
void UpdatePropBlock() {
if ( _meshRenderer ) {
if ( _curPropBlock == null ) {
_curPropBlock = new MaterialPropertyBlock();
}
_meshRenderer.GetPropertyBlock(_curPropBlock);
_curPropBlock.SetColor(
"_Color",
tint);
_curPropBlock.SetTexture(
"_MainTex",
clip && clip.Atlas ? clip.Atlas : Texture2D.whiteTexture);
@@ -241,14 +272,14 @@ namespace FlashTools {
void OnEnable() {
var swf_manager = SwfManager.GetInstance(true);
if ( swf_manager ) {
swf_manager.AddSwfClip(this);
swf_manager.AddClip(this);
}
}
void OnDisable() {
var swf_manager = SwfManager.GetInstance(false);
if ( swf_manager ) {
swf_manager.RemoveSwfClip(this);
swf_manager.RemoveClip(this);
}
}

View File

@@ -70,16 +70,17 @@ namespace FlashTools {
}
}
}
[System.Serializable]
public class Sequence {
public string Name = string.Empty;
public List<Frame> Frames = new List<Frame>();
}
[SwfReadOnly]
public string Name;
[SwfReadOnly]
public Texture2D Atlas;
[SwfAssetGUID(true)]
public string Container;
[SwfReadOnly]
public float FrameRate;
[HideInInspector]
@@ -87,8 +88,8 @@ namespace FlashTools {
#if UNITY_EDITOR
void Reset() {
Name = string.Empty;
Atlas = null;
Container = string.Empty;
FrameRate = 1.0f;
Sequences = new List<Sequence>();
}

View File

@@ -51,6 +51,13 @@ namespace FlashTools {
set { _rateScale = Mathf.Clamp(value, 0.0f, float.MaxValue); }
}
[SerializeField]
string _groupName = string.Empty;
public string groupName {
get { return _groupName; }
set { _groupName = value; }
}
[SerializeField]
PlayModes _playMode = PlayModes.Forward;
public PlayModes playMode {
@@ -65,12 +72,16 @@ namespace FlashTools {
set { _loopMode = value; }
}
public SwfClip clip {
get { return _clip; }
}
public bool isPlaying {
get { return _isPlaying; }
}
public bool isStopped {
get { return !_isPlaying; }
get { return !isPlaying; }
}
// ---------------------------------------------------------------------
@@ -80,47 +91,101 @@ namespace FlashTools {
// ---------------------------------------------------------------------
public void GotoAndStop(int frame) {
if ( _clip ) {
_clip.currentFrame = frame;
if ( clip ) {
clip.currentFrame = frame;
}
Stop();
Stop(false);
}
public void GotoAndStop(string sequence, int frame) {
if ( clip ) {
clip.sequence = sequence;
}
GotoAndStop(frame);
}
//
//
//
public void GotoAndPlay(int frame) {
if ( _clip ) {
_clip.currentFrame = frame;
if ( clip ) {
clip.currentFrame = frame;
}
Play();
Play(false);
}
public void Stop() {
public void GotoAndPlay(string sequence, int frame) {
if ( clip ) {
clip.sequence = sequence;
}
GotoAndPlay(frame);
}
//
//
//
public void Stop(bool rewind) {
var is_playing = isPlaying;
_isPlaying = false;
_tickTimer = 0.0f;
if ( is_playing ) {
_isPlaying = false;
_tickTimer = 0.0f;
}
if ( rewind ) {
Rewind();
}
if ( is_playing && OnStopPlayingEvent != null ) {
OnStopPlayingEvent(this);
}
}
public void Play() {
public void Stop(string sequence) {
if ( clip ) {
clip.sequence = sequence;
}
Stop(true);
}
//
//
//
public void Play(bool rewind) {
var is_stopped = isStopped;
_isPlaying = true;
_tickTimer = 0.0f;
if ( is_stopped ) {
_isPlaying = true;
_tickTimer = 0.0f;
}
if ( rewind ) {
Rewind();
}
if ( is_stopped && OnPlayStoppedEvent != null ) {
OnPlayStoppedEvent(this);
}
}
public void Play(string sequence) {
if ( clip ) {
clip.sequence = sequence;
}
Play(true);
}
//
//
//
public void Rewind() {
switch ( playMode ) {
case PlayModes.Forward:
if ( _clip ) {
_clip.ToBeginFrame();
if ( clip ) {
clip.ToBeginFrame();
}
break;
case PlayModes.Backward:
if ( _clip ) {
_clip.ToEndFrame();
if ( clip ) {
clip.ToEndFrame();
}
break;
default:
@@ -146,7 +211,7 @@ namespace FlashTools {
}
void UpdateTimer(float dt) {
var frame_rate = _clip ? _clip.frameRate : 1.0f;
var frame_rate = clip ? clip.frameRate : 1.0f;
_tickTimer += frame_rate * rateScale * dt;
while ( _tickTimer > 1.0f ) {
_tickTimer -= 1.0f;
@@ -158,7 +223,7 @@ namespace FlashTools {
if ( !NextClipFrame() ) {
switch ( loopMode ) {
case LoopModes.Once:
Stop();
Stop(false);
break;
case LoopModes.Loop:
Rewind();
@@ -174,9 +239,9 @@ namespace FlashTools {
bool NextClipFrame() {
switch ( playMode ) {
case PlayModes.Forward:
return _clip ? _clip.ToNextFrame() : false;
return clip ? clip.ToNextFrame() : false;
case PlayModes.Backward:
return _clip ? _clip.ToPrevFrame() : false;
return clip ? clip.ToPrevFrame() : false;
default:
throw new UnityException(string.Format(
"SwfClipController. Incorrect play mode: {0}",
@@ -193,21 +258,21 @@ namespace FlashTools {
void Awake() {
_clip = GetComponent<SwfClip>();
if ( autoPlay && Application.isPlaying ) {
Play();
Play(false);
}
}
void OnEnable() {
var swf_manager = SwfManager.GetInstance(true);
if ( swf_manager ) {
swf_manager.AddSwfClipController(this);
swf_manager.AddController(this);
}
}
void OnDisable() {
var swf_manager = SwfManager.GetInstance(false);
if ( swf_manager ) {
swf_manager.RemoveSwfClipController(this);
swf_manager.RemoveController(this);
}
}
}

View File

@@ -1,13 +1,18 @@
using UnityEngine;
using FlashTools.Internal;
using System.Collections.Generic;
namespace FlashTools {
[ExecuteInEditMode, DisallowMultipleComponent]
public class SwfManager : MonoBehaviour {
SwfAssocList<SwfClip> _clips = new SwfAssocList<SwfClip>();
SwfAssocList<SwfClipController> _controllers = new SwfAssocList<SwfClipController>();
SwfList<SwfClipController> _safeUpdates = new SwfList<SwfClipController>();
SwfAssocList<SwfClip> _clips = new SwfAssocList<SwfClip>();
SwfAssocList<SwfClipController> _controllers = new SwfAssocList<SwfClipController>();
SwfList<SwfClipController> _safeUpdates = new SwfList<SwfClipController>();
bool _isPaused = false;
float _rateScale = 1.0f;
HashSet<string> _groupPauses = new HashSet<string>();
Dictionary<string, float> _groupRateScales = new Dictionary<string, float>();
// ---------------------------------------------------------------------
//
@@ -27,46 +32,114 @@ namespace FlashTools {
return _instance;
}
// ---------------------------------------------------------------------
//
// Properties
//
// ---------------------------------------------------------------------
public int clipCount {
get { return _clips.Count; }
}
public int controllerCount {
get { return _controllers.Count; }
}
public bool isPaused {
get { return _isPaused; }
}
public bool isPlaying {
get { return !isPaused; }
}
public float rateScale {
get { return _rateScale; }
set { _rateScale = Mathf.Clamp(value, 0.0f, float.MaxValue); }
}
// ---------------------------------------------------------------------
//
// Functions
//
// ---------------------------------------------------------------------
public void Pause() {
_isPaused = true;
}
public void Resume() {
_isPaused = false;
}
public void PauseGroup(string group_name) {
if ( !string.IsNullOrEmpty(group_name) ) {
_groupPauses.Add(group_name);
}
}
public void ResumeGroup(string group_name) {
if ( !string.IsNullOrEmpty(group_name) ) {
_groupPauses.Remove(group_name);
}
}
public bool IsGroupPaused(string group_name) {
return _groupPauses.Contains(group_name);
}
public bool IsGroupPlaying(string group_name) {
return !IsGroupPaused(group_name);
}
public void SetGroupRateScale(string group_name, float rate_scale) {
if ( !string.IsNullOrEmpty(group_name) ) {
_groupRateScales[group_name] = Mathf.Clamp(rate_scale, 0.0f, float.MaxValue);
}
}
public float GetGroupRateScale(string group_name) {
float rate_scale;
return _groupRateScales.TryGetValue(group_name, out rate_scale)
? rate_scale
: 1.0f;
}
// ---------------------------------------------------------------------
//
// Internal
//
// ---------------------------------------------------------------------
public int AllClipCount {
get { return _clips.Count; }
}
public void AddSwfClip(SwfClip clip) {
public void AddClip(SwfClip clip) {
_clips.Add(clip);
}
public void RemoveSwfClip(SwfClip clip) {
public void RemoveClip(SwfClip clip) {
_clips.Remove(clip);
}
public int AllClipControllerCount {
get { return _controllers.Count; }
public void GetAllClips(SwfList<SwfClip> clips) {
_clips.AssignTo(clips);
}
public void AddSwfClipController(SwfClipController controller) {
public void AddController(SwfClipController controller) {
_controllers.Add(controller);
}
public void RemoveSwfClipController(SwfClipController controller) {
public void RemoveController(SwfClipController controller) {
_controllers.Remove(controller);
}
// ---------------------------------------------------------------------
//
// Private
//
// ---------------------------------------------------------------------
public void GetAllControllers(SwfList<SwfClipController> controllers) {
_controllers.AssignTo(controllers);
}
void GrabEnabledClips() {
var all_clips = FindObjectsOfType<SwfClip>();
for ( int i = 0, e = all_clips.Length; i < e; ++i ) {
var clip = all_clips[i];
var clips = FindObjectsOfType<SwfClip>();
for ( int i = 0, e = clips.Length; i < e; ++i ) {
var clip = clips[i];
if ( clip.enabled ) {
_clips.Add(clip);
}
@@ -74,9 +147,9 @@ namespace FlashTools {
}
void GrabEnabledControllers() {
var all_controllers = FindObjectsOfType<SwfClipController>();
for ( int i = 0, e = all_controllers.Length; i < e; ++i ) {
var controller = all_controllers[i];
var controllers = FindObjectsOfType<SwfClipController>();
for ( int i = 0, e = controllers.Length; i < e; ++i ) {
var controller = controllers[i];
if ( controller.enabled ) {
_controllers.Add(controller);
}
@@ -96,9 +169,16 @@ namespace FlashTools {
for ( int i = 0, e = _safeUpdates.Count; i < e; ++i ) {
var ctrl = _safeUpdates[i];
if ( ctrl ) {
ctrl.InternalUpdate(dt);
var group_name = ctrl.groupName;
if ( string.IsNullOrEmpty(group_name) ) {
ctrl.InternalUpdate(dt);
} else if ( !IsGroupPaused(group_name) ) {
var group_rate_scale = GetGroupRateScale(group_name);
ctrl.InternalUpdate(group_rate_scale * dt);
}
}
}
_safeUpdates.Clear();
}
void LateUpdateClips() {
@@ -127,8 +207,10 @@ namespace FlashTools {
}
void Update() {
var dt = Time.deltaTime;
UpdateControllers(dt);
if ( isPlaying ) {
var dt = Time.deltaTime;
UpdateControllers(rateScale * dt);
}
}
void LateUpdate() {

View File

@@ -1,10 +1,9 @@
<Properties StartupItem="Assembly-CSharp.csproj">
<MonoDevelop.Ide.Workspace ActiveConfiguration="Debug" PreferredExecutionTarget="Unity.Instance.Unity Editor" />
<MonoDevelop.Ide.Workbench ActiveDocument="Assets/FlashTools/Scripts/SwfClipAsset.cs">
<MonoDevelop.Ide.Workbench ActiveDocument="Assets/FlashTools/Scripts/Internal/Editor/Postprocessors/SwfAssetPostprocessor.cs">
<Files>
<File FileName="Assets/FlashTools/Scripts/SwfClipAsset.cs" Line="37" Column="18" />
<File FileName="Assets/FlashTools/Scripts/Internal/Editor/Postprocessors/SwfAssetPostprocessor.cs" Line="239" Column="20" />
<File FileName="Assets/FlashTools/Scripts/Internal/SwfUtils.cs" Line="131" Column="7" NotebookId="1" />
<File FileName="Assets/FlashTools/Scripts/Internal/Editor/Postprocessors/SwfAssetPostprocessor.cs" Line="160" Column="33" />
<File FileName="Assets/FlashTools/Scripts/Internal/Editor/Editors/SwfAssetEditor.cs" Line="1" Column="1" />
</Files>
</MonoDevelop.Ide.Workbench>
<MonoDevelop.Ide.DebuggingService.Breakpoints>