Insanely huge initial commit

This commit is contained in:
2026-02-21 16:40:15 -08:00
parent 2ba1c94b88
commit ee9aee0a1b
33825 changed files with 5213498 additions and 0 deletions

View File

@@ -0,0 +1,9 @@
using UnityEngine;
namespace LeTai.Asset.TranslucentImage
{
public class BlurConfig : ScriptableObject
{
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 5a1c97a4c20d4c698acd8a00210f69fe
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {fileID: 2800000, guid: c2fc80b7e20a4104db1297bcddfd83b5, type: 3}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,41 @@
using System;
using UnityEngine;
using UnityEngine.Rendering;
namespace LeTai.Asset.TranslucentImage
{
public enum BlurAlgorithmType
{
ScalableBlur
}
public enum BackgroundFillMode
{
None,
Color
}
[Serializable]
public class BackgroundFill
{
public BackgroundFillMode mode = BackgroundFillMode.None;
public Color color = Color.white;
}
public interface IBlurAlgorithm
{
void Init(BlurConfig config, bool isBirp);
void Blur(
CommandBuffer cmd,
RenderTargetIdentifier src,
Rect srcCropRegion,
BackgroundFill backgroundFill,
RenderTexture target
);
int GetScratchesCount();
void GetScratchDescriptor(int index, ref RenderTextureDescriptor descriptor);
void SetScratch(int index, RenderTargetIdentifier value);
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: 6cf12665875748ef9dd9416b900b5143
timeCreated: 1558514104

View File

@@ -0,0 +1,132 @@
using UnityEngine;
using UnityEngine.Rendering;
namespace LeTai.Asset.TranslucentImage
{
public class ScalableBlur : IBlurAlgorithm
{
const int BLUR_PASS = 0;
const int CROP_BLUR_PASS = 1;
readonly RenderTargetIdentifier[] scratches = new RenderTargetIdentifier[14];
bool isBirp;
Material material;
ScalableBlurConfig config;
Material Material
{
get
{
if (material == null)
Material = new Material(Shader.Find(isBirp
? "Hidden/EfficientBlur"
: "Hidden/EfficientBlur_UniversalRP"));
return material;
}
set => material = value;
}
public void Init(BlurConfig config, bool isBirp)
{
this.isBirp = isBirp;
this.config = (ScalableBlurConfig)config;
}
public void Blur(
CommandBuffer cmd,
RenderTargetIdentifier src,
Rect srcCropRegion,
BackgroundFill backgroundFill,
RenderTexture target
)
{
float radius = ScaleWithResolution(config.Radius,
target.width * srcCropRegion.width,
target.height * srcCropRegion.height);
ConfigMaterial(radius, srcCropRegion.ToMinMaxVector(), backgroundFill);
int stepCount = Mathf.Clamp(config.Iteration * 2 - 1, 1, scratches.Length * 2 - 1);
if(stepCount > 1)
cmd.BlitCustom(src, scratches[0], Material, CROP_BLUR_PASS, isBirp);
var depth = Mathf.Min(config.Iteration - 1, scratches.Length - 1);
for (var i = 1; i < stepCount; i++)
{
var fromIdx = SimplePingPong(i - 1, depth);
var toIdx = SimplePingPong(i, depth);
cmd.BlitCustom(scratches[fromIdx], scratches[toIdx], Material, 0, isBirp);
}
cmd.BlitCustom(stepCount > 1 ? scratches[0] : src,
target,
Material,
stepCount > 1 ? BLUR_PASS : CROP_BLUR_PASS,
isBirp);
}
public int GetScratchesCount()
{
return Mathf.Min(config.Iteration, scratches.Length);
}
public void GetScratchDescriptor(int index, ref RenderTextureDescriptor descriptor)
{
if (index == 0)
{
int firstDownsampleFactor = config.Iteration > 0 ? 1 : 0;
descriptor.width >>= firstDownsampleFactor;
descriptor.height >>= firstDownsampleFactor;
}
else
{
descriptor.width >>= 1;
descriptor.height >>= 1;
}
if (descriptor.width <= 0) descriptor.width = 1;
if (descriptor.height <= 0) descriptor.height = 1;
}
public void SetScratch(int index, RenderTargetIdentifier value)
{
scratches[index] = value;
}
protected void ConfigMaterial(float radius, Vector4 cropRegion, BackgroundFill backgroundFill)
{
switch (backgroundFill.mode)
{
case BackgroundFillMode.None:
Material.EnableKeyword("BACKGROUND_FILL_NONE");
Material.DisableKeyword("BACKGROUND_FILL_COLOR");
break;
case BackgroundFillMode.Color:
Material.EnableKeyword("BACKGROUND_FILL_COLOR");
Material.DisableKeyword("BACKGROUND_FILL_NONE");
Material.SetColor(ShaderId.BACKGROUND_COLOR, backgroundFill.color);
break;
}
Material.SetFloat(ShaderId.RADIUS, radius);
Material.SetVector(ShaderId.CROP_REGION, cropRegion);
}
///<summary>
/// Relative blur size to maintain same look across multiple resolution
/// </summary>
float ScaleWithResolution(float baseRadius, float width, float height)
{
float scaleFactor = Mathf.Min(width, height) / 1080f;
scaleFactor = Mathf.Clamp(scaleFactor, .5f, 2f); //too much variation cause artifact
return baseRadius * scaleFactor;
}
public static int SimplePingPong(int t, int max)
{
if (t > max)
return 2 * max - t;
return t;
}
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: 4406fc9923f04f9caf40ac4f57cb0eba
timeCreated: 1558514023

View File

@@ -0,0 +1,65 @@
using UnityEngine;
namespace LeTai.Asset.TranslucentImage
{
[CreateAssetMenu(fileName = "New Scalable Blur Config",
menuName = "Translucent Image/ Scalable Blur Config",
order = 100)]
public class ScalableBlurConfig : BlurConfig
{
[SerializeField]
[Tooltip("Blurriness. Does NOT affect performance")]
float radius = 4;
[SerializeField]
[Tooltip("The number of times to run the algorithm to increase the smoothness of the effect. Can affect performance when increase")]
[Range(0, 8)]
int iteration = 4;
[SerializeField]
[Tooltip("How strong the blur is")]
float strength;
/// <summary>
/// Distance between the base texel and the texel to be sampled.
/// </summary>
public float Radius
{
get { return radius; }
set { radius = Mathf.Max(0, value); }
}
/// <summary>
/// Half the number of time to process the image. It is half because the real number of iteration must alway be even. Using half also make calculation simpler
/// </summary>
/// <value>
/// Must be non-negative
/// </value>
public int Iteration
{
get { return iteration; }
set { iteration = Mathf.Max(0, value); }
}
/// <summary>
/// User friendly property to control the amount of blur
/// </summary>
///<value>
/// Must be non-negative
/// </value>
public float Strength
{
get { return strength = Radius * Mathf.Pow(2, Iteration); }
set
{
strength = Mathf.Clamp(value, 0, (1 << 14) * (1 << 14));
// Bit fiddling would be faster, but need unsafe or .NET Core 3.0+
// for BitOperations, and BitConverter that doesn't creates garbages :(
radius = Mathf.Sqrt(strength);
iteration = 0;
while ((1 << iteration) < radius)
iteration++;
radius = strength / (1 << iteration);
}
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 510c61cdec524e86b647525bb5947f82
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {fileID: 2800000, guid: c2fc80b7e20a4104db1297bcddfd83b5, type: 3}
userData:
assetBundleName:
assetBundleVariant: