存档
This commit is contained in:
@@ -1,3 +1,4 @@
|
||||
using Assets.MyGame.Scripts.Net;
|
||||
using TMPro;
|
||||
using UnityEngine;
|
||||
using UnityEngine.EventSystems;
|
||||
@@ -10,17 +11,14 @@ using UnityEngine.UI;
|
||||
/// RawImage (prizeImage) ← 最下层:奖品图
|
||||
/// Text (tmp_AwardName) ← 中间层:奖品文字
|
||||
/// RawImage (scratchImage) ← 最上层:涂层遮罩(挂本脚本)
|
||||
///
|
||||
/// 原理:
|
||||
/// 涂层遮罩用 ScratchMask.shader,遮罩 RT 全白 = 不透明(未刮),
|
||||
/// 全黑 = 透明(已刮)。刮擦通过 Graphics.Blit + ScratchErase.shader
|
||||
/// 在 GPU 内完成,零 CPU 像素操作。
|
||||
/// </summary>
|
||||
public class GuaGuaLeGPU : SubUIBase, IPointerDownHandler, IDragHandler
|
||||
{
|
||||
[Header("UI 引用(必填)")]
|
||||
public RawImage scratchImage; // 最上层:涂层遮罩(挂此脚本)
|
||||
public TextMeshProUGUI tmp_AwardName; // 中间层:奖品文字
|
||||
public TextMeshProUGUI tmp_AwardName; // 中间层:奖品文字
|
||||
public GuaGuaLeItem giftPrefab; // 奖品预制体(用于显示奖品图片)
|
||||
public Transform giftPrefabParent;
|
||||
|
||||
[Header("材质(模板)")]
|
||||
public Material maskMat; // 使用 ScratchMask.shader(涂层遮罩)
|
||||
@@ -36,10 +34,6 @@ public class GuaGuaLeGPU : SubUIBase, IPointerDownHandler, IDragHandler
|
||||
[Range(0f, 1f)] public float revealThreshold = 0.6f;
|
||||
public bool autoReveal = true;
|
||||
|
||||
[Header("奖品配置")]
|
||||
public string[] awards = { "谢谢参与", "一等奖", "二等奖", "三等奖", "再来一次" };
|
||||
public float[] awardWeights = { 0.50f, 0.05f, 0.10f, 0.15f, 0.20f };
|
||||
|
||||
[Header("事件")]
|
||||
public UnityEngine.Events.UnityEvent onRevealed;
|
||||
|
||||
@@ -59,30 +53,24 @@ public class GuaGuaLeGPU : SubUIBase, IPointerDownHandler, IDragHandler
|
||||
|
||||
private Texture2D progressReadTex;
|
||||
private int dragCount;
|
||||
|
||||
protected override void OnShow(object args = null)
|
||||
{
|
||||
base.OnShow(args);
|
||||
ResetCard();
|
||||
}
|
||||
|
||||
private void Start()
|
||||
{
|
||||
if (scratchImage == null) { Debug.LogError("[GPU] scratchImage 为空!"); return; }
|
||||
if (maskMat == null) { Debug.LogError("[GPU] maskMat 为空!"); return; }
|
||||
if (eraseMat == null) { Debug.LogError("[GPU] eraseMat 为空!"); return; }
|
||||
|
||||
if (awardWeights == null || awardWeights.Length != awards.Length)
|
||||
{
|
||||
awardWeights = new float[awards.Length];
|
||||
float w = 1f / Mathf.Max(1, awards.Length);
|
||||
for (int i = 0; i < awardWeights.Length; i++) awardWeights[i] = w;
|
||||
}
|
||||
|
||||
InitCard();
|
||||
}
|
||||
|
||||
private void InitCard()
|
||||
{
|
||||
// 1. 遮罩 RT(全白 = 未刮,不透明)
|
||||
maskRT = new RenderTexture(rtWidth, rtHeight, 0, RenderTextureFormat.ARGB32)
|
||||
{
|
||||
filterMode = FilterMode.Bilinear
|
||||
@@ -90,9 +78,6 @@ public class GuaGuaLeGPU : SubUIBase, IPointerDownHandler, IDragHandler
|
||||
maskRT.Create();
|
||||
ClearRT(maskRT, Color.white);
|
||||
|
||||
|
||||
|
||||
// 3. 最上层:涂层遮罩材质(实例化,避免 UGUI 材质共享问题)
|
||||
instanceMaskMat = new Material(maskMat);
|
||||
instanceMaskMat.SetTexture("_MaskTex", maskRT);
|
||||
instanceMaskMat.SetColor("_CoatColor", coatColor);
|
||||
@@ -100,20 +85,13 @@ public class GuaGuaLeGPU : SubUIBase, IPointerDownHandler, IDragHandler
|
||||
scratchImage.material = instanceMaskMat;
|
||||
scratchImage.texture = null;
|
||||
|
||||
// 4. 擦除材质实例
|
||||
instanceEraseMat = new Material(eraseMat);
|
||||
instanceEraseMat.SetFloat("_BrushSize", brushSize);
|
||||
|
||||
// 5. 摇奖
|
||||
currentAward = RollAward();
|
||||
if (tmp_AwardName != null)
|
||||
tmp_AwardName.text = currentAward;
|
||||
|
||||
// 6. 进度读取用纹理
|
||||
progressReadTex = new Texture2D(rtWidth, rtHeight, TextureFormat.ARGB32, false);
|
||||
|
||||
ResetState();
|
||||
Debug.Log($"[GPU] 初始化完成 {rtWidth}x{rtHeight}");
|
||||
FetchAward();
|
||||
}
|
||||
|
||||
private void ResetState()
|
||||
@@ -124,6 +102,34 @@ public class GuaGuaLeGPU : SubUIBase, IPointerDownHandler, IDragHandler
|
||||
dragCount = 0;
|
||||
}
|
||||
|
||||
// ================================================================
|
||||
// API 抽奖
|
||||
// ================================================================
|
||||
|
||||
private void FetchAward()
|
||||
{
|
||||
APIRequestList.ScratchCardDraw(result =>
|
||||
{
|
||||
if (result == null) return;
|
||||
|
||||
currentAward = result.prizeName ?? "谢谢参与";
|
||||
if (tmp_AwardName != null)
|
||||
tmp_AwardName.text = currentAward;
|
||||
|
||||
// 清除旧的奖励物品
|
||||
for (int i = giftPrefabParent.childCount - 1; i >= 0; i--)
|
||||
Destroy(giftPrefabParent.GetChild(i).gameObject);
|
||||
|
||||
// 显示奖品图片(baseProduct.imageUrl)
|
||||
string imgUrl = result.baseProduct?.imageUrl;
|
||||
if (!string.IsNullOrEmpty(imgUrl) && giftPrefab != null)
|
||||
{
|
||||
var item = Instantiate(giftPrefab, giftPrefabParent);
|
||||
item.Init(imgUrl, result.count);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
// ================================================================
|
||||
// 公开方法
|
||||
// ================================================================
|
||||
@@ -135,12 +141,10 @@ public class GuaGuaLeGPU : SubUIBase, IPointerDownHandler, IDragHandler
|
||||
ClearRT(maskRT, Color.white);
|
||||
ResetState();
|
||||
|
||||
currentAward = RollAward();
|
||||
if (tmp_AwardName != null)
|
||||
tmp_AwardName.text = currentAward;
|
||||
|
||||
if (instanceMaskMat != null)
|
||||
instanceMaskMat.SetColor("_CoatColor", coatColor);
|
||||
|
||||
FetchAward();
|
||||
}
|
||||
|
||||
public void RevealAll()
|
||||
@@ -284,26 +288,6 @@ public class GuaGuaLeGPU : SubUIBase, IPointerDownHandler, IDragHandler
|
||||
return uv.x >= 0f && uv.x <= 1f && uv.y >= 0f && uv.y <= 1f;
|
||||
}
|
||||
|
||||
private string RollAward()
|
||||
{
|
||||
if (awards == null || awards.Length == 0) return "谢谢参与";
|
||||
int n = Mathf.Min(awards.Length, awardWeights == null ? 0 : awardWeights.Length);
|
||||
if (n <= 0) return awards[0];
|
||||
|
||||
float sum = 0f;
|
||||
for (int i = 0; i < n; i++) sum += Mathf.Max(0f, awardWeights[i]);
|
||||
if (sum <= 0f) return awards[0];
|
||||
|
||||
float r = Random.value * sum;
|
||||
float acc = 0f;
|
||||
for (int i = 0; i < n; i++)
|
||||
{
|
||||
acc += Mathf.Max(0f, awardWeights[i]);
|
||||
if (r <= acc) return awards[i];
|
||||
}
|
||||
return awards[n - 1];
|
||||
}
|
||||
|
||||
public string CurrentAward => currentAward;
|
||||
public bool IsRevealed => isRevealed;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user