在Unity中实现ScrollRect组件的全方位教程:自动布局与视口内元素精准定位-一、自动生成内容布局篇
最编程
2024-02-21 18:25:06
...
1、首先要往我们的unity项目中导入两个脚本文件,脚本文件名称分别是UIScrollEventListener和CZScrollRect,这两个脚本文件代码如下所示。
1-1、介绍UIScrollEventListener脚本写法。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.EventSystems;
public class UIScrollEventListener : MonoBehaviour, IBeginDragHandler, IEndDragHandler , IPointerUpHandler, IPointerDownHandler , IDragHandler
{
public delegate void VoidDelegate(PointerEventData pdata);
public VoidDelegate onBeginDrag;
public VoidDelegate onEndDrag;
public VoidDelegate onUp;
public VoidDelegate onDown;
public VoidDelegate onDrag;
bool isDrag = false;
List<Image> registers = new List<Image>();
public static UIScrollEventListener Get(GameObject go)
{
UIScrollEventListener listener = go.GetComponent<UIScrollEventListener>();
if (listener == null) listener = go.AddComponent<UIScrollEventListener>();
return listener;
}
public void OnBeginDrag(PointerEventData eventData)
{
isDrag = true;
if (onBeginDrag != null) onBeginDrag(eventData);
}
public void OnEndDrag(PointerEventData eventData)
{
isDrag = false;
if (onEndDrag != null) onEndDrag(eventData);
}
public void OnPointerUp(PointerEventData eventData)
{
if (!isDrag) {
SetRegisterEvent(true);
PraseObject(eventData);
SetRegisterEvent(false);
}
if (onUp != null) onUp(eventData);
}
public void OnPointerDown(PointerEventData eventData)
{
if (onDown != null) onDown(eventData);
}
public void OnDrag(PointerEventData eventData) {
if (onDrag != null) onDrag(eventData);
}
public void RegisterButton(GameObject go)
{
Image img = go.GetComponent<Image>();
if (img != null)
{
img.raycastTarget = false;
registers.Add(img);
}
}
void SetRegisterEvent(bool b) {
if (registers.Count > 0)
{
for (int i = 0; i < registers.Count; ++i)
{
registers[i].raycastTarget = b;
}
}
}
void PraseObject(PointerEventData eventData) {
if (registers.Count > 0)
{
for (int i = 0; i < registers.Count; ++i)
{
if (EventSystem.current != null)
{
List<RaycastResult> result = new List<RaycastResult>();
EventSystem.current.RaycastAll(eventData, result);
foreach (RaycastResult r in result)
{
//Debug.Log(r.gameObject.name);
foreach (Image img in registers)
{
if (img.gameObject.Equals(r.gameObject))
{
InputField inputfield = img.gameObject.GetComponent<InputField>();
if (inputfield != null) inputfield.ActivateInputField();
}
}
}
}
}
}
}
}
1-2、介绍CZScrollRect脚本写法。
using System;
using UnityEngine;
using UnityEngine.UI;
public class ScrollObj
{
public GameObject obj;
public int dex;
}
public class CZScrollRect
{
public enum TipType
{
UNDO_REFRESH = 0,
PULL_REFRESH = 1,
UNDO_APPEND = 2,
PULL_AAPEND = 3,
NODATA = 4,
NONE = 5
}
const int OPEAT_HEIGHT = 100;//高度差判断操作类型
const int INIT_NUM_LIMIT = 8;//列表实例化个数
public delegate void OperatDelegate();
public delegate void OperatObjDelegate(GameObject obj , int index);
public delegate void OperatTextObjDelegate(GameObject obj, TipType t);
public OperatDelegate onRefresh;//下拉刷新时回调
public OperatDelegate onAppend;//需要加载更多时回调
public OperatObjDelegate onScrollObj;//需刷新时回调
public OperatTextObjDelegate onUpdateTextObj;//需刷新文本状态时回调
public ScrollRect scrollRect;//ScrollRect
private RectTransform scrollRectContent;//RectTransform
public GameObject prefab;//实例化的对象
public GameObject text_up;//下拉刷新文本
public GameObject text_down;//上拉加载更多文本
TipType textup_status;
int opeartLen = 0;//记录总长度
public int layoutwidth = 1242;//填写item的长度
public int limitNum = 8;//列表实例化个数
public float interval = 200;//每个item的高度
public float spacing = 5;//每个tiem的间隔
ScrollObj[] list;//用于管理生成的对象
int opeartType;
int pageindex;//页码
bool bHasMore;//是否能加载更多
int halfWidth;
//
public GameObject batchContent;
public CZScrollRect()
{
opeartType = -1;
hasMore = false;
}
/// <summary>
/// 用于控制scrollrect是否能够滑动
/// (用于等待网络请求等业务)
/// </summary>
public bool vertical
{
get{
return scrollRect.vertical;
}set{
scrollRect.vertical = value;
}
}
/// <summary>
/// 是否存在更多
/// </summary>
public bool hasMore
{
get{
return bHasMore;
}set{
bHasMore = value;
}
}
/// <summary>
/// 获取对象所在的索引
/// </summary>
/// <param name="obj"></param>
/// <returns></returns>
public int GetObjIndex(GameObject obj) {
for(int i = 0; i < list.Length; ++i)
{
if (obj.Equals(list[i].obj))