change: use list pool to improve performance

pull/197/head
mob-sakai 2022-02-18 04:40:38 +09:00
parent 40be7320dd
commit d94fcdc117
2 changed files with 84 additions and 8 deletions

View File

@ -41,11 +41,11 @@ namespace Coffee.UIExtensions
private bool _shouldBeRemoved;
private Mesh _bakedMesh;
private readonly List<Material> _modifiedMaterials = new List<Material>();
private readonly List<Material> _maskMaterials = new List<Material>();
private readonly List<bool> _activeMeshIndices = new List<bool>();
private static readonly List<Material> s_TempMaterials = new List<Material>(2);
private List<Material> _modifiedMaterials;
private List<Material> _maskMaterials;
private List<bool> _activeMeshIndices;
private static MaterialPropertyBlock s_Mpb;
private static readonly List<Material> s_TempMaterials = new List<Material>(2);
private static readonly List<Material> s_PrevMaskMaterials = new List<Material>();
private static readonly List<Material> s_PrevModifiedMaterials = new List<Material>();
private static readonly List<Component> s_Components = new List<Component>();
@ -259,7 +259,7 @@ namespace Coffee.UIExtensions
{
var mat = GetModifiedMaterial(s_TempMaterials[0], ps.GetTextureForSprite());
for (var k = 1; k < s_Components.Count; k++)
mat = (s_Components[k] as IMaterialModifier).GetModifiedMaterial(mat);
mat = ((IMaterialModifier)s_Components[k]).GetModifiedMaterial(mat);
canvasRenderer.SetMaterial(mat, j);
UpdateMaterialProperties(r, j);
j++;
@ -272,7 +272,7 @@ namespace Coffee.UIExtensions
{
var mat = GetModifiedMaterial(s_TempMaterials[1], null);
for (var k = 1; k < s_Components.Count; k++)
mat = (s_Components[k] as IMaterialModifier).GetModifiedMaterial(mat);
mat = ((IMaterialModifier)s_Components[k]).GetModifiedMaterial(mat);
canvasRenderer.SetMaterial(mat, j++);
}
}
@ -362,7 +362,10 @@ namespace Coffee.UIExtensions
#if !SERIALIZE_FIELD_MASKABLE
maskable = m_Maskable;
#endif
activeMeshIndices.Clear();
_modifiedMaterials = ListPool.Rent<Material>();
_maskMaterials = ListPool.Rent<Material>();
_activeMeshIndices = ListPool.Rent<bool>();
UIParticleUpdater.Register(this);
particles.Exec(p => p.GetComponent<ParticleSystemRenderer>().enabled = false);
@ -407,6 +410,16 @@ namespace Coffee.UIExtensions
MeshPool.Return(_bakedMesh);
_bakedMesh = null;
activeMeshIndices.Clear();
UpdateMaterial();
ListPool.Return(_modifiedMaterials);
ListPool.Return(_maskMaterials);
ListPool.Return(_activeMeshIndices);
_modifiedMaterials = null;
_maskMaterials = null;
_activeMeshIndices = null;
base.OnDisable();
}

View File

@ -1,4 +1,5 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Reflection;
using UnityEngine;
@ -6,7 +7,69 @@ using Object = UnityEngine.Object;
namespace Coffee.UIParticleExtensions
{
internal static class Vector3Extensions
internal static class ListPool
{
private static readonly Dictionary<Type, object> _pools = new Dictionary<Type, object>();
public static List<T> Rent<T>()
{
return GetListPool<T>().Rent();
}
public static void Return<T>(List<T> insance)
{
GetListPool<T>().Return(insance);
}
private static ObjectPool<List<T>> GetListPool<T>()
{
object pool;
if (!_pools.TryGetValue(typeof(T), out pool))
{
pool = new ObjectPool<List<T>>(() => new List<T>(), x => true, x => x.Clear());
_pools.Add(typeof(T), pool);
}
return pool as ObjectPool<List<T>>;
}
}
internal class ObjectPool<T>
{
private readonly Stack<T> _pool = new Stack<T>(32);
private readonly Func<T> _onCreate;
private readonly Predicate<T> _onValid;
private readonly Action<T> _onReturn;
public ObjectPool(Func<T> onCreate, Predicate<T> onValid, Action<T> onReturn)
{
_onCreate = onCreate;
_onValid = onValid;
_onReturn = onReturn;
}
public T Rent()
{
while (0 < _pool.Count)
{
var instance = _pool.Pop();
if (_onValid(instance))
return instance;
}
return _onCreate();
}
public void Return(T instance)
{
if (instance == null || _pool.Contains(instance)) return;
_onReturn(instance);
_pool.Push(instance);
}
}
public static class Vector3Extensions
{
public static Vector3 Inverse(this Vector3 self)
{