UGUI(七)界面拖动和焦点界面
2015-08-25 10:07
513 查看
一般软件和游戏有多窗口多界面时,都可以拖动子界面和排序子界面【点击后变成焦点界面显示在最前面】。如下图:
UGUI的官方例子中有实现拖动的脚本DragPanel,不过它没支持界面排序,加个排序很简单,在按下鼠标时调用tranform的SetSiblingIndex即可,值越大越靠前,在这里我只是简单的实现了这个基本功能,最终用到项目是需要设计一下的,因为很多时候需要记录打开界面的一些信息,在这里就不多说了。
代码如下:
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.EventSystems;
using System.Collections;
public class DragPanel : MonoBehaviour, IPointerDownHandler, IDragHandler {
// 鼠标起点
private Vector2 originalLocalPointerPosition;
// 面板起点
private Vector3 originalPanelLocalPosition;
// 当前面板
private RectTransform panelRectTransform;
// 父节点,这个最好是UI父节点,因为它的矩形大小刚好是屏幕大小
private RectTransform parentRectTransform;
private static int siblingIndex = 0;
void Awake () {
panelRectTransform = transform.parent as RectTransform;
parentRectTransform = panelRectTransform.parent as RectTransform;
}
// 鼠标按下
public void OnPointerDown (PointerEventData data) {
siblingIndex++;
panelRectTransform.transform.SetSiblingIndex(siblingIndex);
// 记录当前面板起点
originalPanelLocalPosition = panelRectTransform.localPosition;
// 通过屏幕中的鼠标点,获取在父节点中的鼠标点
// parentRectTransform:父节点
// data.position:当前鼠标位置
// data.pressEventCamera:当前事件的摄像机
// originalLocalPointerPosition:获取当前鼠标起点
RectTransformUtility.ScreenPointToLocalPointInRectangle (parentRectTransform, data.position, data.pressEventCamera, out originalLocalPointerPosition);
}
// 拖动
public void OnDrag (PointerEventData data) {
if (panelRectTransform == null || parentRectTransform == null)
return;
Vector2 localPointerPosition;
// 获取本地鼠标位置
if (RectTransformUtility.ScreenPointToLocalPointInRectangle (parentRectTransform, data.position, data.pressEventCamera, out localPointerPosition)) {
// 移动位置 = 本地鼠标当前位置 - 本地鼠标起点位置
Vector3 offsetToOriginal = localPointerPosition - originalLocalPointerPosition;
// 当前面板位置 = 面板起点 + 移动位置
panelRectTransform.localPosition = originalPanelLocalPosition + offsetToOriginal;
}
ClampToWindow ();
}
// 限制当前面板在父节点中的区域位置
void ClampToWindow () {
// 面板位置
Vector3 pos = panelRectTransform.localPosition;
// 如果是UI父节点,设置面板大小为0,那么最大最小位置为正负屏幕的一半
Vector3 minPosition = parentRectTransform.rect.min - panelRectTransform.rect.min;
Vector3 maxPosition = parentRectTransform.rect.max - panelRectTransform.rect.max;
pos.x = Mathf.Clamp (panelRectTransform.localPosition.x, minPosition.x, maxPosition.x);
pos.y = Mathf.Clamp (panelRectTransform.localPosition.y, minPosition.y, maxPosition.y);
panelRectTransform.localPosition = pos;
}
}
UGUI的官方例子中有实现拖动的脚本DragPanel,不过它没支持界面排序,加个排序很简单,在按下鼠标时调用tranform的SetSiblingIndex即可,值越大越靠前,在这里我只是简单的实现了这个基本功能,最终用到项目是需要设计一下的,因为很多时候需要记录打开界面的一些信息,在这里就不多说了。
代码如下:
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.EventSystems;
using System.Collections;
public class DragPanel : MonoBehaviour, IPointerDownHandler, IDragHandler {
// 鼠标起点
private Vector2 originalLocalPointerPosition;
// 面板起点
private Vector3 originalPanelLocalPosition;
// 当前面板
private RectTransform panelRectTransform;
// 父节点,这个最好是UI父节点,因为它的矩形大小刚好是屏幕大小
private RectTransform parentRectTransform;
private static int siblingIndex = 0;
void Awake () {
panelRectTransform = transform.parent as RectTransform;
parentRectTransform = panelRectTransform.parent as RectTransform;
}
// 鼠标按下
public void OnPointerDown (PointerEventData data) {
siblingIndex++;
panelRectTransform.transform.SetSiblingIndex(siblingIndex);
// 记录当前面板起点
originalPanelLocalPosition = panelRectTransform.localPosition;
// 通过屏幕中的鼠标点,获取在父节点中的鼠标点
// parentRectTransform:父节点
// data.position:当前鼠标位置
// data.pressEventCamera:当前事件的摄像机
// originalLocalPointerPosition:获取当前鼠标起点
RectTransformUtility.ScreenPointToLocalPointInRectangle (parentRectTransform, data.position, data.pressEventCamera, out originalLocalPointerPosition);
}
// 拖动
public void OnDrag (PointerEventData data) {
if (panelRectTransform == null || parentRectTransform == null)
return;
Vector2 localPointerPosition;
// 获取本地鼠标位置
if (RectTransformUtility.ScreenPointToLocalPointInRectangle (parentRectTransform, data.position, data.pressEventCamera, out localPointerPosition)) {
// 移动位置 = 本地鼠标当前位置 - 本地鼠标起点位置
Vector3 offsetToOriginal = localPointerPosition - originalLocalPointerPosition;
// 当前面板位置 = 面板起点 + 移动位置
panelRectTransform.localPosition = originalPanelLocalPosition + offsetToOriginal;
}
ClampToWindow ();
}
// 限制当前面板在父节点中的区域位置
void ClampToWindow () {
// 面板位置
Vector3 pos = panelRectTransform.localPosition;
// 如果是UI父节点,设置面板大小为0,那么最大最小位置为正负屏幕的一半
Vector3 minPosition = parentRectTransform.rect.min - panelRectTransform.rect.min;
Vector3 maxPosition = parentRectTransform.rect.max - panelRectTransform.rect.max;
pos.x = Mathf.Clamp (panelRectTransform.localPosition.x, minPosition.x, maxPosition.x);
pos.y = Mathf.Clamp (panelRectTransform.localPosition.y, minPosition.y, maxPosition.y);
panelRectTransform.localPosition = pos;
}
}
相关文章推荐
- UGUI Text Gradient
- 按钮的监听事件系统
- <Unity3D>实例化UGUI中GameObject 并设置它的位置
- Unity3d中EventTrigger的封装
- UGUI之Toggle之单选框及复选框制作
- uGUI使用代码动态添加Button.OnClick()事件(Unity3D开发之十二)
- [UnityUI]使用UGUI制作排行榜
- [UnityUI]美术字体的制作与使用
- UI Overview——UI概述
- Canvas——画布
- Basic Layout——基本布局
- UGUI ScrollRect 优化
- UGUI全面实践教程
- UGUI的优点新UI系统
- UGUI(一)List列表的封装
- UGUI(二)摄像机渲染纹理
- UGUI(三)无限循环列表
- UGUI(四)事件系统的封装
- UGUI(五)动画系统
- UGUI(六)资源下载之Icon