• Unity3d制作游戏背包系统


    这一次背包系统很大程度上是参考这个博客进行制作,这篇博客写得很详尽很好,我相对来说增添了一些这里面没有贴出来的细节,大家可以参照着这一篇一起把游戏背包制作出来

    http://blog.csdn.net/qq_20496459/article/details/51421360

    任务

    参考 http://www.tasharen.com/ngui/exampleX.html ,使用 UI 制作背包系统(武器装备系统)

    看这个参考需要使用到unity web player,在旧版浏览器或者IE浏览器上可以下载unity web player使用查看

    前提学习

    这一次作业与前面学习到的知识:camera的使用、多camera的场景、newUI使用息息相关,所以需要先将这些基础知识了解,这里就贴一个camera的unity官方文档,其他的大家可以自己去查询;

     http://wiki.ceeger.com/script/unityengine/classes/camera/camera?s[]=camera

    制作效果

    我的制作效果就没有参考的那么炫酷厉害了,不过基本的要求基本上都达到了~

    制作过程

    UI层的制作

    可以看到,Scene是我的UI层,利用UI Camera渲染呈现,而UI层中存在的东西有:一张画布(UI panel)即scene,然后下面再有一张子画布,画布下有装备栏还有背包栏,也是UI panel;

    而在Bag和Equipment画布下是一个一个UI button,能够得到想要的效果,其中Mouse_Image是用以展示贴到鼠标上的图片,这个在后面还会进行解释;

    其中,装备栏和背包栏使用了Grid Layout Group组件,便于分格:

    上图是Bag的组件设置,Equipment的类似;

    其中注意所有的UI Camera渲染的都是UI层的,并且深度设置为介于Main Camera的层和Hero Camera的层之间,主要是因为我的UI层是起着遮挡Main Camera显示以及在其表面加上两个栏的作用,然后我们要先渲染Hero,防止Hero被遮挡;

    UI Camera的组件设置如下:

    将UI层布置好之后就紧接着开始布置SF Scene Element了;

    SF Scene Element

    这一层很简单,主要就是来放背景图片,然后再加一个粒子系统:

    从Main Camera的预览图可以看到这就是我们这一层所要达到的效果;

    我们只要把图片放在Background里面,然后加一个Particle System制造出一个神秘的背景即可;

    这里需要注意的是,图片需要设置为Sprite才能够放入image组件中:

    在这里MainCamera的组件设置如下,它的深度为最低的一个,因为它需要放在其他的后面,制造出一种虚幻的效果:

    粒子系统,自然简单一点就好,不需要修改太多;

    主角

    主角我是从Asset Store中下载来的,从Asset Store中一搜人物模型,竟然就搜到跟参考博客一样的模型,提供一下链接给大家:

    https://www.assetstore.unity3d.com/cn/#!/content/44041

    其实还有很多很不错的资源,比如我看到有骷颅人、小野人等等;

    是不是感觉这人物怎么放的这么奇怪,对的,人物是放在了图片和UI的背后,然后相机也在这背后,因为这一层只是需要渲染出人物这一个模型即可,其他的层放在那儿都是干扰,所以就直接放在这里,便于Hero Camera的渲染;

    其中,大家可以通过切换成3D来看到这个视图,前面两个我都是用2D视图的;

    Hero Camera的组件设置如下:

    这样,通过三个camera就将最终需要的场景给渲染出来了,是不是很不错~!

    接下来,就应该让那些装备栏里面的物体能够被移动,以及画布随着鼠标的变化而变化了~!

    代码编写

     首先利用了上课给的一个scripts,能够让画布跟随着鼠标变化:

     1 using UnityEngine;
     2 
     3 public class TiltWindows : MonoBehaviour
     4 {
     5     public Vector2 range = new Vector2(5f, 3f);
     6 
     7     Transform mTrans;
     8     Quaternion mStart;
     9     Vector2 mRot = Vector2.zero;
    10 
    11     void Start ()
    12     {
    13         mTrans = transform;
    14         mStart = mTrans.localRotation;
    15     }
    16 
    17     void Update ()
    18     {
    19         Vector3 pos = Input.mousePosition;
    20 
    21         float halfWidth = Screen.width * 0.5f;
    22         float halfHeight = Screen.height * 0.5f;
    23         float x = Mathf.Clamp((pos.x - halfWidth) / halfWidth, -1f, 1f);
    24         float y = Mathf.Clamp((pos.y - halfHeight) / halfHeight, -1f, 1f);
    25         mRot = Vector2.Lerp(mRot, new Vector2(x, y), Time.deltaTime * 5f);
    26 
    27         mTrans.localRotation = mStart * Quaternion.Euler(-mRot.y * range.y, mRot.x * range.x, 0f);
    28     }
    29 }

    接着,创建一个空对象并命名为Manager,在其下挂载Game_Manager代码,Game manager利用实例化,可用来联系各个类,并且能够让其他类很方便地使用它里面的函数:

     1 using UnityEngine;
     2 using System.Collections;
     3 using Game_Manager;
     4 
     5 namespace Game_Manager {
     6 
     7     public class Game_Scene_Manager : System.Object {
     8         private static Game_Scene_Manager _instance;
     9         private static Mouse_Image _Mouse;
    10         private int IsHair = 0; // 是否头部有装备
    11         private int IsWeapon = 0; // 是否有武器装备
    12         private int IsFoot = 0; // 是否有脚部装备
    13 
    14         public static Game_Scene_Manager GetInstance() {
    15             if (_instance == null) {
    16                 _instance = new Game_Scene_Manager();
    17             }
    18             return _instance;
    19         }
    20 
    21         public void SetMouse(Mouse_Image _mouse) {
    22             if (_Mouse == null) {
    23                 _Mouse = _mouse;
    24             }
    25         }
    26 
    27         public Mouse_Image GetMouse() {
    28             return _Mouse;
    29         }
    30 
    31         public void GenAll() {
    32             IsFoot = 1;
    33             IsHair = 1;
    34             IsWeapon = 1;
    35         }
    36 
    37         public int GetHair() { return IsHair; }
    38         public int GetWeapon() { return IsWeapon; }
    39         public int GetFoot() { return IsFoot; }
    40 
    41         public void SetHair(int a) { IsHair = a; }
    42         public void SetWeapon(int a) { IsWeapon = a; }
    43         public void SetFoot(int a) { IsFoot = a; }
    44     }
    45 
    46 }
    47 
    48 public class Mouse : MonoBehaviour {
    49     // Use this for initialization
    50     void Start () {
    51 
    52     }
    53 
    54     // Update is called once per frame
    55     void Update () {
    56 
    57     }
    58 }

    还记得我们在UI层里面创建了一个Mouse_Image吗?它就是为了实现点击图片时,图片跟随鼠标移动的效果的,当鼠标点击一个背包栏,进行判定能够将图片移动后,图片会放入Mouse_Image中,Mouse_Image跟随着鼠标移动,因此就实现了这样的效果,其中Mouse_Image是UI Image类,需要在Mouse_Image下挂上这一个代码:

     1 using UnityEngine;
     2 using System.Collections;
     3 using Game_Manager;
     4 using UnityEngine.UI;
     5 
     6 public class Mouse_Image : MonoBehaviour {
     7 
     8     private Game_Scene_Manager gsm;
     9     private Image mouse_image;
    10     private int mouse_type = 0;
    11     public Sprite none;
    12     public Sprite hair; // 保存相应的装备
    13     public Sprite weapon; // 保存相应的装备
    14     public Sprite foot; // 保存相应的装备
    15     public Color None;
    16     public Color NotNone;
    17     public Camera cam;
    18 
    19     void Awake() {
    20         gsm = Game_Scene_Manager.GetInstance();
    21         gsm.SetMouse(this);
    22         mouse_image = GetComponent<Image>();
    23     }
    24 
    25     public int GetMouseType() {
    26         return mouse_type;
    27     }
    28 
    29     public void SetMouseType(int Mouse_type) {
    30         mouse_type = Mouse_type;
    31     }
    32 
    33     void Update () {
    34         if (mouse_type == 0) // 每一帧进行更新,检查鼠标上是否需要有装备,根据mousetype更新,如果mousetype为0则装备无
    35         {
    36             mouse_image.sprite = none;
    37             mouse_image.color = None;
    38         }
    39         else
    40         { // mousetype不为零,根据mousetype加上相应装备
    41             //Debug.Log("I am mouse image");
    42             //Debug.Log(mouse_type);
    43 
    44             mouse_image.color = new Color(1F, 1F, 1F, 1F);
    45             //Debug.Log(mouse_image.color);
    46             if (mouse_type == 1) mouse_image.sprite = hair;
    47             else if (mouse_type == 2) mouse_image.sprite = weapon;
    48             else if (mouse_type == 3) mouse_image.sprite = foot;
    49         }
    50         transform.position = new Vector3 (Input.mousePosition.x-600, Input.mousePosition.y-230, 0);
    51     }
    52 }

    接下来就是背包栏的每一格点击会发生的事件了,若有装备在背包栏中,要么能够让装备转移到鼠标上,要么鼠标上已经有了图片,不能移动;若没有装备在此格中,则点击此格,如果鼠标上有装备,那么装备会放入背包栏中,如果鼠标上没有,那么什么也不发生,因此我们可以给背包栏的每一个格即UI Button添加一个script,装备栏也类似,不过装备栏中的每个格确定了装备应该是什么类型的;

    using UnityEngine;
    using System.Collections;
    using UnityEngine.UI;
    using Game_Manager;
    
    public class MyBag : MonoBehaviour {
        private Game_Scene_Manager gsm;
        private Image bag_image;
        public int mouse_type = 0; // 0->没有装备,1...有不同装备
        public Sprite hair;
        public Sprite weapon;
        public Sprite foot;
        public Sprite UISprite;
        public Color weapon_color;
        public Color UISprite_color;
    
        void Awake()
        {
            gsm = Game_Scene_Manager.GetInstance();
            bag_image = GetComponent<Image>();
        }
    
        public void On_equip_Button()
        {
            Debug.Log("my bag click!");
            int MouseType = gsm.GetMouse().GetMouseType(); // 得到鼠标目前的mousetype
            if (bag_image.sprite != UISprite && MouseType == 0) // 若鼠标没有图片在上面,并且bag的image不为空有装备,则取走bag_image的装备
            {
                Debug.Log(mouse_type);
                bag_image.sprite = UISprite;
                bag_image.color = UISprite_color;
                gsm.GetMouse().SetMouseType(mouse_type); // 将当前装备的type给鼠标
                mouse_type = 0; // 此背包的mousetype变为0,则当前背包啥都没有
            }
            else
            {   // 若鼠标上有装备,则改背包的image sprite改变,根据type变为不同装备图片
                Debug.Log("my bag equipped!");
                if (MouseType == 1) bag_image.sprite = hair;
                else if (MouseType == 2) bag_image.sprite = weapon;
                else if (MouseType == 3) bag_image.sprite = foot;
                mouse_type = MouseType; // mousetype变为鼠标的mousetype
                bag_image.color = weapon_color; // 有装备了
                gsm.GetMouse().SetMouseType(0); // 鼠标装备消失
            }
        }
    }

    上面是挂在bag的每一个Button上面的,其中bag中的组件设置,以及对这个script的变量设置要注意,我在这里就遇到了几个问题,其中weapon_color不要设置成为透明了,否则我们将装备移动的效果就看不到了,由于我的button是有颜色的,所以我的UISprite_color也不能够透明,需要跟原本的颜色一致;

    然后hair,weapon,foot这些记得依次根据自己的赋值,这些是当mouse_type改变时,这个格子中会放入的装备,以一个bag button设置为示例,其他都类似:

    其中,点击事件不要忘记添加,每一个需要将自己函数里面写的点击事件添加进去;

    然后装备栏的代码如下:

     1 using UnityEngine;
     2 using System.Collections;
     3 using UnityEngine.UI;
     4 using Game_Manager;
     5 
     6 public class equip : MonoBehaviour {
     7 
     8     private Game_Scene_Manager gsm;
     9     private Image equip_image;
    10     public int mouse_type;
    11     public Sprite weapon; // 为此背包中相应的装备
    12     public Sprite UISprite;
    13     public Color weapon_color;
    14     public Color UISprite_color;
    15 
    16     void Awake()
    17     {
    18         gsm = Game_Scene_Manager.GetInstance();
    19         equip_image = GetComponent<Image>();
    20     }
    21 
    22     public void On_equip_Button() {
    23         Debug.Log("equip click");
    24         int MouseType = gsm.GetMouse().GetMouseType(); // 得到鼠标上的mousetype
    25         if (equip_image.sprite == weapon && MouseType == 0) // 取走装备区装备,当装备区含有装备并且mousetype=0鼠标上没有装备
    26         {
    27             equip_image.sprite = UISprite;
    28             equip_image.color = UISprite_color;
    29             gsm.GetMouse().SetMouseType(mouse_type);
    30         }
    31         else
    32         {
    33             // 只有相同各类型的装备能够放到相应的装备区,并且不能够重复装备
    34             if (mouse_type == MouseType && equip_image.sprite != weapon) {
    35                 // 将装备佩戴到装备区中
    36                 equip_image.sprite = weapon;
    37                 equip_image.color = weapon_color;
    38                 mouse_type = MouseType;
    39                 gsm.GetMouse().SetMouseType(0);
    40             }
    41         }
    42     }
    43 
    44     // Use this for initialization
    45     void Start () {
    46 
    47     }
    48 
    49     // Update is called once per frame
    50     void Update () {
    51         // 防止重复装备
    52         if (mouse_type == 1 && gsm.GetHair() == 1)
    53         {
    54             Debug.Log("mouse_type");
    55             gsm.SetHair(0); // 已装备头部不能够再装备头部
    56             equip_image.sprite = weapon;
    57             equip_image.color = weapon_color;
    58         } else if (mouse_type == 2 && gsm.GetWeapon() == 1)
    59         {
    60             gsm.SetWeapon(0); // 已装备武器不能够再装备武器
    61             equip_image.sprite = weapon;
    62             equip_image.color = weapon_color;
    63         } else if (mouse_type == 3 && gsm.GetFoot() == 1)
    64         {
    65             gsm.SetFoot(0); // 已装备脚部
    66             equip_image.sprite = weapon;
    67             equip_image.color = weapon_color;
    68         }
    69     }
    70 }

    基本上和背包栏类似,但是由于装备栏每一个格只会装一个类型的,并且不能够重复装,所以多了一些判断,又少了一些变量;

    其中以一个装备栏设置为例,其他类似:

    最后,所有的代码完成,挂上去,最终就得到了想要的效果啦~

    还有,在装备栏装上装备后,自己可以做一个动画,人物穿上某一个盔甲,或者拿上一把剑等等,并且将动画按照装备分类分别添加,就能够展现出简单的穿戴装备的效果了~!

    总结

    这一次通过制作游戏背包发现之前的很多知识都没有掌握透彻,比如多camera如何渲染场景,其实这些也不是什么难的知识,只是自己没有用心,以后一定要多用心去学习!

    然后还是有一些自己想要完成的没有完成,比如穿戴剑、刀、弓箭、衣服、战靴等等,由于现在的代码写的有限制,每种类型的装备就只产生一个穿戴的效果,不过应该实现起来也不会很难,以后有时间再去实现~

  • 相关阅读:
    windows启动、停止和重新启动Apache服务
    Mysql用户密码设置修改和权限分配
    MySQL数据库恢复(使用mysqlbinlog命令)
    影响MySQL性能的五大配置参数
    PHP获取文件后缀名的三种方法
    php 设计模式
    蓦然回首,那人却在灯火阑珊处
    websocket消息推送实现
    Spring任务调度之Quartz
    使用easyui的form提交表单,在IE下出现类似附件下载时提示是否保存的现象
  • 原文地址:https://www.cnblogs.com/iamxiaoyubei/p/6828720.html
Copyright © 2020-2023  润新知