游戏蛮牛学习群(纯技术交流,不闲聊):159852603
游戏蛮牛 手机端
开启辅助访问
 找回密码
 注册帐号

扫一扫,访问微社区

开发者专栏

关注:2332

当前位置:游戏蛮牛 技术专区 开发者专栏

__________________________________________________________________________________
开发者干货区版块规则:

  1、文章必须是图文形式。(至少2幅图)
      2、文章字数必须保持在1500字节以上。(编辑器右下角有字数检查)
      3、本版块只支持在游戏蛮牛原创首发,不支持转载。
      4、本版块回复不得无意义,如:顶、呵呵、不错......【真的会扣分的哦】
      5、......
__________________________________________________________________________________
查看: 909|回复: 46

[zhang273162308] Unity实用小工具或脚本——屏幕消息打印显示

[复制链接]  [移动端链接]
排名
143
昨日变化

114

主题

550

帖子

6666

积分

Rank: 9Rank: 9Rank: 9

UID
3579
好友
103
蛮牛币
4358
威望
0
注册时间
2013-9-10
在线时间
1413 小时
最后登录
2018-10-19

专栏作家社区QQ达人活力之星游戏蛮牛QQ群会员蛮牛哥

发表于 2018-9-11 16:15:30 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有帐号?注册帐号

x
一、前言
       在屏幕上打印游戏中的消息是经常需要的功能,本文实现一个带有一定特色的文字消息打印,效果如图所示:消息列表框会根据消息缓存的行数来决定显示速度,如果缓存列表里存储的消息行数比较多,则显示的速度会加快。另外,在打印消息的时候,还加入了一个输入光标“-”在每行消息的末尾,消息打印完毕则隐藏。该效果是在Unity的UGUI里实现,一个文本Text显示控件+一个背景图就可以搞定了。

printMessageShow.gif
二、实现
1、主要思路:先将消息按照一行一条存储到列表中;然后取出一条进行逐字符打印,并且删除列表中这一行。
[C#] 纯文本查看 复制代码
        if(listMessage.Count>0)
        {
            if(!isPrinting)
            {
                isPrinting = true;
                string tempPrintStr = listMessage[0];
                listMessage.RemoveAt(0);
                StartCoroutine(PrintMessage(tempPrintStr));
            }
        }


打印这一行消息的时候,首先将其转化成字符数组,然后按照一次显示的文字行数= 预设值的固定值 + 列表中存储的消息行数
如果队列中存储了很多待显示的消息,则加快显示的速度。在显示的过程中先产出尾部的光标(如果有的话),然后按照一次将要显示的文字个数将当前这条要显示的消息文字添加进来;接着追加上光标,如果超过了最大显示的行数,则删除;最后,文字显示结束后再次删除光标。

[C#] 纯文本查看 复制代码
 char[] tempMesCharactors = new char[256];

        //删除超过存储空间的文字
        if(255<strMes.Length)
        {
            strMes = strMes.Substring(0, 254);
        }
        //将每个文字分割开
        tempMesCharactors = strMes.ToCharArray();
        //获取当前已经显示的文字
        string tempCurScreenShowText = uiTextshowMessage.text;
        tempCurScreenShowText += "\n";

        //一次显示的文字行数= 预设值的固定值 + 列表中存储的消息行数
        //如果队列中存储了很多待显示的消息,则加快显示的速度
        int tempAdditionNum = ADDITION_NUM + listMessage.Count;

        for (int i = 0; i < tempMesCharactors.Length; i+=tempAdditionNum)
        {
            //暂时删除尾部的光标
            if (tempCurScreenShowText.EndsWith(CURSOR_STR))
            {
                tempCurScreenShowText = tempCurScreenShowText.Remove(tempCurScreenShowText.Length - 1);
            }

            //按照一次显示tempAdditionNum个将当前这条要显示的消息文字添加进来
            for (int j = 0; j < tempAdditionNum; j++)
            {
                if(i+j>=tempMesCharactors.Length)
                {
                    break;
                }
                tempCurScreenShowText += tempMesCharactors[i + j];
            }

            //追加光标
            tempCurScreenShowText += CURSOR_STR;
            //删除超过画面外的行
            string[] tempLines = tempCurScreenShowText.Split('\n');
            if(MAX_ROW_COUNT<tempLines.Length)
            {
                tempCurScreenShowText = "";
                //从后往前追加MAX_ROW_COUNT行
                for (int j = tempLines.Length-MAX_ROW_COUNT; j < tempLines.Length; j++)
                {
                    tempCurScreenShowText += tempLines[j];
                    if(j<tempLines.Length-1)
                    {
                        tempCurScreenShowText += "\n";
                    }
                }
            }

            uiTextshowMessage.text = tempCurScreenShowText;

            yield return new WaitForSeconds(0.001f);
        }

        //文字显示结束后,隐藏光标
        if(tempCurScreenShowText.EndsWith(CURSOR_STR))
        {
            tempCurScreenShowText = tempCurScreenShowText.Remove(tempCurScreenShowText.Length - 1);
            uiTextshowMessage.text = tempCurScreenShowText;
        }


2、完整的脚本代码
[C#] 纯文本查看 复制代码
using System.Collections;
using System.Collections.Generic;
using TMPro;
using UnityEngine;
using UnityEngine.UI;

public class ScreenMessageCtr : MonoBehaviour {

    public static ScreenMessageCtr M_Instance
    {
        get
        {
            if(null==_instance)
            {
                _instance = FindObjectOfType<ScreenMessageCtr>();
            }
            return _instance;
        }
    }
    [SerializeField]
    private  TextMeshProUGUI uiTextshowMessage;

    private static ScreenMessageCtr _instance;

    private List<string> listMessage = new List<string>();
    private bool isPrinting = false;

    /// <summary>
    /// 显示的最大行数
    /// </summary>
    private const int MAX_ROW_COUNT = 6;
    /// <summary>
    /// 一次显示的字符数
    /// </summary>
    private const int ADDITION_NUM = 1;
    /// <summary>
    /// 光标文字
    /// </summary>
    private const string CURSOR_STR = "_";

    private int textNum = 0;
        // Use this for initialization
        void Start () {
        // 向sub screen添加换行(为了让第一条消息从最下面开始显示)
        uiTextshowMessage.text = "\n\n\n\n\n\n";
        // 游戏开始时显示消息
        AddMessage("Start PrintMessage");
        AddMessage(" ");
    }
        
        // Update is called once per frame
        void Update () {

        if(Input.GetKey(KeyCode.Space))
        {
            string textMes = "This is text message type one:" + textNum++;
            AddMessage(textMes);
        }

                if(listMessage.Count>0)
        {
            if(!isPrinting)
            {
                isPrinting = true;
                string tempPrintStr = listMessage[0];
                listMessage.RemoveAt(0);
                StartCoroutine(PrintMessage(tempPrintStr));
            }
        }
        }

    private IEnumerator PrintMessage(string strMes)
    {
        char[] tempMesCharactors = new char[256];

        //删除超过存储空间的文字
        if(255<strMes.Length)
        {
            strMes = strMes.Substring(0, 254);
        }
        //将每个文字分割开
        tempMesCharactors = strMes.ToCharArray();
        //获取当前已经显示的文字
        string tempCurScreenShowText = uiTextshowMessage.text;
        tempCurScreenShowText += "\n";

        //一次显示的文字行数= 预设值的固定值 + 列表中存储的消息行数
        //如果队列中存储了很多待显示的消息,则加快显示的速度
        int tempAdditionNum = ADDITION_NUM + listMessage.Count;

        for (int i = 0; i < tempMesCharactors.Length; i+=tempAdditionNum)
        {
            //暂时删除尾部的光标
            if (tempCurScreenShowText.EndsWith(CURSOR_STR))
            {
                tempCurScreenShowText = tempCurScreenShowText.Remove(tempCurScreenShowText.Length - 1);
            }

            //按照一次显示tempAdditionNum个将当前这条要显示的消息文字添加进来
            for (int j = 0; j < tempAdditionNum; j++)
            {
                if(i+j>=tempMesCharactors.Length)
                {
                    break;
                }
                tempCurScreenShowText += tempMesCharactors[i + j];
            }

            //追加光标
            tempCurScreenShowText += CURSOR_STR;
            //删除超过画面外的行
            string[] tempLines = tempCurScreenShowText.Split('\n');
            if(MAX_ROW_COUNT<tempLines.Length)
            {
                tempCurScreenShowText = "";
                //从后往前追加MAX_ROW_COUNT行
                for (int j = tempLines.Length-MAX_ROW_COUNT; j < tempLines.Length; j++)
                {
                    tempCurScreenShowText += tempLines[j];
                    if(j<tempLines.Length-1)
                    {
                        tempCurScreenShowText += "\n";
                    }
                }
            }

            uiTextshowMessage.text = tempCurScreenShowText;

            yield return new WaitForSeconds(0.001f);
        }

        //文字显示结束后,隐藏光标
        if(tempCurScreenShowText.EndsWith(CURSOR_STR))
        {
            tempCurScreenShowText = tempCurScreenShowText.Remove(tempCurScreenShowText.Length - 1);
            uiTextshowMessage.text = tempCurScreenShowText;
        }

        //结束显示处理
        isPrinting = false;
    }

    public void AddMessage(string mes)
    {
        listMessage.Add(mes);
    }
}


三、总结
1、能够同时存储N条数据,然后逐条逐字显示,在打印显示的过程中还有光标的效果,视觉感比较好
2、同时存储的信息再多也能显示出来,但是一条信息不能超过字符数组的长度,我这里设置为256,如果超过了就去掉,这里还可以优化一下
3、工程地址
游客,如果您要查看本帖隐藏内容请回复










回复

使用道具 举报

7日久生情
1508/5000
排名
1703
昨日变化
3

20

主题

195

帖子

1508

积分

Rank: 7Rank: 7Rank: 7Rank: 7

UID
225323
好友
1
蛮牛币
464
威望
0
注册时间
2017-6-5
在线时间
573 小时
最后登录
2018-10-18
发表于 2018-9-11 17:19:53 | 显示全部楼层
非常实用的Debug小工具~!

回复 支持 反对

使用道具 举报

4四处流浪
498/500
排名
6466
昨日变化
102

0

主题

53

帖子

498

积分

Rank: 4

UID
283972
好友
2
蛮牛币
249
威望
0
注册时间
2018-6-3
在线时间
251 小时
最后登录
2018-10-20
发表于 2018-9-11 18:14:52 | 显示全部楼层
11111111111111111111

回复 支持 反对

使用道具 举报

7日久生情
3669/5000
排名
492
昨日变化
2

96

主题

603

帖子

3669

积分

Rank: 7Rank: 7Rank: 7Rank: 7

UID
7831
好友
3
蛮牛币
18798
威望
0
注册时间
2013-11-12
在线时间
1180 小时
最后登录
2018-10-20

活力之星一掷千金

发表于 2018-9-11 20:47:59 | 显示全部楼层
富文本有用吗?

回复

使用道具 举报

7日久生情
2943/5000
排名
359
昨日变化

1

主题

374

帖子

2943

积分

Rank: 7Rank: 7Rank: 7Rank: 7

UID
2219
好友
1
蛮牛币
7886
威望
0
注册时间
2013-8-19
在线时间
900 小时
最后登录
2018-10-19
发表于 2018-9-11 21:57:25 | 显示全部楼层
Unity实用小工具或脚本—

回复 支持 反对

使用道具 举报

3偶尔光临
269/300
排名
7041
昨日变化
57

1

主题

14

帖子

269

积分

Rank: 3Rank: 3Rank: 3

UID
270889
好友
0
蛮牛币
451
威望
0
注册时间
2018-3-6
在线时间
80 小时
最后登录
2018-10-19
发表于 2018-9-12 08:25:11 | 显示全部楼层
战斗日志。

回复

使用道具 举报

7日久生情
2656/5000
排名
1083
昨日变化
1

0

主题

489

帖子

2656

积分

Rank: 7Rank: 7Rank: 7Rank: 7

UID
155931
好友
0
蛮牛币
108
威望
0
注册时间
2016-7-8
在线时间
1181 小时
最后登录
2018-10-12
发表于 2018-9-12 08:27:15 | 显示全部楼层
6666666666666666666666666

回复 支持 反对

使用道具 举报

6蛮牛粉丝
1390/1500
排名
1639
昨日变化
12

0

主题

402

帖子

1390

积分

Rank: 6Rank: 6Rank: 6

UID
87577
好友
0
蛮牛币
4633
威望
0
注册时间
2015-3-31
在线时间
240 小时
最后登录
2018-10-20
发表于 2018-9-12 08:32:54 | 显示全部楼层
too good too strong!

回复 支持 反对

使用道具 举报

7日久生情
1610/5000
排名
2467
昨日变化
7

12

主题

749

帖子

1610

积分

Rank: 7Rank: 7Rank: 7Rank: 7

UID
218409
好友
3
蛮牛币
5107
威望
0
注册时间
2017-4-19
在线时间
315 小时
最后登录
2018-10-19
发表于 2018-9-12 09:04:13 | 显示全部楼层
6666666666666666666666666666

回复 支持 反对

使用道具 举报

排名
22113
昨日变化
6

0

主题

13

帖子

66

积分

Rank: 2Rank: 2

UID
211128
好友
0
蛮牛币
89
威望
0
注册时间
2017-3-10
在线时间
33 小时
最后登录
2018-10-15
发表于 2018-9-12 09:18:15 | 显示全部楼层
666666666666666666666

回复 支持 反对

使用道具 举报

5熟悉之中
631/1000
排名
4839
昨日变化
7

1

主题

143

帖子

631

积分

Rank: 5Rank: 5

UID
224031
好友
3
蛮牛币
2038
威望
0
注册时间
2017-5-27
在线时间
203 小时
最后登录
2018-9-12
发表于 2018-9-12 09:22:30 | 显示全部楼层
66666666666666666

回复 支持 反对

使用道具 举报

2初来乍到
108/150
排名
14900
昨日变化
301

0

主题

38

帖子

108

积分

Rank: 2Rank: 2

UID
295054
好友
0
蛮牛币
62
威望
0
注册时间
2018-8-29
在线时间
24 小时
最后登录
2018-10-20
发表于 2018-9-12 09:23:29 | 显示全部楼层
666,感谢楼主分享

回复 支持 反对

使用道具 举报

7日久生情
2184/5000
排名
965
昨日变化
1

1

主题

641

帖子

2184

积分

Rank: 7Rank: 7Rank: 7Rank: 7

UID
56496
好友
0
蛮牛币
6536
威望
0
注册时间
2014-11-19
在线时间
492 小时
最后登录
2018-10-19
发表于 2018-9-12 09:28:00 | 显示全部楼层
稳啊,其实我也想发一个上来的,可是懒

回复 支持 反对

使用道具 举报

4四处流浪
496/500
排名
4296
昨日变化
46

0

主题

80

帖子

496

积分

Rank: 4

UID
276682
好友
0
蛮牛币
1117
威望
0
注册时间
2018-4-11
在线时间
96 小时
最后登录
2018-10-20
发表于 2018-9-12 09:29:54 | 显示全部楼层
感谢分享

回复

使用道具 举报

4四处流浪
390/500
排名
6164
昨日变化
3

3

主题

45

帖子

390

积分

Rank: 4

UID
185502
好友
1
蛮牛币
1377
威望
0
注册时间
2016-11-21
在线时间
136 小时
最后登录
2018-9-21
发表于 2018-9-12 09:44:24 | 显示全部楼层
谢谢楼主分享
[发帖际遇]: 一个袋子砸在了 huxingyue 头上,huxingyue 赚了 1 蛮牛币. 幸运榜 / 衰神榜

回复

使用道具 举报

您需要登录后才可以回帖 登录 | 注册帐号

本版积分规则

快速回复 返回顶部 返回列表