/// <inheritdoc /> public override void Pick() { // Ensure player is not moving objects if (ActiveAxis != Axis.None) { return; } // Get mouse ray and try to hit any object var ray = Owner.MouseRay; var view = new Ray(Owner.ViewPosition, Owner.ViewDirection); var renderView = Owner.RenderTask.View; bool selectColliders = (renderView.Flags & ViewFlags.PhysicsDebug) == ViewFlags.PhysicsDebug || renderView.Mode == ViewMode.PhysicsColliders; SceneGraphNode.RayCastData.FlagTypes rayCastFlags = SceneGraphNode.RayCastData.FlagTypes.None; if (!selectColliders) { rayCastFlags |= SceneGraphNode.RayCastData.FlagTypes.SkipColliders; } var hit = Editor.Instance.Scene.Root.RayCast(ref ray, ref view, out _, rayCastFlags); // Update selection var sceneEditing = Editor.Instance.SceneEditing; if (hit != null) { // For child actor nodes (mesh, link or sth) we need to select it's owning actor node first or any other child node (but not a child actor) if (hit is ActorChildNode actorChildNode && !actorChildNode.CanBeSelectedDirectly) { var parentNode = actorChildNode.ParentNode; bool canChildBeSelected = sceneEditing.Selection.Contains(parentNode); if (!canChildBeSelected) { for (int i = 0; i < parentNode.ChildNodes.Count; i++) { if (sceneEditing.Selection.Contains(parentNode.ChildNodes[i])) { canChildBeSelected = true; break; } } } if (canChildBeSelected && sceneEditing.Selection.Count > 1) { // Don't select child node if multiple nodes are selected canChildBeSelected = false; } if (!canChildBeSelected) { // Select parent hit = parentNode; } } // Select prefab root and then go down until you find the actual item in which case select the prefab root again if (hit is ActorNode actorNode) { ActorNode prefabRoot = GetPrefabRootInParent(actorNode); if (prefabRoot != null && actorNode != prefabRoot) { hit = WalkUpAndFindActorNodeBeforeSelection(actorNode, prefabRoot); } } bool addRemove = Owner.IsControlDown; bool isSelected = sceneEditing.Selection.Contains(hit); if (addRemove) { if (isSelected) { sceneEditing.Deselect(hit); } else { sceneEditing.Select(hit, true); } } else { sceneEditing.Select(hit); } } else { sceneEditing.Deselect(); } }
/// <inheritdoc /> public override void Pick() { // Ensure player is not moving objects if (ActiveAxis != Axis.None) { return; } // Get mouse ray and try to hit any object var ray = Owner.MouseRay; bool selectColliders = (Owner.RenderTask.View.Flags & ViewFlags.PhysicsDebug) == ViewFlags.PhysicsDebug; SceneGraphNode.RayCastData.FlagTypes rayCastFlags = SceneGraphNode.RayCastData.FlagTypes.None; if (!selectColliders) { rayCastFlags |= SceneGraphNode.RayCastData.FlagTypes.SkipColliders; } var hit = Editor.Instance.Scene.Root.RayCast(ref ray, out _, rayCastFlags); // Update selection var sceneEditing = Editor.Instance.SceneEditing; if (hit != null) { // For child actor nodes (mesh, link or sth) we need to select it's owning actor node first or any other child node (but not a child actor) if (hit is ActorChildNode actorChildNode) { var parentNode = actorChildNode.ParentNode; bool canChildBeSelected = sceneEditing.Selection.Contains(parentNode); if (!canChildBeSelected) { for (int i = 0; i < parentNode.ChildNodes.Count; i++) { if (sceneEditing.Selection.Contains(parentNode.ChildNodes[i])) { canChildBeSelected = true; break; } } } if (!canChildBeSelected) { // Select parent hit = parentNode; } } bool addRemove = Owner.IsControlDown; bool isSelected = sceneEditing.Selection.Contains(hit); if (addRemove) { if (isSelected) { sceneEditing.Deselect(hit); } else { sceneEditing.Select(hit, true); } } else { sceneEditing.Select(hit); } } else { sceneEditing.Deselect(); } }
/// <inheritdoc /> protected override void OnLeftMouseButtonUp() { // Skip if was controlling mouse or mouse is not over the area if (_prevInput.IsControllingMouse || !Bounds.Contains(ref _viewMousePos)) { return; } if (TransformGizmo.IsActive) { // Ensure player is not moving objects if (TransformGizmo.ActiveAxis != TransformGizmo.Axis.None) { return; } } else { // For now just pick objects in transform gizmo mode return; } // Get mouse ray and try to hit any object var ray = MouseRay; float closest = float.MaxValue; bool selectColliders = (Task.Flags & ViewFlags.PhysicsDebug) == ViewFlags.PhysicsDebug; SceneGraphNode.RayCastData.FlagTypes rayCastFlags = SceneGraphNode.RayCastData.FlagTypes.None; if (!selectColliders) { rayCastFlags |= SceneGraphNode.RayCastData.FlagTypes.SkipColliders; } var hit = Editor.Instance.Scene.Root.RayCast(ref ray, ref closest, rayCastFlags); // Update selection var sceneEditing = Editor.Instance.SceneEditing; if (hit != null) { // For child actor nodes (mesh, link or sth) we need to select it's owning actor node first or any other child node (but not a child actor) if (hit is ActorChildNode actorChildNode) { var parentNode = actorChildNode.ParentNode; bool canChildBeSelected = sceneEditing.Selection.Contains(parentNode); if (!canChildBeSelected) { for (int i = 0; i < parentNode.ChildNodes.Count; i++) { if (sceneEditing.Selection.Contains(parentNode.ChildNodes[i])) { canChildBeSelected = true; break; } } } if (!canChildBeSelected) { // Select parent hit = parentNode; } } bool addRemove = Root.GetKey(Keys.Control); bool isSelected = sceneEditing.Selection.Contains(hit); if (addRemove) { if (isSelected) { sceneEditing.Deselect(hit); } else { sceneEditing.Select(hit, true); } } else { sceneEditing.Select(hit); } } else { sceneEditing.Deselect(); } // Keep focus Focus(); base.OnLeftMouseButtonUp(); }