Esempio n. 1
0
        /// <summary>
        /// Unsubscribes from manipulation events.
        /// </summary>
        private void OnDisable()
        {
            if (objectManipulator != null)
            {
                objectManipulator.OnManipulationStarted.RemoveListener(OnManipulationStarted);
                objectManipulator.OnManipulationEnded.RemoveListener(OnManipulationEnded);

                objectManipulator = null;
            }

            if (manipulationHandler != null)
            {
                manipulationHandler.OnManipulationStarted.RemoveListener(OnManipulationStarted);
                manipulationHandler.OnManipulationEnded.RemoveListener(OnManipulationEnded);

                manipulationHandler = null;
            }

            if (dockedPosition != null)
            {
                dockedPosition.DockedObject = null;
                dockedPosition = null;
            }

            overlappingPositions.Clear();
        }
Esempio n. 2
0
        /// <summary>
        /// Undocks this <see cref="Dockable"/> from the current <see cref="DockPosition"/> where it is docked.
        /// </summary>
        public void Undock()
        {
            if (!CanUndock)
            {
                Debug.LogError($"Trying to undock an object that was not docked. State = {dockingState}");
                return;
            }

            Debug.Log($"Undocking object {gameObject.name} from position {dockedPosition.gameObject.name}");

            dockedPosition.DockedObject = null;
            dockedPosition      = null;
            dockedPositionScale = Vector3.one;
            dockingState        = DockingState.Undocking;
        }
Esempio n. 3
0
        /// <summary>
        /// Gets the overlapping <see cref="DockPosition"/> that is closest to this Dockable.
        /// </summary>
        /// <returns>The overlapping <see cref="DockPosition"/> that is closest to this <see cref="Dockable"/>, or null if no positions overlap.</returns>
        private DockPosition GetClosestPosition()
        {
            var          bounds          = gameObject.GetComponent <Collider>().bounds;
            var          minDistance     = float.MaxValue;
            DockPosition closestPosition = null;

            foreach (var position in overlappingPositions)
            {
                var distance = (position.gameObject.GetComponent <Collider>().bounds.center - bounds.center).sqrMagnitude;
                if (closestPosition == null || distance < minDistance)
                {
                    closestPosition = position;
                    minDistance     = distance;
                }
            }

            return(closestPosition);
        }
Esempio n. 4
0
        /// <summary>
        /// Docks this object in a given <see cref="DockPosition"/>.
        /// </summary>
        /// <param name="position">The <see cref="DockPosition"/> where we'd like to dock this object.</param>
        public void Dock(DockPosition position)
        {
            if (!CanDock)
            {
                Debug.LogError($"Trying to dock an object that was not undocked. State = {dockingState}");
                return;
            }

            Debug.Log($"Docking object {gameObject.name} on position {position.gameObject.name}");

            dockedPosition = position;
            dockedPosition.DockedObject = this;
            float scaleToFit = gameObject.GetComponent <Collider>().bounds.GetScaleToFitInside(dockedPosition.GetComponent <Collider>().bounds);

            dockedPositionScale = transform.localScale * scaleToFit;

            if (dockingState == DockingState.Undocked)
            {
                // Only register the original scale when first docking
                originalScale = transform.localScale;
            }

            dockingState = DockingState.Docking;
        }
Esempio n. 5
0
        /// <summary>
        /// Moves elements near the desired position to make space for a new element,
        /// if possible.
        /// </summary>
        /// <param name="position">The desired position where an object wants to be docked.</param>
        /// <returns>Returns true if the desired position is now available, false otherwise.</returns>
        public bool TryMoveToFreeSpace(DockPosition position)
        {
            if (dockPositions == null)
            {
                UpdatePositions();
            }

            if (!dockPositions.Contains(position))
            {
                Debug.LogError("Looking for a DockPosition in the wrong Dock.");
                return(false);
            }

            var index = dockPositions.IndexOf(position);

            if (!dockPositions[index].IsOccupied)
            {
                // Already free
                return(true);
            }

            // Where is the closest free space? (on a tie, favor left)
            int?closestFreeSpace           = null;
            int distanceToClosestFreeSpace = int.MaxValue;

            for (int i = 0; i < dockPositions.Count; i++)
            {
                var distance = Math.Abs(index - i);
                if (!dockPositions[i].IsOccupied && distance < distanceToClosestFreeSpace)
                {
                    closestFreeSpace           = i;
                    distanceToClosestFreeSpace = distance;
                }
            }

            if (closestFreeSpace == null)
            {
                // No free space
                return(false);
            }

            if (closestFreeSpace < index)
            {
                // Move left

                // Check if we can undock all of them
                for (int i = closestFreeSpace.Value + 1; i <= index; i++)
                {
                    if (!dockPositions[i].DockedObject.CanUndock)
                    {
                        return(false);
                    }
                }

                for (int i = closestFreeSpace.Value + 1; i <= index; i++)
                {
                    MoveDockedObject(i, i - 1);
                }
            }
            else
            {
                // Move right

                // Check if we can undock all of them
                for (int i = closestFreeSpace.Value - 1; i >= index; i--)
                {
                    if (!dockPositions[i].DockedObject.CanUndock)
                    {
                        return(false);
                    }
                }

                for (int i = closestFreeSpace.Value - 1; i >= index; i--)
                {
                    MoveDockedObject(i, i + 1);
                }
            }

            return(true);
        }