Unity 我的 Texturekit 工具类

插眼 : 2024/03/15 更新 

1. 更新获取到目录文件夹下包括 JPG 和 PNG 格式的所有图片

2. 调整了 函数 顺序

3. 增加了 函数调用示例 

TextureKit.LoadSpritesToArr(Application.streamingAssetsPath + "/Seed/SeedIcons");

using System;
using System.Collections;
using System.Collections.Generic;
using System.Drawing;
using System.IO;
using UnityEngine;
using UnityEngine.Experimental.Rendering;
using UnityEngine.Networking;

public static class TextureKit
{
    /// <summary>
    /// 返回 Texture2D 本地图片转Texture2D
    /// </summary>
    /// <param name="sFullPath">图片完整路径</param>
    /// <returns></returns>
    public static Texture2D LoadTexture2DSingle(string sFullPath)
    {
        if (!File.Exists(sFullPath)) return null;
        Image image = Image.FromStream(new MemoryStream(FileToBytes(sFullPath)));

        Texture2D t2d = new Texture2D(image.Width, image.Height);
        //根据路劲读取字节流再转换成图片形式
        t2d.LoadImage(FileToBytes(sFullPath));

        return t2d;
    }

    /// <summary>
    /// 返回List 在指定目录下加载的所有图片的 Texture2D 
    /// </summary>
    /// <returns></returns>
    public static List<Texture2D> LoadTexture2DToList(string sFold)
    {
        List<Texture2D> lLoadT2ds = new List<Texture2D>();
        //获取到路劲
        List<string> filePaths = new List<string>();

        filePaths = GetImagesPath(sFold);
        //新建时要给上大小,小于原先的图片大小会出现图片值截取一块的情况

        if (filePaths.Count > 0)
        {
            //根据读取到的文件路径,一个文件一个文件的将图片存储进去
            for (int i = 0; i < filePaths.Count; i++)
            {
                Image image = Image.FromStream(new MemoryStream(FileToBytes(filePaths[i])));

                Texture2D t2d = new Texture2D(image.Width, image.Height);
                //根据路劲读取字节流再转换成图片形式
                t2d.LoadImage(FileToBytes(filePaths[i]));
                //放到集合里面
                lLoadT2ds.Add(t2d);
                Debug.Log(filePaths[i]);
            }
        }

        return lLoadT2ds;
    }

    /// <summary>
    /// 返回单张 Sprite 本地图片转Sprite
    /// </summary>
    /// <param name="sFullPath">图片完整路径</param>
    /// <returns></returns>
    public static Sprite LoadSpriteSingle(string sFullPath)
    {
        if (!File.Exists(sFullPath))
        {
            Debug.LogError("LoadSpriteSingle方法 路径不正确");
            return null;
        }
        Image image = Image.FromStream(new MemoryStream(FileToBytes(sFullPath)));

        Texture2D t2d = new Texture2D(image.Width, image.Height);
        //根据路劲读取字节流再转换成图片形式
        t2d.LoadImage(FileToBytes(sFullPath));
        //创建Sprite
        Sprite sprite = Sprite.Create(t2d, new Rect(0, 0, t2d.width, t2d.height), new Vector2(0.5f, 0.5f));
        return sprite;
    }

    /// <summary>
    /// 返回List 在指定目录下加载的所有图片的 Sprite 包括jpg 和 png
    /// 使用示例:  TextureKit.LoadSpritesToArr(Application.streamingAssetsPath + "/Seed/SeedIcons");
    /// </summary>
    /// <returns></returns>
    public static Sprite[] LoadSpritesToArr(string sFold)
    {
        //获取到路劲
        List<string> filePaths = new List<string>();

        filePaths = GetMultiNameSuffixFilePath(sFold);


        Sprite[] SpritesArr = new Sprite[filePaths.Count];
        //新建时要给上大小,小于原先的图片大小会出现图片值截取一块的情况

        //根据读取到的文件路径,一个文件一个文件的将图片存储进去
        for (int i = 0; i < filePaths.Count; i++)
        {
            Image image = Image.FromStream(new MemoryStream(FileToBytes(filePaths[i])));

            Texture2D t2d = new Texture2D(image.Width, image.Height);
            //根据路劲读取字节流再转换成图片形式
            t2d.LoadImage(FileToBytes(filePaths[i]));

            //创建Sprite
            Sprite sprite = Sprite.Create(t2d, new Rect(0, 0, t2d.width, t2d.height), new Vector2(0.5f, 0.5f));

            SpritesArr[i] = sprite;
        }

        return SpritesArr;
    }

    /// <summary>
    /// 返回List 在指定目录下加载的所有图片的 Sprite 包括 jpg 和 png格式
    /// 使用示例:  TextureKit.LoadSpritesToList(Application.streamingAssetsPath + "/Seed/SeedIcons");
    /// </summary>
    /// <returns></returns>
    public static List<Sprite> LoadSpritesToList(string sFold)
    {

        List<Sprite> lLoadSprites = new List<Sprite>();
        //获取到路劲
        List<string> filePaths = new List<string>();

        filePaths = GetMultiNameSuffixFilePath(sFold);
        //新建时要给上大小,小于原先的图片大小会出现图片值截取一块的情况

        //根据读取到的文件路径,一个文件一个文件的将图片存储进去
        for (int i = 0; i < filePaths.Count; i++)
        {
            Image image = Image.FromStream(new MemoryStream(FileToBytes(filePaths[i])));

            Texture2D t2d = new Texture2D(image.Width, image.Height);
            //根据路劲读取字节流再转换成图片形式
            t2d.LoadImage(FileToBytes(filePaths[i]));

            //创建Sprite
            Sprite sprite = Sprite.Create(t2d, new Rect(0, 0, t2d.width, t2d.height), new Vector2(0.5f, 0.5f));


            //放到集合里面
            lLoadSprites.Add(sprite);
        }

        return lLoadSprites;
    }

    /// <summary>
    /// 返回List 在指定目录下加载的所有图片的 Sprite
    /// </summary>
    /// <returns></returns>
    public static List<Sprite> LoadAndSetPivotSpritesToList(string sFold, Vector2 pivot)
    {

        List<Sprite> lLoadSprites = new List<Sprite>();
        //获取到路劲
        List<string> filePaths = new List<string>();

        filePaths = GetImagesPath(sFold);
        //新建时要给上大小,小于原先的图片大小会出现图片值截取一块的情况

        //根据读取到的文件路径,一个文件一个文件的将图片存储进去
        for (int i = 0; i < filePaths.Count; i++)
        {
            Image image = Image.FromStream(new MemoryStream(FileToBytes(filePaths[i])));

            Texture2D t2d = new Texture2D(image.Width, image.Height);
            //根据路劲读取字节流再转换成图片形式
            t2d.LoadImage(FileToBytes(filePaths[i]));

            //创建Sprite
            Sprite sprite = Sprite.Create(t2d, new Rect(0, 0, t2d.width, t2d.height), pivot);


            //放到集合里面
            lLoadSprites.Add(sprite);
        }

        return lLoadSprites;
    }

    /// <summary>
    /// 得到指定后缀格式的所有文件路径
    /// 默认后缀为  "*.PNG"
    /// </summary>
    /// <returns></returns>
    public static List<string> GetImagesPath(string sFold, string sNameSuffix = "*.PNG")
    {
        List<string> filePaths = new List<string>();
        //获取unity根目录下的图片文件夹下的所有文件的路径 路径+ 名称全部存储在字符串数组中
        //string[] dirs = Directory.GetFiles(Application.streamingAssetsPath + "/BlendFaceImages", sNameSuffix);
        try
        {
            string[] dirs = Directory.GetFiles(sFold, sNameSuffix);

            if (dirs.Length > 0)
            {
                for (int j = 0; j < dirs.Length; j++)
                {
                    if (!File.Exists(dirs[j]))
                    {
                        Debug.LogError(dirs[j] + "GetImagesPath方法 路径不正确");
                        return null;
                    }
                    filePaths.Add(dirs[j]);
                    Debug.Log("图片路径为     " + dirs[j]);
                }
                Debug.Log("一共读取到" + dirs.Length + "张图片");
            }
            else
            {
                Debug.Log("文件夹内未读取到文件" + sFold);
            }
        }
        catch (Exception e)
        {
            Debug.Log(e);
        }


        return filePaths;
    }

    /// <summary>
    /// 得到多个指定后缀格式的所有文件路径 
    /// Case : 需自己修改 imgtype按照格式去添加后缀格式
    /// </summary>
    /// <returns></returns>
    public static List<string> GetMultiNameSuffixFilePath(string sFold)
    {
        List<string> filePaths = new List<string>();
        string imgtype = "*.JPG|*.PNG";
        string[] ImageType = imgtype.Split('|');
        for (int i = 0; i < ImageType.Length; i++)
        {

            //获取unity根目录下的图片文件夹下的所有文件的路径 路径+ 名称全部存储在字符串数组中
            string[] dirs = Directory.GetFiles(sFold, ImageType[i]);

            for (int j = 0; j < dirs.Length; j++)
            {
                filePaths.Add(dirs[j]);
                Debug.Log("文件路径为     " + dirs[j]);
            }
            Debug.Log("一共读取到" + dirs.Length + "个文件");
        }

        return filePaths;
    }

    /// <summary>
    /// 文件 转 字节
    /// </summary>
    /// <param name="sFilePath"></param>
    /// <returns></returns>
    public static byte[] FileToBytes(string sFilePath)
    {
        //读取到文件
        FileStream files = new FileStream(sFilePath, FileMode.Open);
        //新建比特流对象
        byte[] bArrFileBytes = new byte[files.Length];
        //将文件写入对应比特流对象
        files.Read(bArrFileBytes, 0, bArrFileBytes.Length);
        //关闭文件
        files.Close();
        //返回比特流的值
        return bArrFileBytes;
    }

    /// <summary>
    /// 文件夹目录最多只保留指定数量的图片
    /// sNameSuffix 后缀名 
    /// </summary>
    public static void DeleteWhenOverLoad(string sFoldPath, string sNameSuffix = "*.PNG", int iFoldMaxSaveNum = 40)
    {
        //获取unity根目录下的图片文件夹下的所有文件的路径 路径+ 名称全部存储在字符串数组中
        //string[] dirs = Directory.GetFiles(Application.streamingAssetsPath + "/BlendFaceImages", "*.PNG");
        //string[] dirs = Directory.GetFiles(sFoldPath, "*.PNG");
        string[] dirs = Directory.GetFiles(sFoldPath, sNameSuffix);


        //需要删除的数量 
        int iNeedDeleteNum = dirs.Length - iFoldMaxSaveNum;
        if (iNeedDeleteNum > 0)
        {
            for (int i = 0; i < iNeedDeleteNum; i++)
            {
                File.Delete(dirs[i]);
            }
        }
    }

    /// <summary>
    /// IO保存 Texture2D 到本地为 Png
    /// </summary>
    /// <param name="texture">传入要保存的 Texture2D</param>
    /// <param name="sFullPath">传入你要保存的位置 完整路径</param>
    public static void SaveTexture2DToPNG(Texture2D texture, string sFullPath)
    {
         第一种方式
        //var bytes = texture.EncodeToPNG();
        //var file = File.Open(sFullPath, FileMode.Create);
        //var binary = new BinaryWriter(file);
        //binary.Write(bytes);
        //file.Close();

        // 第二种方式 EncodeToPNG这个会导致主线程卡顿   携程一样
        System.IO.File.WriteAllBytes(sFullPath, texture.EncodeToPNG());
    }

    /// <summary>
    ///  默认使用 携程来保存图片到路径 其他方式可能造成主线程一瞬间的卡顿 携程完成有回调
    /// </summary>
    /// <param name="sBlendFaceImageName"></param>
    /// <param name="texture"></param>
    /// <param name="sFullPath"></param>
    /// <returns></returns>
    public static IEnumerator SaveTexture2DToPNGCoroutine(string sBlendFaceImageName, Texture2D texture, string sFullPath, Action callback)
    {
        //yield return new WaitForSeconds(5f);
        yield return new WaitForEndOfFrame();
        byte[] bytes = texture.EncodeToPNG();
        //将纹理数据,转化成一个png图片 
        System.IO.File.WriteAllBytes(sFullPath, bytes);

        //写入文件之后触发
        callback?.Invoke();

        #region
         使用示例
         携程保存图片
        //StartCoroutine(TextureKit.Instance.SaveTexture2DToPNGCoroutine(sBlendFaceImageName, m_tBlendTexture as Texture2D, DataManager.Instance.sBlendFaceImagesFoldPath + sBlendFaceImageName, (() =>
        //{
        //    //Debug.Log("妈妈再也不担心我存图片了");
        //    // 人脸融合完成,广播事件
        //    QEventSystem.SendEvent(FaceEvent.OnFaceMergeFinish, sBlendFaceImageName);
        //})));
        #endregion

    }

    /// <summary>
    /// PNG 图片存储大小压缩
    /// </summary>
    /// <param name="imagePath"></param>
    public static void CompressPNG(string imagePath)
    {
        byte[] fileData = File.ReadAllBytes(imagePath);

        Texture2D tex = new Texture2D((int)(Screen.width), (int)(Screen.height), TextureFormat.RGB24, true);
        tex.LoadImage(fileData);

        float miniSize = Mathf.Max(tex.width, tex.height);

        float scale = 1200.0f / miniSize;
        if (scale > 1.0f)
        {
            scale = 1.0f;
        }
        Texture2D temp = ScaleTexture(tex, (int)(tex.width * scale), (int)(tex.height * scale));
        byte[] pngData = temp.EncodeToPNG();
        // string miniImagePath = imagePath.Replace(".png", "_min.jpg");
        File.WriteAllBytes(imagePath, pngData);
    }

    /// <summary>
    /// 图片尺寸大小缩放
    /// </summary>
    /// <param name="source"></param>
    /// <param name="targetWidth"></param>
    /// <param name="targetHeight"></param>
    /// <returns></returns>
    public static Texture2D ScaleTexture(Texture2D source, int targetWidth, int targetHeight)
    {
        Texture2D result = new Texture2D(targetWidth, targetHeight, source.format, true);
        UnityEngine.Color[] rpixels = result.GetPixels(0);
        float incX = ((float)1 / source.width) * ((float)source.width / targetWidth);
        float incY = ((float)1 / source.height) * ((float)source.height / targetHeight);
        for (int px = 0; px < rpixels.Length; px++)
        {
            rpixels[px] = source.GetPixelBilinear(incX * ((float)px % targetWidth), incY * ((float)Mathf.Floor(px / targetWidth)));
        }
        result.SetPixels(rpixels, 0);
        result.Apply();
        return result;
    }

    /// <summary>
    /// 两张图像合并
    /// </summary>
    /// <param name="src1"></param>
    /// <param name="src2"></param>
    /// <returns></returns>
    public static Texture2D ImageConbine(Texture2D src1, Texture2D src2)
    {
        // 偏差
        int offsetX = 0;
        int offsetY = 0;
        for (int x = 0; x < src2.width; x++)
        {
            for (int y = 0; y < src2.height; y++)

            {
                if (src2.GetPixel(x, y).a > 0.9)
                {
                    src1.SetPixel(src1.width - x + offsetX, src1.height + y + offsetY, src2.GetPixel(x, y));

                }
            }

        }
        src1.Apply();
        return src1;
    }

    /// <summary>
    /// 输入一张texture2D,返回矩形区域内的不透明的像素
    /// </summary>
    /// <param name="src"></param>
    /// <param name="dstWidth"></param>
    /// <param name="dstHeight"></param>
    /// <param name="offsetX"></param>
    /// <param name="offsetY"></param>
    /// <returns></returns>
    public static Texture2D GetRectOpaqueT2D(Texture2D src, int dstWidth = 729, int dstHeight = 729, int offsetX = 612, int offsetY = 175)
    {
        Texture2D miniMask = new Texture2D(dstWidth, dstHeight, TextureFormat.RGBA32, false);
        for (int x = 0; x < src.width; x++)
        {

            for (int y = 0; y < src.height; y++)

            {
                if (src.GetPixel(x, y).a > 0.9)
                {
                    miniMask.SetPixel(x - offsetX, y - offsetY, src.GetPixel(x, y));
                }
            }
        }
        //miniMask.alphaIsTransparency = true;
        miniMask.Apply();
        return miniMask;
    }

    /// <summary>
    /// RenderTexture 转 Texture2D
    /// </summary>
    /// <param name="renderT"></param>
    /// <returns></returns>
    public static Texture2D GetTexture2DFromRenderTexture(RenderTexture renderT)
    {
        if (renderT == null)
            Debug.LogError("RenderTexture 未赋值");

        int width = renderT.width;
        int height = renderT.height;
        Texture2D tex2d = new Texture2D(width, height, TextureFormat.ARGB32, false);
        RenderTexture.active = renderT;
        tex2d.ReadPixels(new Rect(0, 0, width, height), 0, 0);
        tex2d.Apply();

        //byte[] b = tex2d.EncodeToPNG();
        //Destroy(tex2d); 

        //File.WriteAllBytes(Application.dataPath + "1.jpg", b); 
        return tex2d;
    }

    /// <summary>
    ///  保存 RenderTexture 
    /// </summary>
    /// <param name="renderT"></param>
    /// <returns></returns>
    public static void SaveRenderTextureToPNG(string sFullPath, RenderTexture renderT, Action<Texture2D> callback)
    {
        try
        {
            Texture2D tex2d = GetTexture2DFromRenderTexture(renderT);
            byte[] b = tex2d.EncodeToPNG();

            File.WriteAllBytes(sFullPath, b);
            //写入文件之后触发
            callback?.Invoke(tex2d);
        }
        catch (Exception e)
        {
            Debug.Log(e.Message);
            throw;
        }

    }
    public static IEnumerator SaveRenderTextureToPNGAsyncGPU(string sFullPath, RenderTexture renderT, Action<Texture2D> callback)
    {

        int nw = renderT.width;
        int nh = renderT.height;
        GraphicsFormat format = renderT.graphicsFormat;
        UnityEngine.Rendering.AsyncGPUReadbackRequest request = UnityEngine.Rendering.AsyncGPUReadback.Request(renderT, 0);
        yield return 0;


        while (!request.done)
        {
            yield return new WaitForEndOfFrame();
        }

        if (request.hasError)
        {
            Debug.Log("GPU readback error detected.");
            yield break;
        }

        byte[] array = request.GetData<byte>().ToArray();
        byte[] datas = ImageConversion.EncodeArrayToPNG(array, format, (uint)nw, (uint)nh);
        try
        {
            File.WriteAllBytes(sFullPath, datas);
            //写入文件之后触发
            Texture2D tex2d = GetTexture2DFromRenderTexture(renderT);
            callback?.Invoke(tex2d);
        }
        catch (Exception e)
        {
            Debug.Log(e.Message);
            throw;
        }

    }
    public static void OnSingletonInit()
    {

    }
}

 

using System;
using System.Collections;
using System.Collections.Generic;
using System.IO;
using UnityEngine;
using UnityEngine.Networking;

public class NewTintTextureKit : MonoBehaviour
{
    string sFold = Application.streamingAssetsPath + "/0";

    public List<Sprite> sprite = new List<Sprite>();

    void Start()
    {
        sprite = LoadSpritesToList(sFold);
    }

    /// <summary>
    /// 返回List 在指定目录下加载的所有图片的 Sprite
    /// </summary>
    /// <returns></returns>
    public List<Sprite> LoadSpritesToList(string sFold, string sNameSuffix = "*.PNG")
    {

        List<Sprite> lLoadSprites = new List<Sprite>();
        //获取到路劲
        List<string> filePaths = new List<string>();

        filePaths = GetImagesPath(sFold, sNameSuffix);
        //新建时要给上大小,小于原先的图片大小会出现图片值截取一块的情况

        //根据读取到的文件路径,一个文件一个文件的将图片存储进去
        for (int i = 0; i < filePaths.Count; i++)
        {
            StartCoroutine(DownloadImage(filePaths[i], (sprite) =>
            {
                //放到集合里面
                lLoadSprites.Add(sprite);

            }));
        }

        return lLoadSprites;
    }

    /// <summary>
    /// 得到指定后缀格式的所有文件路径
    /// 默认后缀为  "*.PNG"
    /// </summary>
    /// <returns></returns>
    public  List<string> GetImagesPath(string sFold, string sNameSuffix = "*.PNG")
    {
        List<string> filePaths = new List<string>();
        //获取unity根目录下的图片文件夹下的所有文件的路径 路径+ 名称全部存储在字符串数组中
        //string[] dirs = Directory.GetFiles(Application.streamingAssetsPath + "/BlendFaceImages", sNameSuffix);
        try
        {
            string[] dirs = Directory.GetFiles(sFold, sNameSuffix);

            if (dirs.Length > 0)
            {
                for (int j = 0; j < dirs.Length; j++)
                {
                    if (!File.Exists(dirs[j]))
                    {
                        Debug.LogError(dirs[j] + "GetImagesPath方法 路径不正确");
                        return null;
                    }
                    filePaths.Add(dirs[j]);
                    //Debug.Log("图片路径为     " + dirs[j]);
                }
                Debug.Log("一共读取到" + dirs.Length + "张图片");
            }
        }
        catch (Exception)
        {
            Debug.Log("文件夹内未读取到文件" + sFold);
        }


        return filePaths;
    }


    IEnumerator DownloadImage(string MediaUrl, Action<Sprite> action)
    {
        UnityWebRequest request = UnityWebRequestTexture.GetTexture(MediaUrl);
        yield return request.SendWebRequest();
        if (request.isNetworkError || request.isHttpError)
            Debug.Log(request.error);
        else
        {
            Texture2D tex = ((DownloadHandlerTexture)request.downloadHandler).texture;
            Sprite sprite = Sprite.Create(tex, new Rect(0, 0, tex.width, tex.height), new Vector2(tex.width / 2, tex.height / 2));

            action?.Invoke(sprite);
        }
    }
}

使用只需要将单例方法更改一下就行,后续将持续进行更新,用到哪补充到哪  

如在使用过程中有任何不适,请评论区插眼,谢谢

插眼 : 2020/10/31 更新

1. 返回 在指定目录下加载的所有图片的 Texture2D 

2. 文件 转 字节

3. 得到指定后缀格式的所有文件路径

4. 得到多个指定后缀格式的所有文件路径 

5. 文件夹目录最多只保留指定数量的图片

6. IO保存 Texture2D 到本地为 Png

7. 默认使用 携程来保存图片到路径 其他方式可能造成主线程一瞬间的卡顿 携程完成有回调

8. PNG 图片存储大小压缩

9. 图片尺寸大小缩放

using System;
using System.Collections;
using System.Collections.Generic;
using System.Drawing;
using System.IO;
using UnityEngine;

namespace QFramework.Example
{
    public class TextureKit : ISingleton
    {
        private TextureKit() { }
        public static TextureKit Instance
        {
            get { return SingletonProperty<TextureKit>.Instance; }
        }

        /// <summary>
        /// 返回 在指定目录下加载的所有图片的 Texture2D 
        /// </summary>
        /// <returns></returns>
        public List<Texture2D> LoadTexture2DToList(string sFold)
        {
            List<Texture2D> lLoadT2ds = new List<Texture2D>();
            //获取到路劲
            List<string> filePaths = new List<string>();

            filePaths = GetImagesPath(sFold);
            //新建时要给上大小,小于原先的图片大小会出现图片值截取一块的情况

            //根据读取到的文件路径,一个文件一个文件的将图片存储进去
            for (int i = 0; i < filePaths.Count; i++)
            {
                Image image = Image.FromStream(new MemoryStream(FileToBytes(filePaths[i])));

                Texture2D t2d = new Texture2D(image.Width, image.Height);
                //根据路劲读取字节流再转换成图片形式
                t2d.LoadImage(FileToBytes(filePaths[i]));
                //放到集合里面
                lLoadT2ds.Add(t2d);
            }

            return lLoadT2ds;
        }

        /// <summary>
        /// 文件 转 字节
        /// </summary>
        /// <param name="sFilePath"></param>
        /// <returns></returns>
        public static byte[] FileToBytes(string sFilePath)
        {
            //读取到文件
            FileStream files = new FileStream(sFilePath, FileMode.Open);
            //新建比特流对象
            byte[] bArrFileBytes = new byte[files.Length];
            //将文件写入对应比特流对象
            files.Read(bArrFileBytes, 0, bArrFileBytes.Length);
            //关闭文件
            files.Close();
            //返回比特流的值
            return bArrFileBytes;
        }

        /// <summary>
        /// 得到指定后缀格式的所有文件路径
        /// 默认后缀为  "*.PNG"
        /// </summary>
        /// <returns></returns>
        public List<string> GetImagesPath(string sFold, string sNameSuffix = "*.PNG")
        {
            List<string> filePaths = new List<string>();
            //获取unity根目录下的图片文件夹下的所有文件的路径 路径+ 名称全部存储在字符串数组中
            //string[] dirs = Directory.GetFiles(Application.streamingAssetsPath + "/BlendFaceImages", sNameSuffix);
            string[] dirs = Directory.GetFiles(sFold, sNameSuffix);

            for (int j = 0; j < dirs.Length; j++)
            {
                filePaths.Add(dirs[j]);
                //Debug.Log("图片路径为     " + dirs[j]);
            }
            Debug.Log("一共读取到" + dirs.Length + "张图片");


            return filePaths;
        }

        /// <summary>
        /// 得到多个指定后缀格式的所有文件路径 
        /// Case : 需自己修改 imgtype按照格式去添加后缀格式
        /// </summary>
        /// <returns></returns>
        public List<string> GetMultiNameSuffixFilePath(string sFold)
        {
            List<string> filePaths = new List<string>();
            string imgtype = "*.JPG|*.PNG";
            string[] ImageType = imgtype.Split('|');
            for (int i = 0; i < ImageType.Length; i++)
            {

                //获取unity根目录下的图片文件夹下的所有文件的路径 路径+ 名称全部存储在字符串数组中
                string[] dirs = Directory.GetFiles(sFold, ImageType[i]);

                for (int j = 0; j < dirs.Length; j++)
                {
                    filePaths.Add(dirs[j]);
                    Debug.Log("文件路径为     " + dirs[j]);
                }
                Debug.Log("一共读取到" + dirs.Length + "个文件");
            }

            return filePaths;
        }

        /// <summary>
        /// 文件夹目录最多只保留指定数量的图片
        /// sNameSuffix 后缀名 
        /// </summary>
        public void DeleteWhenOverLoad(string sFoldPath, string sNameSuffix = "", int iFoldMaxSaveNum = 40)
        {
            //获取unity根目录下的图片文件夹下的所有文件的路径 路径+ 名称全部存储在字符串数组中
            //string[] dirs = Directory.GetFiles(Application.streamingAssetsPath + "/BlendFaceImages", "*.PNG");
            string[] dirs = Directory.GetFiles(sFoldPath, "*.PNG");
            Log.I("文件夹目录大小 : " + dirs.Length);

            //需要删除的数量 
            int iNeedDeleteNum = dirs.Length - iFoldMaxSaveNum;
            if (iNeedDeleteNum > 0)
            {
                for (int i = 0; i < iNeedDeleteNum; i++)
                {
                    File.Delete(dirs[i]);
                    Log.I("++++++++++++++ 文件被删除  +++++" + dirs[i]);
                }
            }
        }

        /// <summary>
        /// IO保存 Texture2D 到本地为 Png
        /// </summary>
        /// <param name="texture">传入要保存的 Texture2D</param>
        /// <param name="sFullPath">传入你要保存的位置 完整路径</param>
        public void SaveTexture2DToPNG(Texture2D texture, string sFullPath)
        {
             第一种方式
            //var bytes = texture.EncodeToPNG();
            //var file = File.Open(sFullPath, FileMode.Create);
            //var binary = new BinaryWriter(file);
            //binary.Write(bytes);
            //file.Close();

            // 第二种方式 EncodeToPNG这个会导致主线程卡顿   携程一样
            System.IO.File.WriteAllBytes(sFullPath, texture.EncodeToPNG());
        }

        /// <summary>
        ///  默认使用 携程来保存图片到路径 其他方式可能造成主线程一瞬间的卡顿 携程完成有回调
        /// </summary>
        /// <param name="sBlendFaceImageName"></param>
        /// <param name="texture"></param>
        /// <param name="sFullPath"></param>
        /// <returns></returns>
        public IEnumerator SaveTexture2DToPNGCoroutine(string sBlendFaceImageName, Texture2D texture, string sFullPath, Action callback)
        {
            //yield return new WaitForSeconds(5f);
            yield return new WaitForEndOfFrame();
            byte[] bytes = texture.EncodeToPNG();
            //将纹理数据,转化成一个png图片 
            System.IO.File.WriteAllBytes(sFullPath, bytes);

            //写入文件之后触发
            callback?.Invoke();

            #region
            // 使用示例
            // 携程保存图片
            //StartCoroutine(TextureKit.Instance.SaveTexture2DToPNGCoroutine(sBlendFaceImageName, m_tBlendTexture as Texture2D, DataManager.Instance.sBlendFaceImagesFoldPath + sBlendFaceImageName, (() =>
            //{
            //    //Debug.Log("妈妈再也不担心我存图片了");
            //    // 人脸融合完成,广播事件
            //    QEventSystem.SendEvent(FaceEvent.OnFaceMergeFinish, sBlendFaceImageName);
            //})));
            #endregion

        }

        /// <summary>
        /// PNG 图片存储大小压缩
        /// </summary>
        /// <param name="imagePath"></param>
        public void CompressPNG(string imagePath)
        {
            byte[] fileData = File.ReadAllBytes(imagePath);

            Texture2D tex = new Texture2D((int)(Screen.width), (int)(Screen.height), TextureFormat.RGB24, true);
            tex.LoadImage(fileData);

            float miniSize = Mathf.Max(tex.width, tex.height);

            float scale = 1200.0f / miniSize;
            if (scale > 1.0f)
            {
                scale = 1.0f;
            }
            Texture2D temp = ScaleTexture(tex, (int)(tex.width * scale), (int)(tex.height * scale));
            byte[] pngData = temp.EncodeToPNG();
            // string miniImagePath = imagePath.Replace(".png", "_min.jpg");
            File.WriteAllBytes(imagePath, pngData);
        }

        /// <summary>
        /// 图片尺寸大小缩放
        /// </summary>
        /// <param name="source"></param>
        /// <param name="targetWidth"></param>
        /// <param name="targetHeight"></param>
        /// <returns></returns>
        private Texture2D ScaleTexture(Texture2D source, int targetWidth, int targetHeight)
        {
            Texture2D result = new Texture2D(targetWidth, targetHeight, source.format, true);
            UnityEngine.Color[] rpixels = result.GetPixels(0);
            float incX = ((float)1 / source.width) * ((float)source.width / targetWidth);
            float incY = ((float)1 / source.height) * ((float)source.height / targetHeight);
            for (int px = 0; px < rpixels.Length; px++)
            {
                rpixels[px] = source.GetPixelBilinear(incX * ((float)px % targetWidth), incY * ((float)Mathf.Floor(px / targetWidth)));
            }
            result.SetPixels(rpixels, 0);
            result.Apply();
            return result;
        }

        public void OnSingletonInit()
        {

        }
    }
}

 插眼 : 2020/10/21 更新

1. 返回 在指定目录下加载的所有图片的 Texture2D 

2. 文件 转 字节

3. 得到指定后缀格式的所有文件路径

4. 得到多个指定后缀格式的所有文件路径 

5. 文件夹目录最多只保留指定数量的图片

using System.Collections.Generic;
using System.IO;
using UnityEngine;
using System.Drawing;

namespace QFramework.Example
{
    public class TextureKit:ISingleton
    {
        private TextureKit() { }
        public static TextureKit Instance
        {
            get { return SingletonProperty<TextureKit>.Instance; }
        }


        /// <summary>
        /// 返回 在指定目录下加载的所有图片的 Texture2D 
        /// </summary>
        /// <returns></returns>
        public List<Texture2D> LoadTexture2DToList(string sFold)
        {
            List<Texture2D> lLoadT2ds = new List<Texture2D>();
            //获取到路劲
            List<string> filePaths = new List<string>();

            filePaths = GetImagesPath(sFold);
            //新建时要给上大小,小于原先的图片大小会出现图片值截取一块的情况

            //根据读取到的文件路径,一个文件一个文件的将图片存储进去
            for (int i = 0; i < filePaths.Count; i++)
            {
                Image image = Image.FromStream(new MemoryStream(FileToBytes(filePaths[i])));

                Texture2D t2d = new Texture2D(image.Width, image.Height);
                //根据路劲读取字节流再转换成图片形式
                t2d.LoadImage(FileToBytes(filePaths[i]));
                //放到集合里面
                lLoadT2ds.Add(t2d);
            }

            return lLoadT2ds;
        }

        /// <summary>
        /// 文件 转 字节
        /// </summary>
        /// <param name="sFilePath"></param>
        /// <returns></returns>
        public static byte[] FileToBytes(string sFilePath)
        {
            //读取到文件
            FileStream files = new FileStream(sFilePath, FileMode.Open);
            //新建比特流对象
            byte[] bArrFileBytes = new byte[files.Length];
            //将文件写入对应比特流对象
            files.Read(bArrFileBytes, 0, bArrFileBytes.Length);
            //关闭文件
            files.Close();
            //返回比特流的值
            return bArrFileBytes;
        }

        /// <summary>
        /// 得到指定后缀格式的所有文件路径
        /// 默认后缀为  "*.PNG"
        /// </summary>
        /// <returns></returns>
        public List<string> GetImagesPath(string sFold, string sNameSuffix = "*.PNG")
        {
            List<string> filePaths = new List<string>();
            //获取unity根目录下的图片文件夹下的所有文件的路径 路径+ 名称全部存储在字符串数组中
            //string[] dirs = Directory.GetFiles(Application.streamingAssetsPath + "/BlendFaceImages", sNameSuffix);
            string[] dirs = Directory.GetFiles(sFold, sNameSuffix);

            for (int j = 0; j < dirs.Length; j++)
            {
                filePaths.Add(dirs[j]);
                //Debug.Log("图片路径为     " + dirs[j]);
            }
            Debug.Log("一共读取到" + dirs.Length + "张图片");


            return filePaths;
        }

        /// <summary>
        /// 得到多个指定后缀格式的所有文件路径 
        /// Case : 需自己修改 imgtype按照格式去添加后缀格式
        /// </summary>
        /// <returns></returns>
        public List<string> GetMultiNameSuffixFilePath(string sFold)
        {
            List<string> filePaths = new List<string>();
            string imgtype = "*.JPG|*.PNG";
            string[] ImageType = imgtype.Split('|');
            for (int i = 0; i < ImageType.Length; i++)
            {

                //获取unity根目录下的图片文件夹下的所有文件的路径 路径+ 名称全部存储在字符串数组中
                string[] dirs = Directory.GetFiles(sFold, ImageType[i]);

                for (int j = 0; j < dirs.Length; j++)
                {
                    filePaths.Add(dirs[j]);
                    Debug.Log("文件路径为     " + dirs[j]);
                }
                Debug.Log("一共读取到" + dirs.Length + "个文件");
            }

            return filePaths;
        }

        /// <summary>
        /// 文件夹目录最多只保留指定数量的图片
        /// sNameSuffix 后缀名 
        /// </summary>
        public void DeleteWhenOverLoad(string sFoldPath, string sNameSuffix = "", int iFoldMaxSaveNum = 40)
        {
            //获取unity根目录下的图片文件夹下的所有文件的路径 路径+ 名称全部存储在字符串数组中
            //string[] dirs = Directory.GetFiles(Application.streamingAssetsPath + "/BlendFaceImages", "*.PNG");
            string[] dirs = Directory.GetFiles(sFoldPath, "*.PNG");
            Log.I("文件夹目录大小 : " + dirs.Length);

            //需要删除的数量 
            int iNeedDeleteNum = dirs.Length - iFoldMaxSaveNum;
            if (iNeedDeleteNum > 0)
            {
                for (int i = 0; i < iNeedDeleteNum; i++)
                {
                    File.Delete(dirs[i]);
                    Log.I("++++++++++++++ 文件被删除  +++++" + dirs[i]);
                }
            }
        }

        public void OnSingletonInit()
        {
           
        }
    }
}

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 5
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值