一、脚本编写
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.EventSystems;
public class DragTest : MonoBehaviour
{
//3D目标
public List<GameObject> listTargets = new List<GameObject>();
//2D目标点
public List<Image> listUITargets = new List<Image>();
//操作模式
bool isUI = false;
public Button buttonUI;
public Button buttonModel;
//起始坐标
Vector3 starPos;
private void Start()
{
starPos = transform.localPosition;
buttonUI.onClick.AddListener(()=>
{
isUI = true;
});
buttonModel.onClick.AddListener(() =>
{
isUI = false;
});
}
public void OnMouseDrag()
{
Vector3 screenPos = Camera.main.WorldToScreenPoint(transform.position);
Vector3 mouseScreenPos = new Vector3(Input.mousePosition.x, Input.mousePosition.y, screenPos.z);
transform.position = Camera.main.ScreenToWorldPoint(mouseScreenPos);
Debug.Log("OnMouseDrag");
}
public void OnMouseUp()
{
if (isUI==false)
{
//是否落位
bool isTarget = false;
foreach (GameObject item in listTargets)
{
if (GetOverGameObject(Camera.main.gameObject).Contains(item))
{
isTarget = true;
transform.position = item.transform.position;
break;
}
}
if (isTarget == false)
{
transform.position = starPos;
}
}
else
{
foreach (Image item in listUITargets)
{
if (GetOverUI(GameObject.Find("Canvas")).Count>0)
{
List<GameObject> listTemp = new List<GameObject>();
listTemp.AddRange(GetOverUI(GameObject.Find("Canvas")));
if (listTemp.Contains(item.gameObject))
{
//简单做一个变色效果,实际应用中可能会是改Image的sprite之类的操作
item.GetComponent<Image>().color = Color.green;
break;
}
}
}
transform.position = starPos;
}
//有时候操作次数多了会出现不能拖拽的问题,暂时没去看是什么原因,将该对象关闭打开一次可暂时解决。
gameObject.SetActive(false);
gameObject.SetActive(true);
}
//获取光标停留的3D物体
public List<GameObject> GetOverGameObject(GameObject raycaster)
{
PointerEventData pointerEventData = new PointerEventData(EventSystem.current);
pointerEventData.position = Input.mousePosition;
PhysicsRaycaster pr = raycaster.GetComponent<PhysicsRaycaster>();
List<RaycastResult> results = new List<RaycastResult>();
pr.Raycast(pointerEventData, results);
List<GameObject> listObjs = new List<GameObject>();
if (results.Count != 0)
{
foreach (RaycastResult item in results)
{
listObjs.Add(item.gameObject);
}
//return listObjs;
}
return listObjs;
}
//获取光标停留的UI物体
public List<GameObject> GetOverUI(GameObject canvas)
{
PointerEventData pointerEventData = new PointerEventData(EventSystem.current);
pointerEventData.position = Input.mousePosition;
GraphicRaycaster gr = canvas.GetComponent<GraphicRaycaster>();
List<RaycastResult> results = new List<RaycastResult>();
gr.Raycast(pointerEventData, results);
List<GameObject> listObjs = new List<GameObject>();
if (results.Count != 0)
{
foreach (RaycastResult item in results)
{
listObjs.Add(item.gameObject);
}
//return listObjs;
}
return listObjs;
}
}
二、编辑场景
1.新建一个cube作为我们用来拖拽的物体:
2.给该cube添加我们刚刚编写的脚本:
3.场景中新建几个cube命名为Taget3D,摆在不同的位置并将这些新的cube传入到ListTartgets中:
4.新建几个Image命名为TargetUI,放在不同的位置并传入到ListUITarget中 :
5.新建两个Button分别对应传入buttonUI和buttonModel:
6.在Main Camera上添加PhisicsRaycaster组件:
三、运行调试
此时点击运行,点击”模型模式“Button,然后拖动我们的cube到左边的一排Target3D物体上去,效果如下:
然后我们点击”UI模式“Button,再去拖动我们的cube与右边的一排TargetUI对象进行交互,可以看到效果如下:
文章来源:https://www.toymoban.com/news/detail-507374.html
至此,我们的拖拽功能就基本实现了。文章来源地址https://www.toymoban.com/news/detail-507374.html
到了这里,关于Unity中拖拽3D物体并放入到指定位置的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!