Unity Text超框 文字滚动循环显示
//container Text
using System.Collections;
using System.Collections.Generic;
using Unity.VisualScripting;
using UnityEngine;
using UnityEngine.UI;
public class AutoScrollText : MonoBehaviour
{
private Text[] _texts = new Text[2];
private RectTransform _container;
private RectTransform _mask;
[SerializeField] private string _txt; //显示文本
[SerializeField] private float _speed = 30f; //滚动速度
[SerializeField] private float _space; //间距
[SerializeField] private float _overall; //字体长度
[SerializeField] private float _overall2; //总长度
[SerializeField] private float _leftBound = 0;// 左边界
[SerializeField] private bool _scroll = false; //是否滚动
private float _startTime;//开始滚动时间
private void Awake()
{
_mask = this.GetComponent<RectTransform>();
_container = transform.GetChild(0).GetComponent<RectTransform>();
_texts[0] = _container.GetChild(0).GetComponent<Text>();
_texts[1] = _container.GetChild(1).GetComponent<Text>();
_container.pivot = new Vector2(0, 0.5f);
_texts[0].rectTransform.pivot = new Vector2(0, 0.5f);
_texts[1].rectTransform.pivot = new Vector2(0, 0.5f);
var size = _texts[0].gameObject.GetOrAddComponent<ContentSizeFitter>();
size.horizontalFit = ContentSizeFitter.FitMode.PreferredSize;
size = _texts[1].gameObject.GetOrAddComponent<ContentSizeFitter>();
size.horizontalFit = ContentSizeFitter.FitMode.PreferredSize;
}
private void Start()
{
//SetText(_txt,false);
}
private void FixedUpdate()
{
if (_scroll && Time.time > _startTime)
{
if (_container.localPosition.x < -10000000)
{
ResetContainer();
}
// 容器 移动
_container.localPosition += Vector3.left * Time.fixedDeltaTime * _speed;
//文本 位置 更新
for (int i = 0; i < _texts.Length; ++i)
{
if (_texts[i].rectTransform.localPosition.x + _container.localPosition.x < _leftBound)
{
SetToNextViewPos(i);
}
}
}
}
public void StopScroll()//停止 滚动
{
ResetContainer(true);
}
public void StartScroll() //开始 滚动
{
ResetContainer();
}
public void SetText(string _txt, bool IsStopScroll = true)
{
this._txt = _txt;
_texts[0].text = _txt;
_texts[1].text = _txt;
ResetContainer(IsStopScroll);
}
private void ResetContainer(bool IsStopScroll = false)//重置
{
_startTime = Time.time + 0.5f;
_container.localPosition = new Vector2(_mask.rect.xMin + 5f, _container.localPosition.y);
_texts[0].rectTransform.localPosition = new Vector2(0, _texts[0].rectTransform.localPosition.y);
LayoutRebuilder.ForceRebuildLayoutImmediate(_texts[0].rectTransform);
if (!IsStopScroll && _texts[0].rectTransform.rect.width > _mask.rect.width)
{
var relative = new Vector2(-_texts[0].rectTransform.rect.width + _mask.rect.min.x, _mask.rect.min.y);
_leftBound = relative.x;
_overall = _space + _texts[0].rectTransform.rect.width;
_overall2 = _overall * 2;
_texts[1].rectTransform.localPosition = _texts[0].rectTransform.localPosition + Vector3.right * _overall;
_scroll = true;
_texts[1].gameObject.SetActive(true);
}
else
{
_texts[1].gameObject.SetActive(false);
_scroll = false;
}
}
private void SetToNextViewPos(int index)//文本位置 交替
{
var count = Mathf.FloorToInt(-_container.localPosition.x / _overall2);
var len = (-_container.localPosition.x) % _overall2;
var x = len > _overall ? _overall2 * (count + 1) : _overall2 * count;
x += index * _overall;
_texts[index].rectTransform.localPosition = new Vector2(x, _texts[index].rectTransform.localPosition.y);
}
}