Files
stas-barecky/Library/PackageCache/com.unity.2d.sprite@82f01c8c75ca/Editor/SpriteEditorModule/SpriteFrameModule/IsometricSlicingUtility.cs
2026-01-08 20:43:08 +05:00

83 lines
3.4 KiB
C#

using System.Collections.Generic;
using UnityEngine;
using UnityTexture2D = UnityEngine.Texture2D;
namespace UnityEditor.U2D.Sprites
{
internal class IsometricSlicingUtility
{
private static bool PixelHasAlpha(int x, int y, int width, bool[] alphaPixelCache)
{
var index = y * width + x;
return alphaPixelCache[index];
}
public static IEnumerable<Rect> GetIsometricRects(UnityTexture2D textureToUse, Vector2 size, Vector2 offset, bool isAlternate, bool keepEmptyRects)
{
var alphaPixelCache = new bool[textureToUse.width * textureToUse.height];
Color32[] pixels = textureToUse.GetPixels32();
for (int i = 0; i < pixels.Length; i++)
alphaPixelCache[i] = pixels[i].a != 0;
var gradient = (size.x / 2) / (size.y / 2);
bool isAlt = isAlternate;
float x = offset.x;
if (isAlt)
x += size.x / 2;
float y = textureToUse.height - offset.y;
while (y - size.y >= 0)
{
while (x + size.x <= textureToUse.width)
{
var rect = new Rect(x, y - size.y, size.x, size.y);
if (!keepEmptyRects)
{
int sx = (int)rect.x;
int sy = (int)rect.y;
int width = (int)size.x;
int odd = ((int)size.y) % 2;
int topY = ((int)size.y / 2) - 1;
int bottomY = topY + odd;
int totalPixels = 0;
int alphaPixels = 0;
{
for (int ry = 0; ry <= topY; ry++)
{
var pixelOffset = Mathf.CeilToInt(gradient * ry);
for (int rx = pixelOffset; rx < width - pixelOffset; ++rx)
{
if (PixelHasAlpha(sx + rx, sy + topY - ry, textureToUse.width, alphaPixelCache))
alphaPixels++;
if (PixelHasAlpha(sx + rx, sy + bottomY + ry, textureToUse.width, alphaPixelCache))
alphaPixels++;
totalPixels += 2;
}
}
}
if (odd > 0)
{
int ry = topY + 1;
for (int rx = 0; rx < size.x; ++rx)
{
if (PixelHasAlpha(sx + rx, sy + ry, textureToUse.width, alphaPixelCache))
alphaPixels++;
totalPixels++;
}
}
if (totalPixels > 0 && ((float)alphaPixels) / totalPixels > 0.01f)
yield return rect;
}
else
yield return rect;
x += size.x;
}
isAlt = !isAlt;
x = offset.x;
if (isAlt)
x += size.x / 2;
y -= size.y / 2;
}
}
}
}