拿一张图片剪切好备用
在Canvas下新建panel作为父物体
在下面建一个Image名为——Cell
在Cell下新建image,改Tag为Cell
在这个image上挂脚本:
using UnityEngine; using System.Collections; using UnityEngine.EventSystems; public class DragOnPic : MonoBehaviour, IBeginDragHandler, IDragHandler, IEndDragHandler { //记录下自己的父物体. Transform myParent; //Panel,使拖拽是显示在最上方. Transform tempParent; CanvasGroup cg; RectTransform rt; //记录鼠标位置. Vector3 newPosition; void Awake() { //添加CanvasGroup组件用于在拖拽是忽略自己,从而检测到被交换的图片. cg = this.gameObject.AddComponent<CanvasGroup>(); rt = this.GetComponent<RectTransform>(); tempParent = GameObject.Find("Canvas").transform; } /// <summary> /// Raises the begin drag event. /// </summary> public void OnBeginDrag(PointerEventData eventData) { //拖拽开始时记下自己的父物体. myParent = transform.parent; //拖拽开始时禁用检测. cg.blocksRaycasts = false; this.transform.SetParent(tempParent); } /// <summary> /// Raises the drag event. /// </summary> void IDragHandler.OnDrag(PointerEventData eventData) { //推拽是图片跟随鼠标移动. RectTransformUtility.ScreenPointToWorldPointInRectangle(rt, Input.mousePosition, eventData.enterEventCamera, out newPosition); transform.position = newPosition; } /// <summary> /// Raises the end drag event. /// </summary> public void OnEndDrag(PointerEventData eventData) { //获取鼠标下面的物体. GameObject target = eventData.pointerEnter; //如果能检测到物体. if (target) { //如果检测到图片,则交换父物体并重置位置. GameManager.SetParent(this.transform, target.transform, myParent); } else { this.transform.SetParent(myParent); this.transform.localPosition = Vector3.zero; } //拖拽结束时启用检测. cg.blocksRaycasts = true; //检测是否完成拼图. if (GameManager.CheckWin()) { Debug.Log("Win!!!"); } if (!GameManager.CheckWin()) { Debug.Log("没拼好"); } } }
新建个脚本GameManager类,随机生成图片位置和拖拽时交换父物体和位置,不需要挂,
using System.Collections; using System.Collections.Generic; using UnityEngine; public class GameManager { /// <summary> /// Randoms the array. /// </summary> static public void RandomArray(Sprite[] sprites) { for (int i = 0; i < sprites.Length; i++) { //随机抽取数字中的一个位置,并将这张图片与第i张图片交换. int index = Random.Range(i, sprites.Length); Sprite temp = sprites[i]; sprites[i] = sprites[index]; sprites[index] = temp; } } /// <summary> /// Sets the parent. /// </summary> static public void SetParent(Transform mine, Transform target, Transform oldParent) { //如果检测到图片,则交换父物体并重置位置. switch (target.tag) { case "Cell": mine.SetParent(target.parent); target.SetParent(oldParent); mine.localPosition = Vector3.zero; target.localPosition = Vector3.zero; break; default: mine.SetParent(oldParent); mine.localPosition = Vector3.zero; break; } } /// <summary> /// Checks is win. /// </summary> static public bool CheckWin() { for (int i = 0; i < ImageCreater._instance.transform.childCount; i++) { if (ImageCreater._instance.transform.GetChild(i).name != ImageCreater._instance.transform.GetChild(i).transform.GetChild(0).name) { return false; } } return true; } }
在panel上添加组件:Grid Layput Group 挂上脚本:
using UnityEngine; using System.Collections; using UnityEngine.UI; public class ImageCreater : MonoBehaviour { //单例模式 public static ImageCreater _instance; //存储裁剪好图片的数组. public Sprite[] sprites; //格子的预设体. public GameObject cellPrefab; void Start() { _instance = this; CreateImages(); } private void CreateImages() { //将图片数组随机排列. GameManager.RandomArray(sprites); //生产图片. for (int i = 0; i < sprites.Length; i++) { //通过预设体生成图片. GameObject cell = (GameObject)Instantiate(cellPrefab); //设置cell的名字方便检测是否完成拼图. cell.name = i.ToString(); //获取cell的子物体. Transform image = cell.transform.GetChild(0); //设置显示的图片. image.GetComponent<Image>().sprite = sprites[i]; //设置子物体的名称,方便检测是否完成拼图. int tempIndex = sprites[i].name.LastIndexOf('_'); image.name = sprites[i].name.Substring(tempIndex + 1); //将Cell设置为Panel的子物体. cell.transform.SetParent(this.transform); //初始化大小. cell.transform.localScale = Vector3.one; } } }
运行即可生成图片,并达到拖拽,换位置信息的功能: