Facepunch / sbox-issues

176 stars 12 forks source link

Interactable Gizmo.Control widgets inside games. #6391

Open MDFL64 opened 3 weeks ago

MDFL64 commented 3 weeks ago

For?

S&Box

What can't you do?

For in-game editors and building/sandbox games, it would be useful to be able to use the built-in gizmo widgets. They render correctly, but cannot be interacted with. It appears the Inputs struct is only populated while in the editor.

How would you like it to work?

It would be nice if it just automagically worked, but I don't particularly care whether it requires some configuration by the game. I'd be content if I could just inject my own inputs.

What have you tried?

I tried to hack it together for several hours:

I'm sure I could have made my own semi-functional widgets in the time I spent trying to figure it out, but the built-in ones are nice and it would be nice to have access to them in games.

Additional context

No response

MDFL64 commented 2 weeks ago

I just couldn't let this go, and eventually cooked up what seems to be a functional workaround:

/// <summary>
/// Add this to your camera, then surround your gizmo usages with: `using (GameGizmo.GizmoInstance.Push()) { }`
/// </summary>
public sealed class GameGizmo : Component, CameraComponent.ISceneCameraSetup
{
    public static Gizmo.Instance GizmoInstance = new Gizmo.Instance();

    public void SetupCamera( CameraComponent camera, SceneCamera sceneCamera )
    {
        sceneCamera.Worlds.Add(GizmoInstance.World);
    }

    protected override void OnUpdate()
    {
        // Just steal the scene camera from the main gizmo instance
        var camera = Gizmo.Camera;
        var cursorPos = Mouse.Position;

        // Needs some refinement, including the option to disable it.
        Gizmo.Inputs gizmoInput = new Gizmo.Inputs {
            Camera = camera,
            CursorPosition = cursorPos,
            CursorRay = camera.GetRay(cursorPos),
            LeftMouse = Input.Down("attack1"), // there must be a better alternative
            IsHovered = true
        };

        GizmoInstance.Input = gizmoInput;
    }
}
handsomematt commented 6 days ago

This is intended to work, we need some extra bits and bobs to support it properly though