Tools
FileTools
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System.IO;
using System.Text;
public static class FileTools {
/// <summary>
/// 读取指定路径的json文件
/// </summary>
/// <param name="path"></param>
/// <returns></returns>
public static string ReadJson(string path)
{
if (!File.Exists(path))
{
return "";
}
string json = "";
StreamReader sr = new StreamReader(path, Encoding.UTF8);
try
{
json = sr.ReadToEnd();
}
catch (System.Exception e)
{
Debug.Log(e.ToString());
}
sr.Close();
return json;
}
/// <summary>
/// 把json写入指定的文件a
/// </summary>
/// <param name="path"></param>
/// <param name="json"></param>
public static void WriteJson(string path, string json)
{
if (!File.Exists(path))
{
FileStream fs = File.Create(path);
fs.Close();
}
StreamWriter sw = new StreamWriter(path, false, Encoding.UTF8);
try
{
sw.Write(json);
}
catch (System.Exception e)
{
Debug.Log(e.ToString());
}
sw.Close();
} }

SaveManager

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class SaveManager
{
#region 单例
private static SaveManager instance;
public static SaveManager Instance
{
get {
if (null == instance)
{
instance = new SaveManager();
}
return instance;
}
}
private SaveManager() { }
#endregion
/// <summary>
/// 初始化数据
/// </summary>
public void InitData()
{
//初始化人物的数据
string playerJson = FileTools.ReadJson(Application.streamingAssetsPath + "/Json/PlayerData.txt");
if (playerJson == "")
{
PlayerData.SetInstance(null);
}
else
{
PlayerData.SetInstance(JsonUtility.FromJson<PlayerData>(playerJson));
}
//Debug.Log(PlayerData.Instance.Atk);
PlayerData.Instance.Init();
//初始化背包数据
string bagJson = FileTools.ReadJson(Application.streamingAssetsPath + "/Json/Bag.txt");
if (bagJson == "")
{
BagData.SetInstance(null);
}
else
{
BagData.SetInstance(JsonUtility.FromJson<BagData>(bagJson));
}
//for (int i = 0; i < BagData.Instance.Items.Count; i++)
//{
// Debug.Log("");
//}
BagData.Instance.UpdateCurrentCapacity();//更新一次负重
}
/// <summary>
/// 保存数据
/// </summary>
public void SaveData()
{
//保存玩家的数据
string playerJson = JsonUtility.ToJson(PlayerData.Instance, true);
FileTools.WriteJson(Application.streamingAssetsPath + "/Json/PlayerData.txt", playerJson);
//保存背包的数据
string bagJson = JsonUtility.ToJson(BagData.Instance, true);
FileTools.WriteJson(Application.streamingAssetsPath + "/Json/Bag.txt", bagJson);
}
}

GameManager

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class GameManager : MonoBehaviour {
// Use this for initialization
void Awake () {
DontDestroyOnLoad(gameObject);
SaveManager.Instance.InitData();
} // Update is called once per frame
void OnDestroy () {
SaveManager.Instance.SaveData();
}
}
Json
PlayerData
{
"items": [
{
"id": ,
"itemName": "肚兜",
"iconName": "FaShi_XiongJia_5",
"atk": 0.0,
"def": 999.0,
"thump": 0.0,
"hp": 1000.0,
"mp": 2000.0,
"anger": 0.0,
"weight": 1.0,
"type":
},
{
"id": ,
"itemName": "大贱",
"iconName": "DaJian_08",
"atk": 999.0,
"def": 0.0,
"thump": 0.9900000095367432,
"hp": 100.0,
"mp": 100.0,
"anger": 500.0,
"weight": 2.0,
"type":
}
],
"atk": 20.0,
"def": 20.0,
"thump": 0.5,
"hp": 100.0,
"mp": 100.0,
"anger": 0.0
}

Bag

{
"items": [
{
"id": ,
"itemName": "肚兜",
"iconName": "FaShi_XiongJia_4",
"atk": 0.0,
"def": 999.0,
"thump": 0.0,
"hp": 1000.0,
"mp": 2000.0,
"anger": 0.0,
"weight": 1.0,
"type":
},
{
"id": ,
"itemName": "大贱",
"iconName": "DaJian_08",
"atk": 999.0,
"def": 0.0,
"thump": 0.9900000095367432,
"hp": 100.0,
"mp": 100.0,
"anger": 500.0,
"weight": 2.0,
"type":
},
{
"id": ,
"itemName": "肚兜",
"iconName": "FaShi_XiongJia_5",
"atk": 0.0,
"def": 999.0,
"thump": 0.0,
"hp": 1000.0,
"mp": 2000.0,
"anger": 0.0,
"weight": 1.0,
"type":
},
{
"id": ,
"itemName": "肚兜",
"iconName": "FaShi_XiongJia_4",
"atk": 0.0,
"def": 999.0,
"thump": 0.0,
"hp": 1000.0,
"mp": 2000.0,
"anger": 0.0,
"weight": 1.0,
"type":
},
{
"id": ,
"itemName": "肚兜",
"iconName": "FaShi_XiongJia_5",
"atk": 0.0,
"def": 999.0,
"thump": 0.0,
"hp": 1000.0,
"mp": 2000.0,
"anger": 0.0,
"weight": 1.0,
"type":
},
{
"id": ,
"itemName": "大贱",
"iconName": "DaJian_08",
"atk": 999.0,
"def": 0.0,
"thump": 0.9900000095367432,
"hp": 100.0,
"mp": 100.0,
"anger": 500.0,
"weight": 2.0,
"type":
},
{
"id": ,
"itemName": "肚兜",
"iconName": "FaShi_XiongJia_4",
"atk": 0.0,
"def": 999.0,
"thump": 0.0,
"hp": 1000.0,
"mp": 2000.0,
"anger": 0.0,
"weight": 1.0,
"type":
}
],
"maxCapacity": 100.0
}
Model
ItemData
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
/// <summary>
/// 该类用于存储装备的基本属性
/// </summary>
[System.Serializable]//因为对于已有的数据是从文件中来的,所以需要加序列化标识
public class ItemData
{
#region 私有变量
[SerializeField]
private int id;//作为物品的唯一标识
[SerializeField]
private string itemName;//物品的名字
[SerializeField]
private string iconName;//物品显示图片的名字
[SerializeField]
private float atk;//攻击力加成
[SerializeField]
private float def;//防御力加成
[SerializeField]
private float thump;//暴击率加成
[SerializeField]
private float hp;//血量加成
[SerializeField]
private float mp;//加成
[SerializeField]
private float anger;//怒气加成
[SerializeField]
private float weight;//重量
[SerializeField]
private ItemType type;//物品的类型
#endregion
#region 属性
public int Id
{
get
{
return id;
}
}
public string ItemName
{
get
{
return itemName;
}
}
public string IconName
{
get
{
return iconName;
}
}
public float Atk
{
get
{
return atk;
}
}
public float Def
{
get
{
return def;
}
}
public float Thump
{
get
{
return thump;
}
}
public float Hp
{
get
{
return hp;
}
}
public float Mp
{
get
{
return mp;
}
}
public float Anger
{
get
{
return anger;
}
}
public float Weight
{
get
{
return weight;
}
}
public ItemType Type
{
get
{
return type;
}
}
#endregion
#region 构造函数
public ItemData() { }
public ItemData(int id, string itemName, string iconName, float atk,
float def, float thump, float hp, float mp, float anger, float weight, ItemType type)
{
this.id = id;
this.itemName = itemName;
this.iconName = iconName;
this.atk = atk;
this.def = def;
this.thump = thump;
this.hp = hp;
this.mp = mp;
this.anger = anger;
this.weight = weight;
this.type = type;
}
#endregion
public static string GetTypeName(ItemType type)
{
string typeName = "";
switch (type)
{
case ItemType.Weapon:
typeName = "武器";
break;
case ItemType.Cap:
typeName = "头盔";
break;
case ItemType.Armour:
typeName = "铠甲";
break;
case ItemType.Belt:
typeName = "腰带";
break;
case ItemType.Ring:
typeName = "戒指";
break;
case ItemType.Headwear:
typeName = "头饰";
break;
case ItemType.Necklace:
typeName = "项链";
break;
case ItemType.Shoe:
typeName = "靴子";
break;
}
return typeName;
}
}

ItemType

/// <summary>
/// 物品的类型, 装备栏能装备的类型
/// </summary>
public enum ItemType
{
Weapon,//武器
Cap,//头盔
Armour,//铠甲
Ring,//戒指
Belt,//腰带
Necklace,//项链
Shoe,//鞋子
Headwear,//头饰
}
PlayerData
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System;
public class PlayerData
{
#region 单例
private static PlayerData instance;//这个数据类的单例,从文件中反序列化来的
public static PlayerData Instance
{
get {
return instance;
}
}
private PlayerData() { }
/// <summary>
/// 对单例进行赋值
/// </summary>
/// <param name="data"></param>
public static void SetInstance(PlayerData data)
{
if (null == data)
{
instance = new PlayerData();
}
else
{
instance = data;
}
}
#endregion
public List<ItemData> items;//人物身上穿戴的装备
#region 私有变量
[SerializeField]
private float atk;//基础攻击力
[SerializeField]
private float def;//基础防御力
[SerializeField]
private float thump;//基础暴击率
[SerializeField]
private float hp;//基础血量
[SerializeField]
private float mp;//基础魔法
[SerializeField]
private float anger;//基础怒气
//装备的属性加成都是装备的装备计算出来的
private float addAtk;//装备攻击力加成
private float addDef;//
private float addThump;//
private float addHp;//
private float addMp;//
private float addAnger;//
#endregion
#region 事件
//当数据发生改变时,通过该事件通知界面
public event Action updateEvent;
#endregion
#region 属性
public float Atk
{
get
{
return atk;
}
}
public float Def
{
get
{
return def;
}
}
public float Thump
{
get
{
return thump;
}
}
public float Hp
{
get
{
return hp;
}
}
public float Mp
{
get
{
return mp;
}
}
public float Anger
{
get
{
return anger;
}
}
public float AddAtk
{
get
{
return addAtk;
}
}
public float AddDef
{
get
{
return addDef;
}
}
public float AddThump
{
get
{
return addThump;
}
}
public float AddHp
{
get
{
return addHp;
}
}
public float AddMp
{
get
{
return addMp;
}
}
public float AddAnger
{
get
{
return addAnger;
}
}
#endregion
#region 提供一些访问或删除装备的方法
/// <summary>
/// 通过装备的ID来访问装备
/// </summary>
/// <param name="id"></param>
/// <returns></returns>
public ItemData GetItem(int id)
{
for (int i = ; i < items.Count; i++)
{
if (id == items[i].Id)
{
return items[i];
}
}
return null;
}
/// <summary>
/// 通过装备的类型来访问装备
/// </summary>
/// <param name="type"></param>
/// <returns></returns>
public ItemData GetItem(ItemType type)
{
for (int i = ; i < items.Count; i++)
{
if (type == items[i].Type)
{
return items[i];
}
}
return null;
}
/// <summary>
/// 添加装备
/// </summary>
/// <param name="data"></param>
public void AddItem(ItemData data)
{
items.Add(data);
//数据发生改变,装备的属性加成需要重新计算
UpdateAdditionData();
//数据发生变化,通知界面
UpdatePanel();
}
/// <summary>
/// 删除装备
/// </summary>
/// <param name="data"></param>
public void RemoveItem(ItemData data)
{
if (items.Contains(data))
{
items.Remove(data);
//数据发生改变,装备的属性加成需要重新计算
UpdateAdditionData();
//数据发生变化,通知界面
UpdatePanel();
}
}
/// <summary>
/// 通过ID删除装备
/// </summary>
/// <param name="id"></param>
public void RemoveItem(int id)
{
ItemData data = GetItem(id);
RemoveItem(data);
}
/// <summary>
/// 通过装备类型删除装备
/// </summary>
/// <param name="type"></param>
public void RemoveItem(ItemType type)
{
ItemData data = GetItem(type);
RemoveItem(data);
}
#endregion
public void Init()
{
UpdateAdditionData();
}
/// <summary>
/// 计算装备的加成数据, 每次当数据发生改变的时候调用
/// </summary>
void UpdateAdditionData()
{
this.addAtk = ;
this.addDef = ;
this.addThump = ;
this.addHp = ;
this.addMp = ;
this.addAnger = ;
//把每一件装备的加成数据加给实际的数据
for (int i = ; i < items.Count; i++)
{
this.addAtk += items[i].Atk;
this.addDef += items[i].Def;
this.addThump += items[i].Thump;
this.addHp += items[i].Hp;
this.addMp += items[i].Mp;
this.addAnger += items[i].Anger;
}
}
/// <summary>
/// 通知界面改变
/// </summary>
void UpdatePanel()
{
if (updateEvent != null)
{
updateEvent();
}
}
}

BagData

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System;
public class BagData
{
#region 单例
private static BagData instance;//从文件中反序列化来的
public static BagData Instance
{
get {
return instance;
}
}
private BagData() { }
public static void SetInstance(BagData data)
{
if (data == null)
{
instance = new BagData();
instance.items = new List<ItemData>();
}
else
{
instance = data;
}
}
#endregion
#region 私有变量
[SerializeField]
private List<ItemData> items;//当前的所有的装备
[SerializeField]
private float maxCapacity;//最大容量, 从文件中读取进来的
private float currentCapacity;//当前容量, 根据当前背包的装备计算出来的
#endregion
#region 事件
public event Action updateEvent;//定义一个事件,当数据改变时,调用事件通知界面更新
#endregion
#region 属性
public float MaxCapacity
{
get
{
return maxCapacity;
}
}
public float CurrentCapacity
{
get
{
return currentCapacity;
}
}
public List<ItemData> Items
{
get
{
return items;
}
}
#endregion
#region 提供一些操作背包装备的方法
/// <summary>
/// 使用ID访问背包中的装备
/// </summary>
/// <param name="id"></param>
/// <returns></returns>
public ItemData GetItem(int id)
{
for (int i = ; i < items.Count; i++)
{
if (items[i].Id == id)
{
return items[i];
}
}
return null;
}
/// <summary>
/// 添加装备
/// </summary>
/// <param name="id"></param>
public void AddItem(ItemData data)
{
items.Add(data);
//每一次数据改变,当前负重都是需要重新计算的
UpdateCurrentCapacity();
//数据变了,通知界面
UpdatePanel();
}
/// <summary>
/// 删除装备
/// </summary>
/// <param name="data"></param>
public void RemoveItem(ItemData data)
{
//判断data是否在Items里
if (items.Contains(data))
{
items.Remove(data);
}
UpdateCurrentCapacity();
//数据变了,通知界面
UpdatePanel();
}
/// <summary>
/// 删除指定ID的装备
/// </summary>
/// <param name="id"></param>
public void RemoveItem(int id)
{
ItemData data = GetItem(id);
if (data != null)
{
RemoveItem(data);
}
}
#endregion
public void UpdateCurrentCapacity()
{
currentCapacity = ;
//把每一件装备的负重累加在一起,就是当前的负重
for (int i = ; i < items.Count; i++)
{
currentCapacity += items[i].Weight;
}
}
/// <summary>
/// 通知界面更新
/// </summary>
void UpdatePanel()
{
if (updateEvent != null)
{
updateEvent();
}
}
public void ItemsSort()
{
items.Sort(ItemSort);
//物品之间的顺序发生了改变, 通知界面更新
UpdatePanel();
}
/// <summary>
/// 物品的排序,以物品的类型排
/// </summary>
/// <param name="a"></param>
/// <param name="b"></param>
/// <returns></returns>
int ItemSort(ItemData a, ItemData b)
{
int tempA = (int)a.Type;
int tempB = (int)b.Type;
if (tempA < tempB)
{
return -;
}
else if (tempA > tempB)
{
return ;
}
else
{
return ;
}
}
}
View
PlayerUI
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class PlayerUI : MonoBehaviour {
private GridBase[] grids;//所有的装备栏
//所有显示属性的Text
private Text atkText;
private Text defText;
private Text thumpText;
private Text hpText;
private Text mpText;
private Text angerText;
void Awake () {
//在子物体里获取所有的GridBase这个组件,返回的是一个数组
grids = gameObject.GetComponentsInChildren<GridBase>();
atkText = transform.Find("Message/AtkText").GetComponent<Text>();
defText = transform.Find("Message/DefText").GetComponent<Text>();
thumpText = transform.Find("Message/ThumpText").GetComponent<Text>();
hpText = transform.Find("Message/HPText").GetComponent<Text>();
mpText = transform.Find("Message/MPText").GetComponent<Text>();
angerText = transform.Find("Message/AngerText").GetComponent<Text>();
//ItemData data = new ItemData();
//Debug.Log(JsonUtility.ToJson(data, true));
}
private void Start()
{
PlayerData.Instance.updateEvent += UpdatePanel;
UpdatePanel();
}
private void OnDestroy()
{
PlayerData.Instance.updateEvent -= UpdatePanel;
}
/// <summary>
/// 更新界面的方法
/// </summary>
void UpdatePanel()
{
//把人物身上装备的物品显示, 所有属性显示
//先把所有的格子清空
for (int i = ; i < grids.Length; i++)
{
grids[i].UpdateItem(-, "");
}
//再把人物身上装备显示在对应的格子上
for (int i = ; i < grids.Length; i++)
{
PlayerGridUI grid = grids[i] as PlayerGridUI;
for (int j = ; j < PlayerData.Instance.items.Count; j++)
{
//当格子的装备与人物数据里的装备的类型是一致时,证明该装备应该放在这个格子上
if (grid.gridType == PlayerData.Instance.items[j].Type)
{
grid.UpdateItem(PlayerData.Instance.items[j].Id, PlayerData.Instance.items[j].IconName);
}
}
}
atkText.text = "攻击力:" + PlayerData.Instance.Atk + "<color=\"green\"> + "
+ PlayerData.Instance.AddAtk + "</color>";
defText.text = "防御力:" + PlayerData.Instance.Def + "<color=\"green\"> + "
+ PlayerData.Instance.AddDef + "</color>";
thumpText.text = "暴击率:" + PlayerData.Instance.Thump + "<color=\"green\"> + "
+ PlayerData.Instance.AddThump + "</color>";
hpText.text = "生命值:" + PlayerData.Instance.Hp + "<color=\"green\"> + "
+ PlayerData.Instance.AddHp + "</color>";
mpText.text = "魔法值:" + PlayerData.Instance.Mp + "<color=\"green\"> + "
+ PlayerData.Instance.AddMp + "</color>";
angerText.text = "怒气值:" + PlayerData.Instance.Anger + "<color=\"green\"> + "
+ PlayerData.Instance.AddAnger + "</color>";
}
}

BagUI

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class BagUI : MonoBehaviour {
private GridBase[] grids;
private Text weightText;
private Text numText;
private Button rightButton;
private Button leftButton;
private Button clearUpButton;
private int currentNum;
private int maxNum;//根据背包里物品数量与当前有多少个格子比较
void Awake () {
//获取所有的格子
grids = gameObject.GetComponentsInChildren<GridBase>();
weightText = transform.Find("CapacityText").GetComponent<Text>();
numText = transform.Find("Num/Num/Text").GetComponent<Text>();
rightButton = transform.Find("Num/RightButton").GetComponent<Button>();
leftButton = transform.Find("Num/LeftButton").GetComponent<Button>();
clearUpButton = transform.Find("ClearUpButton").GetComponent<Button>();
//按钮注册事件
rightButton.onClick.AddListener(RightClick);
leftButton.onClick.AddListener(LeftClick);
clearUpButton.onClick.AddListener(ClearUpClick);
}
private void Start()
{
BagData.Instance.updateEvent += UpdatePanel;
currentNum = ;//界面一开始,当前页是1
UpdatePanel();
}
private void OnDestroy()
{
BagData.Instance.updateEvent -= UpdatePanel;
}
/// <summary>
/// 更新界面
/// </summary>
void UpdatePanel()
{
//更新当前页数的物品, 更新当前页数, 更新当前的负重
//计算当前的最大页数
maxNum = (int)Mathf.Ceil(BagData.Instance.Items.Count / (float)grids.Length);
numText.text = currentNum + "/" + maxNum;
weightText.text = "负重:" + BagData.Instance.CurrentCapacity + "/" +
BagData.Instance.MaxCapacity; //显示当前的页数的物品
//根据当前页数,确定第一个位置应该排背包数据的里的第几个索引(起始索引)
//模拟 格子: 20 当第一页是起始索引为0, 当第二页时起始索引为20
int startIndex = (currentNum - ) * grids.Length;//(当前页数 - 1) * 格子数量
//把从起始索引开始,依次的把物品放在对应的格子上
for (int i = ; i < grids.Length; i++)
{
//当i= 0时,证明是第一个格子,对应的物品索引 startIndex = startIndex + i
//当i= 1时,证明是第二各格子,对应的物品索引 startIndex + 1 = startIndex + i
//....
//当i = grids.Length - 1时, 最后一个格子, 对应的物品索引 startIndex + grids.Length - 1 = startIndex + i
//如果startIndex + i 超出了物品的数量, 证明这个格子没有物品
//如果startIndex + i 没有超出物品的数量, 这个这个格子有物品
if (startIndex + i >= BagData.Instance.Items.Count)
{
//超出了物品的数量,该格子没有物品
grids[i].UpdateItem(-, "");
}
else
{
grids[i].UpdateItem(BagData.Instance.Items[startIndex + i].Id,
BagData.Instance.Items[startIndex + i].IconName);
}
}
}
/// <summary>
/// 翻页的右按钮
/// </summary>
void RightClick()
{
//Debug.Log("RightClick");
//判断是当前页是是最后一页
if (currentNum < maxNum)
{
//不是最后一页
currentNum++;
UpdatePanel();//当前页数变了,需要更新一下界面的显示
}
}
/// <summary>
/// 翻页的左按钮
/// </summary>
void LeftClick()
{
//Debug.Log("LeftClick");
//判断当前页数是不是第一页
if (currentNum > )
{
currentNum--;
UpdatePanel();//当前页数变了,需要更新一下界面的显示
}
}
/// <summary>
/// 整理按钮
/// </summary>
void ClearUpClick()
{
Debug.Log("ClearUpClick");
BagController.Instance.ClearUp();
}
}

GridBase

using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.EventSystems;
public class GridBase : MonoBehaviour,
IPointerEnterHandler,
IPointerExitHandler,
IPointerClickHandler,
IBeginDragHandler,
IDragHandler,
IEndDragHandler
{
public int itemID = -;// 规定-1 那么这个格子空的
public Transform tempParent;//拖动时临时的父物体
private Image image;//显示装备的图片
private Vector2 outPos;//转换之后的坐标
private Vector2 offset;//鼠标偏移量
private RectTransform parentRT;
protected void Init()
{
image = transform.Find("Item").GetComponent<Image>();
parentRT = tempParent as RectTransform;
}
/// <summary>
/// 更新自己本身的物品
/// </summary>
/// <param name="itemID"></param>
/// <param name="iconName"></param>
public virtual void UpdateItem(int itemID, string iconName)
{
if (this.itemID == itemID && itemID >= )
{
return;
}
this.itemID = itemID;
if (itemID < )//没有物品
{
image.enabled = false;
}
else
{
image.enabled = true;
if (image.sprite == null || image.sprite.name != iconName)
{
Sprite sp = Resources.Load<Sprite>("Texture/Icon/" + iconName);
image.sprite = sp;
}
}
}
#region 接口的虚方法
//开始拖动的虚方法
protected virtual void BeginDrag(PointerEventData eventData)
{
if (itemID < ) return;
//Debug.Log("父类:BeginDrag");
image.transform.parent = tempParent;
if (RectTransformUtility.ScreenPointToLocalPointInRectangle(parentRT,
eventData.position, eventData.enterEventCamera, out outPos))
{
offset = outPos - new Vector2(image.transform.localPosition.x, image.transform.localPosition.y);
}
}
//拖动的虚方法
protected virtual void Drag(PointerEventData eventData)
{
if (itemID < ) return;
//Debug.Log("父类:Drag");
if (RectTransformUtility.ScreenPointToLocalPointInRectangle(parentRT,
eventData.position, eventData.enterEventCamera, out outPos))
{
image.transform.localPosition = outPos - offset;
}
}
//拖动结束时的虚方法
protected virtual void EndDrag(PointerEventData eventData)
{
if (itemID < ) return;
//Debug.Log("父类:EndDrag");
image.transform.parent = transform;
image.transform.localPosition = Vector3.zero;
}
//点击的虚方法
protected virtual void Click(PointerEventData eventData)
{
//Debug.Log("父类:Click");
}
//进入的虚方法
protected virtual void Enter(PointerEventData eventData)
{
//Debug.Log("父类:Enter");
//Debug.Log("显示信息");
}
//出去的虚方法
protected virtual void Exit(PointerEventData eventData)
{
//Debug.Log("父类:Exit");
//Debug.Log("隐藏信息");
TipsUI.Instance.HideTips();
}
#endregion
#region 实现的接口
public void OnBeginDrag(PointerEventData eventData)
{
BeginDrag(eventData);
}
public void OnDrag(PointerEventData eventData)
{
Drag(eventData);
}
public void OnEndDrag(PointerEventData eventData)
{
EndDrag(eventData);
}
public void OnPointerClick(PointerEventData eventData)
{
Click(eventData);
}
public void OnPointerEnter(PointerEventData eventData)
{
Enter(eventData);
}
public void OnPointerExit(PointerEventData eventData)
{
Exit(eventData);
}
#endregion
}

PlayerGridUI

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.EventSystems;
public class PlayerGridUI : GridBase {
public ItemType gridType;
private Text text;
// Use this for initialization
void Awake () {
base.Init();
text = transform.Find("Text").GetComponent<Text>();
gameObject.tag = "PlayerGrid";
text.text = ItemData.GetTypeName(gridType);
} public override void UpdateItem(int itemID, string iconName)
{
base.UpdateItem(itemID, iconName);
if (itemID >= )//有装备
{
text.enabled = false;//有装备时,把装备栏的文字隐藏
}
else
{
text.enabled = true;
}
}
protected override void BeginDrag(PointerEventData eventData)
{
if (itemID < ) return;
base.BeginDrag(eventData);
text.enabled = true;//开始拖动时,显示文字
}
protected override void Click(PointerEventData eventData)
{
if (itemID < ) return;
if (eventData.button == PointerEventData.InputButton.Right)
{
Debug.Log("卸下: " + itemID);
BagController.Instance.DemountItem(itemID, CallBck);
}
}
protected override void EndDrag(PointerEventData eventData)
{
if (itemID < ) return;
base.EndDrag(eventData);
text.enabled = false;//开始拖动时,显示文字
if (eventData.pointerCurrentRaycast.gameObject != null &&
eventData.pointerCurrentRaycast.gameObject.CompareTag("BagGrid"))
{
Debug.Log("卸下装备");
BagController.Instance.DemountItem(itemID, CallBck);
}
}
protected override void Enter(PointerEventData eventData)
{
//eventData.dragging 是否处于拖动状态, 鼠标按下,并且再移动
if (eventData.dragging) return;
TipsUI.Instance.ShowTips(itemID, TipsUI.ItemGridType.Player, transform.position);
}
void CallBck(bool isFinish, string message)
{
//暂时测试使用
if (isFinish)
{
Debug.Log("完成了: " + message);
}
else
{
Debug.LogError(message);
}
}
}

BagGridUI

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.EventSystems;
public class BagGridUI : GridBase {
void Awake () {
base.Init();
gameObject.tag = "BagGrid";
}
protected override void Click(PointerEventData eventData)
{
if (itemID < ) return;
if (eventData.button == PointerEventData.InputButton.Right)
{
Debug.Log("装备: " + itemID);
BagController.Instance.EquipmentItem(itemID, BagData.Instance.GetItem(itemID).Type, CallBck);
}
}
protected override void EndDrag(PointerEventData eventData)
{
if (itemID < ) return;
base.EndDrag(eventData);
if (eventData.pointerCurrentRaycast.gameObject == null)//当拖出背包区域时
{
Debug.Log("卖出物品");
BagController.Instance.SellItem(itemID, CallBck);
}
else if(eventData.pointerCurrentRaycast.gameObject.CompareTag("PlayerGrid"))
{
Debug.Log("装备物品");
//获取到鼠标当前检测到的装备栏的类型
PlayerGridUI grid = eventData.pointerCurrentRaycast.gameObject.GetComponent<PlayerGridUI>();
BagController.Instance.EquipmentItem(itemID, grid.gridType, CallBck);
}
}
protected override void Enter(PointerEventData eventData)
{
//eventData.dragging 是否处于拖动状态, 鼠标按下,并且再移动
if (eventData.dragging) return;
TipsUI.Instance.ShowTips(itemID, TipsUI.ItemGridType.Bag, transform.position);
}
void CallBck(bool isFinish, string message)
{
//暂时测试使用
if (isFinish)
{
Debug.Log("完成了: " + message);
}
else
{
Debug.LogError(message);
}
}
}

TipsUI

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class TipsUI : MonoBehaviour
{
private Text nameText;
private Text typeText;
private Text atkText;
private Text defText;
private Text thumpText;
private Text hpText;
private Text mpText;
private Text angerText;
private Text weightText;
private static TipsUI instance;
public static TipsUI Instance
{
get
{
/*
if (null == instance)
{
instance = GameObject.Find("Tips").GetComponent<TipsUI>();
}
*/
return instance;
}
}
// Use this for initialization
void Awake()
{
instance = this;
nameText = transform.Find("NameText").GetComponent<Text>();
typeText = transform.Find("TypeText").GetComponent<Text>();
atkText = transform.Find("AtkText").GetComponent<Text>();
defText = transform.Find("DefText").GetComponent<Text>();
thumpText = transform.Find("ThumpText").GetComponent<Text>();
hpText = transform.Find("HpText").GetComponent<Text>();
mpText = transform.Find("MpText").GetComponent<Text>();
angerText = transform.Find("AngerText").GetComponent<Text>();
weightText = transform.Find("WeightText").GetComponent<Text>();
}
// Update is called once per frame
void Start()
{
gameObject.SetActive(false);
}
/// <summary>
/// 显示物品信息,
/// </summary>
/// <param name="id">物品的id</param>
/// <param name="type">物品在哪</param>
/// <param name="position">物品的位置</param>
public void ShowTips(int id, ItemGridType type, Vector3 position)
{
ItemData data = null;
if (type == ItemGridType.Bag)
{
data = BagData.Instance.GetItem(id);
}
else if (type == ItemGridType.Player)
{
data = PlayerData.Instance.GetItem(id);
}
if (data != null)
{
gameObject.SetActive(true);
nameText.text = "名字:" + data.ItemName;
typeText.text = "类型:" + ItemData.GetTypeName(data.Type);
atkText.text = "攻击力: +" + data.Atk.ToString();
defText.text = "防御力: +" + data.Def.ToString();
thumpText.text = "暴击率: +" + data.Thump.ToString();
hpText.text = "生命值: +" + data.Hp.ToString();
mpText.text = "魔法值: +" + data.Mp.ToString();
angerText.text = "怒气值: +" + data.Anger.ToString();
weightText.text = "负重:" + data.Weight.ToString();
transform.position = position;
Vector2 pivot;
//鼠标偏右
if (Input.mousePosition.x > Screen.width / 2f)
{
pivot.x = ;
}
else
{
pivot.x = ;
}
//鼠标偏上
if (Input.mousePosition.y > Screen.height / 2f)
{
pivot.y = ;
}
else
{
pivot.y = ;
}
(transform as RectTransform).pivot = pivot;
}
}
/// <summary>
/// 隐藏属性显示栏
/// </summary>
public void HideTips()
{
gameObject.SetActive(false);
}
public enum ItemGridType
{
Bag,
Player
}
}
Controller
BagController
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class BagController
{
#region 单例
private static BagController instance;
public static BagController Instance
{
get
{
if (instance == null)
{
instance = new BagController();
}
return instance;
}
}
private BagController() { }
#endregion
//回调信息
//第一个参数,是是否完成, 第二个参数, 传递过去的消息
public delegate void CallBack(bool isFinish, string message);
#region 处理数据的方法
/// <summary>
/// 卖出指定的ID的物品, 规定只能从背包卖
/// 第二个参数是:当完成或者未完成时,回调调用自己的View中的方法。
/// </summary>
/// <param name="id"></param>
public void SellItem(int id, CallBack callback)
{
//通过ID从背包中找到物品
ItemData data = BagData.Instance.GetItem(id);
//如果data是null, 背包中没有这个物品,id有问题
if (data == null)
{
//通知调用这个方法的View 你的ID是有问题的吧。
//Debug.LogError("通知调用这个方法的View 你的ID是有问题的吧。");
if (callback != null)
{
callback(false, "ID有问题!");
}
}
else
{
//删除物品
BagData.Instance.RemoveItem(data);
if (callback != null)
{
callback(true, "卖出成功");
}
}
}
/// <summary>
/// 装备物品
/// </summary>
/// 参数1: 要装备的物品的ID
/// 参数2: 要装备的位置
/// 参数3: View的回调函数(通知View的成功了还是失败)
public void EquipmentItem(int id, ItemType gridType, CallBack callback)
{
//判断ID是否存在
ItemData bagItem = BagData.Instance.GetItem(id);
if (bagItem == null)
{
//背包里没有这个ID的物品
if (callback != null)
{
callback(false, "背包里没有该ID的物品");
}
}
else
{
//如果背包有这个物品,
//判断该装备类型和你要装备的格子类型是否一致
if (bagItem.Type == gridType)//装备类型与格子类型一致,可以装备
{
//1. 装备栏有物品, 替换
//2. 装备栏没有物品, 直接装备
//首先判断装备栏是否有物品
ItemData playerItem = PlayerData.Instance.GetItem(gridType);
if (playerItem == null)
{
//证明该格子上没有装备
//先把该装备从背包数据里删除
BagData.Instance.RemoveItem(bagItem);
//再把物品添加到人物数据里
PlayerData.Instance.AddItem(bagItem);
}
else
{
//证明该格子上有装备
//先把人物身上的装备先删除
PlayerData.Instance.RemoveItem(playerItem);
//再把背包里的装备删除
BagData.Instance.RemoveItem(bagItem);
//把人物身上的装备添加到背包里
BagData.Instance.AddItem(playerItem);
//把背包里的装备添加到人物身上
PlayerData.Instance.AddItem(bagItem);
}
if (callback != null)
{
callback(true, "装备成功");
}
}
else
{
if (callback != null)
{
callback(false, "请把装备装到正确的位置");
}
}
}
}
/// <summary>
/// 卸下指定的id的装备,数据一定在playerData里
/// </summary>
/// <param name="id"></param>
/// <param name="callback"></param>
public void DemountItem(int id, CallBack callback)
{
//判断playerData里是否有这个id的装备
ItemData data = PlayerData.Instance.GetItem(id);
if (data == null)//空的时候,身上没有这个id的物品
{
if (callback != null)
{
callback(false, "人物身上没有该ID的物品");
}
}
else
{
//先把该装备从人物身上删除
PlayerData.Instance.RemoveItem(data);
//再把该装备添加到背包数据里去
BagData.Instance.AddItem(data);
//通知界面成功
if (callback != null)
{
callback(true, "成功卸载装备");
}
}
}
/// <summary>
/// 整理背包的方法
/// </summary>
public void ClearUp()
{
BagData.Instance.ItemsSort();
}
#endregion
}

LessonListSort

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class LessonListSort : MonoBehaviour {
List<int> listInt = new List<int>() { , , , , };
List<Obj> listObj = new List<Obj>() { new Obj(, "小明"), new Obj(, "小红") };
// Use this for initialization
void Start () {
listInt.Sort(ListIntSort);
for (int i = ; i < listInt.Count; i++)
{
Debug.Log(listInt[i]);
}
listObj.Sort(ListObjSort);
for (int i = ; i < listObj.Count; i++)
{
Debug.Log(listObj[i].name);
}
} // Update is called once per frame
void Update () { }
int ListIntSort(int a, int b)
{
if (a < b)
{
return -;
}
else if (a > b)
{
return ;
}
else
{
return ;
}
}
public class Obj
{
public int id;
public string name;
public Obj(int id, string name)
{
this.id = id;
this.name = name;
}
}
int ListObjSort(Obj a, Obj b)
{
if (a.id < b.id)
{
return ;
}
else if (a.id > b.id)
{
return -;
}
else
{
return ;
}
}
}

改格子的枚举

假ID报错

无法再次装备的问题:取消格子里图片和文本的射线检测

整理功能,即列表排序

数值的排序
类对象的排序
List的自定义排序
List.sort(有int返回值,有两个参数List存储类型的参数)
 对于这个方法
Int Sort (T a, T b)
如果返回值是-1,a排在b前
如果返回值是1,b排在a前
如果返回值是,a,b的权重是一致的
枚举转Int,也可比较大
关闭射线检测

Unity3D学习笔记(二十七):MVC框架下的背包系统(2)的更多相关文章

  1. MongoDB学习笔记(三) 在MVC模式下通过Jqgrid表格操作MongoDB数据

    看到下图,是通过Jqgrid实现表格数据的基本增删查改的操作.表格数据增删改是一般企业应用系统开发的常见功能,不过不同的是这个表格数据来源是非关系型的数据库MongoDB.nosql虽然概念新颖,但是 ...

  2. Unity3D学习笔记(二十六):MVC框架下的背包系统(1)

    MVC背包 需求: 1.背包格子的装备是可以拖动的 2.装备栏的装备也是可以拖动的 3.当背包格子的装备拖动到装备栏时,如果是装备类型和装备栏类型是一致的能装上 4.背包的装备是按照顺序放在格子中的, ...

  3. Gin-Go学习笔记二:Gin-Web框架

    Gin-Web框架 1>     首先声明,这个是我自己搭建的纯Gin-Web框架,其中有借鉴学习别的想法和代码.已上传到GitHub上.地址为: https://github.com/weiy ...

  4. Java基础学习笔记二十七 DBUtils和连接池

    DBUtils 如果只使用JDBC进行开发,我们会发现冗余代码过多,为了简化JDBC开发,本案例我们讲采用apache commons组件一个成员:DBUtils.DBUtils就是JDBC的简化开发 ...

  5. Unity3D学习笔记(十七):IK动画、粒子系统和塔防

    新动画系统: 反向动力学动画(IK功能): 魔兽世界(头部动画),神秘海域(手部动画),人类一败涂地(手部动画) 如何启用(调整) 1.必须是新动画系统Animator 设置头.手.肘的目标点 2.动 ...

  6. angular学习笔记(二十七)-$http(5)-使用$http构建RESTful架构

    在angular中有一个特别为RESTful架构而定制的服务,是在$http的基础上进行了封装. 但是为了学习,我们先看看用直接$http是如何构建RESTful架构的: 假设有一个银行卡的列表.需要 ...

  7. Java学习笔记二十七:Java中的抽象类

    Java中的抽象类 一:Java抽象类: 在面向对象的概念中,所有的对象都是通过类来描绘的,但是反过来,并不是所有的类都是用来描绘对象的,如果一个类中没有包含足够的信息来描绘一个具体的对象,这样的类就 ...

  8. PHP学习笔记二十七【重写】

    <?php // class Animal{ public $name; protected $price; function cry(){ echo "动物在叫....<br/ ...

  9. 【工作笔记二】ASP.NET MVC框架下使用MVVM模式

    ASP.NET MVC框架下使用MVVM模式 原文:http://www.cnblogs.com/n-pei/archive/2011/07/21/2113022.html 对于asp.net mvc ...

随机推荐

  1. eclipse更换workspace需要重新设置的内容

    .jdk Window-->java-->Installed JREs,新增或修改你所需要的jdk版本,点击需要的jdk-->edit 在Default VM arguments里面 ...

  2. SQL 中的连接查询

    关于SQL的应用,肯定离不开查询,而相对复杂的查询,总是离不开对表的连接,单个表操作的并不罕见,但是在应用环境大多数的查询都是针对2.3个表甚至更多的表7,至于连接,有内连接.外链接.交叉连接之分,每 ...

  3. 为什么C++函数形参默认值从最末一个赋值?

    [1]函数调用时形参的压栈顺序 1.示例代码如下(VS2010): #include <iostream> using namespace std; ); void fun(int a, ...

  4. STL容器之map

    [1]map容器 map 是关联容器.容器中的每一个元素都是由一个键值和一个数据值组成的. set 是一个集合它以其元素作为键值(同一个键值只能出现一次),且默认以升序排列. list 是一个顺序容器 ...

  5. python XML文件解析:用xml.dom.minidom来解析xml文件

    python解析XML常见的有三种方法: 一是xml.dom.*模块,是W3C DOM API的实现,若需要处理DOM API则该模块很合适, 二是xml.sax.*模块,它是SAX API的实现,这 ...

  6. 直流-直流(DC-DC)变换电路_BUCK&BOOST变换电路

    1. 直流—直流变换器通过对电力电子器件的通断控制,将直流电压断续地加到负载上,通过改变占空比改变输出电压平均值. BUCK线路原理图如上,其中Q管/MOS作为开关管,驱动电压一般为PWM. 当开关管 ...

  7. 20165305 苏振龙《Java程序设计》第八周课上测试补做

    1. 下载附件中的world.sql.zip, 参考http://www.cnblogs.com/rocedu/p/6371315.html#SECDB,导入world.sql,提交导入成功截图 2. ...

  8. Deprecated: getEntityManager is deprecated since Symfony 2.1

    PHP5.3应用中,登陆后台管理时提示错误: Deprecated: getEntityManager is deprecated since Symfony 2.1. Use getManager  ...

  9. Ford VCM II Ford VCM2 Diagnostic Tool with Ford IDS v108 Installed On Laptop Ready to Use

    HOW to VCM2 Ford VCM II with Ford IDS v108 Work Well? VCM2 Ford VCM2 Ford diagnostic tool hot sale i ...

  10. xml文件中[Invalid byte 1 of 1-byte UTF-8 sequence.]的解决方案

    问题描述: 导入项目包后发生xml文件出现错误信息:[Invalid byte 1 of 1-byte UTF-8 sequence.],如下截图所示: 解决方案: 将xml文件全部内容剪切到Note ...