Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add santroller devices #3

Merged
merged 6 commits into from
Apr 15, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,137 @@
using System.Collections.Generic;
using System.Runtime.InteropServices;
using PlasticBand.Devices.LowLevel;
using PlasticBand.LowLevel;
using UnityEngine.InputSystem;
using UnityEngine.InputSystem.Layouts;
using UnityEngine.InputSystem.LowLevel;
using UnityEngine.InputSystem.Utilities;

// PlasticBand reference doc:
// https://github.com/TheNathannator/PlasticBand/blob/main/Docs/Instruments/5-Fret%20Guitar/Guitar%20Hero/Santroller.md
namespace PlasticBand.Devices.LowLevel
{
/// <summary>
/// The state format for Santroller HID Guitar Hero Guitars.
/// </summary>
[StructLayout(LayoutKind.Sequential, Pack = 1)]
internal unsafe struct SantrollerHIDGuitarHeroGuitarState : IInputStateTypeInfo
{
public FourCC format => HidDefinitions.InputFormat;

public byte reportId;

[InputControl(name = "yellowFret", layout = "Button", bit = 0)]
[InputControl(name = "greenFret", layout = "Button", bit = 1)]
[InputControl(name = "redFret", layout = "Button", bit = 2)]
[InputControl(name = "blueFret", layout = "Button", bit = 3)]

[InputControl(name = "orangeFret", layout = "Button", bit = 4)]
[InputControl(name = "spPedal", layout = "Button", bit = 5)]

[InputControl(name = "selectButton", layout = "Button", bit = 8)]
[InputControl(name = "startButton", layout = "Button", bit = 9)]

[InputControl(name = "psButton", layout = "Button", bit = 12, displayName = "PlayStation")]
public ushort buttons;

[InputControl(name = "dpad", layout = "Dpad", format = "BIT", sizeInBits = 4, defaultState = 0x1F)]
[InputControl(name = "dpad/up", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, parameters = "minValue=7,maxValue=1,nullValue=0x1F,wrapAtValue=7")]
[InputControl(name = "dpad/right", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, parameters = "minValue=1,maxValue=3")]
[InputControl(name = "dpad/down", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, parameters = "minValue=3,maxValue=5")]
[InputControl(name = "dpad/left", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, parameters = "minValue=5, maxValue=7")]

[InputControl(name = "strumUp", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, defaultState = 0x1F, parameters = "minValue=7,maxValue=1,nullValue=0x1F,wrapAtValue=7")]
[InputControl(name = "strumDown", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, defaultState = 0x1F, parameters = "minValue=3,maxValue=5,nullValue=0x1F")]
public byte dpad;

[InputControl(name = "tilt", layout = "Axis")]
public byte tilt;

public byte unused1;

[InputControl(name = "whammy", layout = "Axis")]
public byte whammy;

[InputControl(name = "touchGreen", layout = "GuitarHeroSlider", format = "BYTE")]
[InputControl(name = "touchRed", layout = "GuitarHeroSlider", format = "BYTE")]
[InputControl(name = "touchYellow", layout = "GuitarHeroSlider", format = "BYTE")]
[InputControl(name = "touchBlue", layout = "GuitarHeroSlider", format = "BYTE")]
[InputControl(name = "touchOrange", layout = "GuitarHeroSlider", format = "BYTE")]
public byte slider;

public fixed byte unused2[12];

// This was the previous version of the control, left this here in case it's still needed
// [InputControl(name = "tilt", layout = "DiscreteButton", noisy = true, parameters = "minValue=0x0185,maxValue=0x01F7,nullValue=0x0184")]
[InputControl(name = "accelX", layout = "Axis", noisy = true, format = "BIT", sizeInBits = 10, defaultState = 0x200, parameters = "normalize,normalizeMin=0,normalizeMax=1,normalizeZero=0.5")]
public short accelX;

[InputControl(name = "accelZ", layout = "Axis", noisy = true, format = "BIT", sizeInBits = 10, defaultState = 0x200, parameters = "normalize,normalizeMin=0,normalizeMax=1,normalizeZero=0.5")]
public short accelZ;

[InputControl(name = "accelY", layout = "Axis", noisy = true, format = "BIT", sizeInBits = 10, defaultState = 0x200, parameters = "normalize,normalizeMin=0,normalizeMax=1,normalizeZero=0.5")]
public short accelY;

public short unused3;
}
}

namespace PlasticBand.Devices
{
/// <summary>
/// A Santroller HID Guitar Hero Guitar.
/// </summary>
[InputControlLayout(stateType = typeof(SantrollerHIDGuitarHeroGuitarState), displayName = "Santroller HID Guitar Hero Guitar")]
public class SantrollerHIDGuitarHeroGuitar : GuitarHeroGuitar
{
/// <summary>
/// The current <see cref="SantrollerHIDGuitarHeroGuitar"/>.
/// </summary>
public static new SantrollerHIDGuitarHeroGuitar current { get; private set; }

/// <summary>
/// A collection of all <see cref="SantrollerHIDGuitarHeroGuitar"/>s currently connected to the system.
/// </summary>
public new static IReadOnlyList<SantrollerHIDGuitarHeroGuitar> all => s_AllDevices;
private static readonly List<SantrollerHIDGuitarHeroGuitar> s_AllDevices = new List<SantrollerHIDGuitarHeroGuitar>();

/// <summary>
/// Registers <see cref="SantrollerHIDGuitarHeroGuitar"/> to the input system.
/// </summary>
internal new static void Initialize()
{
InputSystem.RegisterLayout<SantrollerHIDGuitarHeroGuitar>();
SantrollerLayoutFinder.RegisterLayout(SantrollerDeviceType.Guitar, SantrollerRhythmType.GuitarHero, nameof(SantrollerHIDGuitarHeroGuitar));
}

/// <summary>
/// Sets this device as the current <see cref="SantrollerHIDGuitarHeroGuitar"/>.
/// </summary>
public override void MakeCurrent()
{
base.MakeCurrent();
current = this;
}

/// <summary>
/// Processes when this device is added to the system.
/// </summary>
protected override void OnAdded()
{
base.OnAdded();
s_AllDevices.Add(this);
}

/// <summary>
/// Processes when this device is removed from the system.
/// </summary>
protected override void OnRemoved()
{
base.OnRemoved();
s_AllDevices.Remove(this);
if (current == this)
current = null;
}
}
}

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
using System.Collections.Generic;
using System.Runtime.InteropServices;
using PlasticBand.Devices.LowLevel;
using PlasticBand.LowLevel;
using UnityEngine.InputSystem;
using UnityEngine.InputSystem.Layouts;
using UnityEngine.InputSystem.LowLevel;
using UnityEngine.InputSystem.Utilities;
using UnityEngine.InputSystem.XInput;

// PlasticBand reference doc:
// https://github.com/TheNathannator/PlasticBand/blob/main/Docs/Instruments/5-Fret%20Guitar/Guitar%20Hero/Xbox%20360.md
namespace PlasticBand.Devices
{
/// <summary>
/// A Santroller XInput Guitar Hero Guitar.
/// </summary>
[InputControlLayout(stateType = typeof(XInputGuitarAlternateState), displayName = "Santroller XInput Guitar Hero Guitar")]
public class SantrollerXInputGuitarAlternate : XInputGuitarAlternate
{
/// <summary>
/// The current <see cref="SantrollerXInputGuitarAlternate"/>.
/// </summary>
public static new SantrollerXInputGuitarAlternate current { get; private set; }

/// <summary>
/// A collection of all <see cref="SantrollerXInputGuitarAlternate"/>s currently connected to the system.
/// </summary>
public new static IReadOnlyList<SantrollerXInputGuitarAlternate> all => s_AllDevices;
private static readonly List<SantrollerXInputGuitarAlternate> s_AllDevices = new List<SantrollerXInputGuitarAlternate>();

/// <summary>
/// Registers <see cref="SantrollerXInputGuitarAlternate"/> to the input system.
/// </summary>
internal new static void Initialize()
{
SantrollerLayoutFinder.Register<SantrollerXInputGuitarAlternate>(XInputController.DeviceSubType.GuitarAlternate);
}

/// <summary>
/// Sets this device as the current <see cref="SantrollerXInputGuitarAlternate"/>.
/// </summary>
public override void MakeCurrent()
{
base.MakeCurrent();
current = this;
}

/// <summary>
/// Processes when this device is added to the system.
/// </summary>
protected override void OnAdded()
{
base.OnAdded();
s_AllDevices.Add(this);
}

/// <summary>
/// Processes when this device is removed from the system.
/// </summary>
protected override void OnRemoved()
{
base.OnRemoved();
s_AllDevices.Remove(this);
if (current == this)
current = null;
}
}
}

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Original file line number Diff line number Diff line change
@@ -0,0 +1,127 @@
using System.Collections.Generic;
using System.Runtime.InteropServices;
using PlasticBand.Devices.LowLevel;
using PlasticBand.LowLevel;
using UnityEngine.InputSystem;
using UnityEngine.InputSystem.Layouts;
using UnityEngine.InputSystem.LowLevel;
using UnityEngine.InputSystem.Utilities;

// PlasticBand reference doc:
// https://github.com/TheNathannator/PlasticBand/blob/main/Docs/Instruments/5-Fret%20Guitar/Rock%20Band/Santroller.md

namespace PlasticBand.Devices.LowLevel
{
/// <summary>
/// The state format for Santroller HID Rock Band Guitars.
/// </summary>
[StructLayout(LayoutKind.Sequential, Pack = 1)]
internal unsafe struct SantrollerHIDRockBandGuitarState : IInputStateTypeInfo
{
public FourCC format => HidDefinitions.InputFormat;

public byte reportId;

[InputControl(name = "blueFret", layout = "Button", bit = 0)]
[InputControl(name = "greenFret", layout = "Button", bit = 1)]
[InputControl(name = "redFret", layout = "Button", bit = 2)]
[InputControl(name = "yellowFret", layout = "Button", bit = 3)]

[InputControl(name = "orangeFret", layout = "Button", bit = 4)]

[InputControl(name = "selectButton", layout = "Button", bit = 8)]
[InputControl(name = "startButton", layout = "Button", bit = 9)]

[InputControl(name = "psButton", layout = "Button", bit = 12, displayName = "PlayStation")]

[InputControl(name = "soloGreen", layout = "MaskButton", format = "USHT", offset = 1, bit = 0, parameters = "mask=0x0042")]
[InputControl(name = "soloRed", layout = "MaskButton", format = "USHT", offset = 1, bit = 0, parameters = "mask=0x0044")]
[InputControl(name = "soloYellow", layout = "MaskButton", format = "USHT", offset = 1, bit = 0, parameters = "mask=0x0048")]
[InputControl(name = "soloBlue", layout = "MaskButton", format = "USHT", offset = 1, bit = 0, parameters = "mask=0x0041")]
[InputControl(name = "soloOrange", layout = "MaskButton", format = "USHT", offset = 1, bit = 0, parameters = "mask=0x0050")]
public ushort buttons;

[InputControl(name = "dpad", layout = "Dpad", format = "BIT", sizeInBits = 4, defaultState = 8)]
[InputControl(name = "dpad/up", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, parameters = "minValue=7,maxValue=1,nullValue=8,wrapAtValue=7")]
[InputControl(name = "dpad/right", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, parameters = "minValue=1,maxValue=3")]
[InputControl(name = "dpad/down", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, parameters = "minValue=3,maxValue=5")]
[InputControl(name = "dpad/left", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, parameters = "minValue=5, maxValue=7")]

[InputControl(name = "strumUp", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, defaultState = 8, parameters = "minValue=7,maxValue=1,nullValue=8,wrapAtValue=7")]
[InputControl(name = "strumDown", layout = "DiscreteButton", format = "BIT", bit = 0, sizeInBits = 4, defaultState = 8, parameters = "minValue=3,maxValue=5,nullValue=8")]
public byte dpad;

[InputControl(name = "tilt", layout = "Axis")]
public byte tilt;

public byte unused1;

[InputControl(name = "whammy", layout = "Axis")]
public byte whammy;

// TODO: Define specific ranges for each of the notches
[InputControl(name = "pickupSwitch", layout = "Axis")]
public byte pickupSwitch;

public fixed byte unused2[21];
}
}

namespace PlasticBand.Devices
{
/// <summary>
/// A Santroller HID Rock Band Guitar.
/// </summary>
[InputControlLayout(stateType = typeof(SantrollerHIDRockBandGuitarState), displayName = "Santroller HID Rock Band Guitar")]
public class SantrollerHIDRockBandGuitar : RockBandGuitar
{
/// <summary>
/// The current <see cref="SantrollerHIDRockBandGuitar"/>.
/// </summary>
public static new SantrollerHIDRockBandGuitar current { get; private set; }

/// <summary>
/// A collection of all <see cref="SantrollerHIDRockBandGuitar"/>s currently connected to the system.
/// </summary>
public new static IReadOnlyList<SantrollerHIDRockBandGuitar> all => s_AllDevices;
private static readonly List<SantrollerHIDRockBandGuitar> s_AllDevices = new List<SantrollerHIDRockBandGuitar>();

/// <summary>
/// Registers <see cref="SantrollerHIDRockBandGuitar"/> to the input system.
/// </summary>
internal new static void Initialize()
{
InputSystem.RegisterLayout<SantrollerHIDRockBandGuitar>();
SantrollerLayoutFinder.RegisterLayout(SantrollerDeviceType.Guitar, SantrollerRhythmType.RockBand, nameof(SantrollerHIDRockBandGuitar));
}

/// <summary>
/// Sets this device as the current <see cref="SantrollerHIDRockBandGuitar"/>.
/// </summary>
public override void MakeCurrent()
{
base.MakeCurrent();
current = this;
}

/// <summary>
/// Processes when this device is added to the system.
/// </summary>
protected override void OnAdded()
{
base.OnAdded();
s_AllDevices.Add(this);
}

/// <summary>
/// Processes when this device is removed from the system.
/// </summary>
protected override void OnRemoved()
{
base.OnRemoved();
s_AllDevices.Remove(this);
if (current == this)
current = null;
}
}
}

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading