149 lines
5.0 KiB
C#
149 lines
5.0 KiB
C#
using System;
|
|
using System.Globalization;
|
|
using UnityEngine;
|
|
|
|
namespace GeometryTD.CustomUtility
|
|
{
|
|
public static class TowerIconComposeUtility
|
|
{
|
|
public static Sprite Compose(
|
|
Sprite muzzleSprite,
|
|
Color muzzleColor,
|
|
Sprite bearingSprite,
|
|
Color bearingColor,
|
|
Sprite baseSprite,
|
|
Color baseColor)
|
|
{
|
|
if (muzzleSprite == null || bearingSprite == null || baseSprite == null)
|
|
{
|
|
return null;
|
|
}
|
|
|
|
Sprite referenceSprite = muzzleSprite ?? bearingSprite ?? baseSprite;
|
|
if (referenceSprite == null)
|
|
{
|
|
return null;
|
|
}
|
|
|
|
int width = Mathf.RoundToInt(referenceSprite.rect.width);
|
|
int height = Mathf.RoundToInt(referenceSprite.rect.height);
|
|
if (width <= 0 || height <= 0)
|
|
{
|
|
return null;
|
|
}
|
|
|
|
return ComposeWithRenderTexture(
|
|
muzzleSprite,
|
|
muzzleColor,
|
|
bearingSprite,
|
|
bearingColor,
|
|
baseSprite,
|
|
baseColor,
|
|
width,
|
|
height,
|
|
referenceSprite);
|
|
}
|
|
|
|
public static string BuildCacheKey(
|
|
long muzzleId,
|
|
long bearingId,
|
|
long baseId,
|
|
Color muzzleColor,
|
|
Color bearingColor,
|
|
Color baseColor)
|
|
{
|
|
return string.Format(
|
|
CultureInfo.InvariantCulture,
|
|
"v2|{0}|{1}|{2}|{3}|{4}|{5}",
|
|
muzzleId,
|
|
bearingId,
|
|
baseId,
|
|
ToColorKey(muzzleColor),
|
|
ToColorKey(bearingColor),
|
|
ToColorKey(baseColor));
|
|
}
|
|
|
|
private static Sprite ComposeWithRenderTexture(
|
|
Sprite muzzleSprite,
|
|
Color muzzleColor,
|
|
Sprite bearingSprite,
|
|
Color bearingColor,
|
|
Sprite baseSprite,
|
|
Color baseColor,
|
|
int width,
|
|
int height,
|
|
Sprite referenceSprite)
|
|
{
|
|
RenderTexture rt = RenderTexture.GetTemporary(width, height, 0, RenderTextureFormat.ARGB32);
|
|
RenderTexture previous = RenderTexture.active;
|
|
try
|
|
{
|
|
RenderTexture.active = rt;
|
|
GL.PushMatrix();
|
|
GL.LoadPixelMatrix(0f, width, 0f, height);
|
|
GL.Clear(true, true, Color.clear);
|
|
|
|
DrawSpriteToRenderTarget(baseSprite, baseColor, width, height);
|
|
DrawSpriteToRenderTarget(bearingSprite, bearingColor, width, height);
|
|
DrawSpriteToRenderTarget(muzzleSprite, muzzleColor, width, height);
|
|
|
|
GL.PopMatrix();
|
|
|
|
Texture2D composedTexture = new Texture2D(width, height, TextureFormat.RGBA32, false);
|
|
composedTexture.ReadPixels(new Rect(0f, 0f, width, height), 0, 0);
|
|
composedTexture.Apply(false, false);
|
|
return CreateSprite(composedTexture, referenceSprite);
|
|
}
|
|
catch (Exception)
|
|
{
|
|
return null;
|
|
}
|
|
finally
|
|
{
|
|
RenderTexture.active = previous;
|
|
RenderTexture.ReleaseTemporary(rt);
|
|
}
|
|
}
|
|
|
|
private static void DrawSpriteToRenderTarget(Sprite sprite, Color color, int width, int height)
|
|
{
|
|
if (sprite == null || sprite.texture == null)
|
|
{
|
|
return;
|
|
}
|
|
|
|
Rect textureRect = sprite.textureRect;
|
|
Texture texture = sprite.texture;
|
|
Rect uvRect = new Rect(
|
|
textureRect.x / texture.width,
|
|
textureRect.y / texture.height,
|
|
textureRect.width / texture.width,
|
|
textureRect.height / texture.height);
|
|
|
|
Graphics.DrawTexture(new Rect(0f, 0f, width, height), texture, uvRect, 0, 0, 0, 0, color);
|
|
}
|
|
|
|
private static Sprite CreateSprite(Texture2D texture, Sprite referenceSprite)
|
|
{
|
|
if (texture == null || referenceSprite == null)
|
|
{
|
|
return null;
|
|
}
|
|
|
|
float width = Mathf.Max(1f, referenceSprite.rect.width);
|
|
float height = Mathf.Max(1f, referenceSprite.rect.height);
|
|
Vector2 pivot = new Vector2(referenceSprite.pivot.x / width, referenceSprite.pivot.y / height);
|
|
return Sprite.Create(texture, new Rect(0f, 0f, texture.width, texture.height), pivot, referenceSprite.pixelsPerUnit);
|
|
}
|
|
|
|
private static string ToColorKey(Color color)
|
|
{
|
|
Color32 c = color;
|
|
return c.r.ToString("X2", CultureInfo.InvariantCulture) +
|
|
c.g.ToString("X2", CultureInfo.InvariantCulture) +
|
|
c.b.ToString("X2", CultureInfo.InvariantCulture) +
|
|
c.a.ToString("X2", CultureInfo.InvariantCulture);
|
|
}
|
|
}
|
|
}
|