Skip to content

[GameController] Implement up to Xcode 16.3. #22699

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

Merged
merged 5 commits into from
May 5, 2025
Merged
Show file tree
Hide file tree
Changes from 2 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
84 changes: 84 additions & 0 deletions src/GameController/GCInput.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

#nullable enable

using System;
using System.Globalization;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;

using CoreFoundation;
using CoreGraphics;
using Foundation;
using ObjCRuntime;

namespace GameController {
public partial class GCInput {
[SupportedOSPlatform ("ios17.4")]
[SupportedOSPlatform ("macos14.4")]
[SupportedOSPlatform ("tvos17.4")]
[SupportedOSPlatform ("maccatalyst17.4")]
[DllImport (Constants.GameControllerLibrary)]
static extern IntPtr /* GCButtonElementName */ GCInputBackLeftButton (nint position);

// A strongly-typed API (the GCInputButtonName enum) is not possible, because it's not an exhaustive enum,
// this method may return strings that aren't in the enum.
/// <summary>Get the name of the back left button on the controller for the specified position.</summary>
/// <param name="position">Zero-based position of the button.</param>
/// <returns>The name of the back left button on the controller for the specified position.</returns>
[SupportedOSPlatform ("ios17.4")]
[SupportedOSPlatform ("macos14.4")]
[SupportedOSPlatform ("tvos17.4")]
[SupportedOSPlatform ("maccatalyst17.4")]
public static NSString? GetBackLeftButtonName (nint position)
{
return Runtime.GetNSObject<NSString> (GCInputBackLeftButton (position));
}

[SupportedOSPlatform ("ios17.4")]
[SupportedOSPlatform ("macos14.4")]
[SupportedOSPlatform ("tvos17.4")]
[SupportedOSPlatform ("maccatalyst17.4")]
[DllImport (Constants.GameControllerLibrary)]
static extern IntPtr /* GCButtonElementName */ GCInputBackRightButton (nint position);

// A strongly-typed API (the GCInputButtonName enum) is not possible, because it's not an exhaustive enum,
// this method may return strings that aren't in the enum.
/// <summary>Get the name of the back right button on the controller for the specified position.</summary>
/// <param name="position">Zero-based position of the button.</param>
/// <returns>The name of the back rught button on the controller for the specified position.</returns>
[SupportedOSPlatform ("ios17.4")]
[SupportedOSPlatform ("macos14.4")]
[SupportedOSPlatform ("tvos17.4")]
[SupportedOSPlatform ("maccatalyst17.4")]
public static NSString? GetBackRightButtonName (nint position)
{
return Runtime.GetNSObject<NSString> (GCInputBackRightButton (position));
}

// headers claim macOS 13.0 / iOS 16.0, but introspection says macOS 14.0 / iOS 17.0, so use that.
[SupportedOSPlatform ("ios17.0")]
[SupportedOSPlatform ("macos14.0")]
[SupportedOSPlatform ("tvos17.0")]
[SupportedOSPlatform ("maccatalyst17.0")]
[DllImport (Constants.GameControllerLibrary)]
static extern IntPtr /* GCButtonElementName */ GCInputArcadeButtonName (nint row, nint column);

// A strongly-typed API (the GCInputButtonName enum) is not possible, because it's not an exhaustive enum,
// this method may return strings that aren't in the enum.
/// <summary>Get the name of the arcade button for the specified position.</summary>
/// <param name="row">The row of the arcade button.</param>
/// <param name="column">The column of the arcade button.</param>
/// <returns>The name of the arcade button on the controller for the specified position.</returns>
[SupportedOSPlatform ("ios17.0")]
[SupportedOSPlatform ("macos14.0")]
[SupportedOSPlatform ("tvos17.0")]
[SupportedOSPlatform ("maccatalyst17.0")]
public static NSString? GetArcadeButtonName (nint row, nint column)
{
return Runtime.GetNSObject<NSString> (GCInputArcadeButtonName (row, column));
}
}
}
29 changes: 29 additions & 0 deletions src/GameController/GCPhysicalInputElementCollection.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

using System;
using System.Collections;
using System.Collections.Generic;

using Foundation;
using ObjCRuntime;

#nullable enable

namespace GameController {
public partial class GCPhysicalInputElementCollection<KeyIdentifierType, ElementIdentifierType> : IEnumerable<KeyIdentifierType> {
#region IEnumerable<KeyIdentifierType>
IEnumerator<KeyIdentifierType> IEnumerable<KeyIdentifierType>.GetEnumerator ()
{
return new NSFastEnumerator<KeyIdentifierType> (this);
}
#endregion

#region IEnumerable implementation
IEnumerator IEnumerable.GetEnumerator ()
{
return new NSFastEnumerator<KeyIdentifierType> (this);
}
#endregion
}
}
109 changes: 109 additions & 0 deletions src/GameController/GCPoint2.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,109 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

#nullable enable

using System;
using System.Globalization;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;

using CoreFoundation;
using CoreGraphics;
using Foundation;
using ObjCRuntime;

namespace GameController {
[SupportedOSPlatform ("ios")]
[SupportedOSPlatform ("maccatalyst")]
[SupportedOSPlatform ("macos")]
[SupportedOSPlatform ("tvos")]
public struct GCPoint2
#if !COREBUILD
: IEquatable<GCPoint2>
#endif
{
float x;
float y;

public float X {
get { return x; }
set { x = value; }
}

public float Y {
get { return y; }
set { y = value; }
}

#if !COREBUILD
public static readonly GCPoint2 Zero;

public static bool operator == (GCPoint2 l, GCPoint2 r)
{
// the following version of Equals cannot be removed by the linker, while == can be
return l.Equals (r);
}

public static bool operator != (GCPoint2 l, GCPoint2 r)
{
return l.x != r.x || l.y != r.y;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Call be lazy, I would have implemented this based on the == operator.

}

public bool IsEmpty {
get { return x == 0.0 && y == 0.0; }
}

public GCPoint2 (float x, float y)
{
this.x = x;
this.y = y;
}

public GCPoint2 (GCPoint2 point)
{
this.x = point.x;
this.y = point.y;
}

public override bool Equals (object? obj)
{
return (obj is GCPoint2 t) && Equals (t);
}

public bool Equals (GCPoint2 point)
{
return point.x == x && point.y == y;
}

public override int GetHashCode ()
{
return HashCode.Combine (x, y);
}

public void Deconstruct (out nfloat x, out nfloat y)
{
x = X;
y = Y;
}

public override string? ToString ()
{
if (OperatingSystem.IsMacOSVersionAtLeast (14, 3) ||
OperatingSystem.IsMacCatalystVersionAtLeast (17, 4) ||
OperatingSystem.IsIOSVersionAtLeast (17, 4) ||
OperatingSystem.IsTvOSVersionAtLeast (17, 4))
return CFString.FromHandle (NSStringFromGCPoint2 (this));
return $"{{{x}, {y}}}";
}

[SupportedOSPlatform ("ios17.4")]
[SupportedOSPlatform ("tvos17.4")]
[SupportedOSPlatform ("maccatalyst17.4")]
[SupportedOSPlatform ("macos14.3")]
[DllImport (Constants.GameControllerLibrary)]
extern static /* NSString* */ IntPtr NSStringFromGCPoint2 (/* GCPoint2 */ GCPoint2 point);
#endif // !COREBUILD
}
}
3 changes: 3 additions & 0 deletions src/frameworks.sources
Original file line number Diff line number Diff line change
Expand Up @@ -947,12 +947,15 @@ GAMECONTROLLER_API_SOURCES = \
GAMECONTROLLER_CORE_SOURCES = \
GameController/GCController.cs \
GameController/GCMotion.cs \
GameController/GCPoint2.cs \

GAMECONTROLLER_SOURCES = \
GameController/GCExtendedGamepadSnapshot.cs \
GameController/GCGamepadSnapshot.cs \
GameController/GCInput.cs \
GameController/GCMicroGamepadSnapshot.cs \
GameController/GCMouse.cs \
GameController/GCPhysicalInputElementCollection.cs \

# GameKit

Expand Down
Loading
Loading