Esempio n. 1
0
        private List <ObjectProximityInfo> FetchObjects(IProximityEffectObjectProvider provider)
        {
            var registeredObjects = new List <ObjectProximityInfo>();

            provider.ForEachProximityObject(proximityObject =>
            {
                registeredObjects.Add(new ObjectProximityInfo()
                {
                    ScaledObject         = proximityObject,
                    ObjectVisualRenderer = proximityObject.gameObject.GetComponentInChildren <Renderer>()
                });
            });

            return(registeredObjects);
        }
Esempio n. 2
0
        /// <summary>
        /// register objects for proximity effect via a <see cref="IProximityEffectObjectProvider"/>
        /// </summary>
        public void AddObjects(IProximityEffectObjectProvider provider)
        {
            RegisteredObjects registeredObject = new RegisteredObjects()
            {
                objectProvider = provider, proximityInfos = new List <ObjectProximityInfo>()
            };

            provider.ForEachProximityObject(proximityObject =>
            {
                registeredObject.proximityInfos.Add(new ObjectProximityInfo()
                {
                    ScaledObject         = proximityObject,
                    ObjectVisualRenderer = proximityObject.gameObject.GetComponentInChildren <Renderer>()
                });
            });
            registeredObjects.Add(registeredObject);
        }
Esempio n. 3
0
 private void RefreshObjects(IProximityEffectObjectProvider provider)
 {
     // refetch object list
     registeredObjects[provider] = FetchObjects(provider);
 }
Esempio n. 4
0
 /// <summary>
 /// register objects for proximity effect via a <see cref="IProximityEffectObjectProvider"/>
 /// </summary>
 public void RegisterObjectProvider(IProximityEffectObjectProvider provider)
 {
     registeredObjects.Add(provider, FetchObjects(provider));
     // subscribe to object changes
     provider.ProximityObjectsChanged.AddListener(RefreshObjects);
 }
Esempio n. 5
0
        /// <summary>
        /// Updates proximity effect and its registered objects.
        /// Highlights and scales objects in proximity according to the pointer distance
        /// </summary>
        /// <param name="boundsCenter">gameobject position the proximity effect is attached to</param>
        /// <param name="boundsExtents">extents of the gameobject the proximity effect is attached to</param>
        public void UpdateScaling(Vector3 boundsCenter, Vector3 boundsExtents)
        {
            // early out if effect is disabled
            if (config.ProximityEffectActive == false || !IsAnyRegisteredObjectVisible())
            {
                return;
            }

            proximityPointers.Clear();
            proximityPoints.Clear();

            // Find all valid pointers
            foreach (var inputSource in CoreServices.InputSystem.DetectedInputSources)
            {
                foreach (var pointer in inputSource.Pointers)
                {
                    // don't use IsInteractionEnabled for near pointers as the pointers might have a different radius when deciding
                    // if they can interact with a near-by object - we might still want to show proximity scaling even if
                    // eg. grab pointer decides it's too far away to actually perform the interaction
                    if (pointer.IsActive && !proximityPointers.Contains(pointer))
                    {
                        proximityPointers.Add(pointer);
                    }
                }
            }

            // Get the max radius possible of our current bounds and extent the range to include proximity scaled objects. This is done by adjusting the original bounds to include the ObjectMediumProximity range in x, y and z axis
            float squareMaxLength = boundsExtents.sqrMagnitude + (3 * config.ObjectMediumProximity * config.ObjectMediumProximity);

            // Grab points within sphere of influence from valid pointers
            foreach (var pointer in proximityPointers)
            {
                if (IsPointWithinBounds(boundsCenter, pointer.Position, squareMaxLength))
                {
                    proximityPoints.Add(pointer.Position);
                }

                if (pointer.Result?.CurrentPointerTarget != null)
                {
                    Vector3?point = pointer.Result?.Details.Point;
                    if (point.HasValue && IsPointWithinBounds(boundsCenter, pointer.Result.Details.Point, squareMaxLength))
                    {
                        proximityPoints.Add(pointer.Result.Details.Point);
                    }
                }
            }

            // Loop through all objects and find closest one
            Transform closestObject      = null;
            float     closestDistanceSqr = float.MaxValue;

            foreach (var point in proximityPoints)
            {
                foreach (var keyValuePair in registeredObjects)
                {
                    foreach (var item in keyValuePair.Value)
                    {
                        // If object can't be visible, skip calculations
                        if (!keyValuePair.Key.IsActive)
                        {
                            continue;
                        }

                        // Perform comparison on sqr distance since sqrt() operation is expensive in Vector3.Distance()
                        float sqrDistance = (item.ScaledObject.transform.position - point).sqrMagnitude;
                        if (sqrDistance < closestDistanceSqr)
                        {
                            closestObject      = item.ScaledObject;
                            closestDistanceSqr = sqrDistance;
                        }
                    }
                }
            }

            // Loop through all objects and update visual state based on closest point
            foreach (var keyValuePair in registeredObjects)
            {
                foreach (var item in keyValuePair.Value)
                {
                    ProximityState newState = (closestObject == item.ScaledObject) ? GetProximityState(closestDistanceSqr) : ProximityState.FullsizeNoProximity;
                    IProximityEffectObjectProvider provider = keyValuePair.Key;

                    // Only apply updates if object is in a new state or closest object needs to lerp scaling
                    if (item.ProximityState != newState)
                    {
                        // Update and save new state
                        item.ProximityState = newState;

                        if (item.ObjectVisualRenderer)
                        {
                            item.ObjectVisualRenderer.material = newState == ProximityState.CloseProximity ? provider.GetHighlightedMaterial() : provider.GetBaseMaterial();
                        }
                    }

                    ScaleObject(newState, item.ScaledObject, provider.GetObjectSize(), true);
                }
            }
        }