【unity实战】教你轻松构建对话系统

先来看最终效果

前言

欢迎来到我们的Unity实战教程系列。在这一篇中,我们将深入探讨如何在Unity中构建一个对话系统。

对话系统是许多游戏中不可或缺的一部分,特别是在角色扮演游戏(RPG)、冒险游戏和视觉小说等类型中。它们为玩家提供了丰富的背景故事,帮助塑造角色性格,甚至决定游戏的发展方向和结局。然而,构建一个既能满足游戏需求又易于管理和扩展的对话系统却是一项挑战。

本教程将指导你如何在Unity中从零开始构建一个灵活且可自定义的对话系统。我们将首先讨论对话系统的基本组成部分,包括对话节点、角色类型和对话内容。然后,我们将逐步引导你创建ScriptableObject以存储对话数据,以及如何使用MonoBehaviour处理对话逻辑。我们还将介绍如何在Unity编辑器中设置对话数据,并模拟实际的对话场景。

无论你是Unity新手,还是有一定经验的开发者,只要你对构建对话系统感兴趣,都可以从本教程中受益。希望你能跟随我们的步骤,动手实践,并最终在你自己的游戏项目中构建出精彩的对话系统。

让我们开始吧!

开始

新建对话结点脚本DialogNode

csharp 复制代码
// CharacterType 是一个枚举,它定义了两种类型的角色:NPC 和玩家。
public enum CharacterType
{
    Npc,     // NPC 角色类型
    Player   // 玩家角色类型
}

// DialogNode 是一个可序列化的类,代表了一个对话节点。
[Serializable]
public class DialogNode
{
    public CharacterType type; // 表示对话的角色类型。
    public string charecterName; // 表示角色的名字。
    
    [TextArea]
    public string dialog; // 表示对话的内容。
}

新增对话脚本Dialogue

csharp 复制代码
// Dialogue 是一个继承自 ScriptableObject 的类,它表示一段对话。
[CreateAssetMenu(fileName = "对话")]
public class Dialogue : ScriptableObject 
{
    // 它包含了这段对话中的所有对话节点。
    public DialogNode[] dialogNodes;
}

新增对话系统脚本DialogueSystem

csharp 复制代码
public class DialogueSystem : MonoBehaviour
{
    [Header("对话")]
    [SerializeField] private Dialogue dialogue;
    [Header("对话框")]
    [SerializeField] private GameObject dialogBox;
    [Header("对话文本")]
    [SerializeField] private TextMeshProUGUI dialog;
    [Header("角色名称")]
    [SerializeField] private TextMeshProUGUI charecterName;
    [Header("角色类型")]
    [SerializeField] private CharacterType type;

    // 用于追踪当前正在播放的对话节点的索引。
    private int index;

    // 表示玩家是否在交互范围内。
    private bool isInTurn;

    // 如果玩家按下 E 键并且在交互范围内,则开始播放对话。
    private void Update()
    {
        if (Input.GetKeyDown(KeyCode.E) && isInTurn)
            Play();
    }

    // 当玩家进入交互范围时,设置 isInTurn 为 true。
    private void OnTriggerEnter2D(Collider2D other) => isInTurn = true;

    // 当玩家离开交互范围时,设置 isInTurn 为 false。
    private void OnTriggerExit2D(Collider2D other) => isInTurn = false;

    // Play 函数用于开始播放对话。
    private void Play()
    {
        // 激活对话框。
        dialogBox.SetActive(true);

        // 获取当前对话节点,并更新索引值。
        DialogNode node = dialogue.dialogNodes[Mathf.Clamp(index++, 0, dialogue.dialogNodes.Length - 1)];

        // 设置对话文本和角色名称。
        dialog.text = node.dialog;
        charecterName.text = node.charecterName;

        // 如果已经播放完所有对话节点,则关闭对话框。
        if (index - 1 == dialogue.dialogNodes.Length)
            dialogBox.SetActive(false);
    }
}

新增对话表,配置我们的对话信息

在角色挂载我们的对话系统脚本DialogueSystem并配置参数

运行效果

完结

赠人玫瑰,手有余香!如果文章内容对你有所帮助,请不要吝啬你的点赞评论和关注,以便我第一时间收到反馈,你的每一次支持都是我不断创作的最大动力。点赞越多,更新越快哦!当然,如果你发现了文章中存在错误或者有更好的解决方法,也欢迎评论私信告诉我哦!

好了,我是向宇https://xiangyu.blog.csdn.net

一位在小公司默默奋斗的开发者,出于兴趣爱好,于是最近才开始自习unity。如果你遇到任何问题,也欢迎你评论私信找我, 虽然有些问题我可能也不一定会,但是我会查阅各方资料,争取给出最好的建议,希望可以帮助更多想学编程的人,共勉~

相关推荐
aerror3 小时前
如何正确的用Trae 打开 Unity 3D 项目
3d·unity·游戏引擎
步、步、为营5 小时前
.NET 的IOC框架Unity代码示例
unity·游戏引擎·.net
Magnum Lehar5 小时前
wpf游戏引擎的script实现
游戏引擎·wpf
留待舞人归9 小时前
【Unity优化】提高热更新和打包速度
游戏·unity·游戏引擎·unity3d·优化
tealcwu9 小时前
【Unity踩坑】Unity 6在Mac平台编译运行时去除‘trial version‘
macos·unity·游戏引擎
为你写首诗ge10 小时前
【热更新知识】学习一 Lua语法学习
unity·lua
为你写首诗ge11 小时前
【热更新知识】学习三 XLua学习
unity·lua
程序员小刘13 小时前
如何开始HarmonyOS 5与Godot引擎融合开发?
华为·游戏引擎·godot·harmonyos
T.D.C21 小时前
【动画】Unity2D骨骼动画-Animation2D
unity·动画
AgilityBaby21 小时前
Unity实现不倒翁
笔记·unity·c#·游戏引擎