You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
77 lines
3.4 KiB
77 lines
3.4 KiB
//========= Copyright 2016-2018, HTC Corporation. All rights reserved. =========== |
|
|
|
using HTC.UnityPlugin.Utility; |
|
using System.Collections.Generic; |
|
using UnityEngine; |
|
using UnityEngine.EventSystems; |
|
using UnityEngine.UI; |
|
|
|
namespace HTC.UnityPlugin.Pointer3D |
|
{ |
|
[DisallowMultipleComponent] |
|
public class CanvasRaycastMethod : BaseRaycastMethod |
|
{ |
|
private static readonly IndexedSet<ICanvasRaycastTarget> canvases = new IndexedSet<ICanvasRaycastTarget>(); |
|
|
|
public static bool AddTarget(ICanvasRaycastTarget obj) { return obj == null ? false : canvases.AddUnique(obj); } |
|
|
|
public static bool RemoveTarget(ICanvasRaycastTarget obj) { return obj == null ? false : canvases.Remove(obj); } |
|
|
|
public override void Raycast(Ray ray, float distance, List<RaycastResult> raycastResults) |
|
{ |
|
var tempCanvases = ListPool<ICanvasRaycastTarget>.Get(); |
|
tempCanvases.AddRange(canvases); |
|
for (int i = tempCanvases.Count - 1; i >= 0; --i) |
|
{ |
|
var target = tempCanvases[i]; |
|
if (target == null || !target.enabled) { continue; } |
|
Raycast(target.canvas, target.ignoreReversedGraphics, ray, distance, raycaster, raycastResults); |
|
} |
|
ListPool<ICanvasRaycastTarget>.Release(tempCanvases); |
|
} |
|
|
|
public static void Raycast(Canvas canvas, bool ignoreReversedGraphics, Ray ray, float distance, Pointer3DRaycaster raycaster, List<RaycastResult> raycastResults) |
|
{ |
|
if (canvas == null) { return; } |
|
|
|
var eventCamera = raycaster.eventCamera; |
|
var screenCenterPoint = Pointer3DInputModule.ScreenCenterPoint; |
|
var graphics = GraphicRegistry.GetGraphicsForCanvas(canvas); |
|
|
|
// Pointer3DRaycaster should set tje eventCamera to correct position |
|
|
|
for (int i = 0; i < graphics.Count; ++i) |
|
{ |
|
var graphic = graphics[i]; |
|
|
|
// -1 means it hasn't been processed by the canvas, which means it isn't actually drawn |
|
if (graphic.depth == -1 || !graphic.raycastTarget) { continue; } |
|
|
|
if (!RectTransformUtility.RectangleContainsScreenPoint(graphic.rectTransform, screenCenterPoint, eventCamera)) { continue; } |
|
|
|
if (ignoreReversedGraphics && Vector3.Dot(ray.direction, graphic.transform.forward) <= 0f) { continue; } |
|
|
|
if (!graphic.Raycast(screenCenterPoint, eventCamera)) { continue; } |
|
|
|
//var dist = Vector3.Dot(transForward, trans.position - ray.origin) / Vector3.Dot(transForward, ray.direction); |
|
float dist; |
|
new Plane(graphic.transform.forward, graphic.transform.position).Raycast(ray, out dist); |
|
if (dist > distance) { continue; } |
|
|
|
raycastResults.Add(new RaycastResult |
|
{ |
|
gameObject = graphic.gameObject, |
|
module = raycaster, |
|
distance = dist, |
|
worldPosition = ray.GetPoint(dist), |
|
worldNormal = -graphic.transform.forward, |
|
screenPosition = screenCenterPoint, |
|
index = raycastResults.Count, |
|
depth = graphic.depth, |
|
sortingLayer = canvas.sortingLayerID, |
|
sortingOrder = canvas.sortingOrder |
|
}); |
|
} |
|
} |
|
} |
|
} |