FM/Assets/Scripts/FUJIFILM/UI/ImageScaler.cs

282 lines
11 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

using UnityEngine;
using UnityEngine.UI;
namespace HK.FUJIFILM
{
public static class RawImageScaler
{
/// <summary>
/// 将Texture2D赋值给RawImage并确保等比缩放保持在RawImage最大范围内
/// </summary>
/// <param name="rawImage">目标RawImage组件</param>
/// <param name="texture">要显示的Texture2D</param>
/// <param name="maxWidth">最大宽度限制若为0则使用RawImage的当前宽度</param>
/// <param name="maxHeight">最大高度限制若为0则使用RawImage的当前高度</param>
public static void SetTextureWithAspectRatio(RawImage rawImage, Texture2D texture, float maxWidth = 0,
float maxHeight = 0)
{
if (rawImage == null || texture == null)
{
Debug.LogError("RawImage或Texture2D不能为空");
return;
}
// 赋值纹理
rawImage.texture = texture;
// 获取纹理原始宽高
float textureWidth = texture.width;
float textureHeight = texture.height;
// 如果未指定最大宽高使用RawImage当前的尺寸作为限制
float limitWidth = maxWidth > 0 ? maxWidth : rawImage.rectTransform.rect.width;
float limitHeight = maxHeight > 0 ? maxHeight : rawImage.rectTransform.rect.height;
// 计算宽高比例
float textureAspect = textureWidth / textureHeight;
float limitAspect = limitWidth / limitHeight;
// 计算缩放后的尺寸(保持比例并适应限制范围)
float scaledWidth, scaledHeight;
if (textureAspect > limitAspect)
{
// 纹理更宽,按宽度限制缩放
scaledWidth = limitWidth;
scaledHeight = scaledWidth / textureAspect;
}
else
{
// 纹理更高或比例相同,按高度限制缩放
scaledHeight = limitHeight;
scaledWidth = scaledHeight * textureAspect;
}
// 应用缩放后的尺寸
rawImage.rectTransform.sizeDelta = new Vector2(scaledWidth, scaledHeight);
// 可选:居中显示
rawImage.rectTransform.anchorMin = new Vector2(0.5f, 0.5f);
rawImage.rectTransform.anchorMax = new Vector2(0.5f, 0.5f);
rawImage.rectTransform.pivot = new Vector2(0.5f, 0.5f);
rawImage.rectTransform.anchoredPosition = Vector2.zero;
}
}
public static class ImageScaler
{
/// <summary>
/// 将Image等比缩放到不超过指定的最大尺寸宽和高中较大的值不超过maxSize
/// </summary>
/// <param name="image">需要缩放的Image组件</param>
/// <param name="maxSize">宽和高中较大值的最大限制</param>
/// <param name="keepOriginalIfSmaller">如果原图比限制小,是否保持原图大小</param>
public static void ScaleImageWithSize(Image image, float maxSize, bool keepOriginalIfSmaller = false)
{
if (image == null)
{
Debug.LogError("Image组件不能为空");
return;
}
// 获取原始尺寸
float originalWidth, originalHeight;
if (image.sprite != null)
{
// 使用Sprite的原始尺寸
originalWidth = image.sprite.rect.width;
originalHeight = image.sprite.rect.height;
}
else
{
// 没有Sprite时使用当前RectTransform的尺寸
originalWidth = image.rectTransform.rect.width;
originalHeight = image.rectTransform.rect.height;
}
// 计算缩放比例
float scaleRatio = CalculateScaleRatio(originalWidth, originalHeight, maxSize, keepOriginalIfSmaller);
// 应用缩放后的尺寸
image.rectTransform.sizeDelta = new Vector2(
originalWidth,
originalHeight
);
// image.rectTransform.sizeDelta = new Vector2(
// originalWidth * scaleRatio,
// originalHeight * scaleRatio
// );
}
public static void ScaleImageWithMaxSize(Image image, float maxSize, bool keepOriginalIfSmaller = false)
{
if (image == null)
{
Debug.LogError("Image组件不能为空");
return;
}
// 获取原始尺寸
float originalWidth, originalHeight;
if (image.sprite != null)
{
// 使用Sprite的原始尺寸
originalWidth = image.sprite.rect.width;
originalHeight = image.sprite.rect.height;
}
else
{
// 没有Sprite时使用当前RectTransform的尺寸
originalWidth = image.rectTransform.rect.width;
originalHeight = image.rectTransform.rect.height;
}
// 计算缩放比例
float scaleRatio = CalculateScaleRatio(originalWidth, originalHeight, maxSize, keepOriginalIfSmaller);
// 应用缩放后的尺寸
image.rectTransform.sizeDelta = new Vector2(
originalWidth * scaleRatio,
originalHeight * scaleRatio
);
}
/// <summary>
/// 计算缩放比例
/// </summary>
private static float CalculateScaleRatio(float originalWidth, float originalHeight, float maxSize,
bool keepOriginalIfSmaller)
{
// 找到原始宽高中的较大值
float maxOriginal = Mathf.Max(originalWidth, originalHeight);
// 如果原图的最大边小于等于限制值,且需要保持原图大小,则不缩放
if (maxOriginal <= maxSize && keepOriginalIfSmaller)
{
return 1f; // 不缩放
}
// 计算缩放比例让最大边刚好等于maxSize
return maxSize / maxOriginal;
}
/// <summary>
/// 保持Image的sizeDelta为原始图片尺寸仅通过修改scale来限制最大显示大小
/// </summary>
/// <param name="image">目标Image组件</param>
/// <param name="maxSize">最大显示尺寸(图片的宽或高中较大者不会超过此值)</param>
/// <param name="keepOriginalIfSmaller">如果原始尺寸小于maxSize是否保持原始大小</param>
public static void ScaleImageWithMaxSize_Scale(Image image, float maxSize, bool keepOriginalIfSmaller = false)
{
if (image == null)
{
Debug.LogError("Image组件不能为空");
return;
}
// 获取原始图片尺寸(像素尺寸)
float originalWidth, originalHeight;
if (image.sprite != null)
{
// 使用Sprite的原始像素尺寸
originalWidth = image.sprite.rect.width;
originalHeight = image.sprite.rect.height;
}
else
{
// 没有Sprite时使用当前RectTransform的尺寸作为原始尺寸
originalWidth = image.rectTransform.rect.width;
originalHeight = image.rectTransform.rect.height;
}
// 将sizeDelta设置为原始图片尺寸保持像素尺寸不变
image.rectTransform.sizeDelta = new Vector2(originalWidth, originalHeight);
// 计算缩放比例
float scaleRatio = CalculateScaleRatio_Scale(originalWidth, originalHeight, maxSize, keepOriginalIfSmaller);
// 仅修改scale来限制最大显示大小
image.rectTransform.localScale = Vector3.one * scaleRatio;
}
/// <summary>
/// 计算缩放比例
/// </summary>
private static float CalculateScaleRatio_Scale(float width, float height, float maxSize,
bool keepOriginalIfSmaller)
{
if (width <= 0 || height <= 0) return 1f;
// 计算原始尺寸中较大的一边
float maxDimension = Mathf.Max(width, height);
// 如果原始尺寸小于maxSize且需要保持原始大小则不缩放
if (maxDimension <= maxSize && keepOriginalIfSmaller)
{
return 1f;
}
// 计算缩放比例确保最大边不超过maxSize
return maxSize / maxDimension;
}
public static void ScaleImageWithMinSize(Image image, float minSize, bool keepOriginalIfLarger = false)
{
Debug.Log(minSize);
if (image == null)
{
Debug.LogError("Image组件不能为空");
return;
}
// 获取原始图片尺寸(像素尺寸)
float originalWidth, originalHeight;
if (image.sprite != null)
{
// 使用Sprite的原始像素尺寸
originalWidth = image.sprite.rect.width;
originalHeight = image.sprite.rect.height;
}
else
{
// 没有Sprite时使用当前RectTransform的尺寸作为原始尺寸
originalWidth = image.rectTransform.rect.width;
originalHeight = image.rectTransform.rect.height;
}
// 将sizeDelta设置为原始图片尺寸保持像素尺寸不变
image.rectTransform.sizeDelta = new Vector2(originalWidth, originalHeight);
// 计算缩放比例
float scaleRatio = CalculateScaleRatio_Min(originalWidth, originalHeight, minSize, keepOriginalIfLarger);
// 应用缩放比例
image.rectTransform.localScale = Vector3.one * scaleRatio;
}
/// <summary>
/// 计算缩放到最小尺寸的比例
/// </summary>
private static float CalculateScaleRatio_Min(float width, float height, float minSize,
bool keepOriginalIfLarger)
{
if (width <= 0 || height <= 0) return 1f;
// 计算原始尺寸中较小的一边
float minDimension = Mathf.Min(width, height);
// 如果原始尺寸大于minSize且需要保持原始大小则不缩放
if (minDimension >= minSize && keepOriginalIfLarger)
{
return 1f;
}
// 计算缩放比例确保最小边不小于minSize
return minSize / minDimension;
}
}
}