unity3d制作背包系统(1)–物品
背包系统的基础:物品
在大多数游戏中,背包系统的用处就是存储物品加显示物品给玩家看,接收玩家对背包UI的操作并反馈到实际存储物品的地方,物品是背包系统操作的基本对象,因此物品类是需要在早期就设计好的。
每个UI的格子里对应存储类中存储的一个物品
1.物品类包含的数据
物品的功能就是作为存放数据的一个单元,在我的项目中,物品类(itemunit,基类)包含如下的数据:
using UnityEngine;
using System.Collections;
using System.Xml.Linq;
[System.Serializable]//方便unity中改值调试
public class itemunit
{//item基类,仅包含数据,非完整代码
public int id=0;//物品ID
public int subid=0;//物品子ID
public int maxnum=10;//物品最大堆叠数
public int num=0;//个数
public int etc=0;//etc做备用
public string name="item"; //物品的真实名称
public string displayname;//物品在UI上的显示名称,默认等于name
public string describe;//物品描述
public string exdata;//物品额外携带的数据
public int type=0;//历史遗留,可不要
public bool show = true;//是否在UI上显示
}
物品分为物品基类(itemunit),武器类(weaponunit,继承itemunit),工具类(toolsunit,继承itemunit),子类只需在父类的基础上增加点数据以及override一下父类的virtual方法就行。
PS:项目中有几个很不好的地方第一是将物品基类直接用作表示无使用功能的物品,应该用一个子类来表示。第二是id的万位被用作表示物品类别(比如万位为0代表itemunnit,为1代表weaponunit,为2代表toolunit),这限制了可以分配给某种类型的新物品的ID数量。还有就是冗余数据较多,比如有了exdata,etc字段就可以去掉。
物品类包含数据可以根据开发的游戏的类型修改,但ID,数量,名字这几个数据是十分基本的,对于背包系统来说可以说是必须的。
2.物品类要有的方法
为了使相同物品能堆叠起来,物品类应该有判断两个物品是否相等的方法
判相等方法
public virtual bool equal(itemunit ite)
{
if (ite == null) return false;
if (ite.id == id && ite.subid == subid)
{
return true;
}
else return false;
}
空的物品应该不予显示,因此有判空方法
public bool isempty()
{
if (id == 0 || num == 0) return true;
else return false;
}
给物品格加减数量时外部不应该也不需要知道格中物品的最大堆叠数,因此加入不会超出堆叠数限制的加减数量方法
public virtual int addnum(int numb)
{//返回值为添加了numb个物品后该物品格单元超出最大堆叠数的量
if (numb >= 0)
{
if (num + numb < maxnum)
{
num += numb;
return 0;
}
else
{
numb -= (maxnum - num);
num = maxnum;
return numb;//只会返回0或正数,正数代表溢出量
}
}
else { Debug.Log("尝试向itemunit中添加负数是违法的"); return num; }
}
public virtual int subnum(int numb)//减去一定数量的物品
{//返回值为不够减差多少的量
if (numb >= 0)
{
if (num > numb)
{
num -= numb;
if (num <= 0)
return 0;//足够返回0
}
else
{
int temp = numb - num;
num = 0;
return temp;//不够返回差多少
}
}
else { Debug.Log("尝试向itemunit中减去负数是违法的");return num; }
}
当出现一些不可预料的情况时,有可能物品的数量会超出最大堆叠数
因此需要判溢出方法
public int isoverflow()
{
if (num > maxnum)
{
return num - maxnum;
}
else return 0;
}
有时会遇到要将该物品设置为满的情况,需要置满方法
public void tomax()
{
num = maxnum;
}
如果想添加存储游戏功能,那么我们的物品类(itemunit)还需要一个toxml方法和一个静态的xmltoitem方法来进行xml(存储用)和物品类(itemunit)的相互转换,这正是我的项目所做的,但现在只讲背包系统,存储功能就不添加免得扰乱代码。
小结
目前物品类(itemunit)有这些代码:(非实际项目的全部代码)
using UnityEngine;
using System.Collections;
using System.Xml.Linq;
[System.Serializable]//方便unity中改值
public class itemunit
{//item基类,仅包含数据,非完整代码
public int id=0;//物品ID
public int subid=0;//物品子ID
public int maxnum=10;//物品最大堆叠数
public int num=0;//个数
public int etc=0;//etc做备用
public string name="item"; //物品的真实名称
public string displayname;//物品在UI上的显示名称,默认等于name
public string describe;//物品描述
public string exdata;//物品额外携带的数据
public int type=0;//
public bool show = true;//是否在UI上显示
public itemunit(){ }//构造方法1
public itemunit(int ids)//构造方法2
{
id = ids;
}
public itemunit(int ids,int subids,int nums)//构造方法3
{
id = ids;num = nums;subid = subids;
}
public virtual bool equal(itemunit ite)//判断itemunit是否相等
{
if (ite == null) return false;
if (ite.id == id && ite.subid == subid)
{
return true;
}
else return false;
}
public bool isempty()
{
if (id == 0 || num == 0) return true;
else return false;
}
public virtual int addnum(int numb)
{//返回值为添加了numb个物品后该物品格单元超出最大堆叠数的量
if (numb >= 0)
{
if (num + numb < maxnum)
{
num += numb;
return 0;
}
else
{
numb -= (maxnum - num);
num = maxnum;
return numb;//只会返回0或正数,正数代表溢出量
}
}
else { Debug.Log("尝试向itemunit中添加负数是违法的"); return num; }
}
public virtual int subnum(int numb)//减去一定数量的物品
{
if (numb >= 0)
{
if (num > numb)
{
num -= numb;
if (num <= 0) return 0;//足够返回0
}
else
{
int temp = numb - num;
num = 0;
return temp;//不够返回差多少
}
}
else { Debug.Log("尝试向itemunit中减去负数是违法的");return num; }
}
public int isoverflow()
{
if (num > maxnum)
{
return num - maxnum;
}
else return 0;
}
public void tomax()
{
num = maxnum;
}
}
现在我们相当于有了物品类这个基本数据类型,接下来就需要一个类来存储他们并且作为玩家的背包使用(是纯数据存储类,未到UI部分)