feat: 双Pass膨胀描边shader替代LineRenderer

- 新增 Custom/OutlineUnlit shader: Pass1膨胀描边(Cull Front)+Pass2内芯填充
- BlueOutline.mat: 蓝色描边+半透蓝填充
- TouchPositionHandler改用MeshRenderer.enabled闪烁
- 球体挂MeshRenderer+Outline材质,0.4s闪烁
This commit is contained in:
yangbear
2026-06-30 03:02:12 +08:00
parent 542268932d
commit 524ad732f9
7 changed files with 131 additions and 68 deletions
@@ -1,8 +1,8 @@
using UnityEngine;
/// <summary>
/// 挂在 touchArray 的每个子球体上,点击时把 woman 移动到 womanPointArray 对应位置。
/// 两个交叉圆环形成球形轮廓闪烁提示。
/// 挂在 touchArray 子球体上。球体用双Pass膨胀描边shaderCustom/OutlineUnlit),
/// 闪烁提示用户点击。点击后移动到对应位置并顺序显示下一个
/// </summary>
public class TouchPositionHandler : MonoBehaviour
{
@@ -10,73 +10,20 @@ public class TouchPositionHandler : MonoBehaviour
public GameObject womanObject;
public GameObject nextTouchObject;
private LineRenderer _ringH; // 水平环
private LineRenderer _ringV; // 垂直环
private MeshRenderer _meshRenderer;
private void Start()
{
var mr = GetComponent<MeshRenderer>();
if (mr != null) mr.enabled = false;
CreateCrossRings();
StartCoroutine(BlinkRings());
_meshRenderer = GetComponent<MeshRenderer>();
StartCoroutine(BlinkMesh());
}
private void CreateCrossRings()
{
float r = 0.15f;
int segs = 32;
float yOff = 0.05f;
Color blue = new Color(0.2f, 0.5f, 1f);
// 水平环 —— 世界空间 XZ 平面
var hGo = new GameObject("RingH");
hGo.transform.SetParent(transform, false);
_ringH = hGo.AddComponent<LineRenderer>();
SetupRing(_ringH, blue);
_ringH.useWorldSpace = true;
_ringH.positionCount = segs;
Vector3 center = transform.position + Vector3.up * yOff;
for (int i = 0; i < segs; i++)
{
float a = i * 2f * Mathf.PI / segs;
_ringH.SetPosition(i, center + new Vector3(Mathf.Cos(a) * r, 0, Mathf.Sin(a) * r));
}
// 垂直环 —— 世界空间 XY 平面(竖起来)
var vGo = new GameObject("RingV");
vGo.transform.SetParent(transform, false);
_ringV = vGo.AddComponent<LineRenderer>();
SetupRing(_ringV, blue);
_ringV.useWorldSpace = true;
_ringV.positionCount = segs;
for (int i = 0; i < segs; i++)
{
float a = i * 2f * Mathf.PI / segs;
_ringV.SetPosition(i, center + new Vector3(Mathf.Cos(a) * r, Mathf.Sin(a) * r, 0));
}
Debug.Log($"[TouchPosition] {name}: 交叉蓝环已创建 (r={r})");
}
private void SetupRing(LineRenderer lr, Color c)
{
lr.loop = true;
lr.startWidth = 0.06f;
lr.endWidth = 0.06f;
lr.material = new Material(Shader.Find("Unlit/Color"));
lr.material.color = c;
lr.startColor = c;
lr.endColor = c;
}
private System.Collections.IEnumerator BlinkRings()
private System.Collections.IEnumerator BlinkMesh()
{
while (true)
{
bool on = !_ringH.enabled;
if (_ringH != null) _ringH.enabled = on;
if (_ringV != null) _ringV.enabled = on;
if (_meshRenderer != null)
_meshRenderer.enabled = !_meshRenderer.enabled;
yield return new WaitForSeconds(0.4f);
}
}
@@ -91,14 +38,9 @@ public class TouchPositionHandler : MonoBehaviour
womanObject.transform.rotation = targetPosition.rotation;
Debug.Log($"[TouchPosition] woman 移动到 {targetPosition.name}");
}
else
{
Debug.LogWarning($"[TouchPosition] {name}: 引用为空");
}
StopAllCoroutines();
if (_ringH != null) _ringH.enabled = false;
if (_ringV != null) _ringV.enabled = false;
if (_meshRenderer != null) _meshRenderer.enabled = false;
gameObject.SetActive(false);
if (nextTouchObject != null)