效果:點擊白色框可拖拽選擇區域ide
代碼:3d
using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.EventSystems; public class jietu : MonoBehaviour, IDragHandler, IEndDragHandler,IBeginDragHandler { void Start() { //DrawTriangle(30, 0, 100, 250, 200, 100, mat);//三角形的三個定點座標 } public void OnBeginDrag(PointerEventData eventData) { dragObj = eventData.rawPointerPress; } public void OnDrag(PointerEventData eventData) { if (dragObj!=null) { dragObj.transform.position = Input.mousePosition; leftBottomPos = leftBottom.transform.position; leftTopPos = leftTop.transform.position; rightTopPos = rightTop.transform.position; rightBottomPos = rightBottom.transform.position; if (dragObj.Equals(leftBottom)) { leftTopPos.x = dragObj.transform.position.x; rightBottomPos.y= dragObj.transform.position.y; leftTop.transform.position = leftTopPos; rightBottom.transform.position = rightBottomPos; } else if (dragObj.Equals(leftTop)) { leftBottomPos.x = dragObj.transform.position.x; rightTopPos.y = dragObj.transform.position.y; leftBottom.transform.position = leftBottomPos; rightTop.transform.position = rightTopPos; } else if (dragObj.Equals(rightTop)) { rightBottomPos.x = dragObj.transform.position.x; leftTopPos.y = dragObj.transform.position.y; rightBottom.transform.position = rightBottomPos; leftTop.transform.position = leftTopPos; } else if (dragObj.Equals(rightBottom)) { rightTopPos.x = dragObj.transform.position.x; leftBottomPos.y = dragObj.transform.position.y; rightTop.transform.position = rightTopPos; leftBottom.transform.position = leftBottomPos; } } } public void OnEndDrag(PointerEventData eventData) { dragObj = null; } GameObject dragObj; public GameObject leftBottom; public GameObject leftTop; public GameObject rightTop; public GameObject rightBottom; Vector2 leftBottomPos = Vector2.zero; Vector2 leftTopPos = Vector2.zero; Vector2 rightTopPos = Vector2.zero; Vector2 rightBottomPos = Vector2.zero; public Material mat; void OnRenderObject() { DrawTriangle();//三角形的三個定點座標 } void DrawTriangle() { GL.PushMatrix(); mat.SetPass(0); GL.LoadOrtho(); GL.Begin(GL.QUADS);//順時針方向 //頂部 GL.Vertex3(leftTop.transform.position.x / Screen.width, leftTop.transform.position.y / Screen.height, 0); GL.Vertex3(0, 1, 0); GL.Vertex3(1, 1, 0); GL.Vertex3(rightTop.transform.position.x / Screen.width, rightTop.transform.position.y / Screen.height, 0); //右側 GL.Vertex3(rightBottom.transform.position.x / Screen.width, rightBottom.transform.position.y / Screen.height, 0); GL.Vertex3(rightTop.transform.position.x / Screen.width, rightTop.transform.position.y / Screen.height, 0); GL.Vertex3(1, 1, 0); GL.Vertex3(1, 0, 0); //底部 GL.Vertex3(0, 0, 0);//屏幕左下角 GL.Vertex3(leftBottom.transform.position.x / Screen.width, leftBottom.transform.position.y / Screen.height, 0);//屏幕左上角 GL.Vertex3(rightBottom.transform.position.x / Screen.width, rightBottom.transform.position.y / Screen.height, 0);//屏幕右上角 GL.Vertex3(1, 0, 0);//屏幕右下角 //左側 GL.Vertex3(0, 0, 0); GL.Vertex3(0, 1, 0); GL.Vertex3(leftTop.transform.position.x / Screen.width, leftTop.transform.position.y / Screen.height, 0); GL.Vertex3(leftBottom.transform.position.x / Screen.width, leftBottom.transform.position.y / Screen.height, 0); GL.End(); GL.PopMatrix(); } }
unity裏的設置orm
改良版:限定剪裁區域的最小範圍blog
using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.EventSystems; public class jietu : MonoBehaviour, IDragHandler, IEndDragHandler, IBeginDragHandler { GameObject dragObj; public GameObject leftBottom; public GameObject leftTop; public GameObject rightTop; public GameObject rightBottom; Vector2 leftBottomPos; Vector2 leftTopPos; Vector2 rightTopPos; Vector2 rightBottomPos; public Material mat; public float x_min = 100; public float y_min = 100; public void OnBeginDrag(PointerEventData eventData) { dragObj = eventData.rawPointerPress; leftBottomPos = leftBottom.transform.position; leftTopPos = leftTop.transform.position; rightTopPos = rightTop.transform.position; rightBottomPos = rightBottom.transform.position; } public void OnDrag(PointerEventData eventData) { if (dragObj != null) { if (dragObj.Equals(leftBottom)) { if ((rightTopPos.x - Input.mousePosition.x) > x_min) { leftBottomPos.x = Input.mousePosition.x; leftTopPos.x = Input.mousePosition.x; leftBottom.transform.position = leftBottomPos; leftTop.transform.position = leftTopPos; } if ((rightTopPos.y - Input.mousePosition.y) > y_min) { leftBottomPos.y = Input.mousePosition.y; rightBottomPos.y = Input.mousePosition.y; leftBottom.transform.position = leftBottomPos; rightBottom.transform.position = rightBottomPos; } } else if (dragObj.Equals(leftTop)) { if ((rightBottomPos.x - Input.mousePosition.x) > x_min) { leftTopPos.x = Input.mousePosition.x; leftBottomPos.x = Input.mousePosition.x; leftTop.transform.position = leftTopPos; leftBottom.transform.position = leftBottomPos; } if ((Input.mousePosition.y - rightBottomPos.y) > y_min) { leftTopPos.y = Input.mousePosition.y; rightTopPos.y = Input.mousePosition.y; leftTop.transform.position = leftTopPos; rightTop.transform.position = rightTopPos; } } else if (dragObj.Equals(rightTop)) { if ((Input.mousePosition.x - leftBottomPos.x) > x_min) { rightTopPos.x = Input.mousePosition.x; rightBottomPos.x = Input.mousePosition.x; rightTop.transform.position = rightTopPos; rightBottom.transform.position = rightBottomPos; } if ((Input.mousePosition.y - leftBottomPos.y) > y_min) { rightTopPos.y = Input.mousePosition.y; leftTopPos.y = Input.mousePosition.y; rightTop.transform.position = rightTopPos; leftTop.transform.position = leftTopPos; } } else if (dragObj.Equals(rightBottom)) { if ((Input.mousePosition.x - leftTopPos.x) > x_min) { rightBottomPos.x = Input.mousePosition.x; rightTopPos.x = Input.mousePosition.x; rightBottom.transform.position = rightBottomPos; rightTop.transform.position = rightTopPos; } if ((leftTopPos.y - Input.mousePosition.y) > y_min) { rightBottomPos.y = Input.mousePosition.y; leftBottomPos.y = Input.mousePosition.y; rightBottom.transform.position = rightBottomPos; leftBottom.transform.position = leftBottomPos; } } } } public void OnEndDrag(PointerEventData eventData) { dragObj = null; } void OnRenderObject() { DrawTriangle();//三角形的三個定點座標 } void DrawTriangle() { GL.PushMatrix(); mat.SetPass(0); GL.LoadOrtho(); GL.Begin(GL.QUADS);//順時針方向 //頂部 GL.Vertex3(leftTop.transform.position.x / Screen.width, leftTop.transform.position.y / Screen.height, 0); GL.Vertex3(0, 1, 0); GL.Vertex3(1, 1, 0); GL.Vertex3(rightTop.transform.position.x / Screen.width, rightTop.transform.position.y / Screen.height, 0); //右側 GL.Vertex3(rightBottom.transform.position.x / Screen.width, rightBottom.transform.position.y / Screen.height, 0); GL.Vertex3(rightTop.transform.position.x / Screen.width, rightTop.transform.position.y / Screen.height, 0); GL.Vertex3(1, 1, 0); GL.Vertex3(1, 0, 0); //底部 GL.Vertex3(0, 0, 0);//屏幕左下角 GL.Vertex3(leftBottom.transform.position.x / Screen.width, leftBottom.transform.position.y / Screen.height, 0);//屏幕左上角 GL.Vertex3(rightBottom.transform.position.x / Screen.width, rightBottom.transform.position.y / Screen.height, 0);//屏幕右上角 GL.Vertex3(1, 0, 0);//屏幕右下角 //左側 GL.Vertex3(0, 0, 0); GL.Vertex3(0, 1, 0); GL.Vertex3(leftTop.transform.position.x / Screen.width, leftTop.transform.position.y / Screen.height, 0); GL.Vertex3(leftBottom.transform.position.x / Screen.width, leftBottom.transform.position.y / Screen.height, 0); GL.End(); GL.PopMatrix(); } }
在實際使用的時候發現用GL畫的圖像,會致使沒法適應UGUI的層級關係,永遠位於UI的下層或者上層(取決於Canvas的Render mode),it
下面是改良版本,完美適應UI的層級關係io
代碼以下:event
using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.EventSystems; using UnityEngine.Serialization; using UnityEngine.UI; public class LineChart : MaskableGraphic, IDragHandler, IEndDragHandler, IBeginDragHandler { protected override void OnPopulateMesh(VertexHelper vh) { vh.Clear(); UIVertex[] verts0 = new UIVertex[4]; //頂部 verts0[0]=SetVertexs(verts0[0], leftTop.transform.localPosition); verts0[1]=SetVertexs(verts0[1], screen_leftTopPos); verts0[2]=SetVertexs(verts0[2], screen_rightTopPos); verts0[3] = SetVertexs(verts0[3], rightTop.transform.localPosition); vh.AddUIVertexQuad(verts0); UIVertex[] verts1 = new UIVertex[4]; //右側 verts1[0] = SetVertexs(verts1[0], rightBottom.transform.localPosition); verts1[1] = SetVertexs(verts1[1], rightTop.transform.localPosition); verts1[2] = SetVertexs(verts1[2], screen_rightTopPos); verts1[3] = SetVertexs(verts1[3], screen_rightBottomPos); vh.AddUIVertexQuad(verts1); //底部 UIVertex[] verts2 = new UIVertex[4]; verts2[0] = SetVertexs(verts2[0], screen_leftBottomPos);//屏幕左下角 verts2[1] = SetVertexs(verts2[1], leftBottom.transform.localPosition);//屏幕左上角 verts2[2] = SetVertexs(verts2[2], rightBottom.transform.localPosition);//屏幕右上角 verts2[3] = SetVertexs(verts2[3], screen_rightBottomPos);//屏幕右下角 vh.AddUIVertexQuad(verts2); //左側 UIVertex[] verts3 = new UIVertex[4]; verts3[0] = SetVertexs(verts3[0], screen_leftBottomPos); verts3[1] = SetVertexs(verts3[1], screen_leftTopPos); verts3[2] = SetVertexs(verts3[2], leftTop.transform.localPosition); verts3[3] = SetVertexs(verts3[3], leftBottom.transform.localPosition); vh.AddUIVertexQuad(verts3); } GameObject dragObj; public GameObject leftBottom; public GameObject leftTop; public GameObject rightTop; public GameObject rightBottom; Vector2 leftBottomPos; Vector2 leftTopPos; Vector2 rightTopPos; Vector2 rightBottomPos; public float x_min = 100; public float y_min = 100; readonly Vector2 screen_leftBottomPos= new Vector3(-Screen.width * 0.5f, -Screen.height * 0.5f); readonly Vector2 screen_leftTopPos= new Vector3(-Screen.width * 0.5f, Screen.height * 0.5f); readonly Vector2 screen_rightTopPos= new Vector3(Screen.width * 0.5f, Screen.height * 0.5f); readonly Vector2 screen_rightBottomPos= new Vector3(Screen.width * 0.5f, -Screen.height * 0.5f); public void OnBeginDrag(PointerEventData eventData) { dragObj = eventData.rawPointerPress; leftBottomPos = leftBottom.transform.localPosition; leftTopPos = leftTop.transform.localPosition; rightTopPos = rightTop.transform.localPosition; rightBottomPos = rightBottom.transform.localPosition; } public void OnDrag(PointerEventData eventData) { if (dragObj != null) { float x = Input.mousePosition.x - Screen.width * 0.5f; float y = Input.mousePosition.y - Screen.height * 0.5f; if (dragObj.Equals(leftBottom)) { if ((rightTopPos.x - x) > x_min) { leftBottomPos.x = x; leftTopPos.x = x; leftBottom.transform.localPosition = leftBottomPos; leftTop.transform.localPosition = leftTopPos; } if ((rightTopPos.y - y) > y_min) { leftBottomPos.y = y; rightBottomPos.y = y; leftBottom.transform.localPosition = leftBottomPos; rightBottom.transform.localPosition = rightBottomPos; } } else if (dragObj.Equals(leftTop)) { if ((rightBottomPos.x - x) > x_min) { leftTopPos.x = x; leftBottomPos.x = x; leftTop.transform.localPosition = leftTopPos; leftBottom.transform.localPosition = leftBottomPos; } if ((y - rightBottomPos.y) > y_min) { leftTopPos.y = y; rightTopPos.y = y; leftTop.transform.localPosition = leftTopPos; rightTop.transform.localPosition = rightTopPos; } } else if (dragObj.Equals(rightTop)) { if ((x - leftBottomPos.x) > x_min) { rightTopPos.x = x; rightBottomPos.x = x; rightTop.transform.localPosition = rightTopPos; rightBottom.transform.localPosition = rightBottomPos; } if ((y - leftBottomPos.y) > y_min) { rightTopPos.y = y; leftTopPos.y = y; rightTop.transform.localPosition = rightTopPos; leftTop.transform.localPosition = leftTopPos; } } else if (dragObj.Equals(rightBottom)) { if ((x - leftTopPos.x) > x_min) { rightBottomPos.x = x; rightTopPos.x = x; rightBottom.transform.localPosition = rightBottomPos; rightTop.transform.localPosition = rightTopPos; } if ((leftTopPos.y - y) > y_min) { rightBottomPos.y = y; leftBottomPos.y = y; rightBottom.transform.localPosition = rightBottomPos; leftBottom.transform.localPosition = leftBottomPos; } } } UpdateGeometry(); } public void OnEndDrag(PointerEventData eventData) { dragObj = null; } UIVertex SetVertexs(UIVertex vertex, Vector2 vertexPos) { vertex.position = vertexPos; vertex.color = color;//color是父類中的屬性 vertex.uv0 = Vector2.zero; return vertex; } }
最終版本:form
using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.EventSystems; using UnityEngine.UI; public class LineChart : Graphic, IDragHandler, IEndDragHandler, IBeginDragHandler { protected override void OnPopulateMesh(VertexHelper vh) { vh.Clear(); //頂部 verts0[0]=SetVertexs(verts0[0], leftTop.transform.localPosition); verts0[1]=SetVertexs(verts0[1], screen_leftTopPos); verts0[2]=SetVertexs(verts0[2], screen_rightTopPos); verts0[3] = SetVertexs(verts0[3], rightTop.transform.localPosition); vh.AddUIVertexQuad(verts0); //右側 verts1[0] = SetVertexs(verts1[0], rightBottom.transform.localPosition); verts1[1] = SetVertexs(verts1[1], rightTop.transform.localPosition); verts1[2] = SetVertexs(verts1[2], screen_rightTopPos); verts1[3] = SetVertexs(verts1[3], screen_rightBottomPos); vh.AddUIVertexQuad(verts1); //底部 verts2[0] = SetVertexs(verts2[0], screen_leftBottomPos);//屏幕左下角 verts2[1] = SetVertexs(verts2[1], leftBottom.transform.localPosition);//屏幕左上角 verts2[2] = SetVertexs(verts2[2], rightBottom.transform.localPosition);//屏幕右上角 verts2[3] = SetVertexs(verts2[3], screen_rightBottomPos);//屏幕右下角 vh.AddUIVertexQuad(verts2); //左側 verts3[0] = SetVertexs(verts3[0], screen_leftBottomPos); verts3[1] = SetVertexs(verts3[1], screen_leftTopPos); verts3[2] = SetVertexs(verts3[2], leftTop.transform.localPosition); verts3[3] = SetVertexs(verts3[3], leftBottom.transform.localPosition); vh.AddUIVertexQuad(verts3); } public GameObject leftBottom; public GameObject leftTop; public GameObject rightTop; public GameObject rightBottom; public float x_min = 100; public float y_min = 100; GameObject dragObj; Vector2 leftBottomPos; Vector2 leftTopPos; Vector2 rightTopPos; Vector2 rightBottomPos; readonly UIVertex[] verts0 = new UIVertex[4]; readonly UIVertex[] verts1 = new UIVertex[4]; readonly UIVertex[] verts2 = new UIVertex[4]; readonly UIVertex[] verts3 = new UIVertex[4]; readonly Vector2 screen_leftBottomPos= new Vector3(-Screen.width * 0.5f, -Screen.height * 0.5f); readonly Vector2 screen_leftTopPos= new Vector3(-Screen.width * 0.5f, Screen.height * 0.5f); readonly Vector2 screen_rightTopPos= new Vector3(Screen.width * 0.5f, Screen.height * 0.5f); readonly Vector2 screen_rightBottomPos= new Vector3(Screen.width * 0.5f, -Screen.height * 0.5f); public void OnBeginDrag(PointerEventData eventData) { dragObj = eventData.rawPointerPress; leftBottomPos = leftBottom.transform.localPosition; leftTopPos = leftTop.transform.localPosition; rightTopPos = rightTop.transform.localPosition; rightBottomPos = rightBottom.transform.localPosition; } public void OnDrag(PointerEventData eventData) { if (dragObj != null) { float x = Input.mousePosition.x - Screen.width * 0.5f; float y = Input.mousePosition.y - Screen.height * 0.5f; if (dragObj.Equals(leftBottom)) { if ((rightTopPos.x - x) > x_min) { leftBottomPos.x = x; leftTopPos.x = x; leftBottom.transform.localPosition = leftBottomPos; leftTop.transform.localPosition = leftTopPos; } if ((rightTopPos.y - y) > y_min) { leftBottomPos.y = y; rightBottomPos.y = y; leftBottom.transform.localPosition = leftBottomPos; rightBottom.transform.localPosition = rightBottomPos; } } else if (dragObj.Equals(leftTop)) { if ((rightBottomPos.x - x) > x_min) { leftTopPos.x = x; leftBottomPos.x = x; leftTop.transform.localPosition = leftTopPos; leftBottom.transform.localPosition = leftBottomPos; } if ((y - rightBottomPos.y) > y_min) { leftTopPos.y = y; rightTopPos.y = y; leftTop.transform.localPosition = leftTopPos; rightTop.transform.localPosition = rightTopPos; } } else if (dragObj.Equals(rightTop)) { if ((x - leftBottomPos.x) > x_min) { rightTopPos.x = x; rightBottomPos.x = x; rightTop.transform.localPosition = rightTopPos; rightBottom.transform.localPosition = rightBottomPos; } if ((y - leftBottomPos.y) > y_min) { rightTopPos.y = y; leftTopPos.y = y; rightTop.transform.localPosition = rightTopPos; leftTop.transform.localPosition = leftTopPos; } } else if (dragObj.Equals(rightBottom)) { if ((x - leftTopPos.x) > x_min) { rightBottomPos.x = x; rightTopPos.x = x; rightBottom.transform.localPosition = rightBottomPos; rightTop.transform.localPosition = rightTopPos; } if ((leftTopPos.y - y) > y_min) { rightBottomPos.y = y; leftBottomPos.y = y; rightBottom.transform.localPosition = rightBottomPos; leftBottom.transform.localPosition = leftBottomPos; } } } UpdateGeometry(); } public void OnEndDrag(PointerEventData eventData) { dragObj = null; } UIVertex SetVertexs(UIVertex vertex, Vector2 vertexPos) { vertex.position = vertexPos; vertex.color = color;//color是父類中的屬性 vertex.uv0 = Vector2.zero; return vertex; } }