很多都是使用NGUI的习惯,因为在NGUI中所有图片都打包在一个图集中,通过更改SpriteName就可以更改图片,so,为了方便调用UGUI的sprite,我们也同样需要为其创建一个asset文件。
其实这个功能相当软肋,既然想到写,还是写出来吧,偶尔用于切换图片或者动态加载之类的还是有点意思
-
首先准备一张图片
-
为我们准备创建的asset文件写一个脚本,他需要继承ScriptableObject,同时我们需要存储一些其他信息,所以需要一个信息脚本,这里需要将信息转为一个资源文件,所以需要使用[Serializable],大概目的就是序列化使其成为两者都能识别的信息,网上查了一个序列化的解释:[Serializable]在C#中的作用-NET 中的对象序列化
SpriteAsset脚本:
using UnityEngine; using System.Collections.Generic; public class UGUISpriteAsset : ScriptableObject { /// <summary> /// 图片资源 /// </summary> public Texture texSource; /// <summary> /// 所有sprite信息 SpriteAssetInfor类为具体的信息类 /// </summary> public List<SpriteAssetInfor> listSpriteAssetInfor; }
sprite信息脚本:
using UnityEngine; using System; [Serializable] public class SpriteAssetInfor { /// <summary> /// ID /// </summary> public int ID; /// <summary> /// 名称 /// </summary> public string name; /// <summary> /// 中心点 /// </summary> public Vector2 pivot; /// <summary> ///坐标&宽高 /// </summary> public Rect rect; /// <summary> /// 精灵 /// </summary> public Sprite sprite; }
3.写一个编辑类,用来创建asset文件,在文件夹中,选中第一步的资源图片,右键然后点击"Create/UGUI Sprite Asset",即可以创建一个同图片同名的.asset文件,UGUICreateSpriteAsset此编辑类需要放在Editor文件夹中
using UnityEngine; using UnityEditor; using System.Collections; using System.IO; using System.Collections.Generic; public static class UGUICreateSpriteAsset { [MenuItem("Assets/Create/UGUI Sprite Asset", false, 10)] static void main() { Object target = Selection.activeObject; if (target == null || target.GetType() != typeof(Texture2D)) return; Texture2D sourceTex = target as Texture2D; //整体路径 string filePathWithName = AssetDatabase.GetAssetPath(sourceTex); //带后缀的文件名 string fileNameWithExtension = Path.GetFileName(filePathWithName); //不带后缀的文件名 string fileNameWithoutExtension = Path.GetFileNameWithoutExtension(filePathWithName); //不带文件名的路径 string filePath = filePathWithName.Replace(fileNameWithExtension, ""); UGUISpriteAsset spriteAsset = AssetDatabase.LoadAssetAtPath(filePath + fileNameWithoutExtension + ".asset", typeof(UGUISpriteAsset)) as UGUISpriteAsset; bool isNewAsset = spriteAsset == null ? true : false; if (isNewAsset) { spriteAsset = ScriptableObject.CreateInstance<UGUISpriteAsset>(); spriteAsset.texSource = sourceTex; spriteAsset.listSpriteAssetInfor = GetSpritesInfor(sourceTex); AssetDatabase.CreateAsset(spriteAsset, filePath + fileNameWithoutExtension + ".asset"); } } public static List<SpriteAssetInfor> GetSpritesInfor(Texture2D tex) { List<SpriteAssetInfor> m_sprites = new List<SpriteAssetInfor>(); string filePath = UnityEditor.AssetDatabase.GetAssetPath(tex); Object[] objects = UnityEditor.AssetDatabase.LoadAllAssetsAtPath(filePath); for (int i = 0; i < objects.Length; i++) { if (objects[i].GetType() == typeof(Sprite)) { SpriteAssetInfor temp = new SpriteAssetInfor(); Sprite sprite = objects[i] as Sprite; temp.ID = i; temp.name = sprite.name; temp.pivot = sprite.pivot; temp.rect = sprite.rect; temp.sprite = sprite; m_sprites.Add(temp); } } return m_sprites; } }
4.选择.asset文件,你就会发现上面就会有一些你想要存储的信息,但是并不是很美观(其实我改过之后还是很一般),这里我们可以通过一个[CustomEditor]来自定义属性面板,他需要继承Editor,并在类名上声明他为哪个类自定义属性表,需要使用OnInspectorGUI函数来绘制,使用方法与OnGUI一样,注意关键字override,同样UGUISpriteAssetEditor类也需要放在Editor文件夹中
using UnityEngine; using UnityEditor; using System.Collections; [CustomEditor(typeof(UGUISpriteAsset))] public class UGUISpriteAssetEditor : Editor { UGUISpriteAsset spriteAsset; public void OnEnable() { spriteAsset = (UGUISpriteAsset)target; } private Vector2 ve2ScorllView; public override void OnInspectorGUI() { ve2ScorllView = GUILayout.BeginScrollView(ve2ScorllView); GUILayout.Label("UGUI Sprite Asset"); if (spriteAsset.listSpriteAssetInfor == null) return; for (int i = 0; i < spriteAsset.listSpriteAssetInfor.Count; i++) { GUILayout.Label(" "); EditorGUILayout.ObjectField("",spriteAsset.listSpriteAssetInfor[i].sprite, typeof(Sprite)); EditorGUILayout.IntField("ID:", spriteAsset.listSpriteAssetInfor[i].ID); EditorGUILayout.LabelField("name:", spriteAsset.listSpriteAssetInfor[i].name); EditorGUILayout.Vector2Field("povit:", spriteAsset.listSpriteAssetInfor[i].pivot); EditorGUILayout.RectField("rect:", spriteAsset.listSpriteAssetInfor[i].rect); GUILayout.Label(" "); } GUILayout.EndScrollView(); } }
5.asset文件:
6.写一个测试脚本,不停的切换图片,后面可以封装一下,通过名称或者ID来索引sprite
using UnityEngine; using UnityEngine.UI; using System.Collections; public class ChangeUGUISprite : MonoBehaviour { public UGUISpriteAsset usa; private float fTime = 0.0f; // Update is called once per frame void Update () { fTime += Time.deltaTime; if (fTime >= 0.3f) { GetComponent<Image>().sprite = usa.listSpriteAssetInfor[Random.Range(0, usa.listSpriteAssetInfor.Count)].sprite; fTime = 0.0f; } } }
7.测试结果: