当前位置: 首页 > news >正文

unity text 文本符号显示问题与打字机效果的结合

问题1:unity text显示文本时,符号可能显示在某行的开头的位置
问题2:打字机效果没有适配问题1的脚本

解决方法:
问题1:通过遍历text组件每一行数据(第二行开始),如果是符号,就在它之前的字符前添加换行符
问题2:适配上述脚本

脚本1 解决文本符号显示问题
TextSymbolFit.cs

public class TextSymbolFit : Text{/// <summary>/// 用于匹配标点符号/// </summary>private readonly string strRegex = @"\p{P}";/// <summary>/// 用于存储text组件中的内容/// </summary>private System.Text.StringBuilder MExplainText = null;/// <summary>/// 用于存储text生成器中的内容/// </summary>private IList<UILineInfo> MExpalinTextLine;protected override void OnPopulateMesh(VertexHelper toFill){base.OnPopulateMesh(toFill);StartCoroutine(MClearUpExplainMode(this, text));}private IEnumerator MClearUpExplainMode(Text _component, string _text){_component.text = _text;yield return new WaitForEndOfFrame();MExplainText = new System.Text.StringBuilder(_component.text);MExpalinTextLine = _component.cachedTextGenerator.lines;int mChangeIndex;// 从第二行开始进行检测for (int i = 1; i < MExpalinTextLine.Count; i++){try{if (MExpalinTextLine[i].startCharIdx >= _component.text.Length) continue;//首位是否有标点bool match = Regex.IsMatch(MExplainText.ToString()[MExpalinTextLine[i].startCharIdx].ToString(), strRegex);if (match){mChangeIndex = MExpalinTextLine[i].startCharIdx - 1;// 解决联系多个都是标点符号的问题for (int j = MExpalinTextLine[i].startCharIdx - 1; j > 0; j--){match = Regex.IsMatch(MExplainText.ToString()[j].ToString(), strRegex);if (match){mChangeIndex--;}else{break;}}MExplainText.Insert(mChangeIndex, "\n");}}catch (Exception e){Debug.LogException(e);}}_component.text = MExplainText.ToString();}}

脚本2,适配TextSymbolFit脚本
UITextType.cs

public class UITextType : MonoBehaviour{public delegate void OnComplete();[SerializeField] float defaultSpeed = 0.05f;private Text label;private string finalText = string.Empty;private Coroutine typeTextCoroutine;private static readonly string[] uguiSymbols = { "b", "i" };private static readonly string[] uguiCloseSymbols = { "b", "i", "size", "color" };private OnComplete OnCompleteCallback;private void InitText(){if (label == null) label = GetComponent<Text>();}public void Awake(){InitText();}public void SetText(string text, float speed = -1){InitText();defaultSpeed = speed > 0 ? speed : defaultSpeed;finalText = ReplaceSpeed(text);label.text = "";if (typeTextCoroutine != null){StopCoroutine(typeTextCoroutine);typeTextCoroutine = null;}typeTextCoroutine = StartCoroutine(InnerTypeText(text));}public void SkipTypeText(){if (typeTextCoroutine != null){StopCoroutine(typeTextCoroutine);typeTextCoroutine = null;}label.text = finalText;OnCompleteCallback?.Invoke();}public IEnumerator InnerTypeText(string text){string currentText = "";int length = text.Length;float speed = defaultSpeed;bool tagOpened = false;string tagType = "";for (int i = 0; i < length; i++){currentText = "";//匹配speedif (text[i] == '[' && i + 6 < length && text.Substring(i, 7).Equals("[speed=")){string parseSpeed = "";for (int j = i + 7; j < length; j++){if (text[j] == ']'){break;}parseSpeed += text[j];}if (!float.TryParse(parseSpeed, out speed)){speed = defaultSpeed;}i += 8 + parseSpeed.Length - 1;continue;}bool symbolDetected = false;//匹配 <i> 或 <b>for (int j = 0; j < uguiSymbols.Length; j++){string symbol = string.Format("<{0}>", uguiSymbols[j]);if (text[i] == '<' && i + 1 + uguiSymbols[j].Length < length && text.Substring(i, 2 + uguiSymbols[j].Length).Equals(symbol)){currentText += symbol;i += (2 + uguiSymbols[j].Length) - 1;symbolDetected = true;tagOpened = true;tagType = uguiSymbols[j];break;}}//匹配富文本color格式if (text[i] == '<' && i + 1 + 15 < length && text.Substring(i, 2 + 6).Equals("<color=#") && text[i + 16] == '>'){currentText += text.Substring(i, 2 + 6 + 8);i += (2 + 14) - 1;symbolDetected = true;tagOpened = true;tagType = "color";}//匹配富文本size格式if (text[i] == '<' && i + 5 < length && text.Substring(i, 6).Equals("<size=")){string parseSize = "";for (var j = i + 6; j < length; j++){if (text[j] == '>'){break;}parseSize += text[j];}if (int.TryParse(parseSize, out _)){currentText += text.Substring(i, 7 + parseSize.Length);i += (7 + parseSize.Length) - 1;symbolDetected = true;tagOpened = true;tagType = "size";}}//匹配富文本结束 </i> </b> </size> </color>for (int j = 0; j < uguiCloseSymbols.Length; j++){string symbol = string.Format("</{0}>", uguiCloseSymbols[j]);if (text[i] == '<' && i + 2 + uguiCloseSymbols[j].Length < length && text.Substring(i, 3 + uguiCloseSymbols[j].Length).Equals(symbol)){currentText += symbol;i += (3 + uguiCloseSymbols[j].Length) - 1;symbolDetected = true;tagOpened = false;break;}}if (symbolDetected) continue;currentText += text[i];label.text += currentText + (tagOpened ? string.Format("</{0}>", tagType) : "");yield return new WaitForSeconds(speed);}typeTextCoroutine = null;OnCompleteCallback?.Invoke();}private string ReplaceSpeed(string text){return Regex.Replace(text, @"\[speed=\d+(\.\d+)?\]", "");}public bool IsSkippable(){return typeTextCoroutine != null;}public void SetOnComplete(OnComplete onComplete){OnCompleteCallback = onComplete;}}public static class UITypeTextUtility{public static void TypeText(this Text label, string text, float speed = 0.05f, UITextType.OnComplete onComplete = null){if (!label.TryGetComponent<UITextType>(out var typeText)){typeText = label.gameObject.AddComponent<UITextType>();}typeText.SetText(text, speed);typeText.SetOnComplete(onComplete);}public static bool IsSkippable(this Text label){if (!label.TryGetComponent<UITextType>(out var typeText)){typeText = label.gameObject.AddComponent<UITextType>();}return typeText.IsSkippable();}public static void SkipTypeText(this Text label){if (!label.TryGetComponent<UITextType>(out var typeText)){typeText = label.gameObject.AddComponent<UITextType>();}typeText.SkipTypeText();}}

相关文章:

unity text 文本符号显示问题与打字机效果的结合

问题1&#xff1a;unity text显示文本时&#xff0c;符号可能显示在某行的开头的位置 问题2&#xff1a;打字机效果没有适配问题1的脚本 解决方法&#xff1a; 问题1&#xff1a;通过遍历text组件每一行数据(第二行开始)&#xff0c;如果是符号&#xff0c;就在它之前的字符前…...

Netty架构详解

文章目录 概述整体结构Netty的核心组件逻辑架构BootStrap & ServerBootStrapChannelPipelineFuture、回调和 ChannelHandler选择器、事件和 EventLoopChannelHandler的各种ChannelInitializer类图 Protocol Support 协议支持层Transport Service 传输服务层Core 核心层模块…...

Unity自带的WebSocket使用说明

Unity中的WebSocket是一种用于实时性强、低延迟的双向通信的技术。它可以在客户端和服务器之间建立一个持久的连接&#xff0c;允许双方随时互相发送数据。这种实时性使得WebSocket在游戏中非常有用&#xff0c;特别是对于多人在线游戏和实时竞技游戏。 在Unity中&#xff0c;…...

【Web】浅聊XStream反序列化之SortedSetTreeMap利用链

前文&#xff1a;【Web】浅聊XStream反序列化本源之恶意动态代理注入-CSDN博客 前言 在上一篇文章我们聊到可以用XStream反序列化来进行恶意动态代理的注入&#xff0c;但其有一个很大的限制就是必须要知道目标靶机会调用哪个接口的方法&#xff0c;才能去相应地精心构造对应…...

HTML CSS学习

# html css 日常学习记录---学习途径--渡一教育-袁老师# 元素包含关系 以前&#xff1a;块级元素可以包含行级元素&#xff0c;行级元素不可以包含块级元素&#xff0c;a元素除外 元素的包含关系由元素的内容类别决定。 例如&#xff0c;查看h1元素中是否可以包含p元素 总…...

MySQL的事务隔离是如何实现的?

目录 从一个例子说起 快照读和当前读 事务的启动时机和读视图生成的时刻 MVCC 隐藏字段 Undo Log回滚日志 Read View - 读视图 可重复读(RC)隔离级别下的MVCC 读提交(RR)隔离级别下的MCC 关于MVCC的一些疑问 1.为什么需要 MVCC &#xff1f;如果没有 MVCC 会怎样&am…...

STM32电源及时钟介绍

一、STM32最小系统 二、电源电路 2.1供电电压VDD&#xff0c;VSS F103VET6 的引角图 在 F103VET6 的引角图中可找到 49\50 角&#xff0c; 74\75 角&#xff0c; 99\100 角&#xff0c; 27\28角&#xff0c;10 \11角一共 5 对的VDD&#xff0c;VSS&#xff0c;也就是给我们芯片…...

使用公式在Excel中指定列值的变化实现自动间隔着色(不是按照固定的行数)

如果你的文件很小&#xff0c;可以手工着色&#xff1b;但如果很大&#xff0c;就要借助公式来着色&#xff1b; 目的是什么&#xff0c;其中之一是&#xff1a;提升可读性。 一起往下看吧&#xff01;&#xff01; 如果你想要根据Excel某列中值的变化来间隔着色&#xff0c;…...

蚓链给传统供应链的数字化解决方案会带来什么价值呢?

传统供应链在蚓链数字化的加持下&#xff0c;通过互相融合、结合将为数字经济带来多方面的影响和变革&#xff0c;包括但不限于以下几点&#xff1a; 1. 提高效率和降低成本&#xff1a;数字化可以优化供应链中的各个环节&#xff0c;例如采购、生产、物流和销售等&#xff0…...

有来团队后台项目-解析8

UnoCss 介绍 UnoCss 官网UnoCss 官网 安装 pnpm add -D unocss引入 vite.config.ts import UnoCSS from unocss/vite // plugins 中引入 UnoCSS({/* options */ }),创建uno.config.ts // uno.config.ts import {defineConfig,presetAttributify,presetIcons,presetTyp…...

vs2022的下载及安装教程(Visual Studio 2022)

vs简介 Visual Studio在团队项目开发中使用非常多且功能强大&#xff0c;支持开发人员编写跨平台的应用程序;Microsoft Visual C 2022正式版(VC2022运行库)&#xff0c;具有程序框架自动生成&#xff0c;灵活方便的类管理&#xff0c;强大的代码编写等功能&#xff0c;可提供编…...

BFS(宽度优先搜索)C++(Acwing)

代码&#xff1a; #include <cstring> #include <iostream> #include <algorithm>using namespace std;typedef pair<int, int> PII;const int N 110;int n, m; int g[N][N]; int d[N][N]; PII q[N * N];int bfs() {int hh 0, tt 0;q[0] {0, 0};m…...

信息收集:端口扫描原理,端口扫描分类,端口扫描工具,手动判断操作系统,操作系统识别工具

「作者主页」&#xff1a;士别三日wyx 「作者简介」&#xff1a;CSDN top100、阿里云博客专家、华为云享专家、网络安全领域优质创作者 「专栏简介」&#xff1a;此文章已录入专栏《网络安全自学教程》 端口&系统版本 一、端口扫描1、telnet2、Nmap3、Masscan4、端口扫描原…...

【Tauri】(5):本地运行candle和 qwen 大模型,并测试速度

1&#xff0c;本地运行candle 关于candle项目 https://github.com/huggingface/candle Hugging Face 使用rust开发的高性能推理框架。 语法简单&#xff0c; 风格与 PyTorch 相似。 CPU 和 Cuda Backend&#xff1a;m1、f16、bf16。 支持 Serverless&#xff08;CPU&#xff…...

基于udp协议的cs网络通信代码(echo版+命令行输入版+执行指令版),netstat指令

目录 引入 基础版 服务端 思路 头文件log类 套接字的初始化 思路 代码 服务器开始运行 思路 代码 注意点 -- ip地址和端口号的来源 ip地址的选择 本地环回地址 端口号 ​编辑 运行情况 netstat -nlup 客户端 思路 初始化 思路 代码 客户端的运行 思…...

centos7网络命令:ping、dig、nsloopup、tcpdump

目录 一、ping1、命令参数&#xff1a;2、示例-将当前的信息打印到一个文件中3、示例-结束进程 二、dig1、安装2、语法格式选项说明 3、示例4、示例-将当前的信息打印到一个文件中 三、nslookup1、安装2、语法格式选项说明 3、示例 四、tcpdump抓包1、安装2、语法格式&#xff…...

Excel判断CD两列在EF两列的列表中是否存在

需求 需要将CD两列的ID和NAME组合起来&#xff0c;查询EF两列的ID和NAME组合起来的列表中是否存在&#xff1f; 比如&#xff0c;判断第二行的“123456ABC”在EF的第二行到第四行中是否存在&#xff0c;若存在则显示Y&#xff0c;不存在则显示N 实现的计算公式 IF(ISNUMBER…...

基于斑翠鸟优化算法(Pied Kingfisher Optimizer ,PKO)的无人机三维路径规划(MATLAB)

一、无人机路径规划模型介绍 二、算法介绍 斑翠鸟优化算法(Pied Kingfisher Optimizer ,PKO),是由Abdelazim Hussien于2024年提出的一种基于群体的新型元启发式算法,它从自然界中观察到的斑翠鸟独特的狩猎行为和共生关系中汲取灵感。PKO 算法围绕三个不同的阶段构建:栖息…...

同程旅行前端面试汇总

一、同程旅行一面 自我介绍技术提问 打开新的tab页、window.open是否共享sessionStorage存储的数据vue、react 源码有没有看过&#xff0c;说一下react17 与 react18区别webpack中loader与plugin&#xff0c;有没有自己写过vuex、reactx 刷新数据丢失 怎么做的持久化 反问 总…...

小美的平衡矩阵_dp思路

小美的平衡矩阵 写在前面: 本博客只是一种解题思路的提供。 小美的平衡矩阵 题目描述&#xff1a; 小美拿到了一个n*n 的矩阵&#xff0c;其中每个元素是 0 或者 1。 小美认为一个矩形区域是完美的&#xff0c;当且仅当该区域内 0 的数量恰好等于 1 的数量。 现在&#xf…...

Python爬虫实战:研究MechanicalSoup库相关技术

一、MechanicalSoup 库概述 1.1 库简介 MechanicalSoup 是一个 Python 库,专为自动化交互网站而设计。它结合了 requests 的 HTTP 请求能力和 BeautifulSoup 的 HTML 解析能力,提供了直观的 API,让我们可以像人类用户一样浏览网页、填写表单和提交请求。 1.2 主要功能特点…...

中南大学无人机智能体的全面评估!BEDI:用于评估无人机上具身智能体的综合性基准测试

作者&#xff1a;Mingning Guo, Mengwei Wu, Jiarun He, Shaoxian Li, Haifeng Li, Chao Tao单位&#xff1a;中南大学地球科学与信息物理学院论文标题&#xff1a;BEDI: A Comprehensive Benchmark for Evaluating Embodied Agents on UAVs论文链接&#xff1a;https://arxiv.…...

mongodb源码分析session执行handleRequest命令find过程

mongo/transport/service_state_machine.cpp已经分析startSession创建ASIOSession过程&#xff0c;并且验证connection是否超过限制ASIOSession和connection是循环接受客户端命令&#xff0c;把数据流转换成Message&#xff0c;状态转变流程是&#xff1a;State::Created 》 St…...

UR 协作机器人「三剑客」:精密轻量担当(UR7e)、全能协作主力(UR12e)、重型任务专家(UR15)

UR协作机器人正以其卓越性能在现代制造业自动化中扮演重要角色。UR7e、UR12e和UR15通过创新技术和精准设计满足了不同行业的多样化需求。其中&#xff0c;UR15以其速度、精度及人工智能准备能力成为自动化领域的重要突破。UR7e和UR12e则在负载规格和市场定位上不断优化&#xf…...

聊一聊接口测试的意义有哪些?

目录 一、隔离性 & 早期测试 二、保障系统集成质量 三、验证业务逻辑的核心层 四、提升测试效率与覆盖度 五、系统稳定性的守护者 六、驱动团队协作与契约管理 七、性能与扩展性的前置评估 八、持续交付的核心支撑 接口测试的意义可以从四个维度展开&#xff0c;首…...

HashMap中的put方法执行流程(流程图)

1 put操作整体流程 HashMap 的 put 操作是其最核心的功能之一。在 JDK 1.8 及以后版本中&#xff0c;其主要逻辑封装在 putVal 这个内部方法中。整个过程大致如下&#xff1a; 初始判断与哈希计算&#xff1a; 首先&#xff0c;putVal 方法会检查当前的 table&#xff08;也就…...

C++使用 new 来创建动态数组

问题&#xff1a; 不能使用变量定义数组大小 原因&#xff1a; 这是因为数组在内存中是连续存储的&#xff0c;编译器需要在编译阶段就确定数组的大小&#xff0c;以便正确地分配内存空间。如果允许使用变量来定义数组的大小&#xff0c;那么编译器就无法在编译时确定数组的大…...

在树莓派上添加音频输入设备的几种方法

在树莓派上添加音频输入设备可以通过以下步骤完成&#xff0c;具体方法取决于设备类型&#xff08;如USB麦克风、3.5mm接口麦克风或HDMI音频输入&#xff09;。以下是详细指南&#xff1a; 1. 连接音频输入设备 USB麦克风/声卡&#xff1a;直接插入树莓派的USB接口。3.5mm麦克…...

深入浅出Diffusion模型:从原理到实践的全方位教程

I. 引言&#xff1a;生成式AI的黎明 – Diffusion模型是什么&#xff1f; 近年来&#xff0c;生成式人工智能&#xff08;Generative AI&#xff09;领域取得了爆炸性的进展&#xff0c;模型能够根据简单的文本提示创作出逼真的图像、连贯的文本&#xff0c;乃至更多令人惊叹的…...

AxureRP-Pro-Beta-Setup_114413.exe (6.0.0.2887)

Name&#xff1a;3ddown Serial&#xff1a;FiCGEezgdGoYILo8U/2MFyCWj0jZoJc/sziRRj2/ENvtEq7w1RH97k5MWctqVHA 注册用户名&#xff1a;Axure 序列号&#xff1a;8t3Yk/zu4cX601/seX6wBZgYRVj/lkC2PICCdO4sFKCCLx8mcCnccoylVb40lP...