【NGUI】扩展NGUI例子实现拖动交换位置功能

来源:互联网 发布:天蝎网络第三季 百度 编辑:程序博客网 时间:2024/06/05 19:15

大家在学习NGUI的时候有接触过这个例子吧?

 

图1 Example 11 - Drag & Drop

这个例子已经很全面的实现了拖动物体和放下物体到某处(3D或2D),为了更深入的理解这个例子,我们现在来学习并扩展这个例子。

  1. 需求:有六张卡牌,拖动任意一张卡牌到相应的另一张卡牌位置上,可以自动进行两张卡牌的位置调换。
  2. 分析:通过这个例子,我们虽然可以拖出物体放置到另一个地方,但是不会和任何物体位置调换,所以我们要适当的扩展相应的代码。
  3. 思路:根据需求,首先我们需要有六张卡牌在Grid下,并且是按一定的编号顺序排列好的,存放在一个List中。然后拖动其中任意一张卡牌到任意位置,如果碰撞器没有Trigger到其他牌,则按原来的List排序顺序排序。反之Trigger到了其他牌,则交换他们的编号,重新排序List,就可以实现交换的效果了。
  4. 实现:

首先Copy一份UIGrid.cs的代码,重命名为XUIGrid.cs,我们自定义三个参数,分别为:

[csharp] view plain copy
  1. public int maxNum = 6;  //最大数量  
  2. public int maxPerLine = 3;  //每行最大数量  
  3. [HideInInspector]  
  4. public string dragName; //当前拖动的排序名称  
  5. [HideInInspector]  
  6. public string replaceName;  //需要替换的排序名称  
  7. protected List<int> listData = new List<int>();    //排序数据  

在Init()方法中初始化listData的数据:

[csharp] view plain copy
  1. protected virtual void Init()  
  2. {  
  3.     //排序编号  
  4.     if (!mInitDone)  
  5.     {  
  6.         for (int i = 0; i < maxNum; i++)  
  7.         {  
  8.             listData.Add(i);  
  9.         }  
  10.         mInitDone = true;  
  11.     }  
  12. }  

新增一个可以处理交换位置的Sort方法,供每次重新排序时调用,即GetChildList()方法:

[csharp] view plain copy
  1. protected void Sort(List<Transform> list)  
  2. {  
  3.     if (!string.IsNullOrEmpty(dragName) && !string.IsNullOrEmpty(replaceName))  
  4.     {  
  5.         int dragNo = listData.IndexOf(int.Parse(dragName));    //根据当前排序名字获取服务器数据存储List中的位置  
  6.         int replaceNo = listData.IndexOf(int.Parse(replaceName));  
  7.         //替换List位置  
  8.         Transform tempList = list[replaceNo];  
  9.         list[replaceNo] = list[dragNo];  
  10.         list[dragNo] = tempList;  
  11.     }  
  12. }  

交换完成后我们还要保证listData中存储最新的排序方式,不然下次再交换会导致交换不正确。在ResetPosition()方法的末尾加上如下代码:

[csharp] view plain copy
  1. if (list.Count > 0 && t != null)  
  2. {  
  3.     SavePos(list);  
  4. }  

SavePos()方法:

[csharp] view plain copy
  1. void SavePos(List<Transform> list)  
  2. {  
  3.     listData.Clear();  
  4.     for (int i = 0; i < list.Count; i++)  
  5.     {  
  6.         listData.Add(int.Parse(list[i].name));  
  7.     }  
  8. }  

这里我们的XUIGrid已经实现得差不多了,现在我们修改一下UIDragDropItem.cs,我们也Copy一份出来,重命名为XUIDragDropItem.cs

首先,我们要获取当前拖动的卡牌编号,即在OnDragDropStart()方法中给XUIGrid的dragName赋值:

[csharp] view plain copy
  1. mGrid = NGUITools.FindInParents<XUIGrid>(mParent);  
  2. if (mGrid != null)  
  3. {  
  4.     mGrid.dragName = mTrans.name;  
  5. }  

然后,在OnDragDropRelease()中调用XUIGrid的repositionNow=true

[csharp] view plain copy
  1. mGrid = NGUITools.FindInParents<XUIGrid>(mParent);  
  2. if (mGrid != null) mGrid.repositionNow = true;  

最后,就是OnTriggerEnter方法的处理,把当前卡牌和目标卡牌编号传递给XUIGrid。

[csharp] view plain copy
  1. void OnTriggerEnter(Collider other)  
  2. {  
  3.     mGrid = NGUITools.FindInParents<XUIGrid>(mTrans.parent);  
  4.     if (mGrid != null)  
  5.     {  
  6.         mGrid.dragName = gameObject.name;  
  7.         mGrid.replaceName = other.name;  
  8.     }  
  9. }  

下面来看看测试效果~

 

 

 

本例子实例项目下载地址:http://download.csdn.net/detail/yangyy753/8696945


Ricky Yang个人原创,版权所有。转载地址:http://blog.csdn.net/yangyy753/article/details/45698785

 


原创粉丝点击