diff --git a/src/CarPlay/CPNowPlayingSportsClock.cs b/src/CarPlay/CPNowPlayingSportsClock.cs
new file mode 100644
index 000000000000..306c93899ef8
--- /dev/null
+++ b/src/CarPlay/CPNowPlayingSportsClock.cs
@@ -0,0 +1,47 @@
+//
+// Copyright (c) Microsoft Corporation.
+// Licensed under MIT License.
+//
+
+using System;
+using Foundation;
+using ObjCRuntime;
+
+#nullable enable
+
+namespace CarPlay {
+
+ public partial class CPNowPlayingSportsClock {
+
+ /// This enum is used to select how to initialize a new instance.
+ [SupportedOSPlatform ("ios18.4")]
+ [SupportedOSPlatform ("maccatalyst18.4")]
+ [SupportedOSPlatform ("macos15.4")]
+ [SupportedOSPlatform ("tvos18.4")]
+ public enum CPNowPlayingSportsClockTimeOption {
+ /// The time parameter passed to the constructor is elapsed time.
+ ElapsedTime,
+ /// The time parameter passed to the constructor is remaining time.
+ RemainingTime,
+ }
+
+ /// Create a new instance with the specified time and paused values.
+ /// The elapsed or remaining time of the clock.
+ /// If the clock is paused or not.
+ /// Use this option to specify whether the parameter refers to elapsed time or remaining time.
+ public CPNowPlayingSportsClock (double time, bool paused, CPNowPlayingSportsClockTimeOption type)
+ : base (NSObjectFlag.Empty)
+ {
+ switch (type) {
+ case CPNowPlayingSportsClockTimeOption.ElapsedTime:
+ InitializeHandle (_InitWithElapsedTime (time, paused), "initWithElapsedTime:paused:");
+ break;
+ case CPNowPlayingSportsClockTimeOption.RemainingTime:
+ InitializeHandle (_InitWithRemainingTime (time, paused), "initWithRemainingTime:paused:");
+ break;
+ default:
+ throw new ArgumentException (nameof (type));
+ }
+ }
+ }
+}
diff --git a/src/carplay.cs b/src/carplay.cs
index 2cebc0388688..819ccacb548a 100644
--- a/src/carplay.cs
+++ b/src/carplay.cs
@@ -811,6 +811,11 @@ interface CPListTemplate : CPBarButtonProviding {
[iOS (15, 0), MacCatalyst (15, 0)]
[Export ("assistantCellConfiguration", ArgumentSemantic.Strong)]
CPAssistantCellConfiguration AssistantCellConfiguration { get; set; }
+
+ [NullAllowed]
+ [iOS (18, 4), MacCatalyst (18, 4)]
+ [Export ("showsSpinnerWhileEmpty", ArgumentSemantic.Assign)]
+ bool ShowsSpinnerWhileEmpty { get; set; }
}
/// Delegate object for objects.
@@ -2129,6 +2134,10 @@ interface CPNowPlayingTemplate {
[Export ("updateNowPlayingButtons:")]
void UpdateNowPlayingButtons (CPNowPlayingButton [] nowPlayingButtons);
+
+ [iOS (18, 4), MacCatalyst (18, 4)]
+ [Export ("nowPlayingMode", ArgumentSemantic.Strong), NullAllowed]
+ CPNowPlayingMode NowPlayingMode { get; set; }
}
[NoTV, NoMac, iOS (14, 0)]
@@ -2445,4 +2454,113 @@ interface CPRouteInformation {
CPTravelEstimates ManeuverTravelEstimates { get; }
}
+ [NoTV, NoMac, iOS (18, 4), MacCatalyst (18, 4)]
+ [BaseType (typeof (NSObject))]
+ [DisableDefaultCtor]
+ interface CPNowPlayingMode : NSSecureCoding {
+ [Static]
+ [Export ("defaultNowPlayingMode")]
+ CPNowPlayingMode DefaultNowPlayingMode { get; }
+ }
+
+ [NoTV, NoMac, iOS (18, 4), MacCatalyst (18, 4)]
+ [BaseType (typeof (CPNowPlayingMode))]
+ interface CPNowPlayingModeSports : NSSecureCoding {
+ [Export ("initWithLeftTeam:rightTeam:eventStatus:backgroundArtwork:")]
+ NativeHandle Constructor (CPNowPlayingSportsTeam leftTeam, CPNowPlayingSportsTeam rightTeam, [NullAllowed] CPNowPlayingSportsEventStatus eventStatus, [NullAllowed] UIImage backgroundArtwork);
+
+ [Export ("leftTeam", ArgumentSemantic.Strong)]
+ CPNowPlayingSportsTeam LeftTeam { get; }
+
+ [Export ("rightTeam", ArgumentSemantic.Strong)]
+ CPNowPlayingSportsTeam RightTeam { get; }
+
+ [NullAllowed, Export ("eventStatus", ArgumentSemantic.Strong)]
+ CPNowPlayingSportsEventStatus EventStatus { get; }
+
+ [NullAllowed, Export ("backgroundArtwork", ArgumentSemantic.Copy)]
+ UIImage BackgroundArtwork { get; }
+ }
+
+ [NoTV, NoMac, iOS (18, 4), MacCatalyst (18, 4)]
+ [BaseType (typeof (NSObject))]
+ [DisableDefaultCtor]
+ interface CPNowPlayingSportsTeam : NSSecureCoding {
+ [Export ("initWithName:logo:teamStandings:eventScore:possessionIndicator:favorite:")]
+ NativeHandle Constructor (string name, CPNowPlayingSportsTeamLogo logo, [NullAllowed] string teamStandings, string eventScore, [NullAllowed] UIImage possessionIndicator, bool favorite);
+
+ [Export ("name")]
+ string Name { get; }
+
+ [Export ("logo", ArgumentSemantic.Copy)]
+ CPNowPlayingSportsTeamLogo Logo { get; }
+
+ [NullAllowed, Export ("teamStandings")]
+ string TeamStandings { get; }
+
+ [Export ("eventScore")]
+ string EventScore { get; }
+
+ [NullAllowed, Export ("possessionIndicator", ArgumentSemantic.Copy)]
+ UIImage PossessionIndicator { get; }
+
+ [Export ("favorite")]
+ bool Favorite { [Bind ("isFavorite")] get; }
+ }
+
+ [NoTV, NoMac, iOS (18, 4), MacCatalyst (18, 4)]
+ [BaseType (typeof (NSObject))]
+ [DisableDefaultCtor]
+ interface CPNowPlayingSportsEventStatus : NSSecureCoding {
+ [Export ("initWithEventStatusText:eventStatusImage:eventClock:")]
+ NativeHandle Constructor ([NullAllowed] string [] eventStatusText, [NullAllowed] UIImage eventStatusImage, [NullAllowed] CPNowPlayingSportsClock eventClock);
+
+ [NullAllowed, Export ("eventStatusText", ArgumentSemantic.Copy)]
+ string [] EventStatusText { get; }
+
+ [NullAllowed, Export ("eventClock", ArgumentSemantic.Copy)]
+ CPNowPlayingSportsClock EventClock { get; }
+
+ [NullAllowed, Export ("eventStatusImage", ArgumentSemantic.Copy)]
+ UIImage EventStatusImage { get; }
+ }
+
+ [NoTV, NoMac, iOS (18, 4), MacCatalyst (18, 4)]
+ [BaseType (typeof (NSObject))]
+ [DisableDefaultCtor]
+ interface CPNowPlayingSportsClock : INSSecureCoding {
+ [Internal]
+ [Export ("initWithElapsedTime:paused:")]
+ NativeHandle _InitWithElapsedTime (double elapsedTime, bool paused);
+
+ [Internal]
+ [Export ("initWithTimeRemaining:paused:")]
+ NativeHandle _InitWithRemainingTime (double timeRemaining, bool paused);
+
+ [Export ("timeValue")]
+ double TimeValue { get; }
+
+ [Export ("paused")]
+ bool Paused { [Bind ("isPaused")] get; }
+
+ [Export ("countsUp")]
+ bool CountsUp { get; }
+ }
+
+ [NoTV, NoMac, iOS (18, 4), MacCatalyst (18, 4)]
+ [BaseType (typeof (NSObject))]
+ [DisableDefaultCtor]
+ interface CPNowPlayingSportsTeamLogo : INSSecureCoding {
+ [Export ("initWithTeamLogo:")]
+ NativeHandle Constructor (UIImage teamLogo);
+
+ [Export ("initWithTeamInitials:")]
+ NativeHandle Constructor (string teamInitials);
+
+ [NullAllowed, Export ("logo", ArgumentSemantic.Copy)]
+ UIImage Logo { get; }
+
+ [NullAllowed, Export ("initials")]
+ string Initials { get; }
+ }
}
diff --git a/src/frameworks.sources b/src/frameworks.sources
index a2c2f5b04f43..bdd9dac759b0 100644
--- a/src/frameworks.sources
+++ b/src/frameworks.sources
@@ -344,6 +344,7 @@ CARPLAY_API_SOURCES = \
CARPLAY_SOURCES = \
CarPlay/CPCompat.cs \
CarPlay/CPNavigationAlert.cs \
+ CarPlay/CPNowPlayingSportsClock.cs \
CarPlay/CPMessageListItem.cs \
# ClassKit
diff --git a/tests/cecil-tests/Documentation.KnownFailures.txt b/tests/cecil-tests/Documentation.KnownFailures.txt
index 2ca9218b7a97..48745d712c5f 100644
--- a/tests/cecil-tests/Documentation.KnownFailures.txt
+++ b/tests/cecil-tests/Documentation.KnownFailures.txt
@@ -23290,6 +23290,10 @@ M:CarPlay.CPMessageListItem.#ctor(System.String,System.String,CarPlay.CPMessageL
M:CarPlay.CPMessageListItem.#ctor(System.String,System.String,CarPlay.CPMessageListItemLeadingConfiguration,CarPlay.CPMessageListItemTrailingConfiguration,System.String,System.String)
M:CarPlay.CPNavigationAlert.EncodeTo(Foundation.NSCoder)
M:CarPlay.CPNowPlayingButton.EncodeTo(Foundation.NSCoder)
+M:CarPlay.CPNowPlayingMode.EncodeTo(Foundation.NSCoder)
+M:CarPlay.CPNowPlayingModeSports.EncodeTo(Foundation.NSCoder)
+M:CarPlay.CPNowPlayingSportsEventStatus.EncodeTo(Foundation.NSCoder)
+M:CarPlay.CPNowPlayingSportsTeam.EncodeTo(Foundation.NSCoder)
M:CarPlay.CPNowPlayingTemplateObserver_Extensions.AlbumArtistButtonTapped(CarPlay.ICPNowPlayingTemplateObserver,CarPlay.CPNowPlayingTemplate)
M:CarPlay.CPNowPlayingTemplateObserver_Extensions.UpNextButtonTapped(CarPlay.ICPNowPlayingTemplateObserver,CarPlay.CPNowPlayingTemplate)
M:CarPlay.CPPointOfInterest.EncodeTo(Foundation.NSCoder)
@@ -49318,6 +49322,8 @@ P:CarPlay.CPMessageListItemLeadingConfiguration.Unread
P:CarPlay.CPNowPlayingButton.Enabled
P:CarPlay.CPNowPlayingButton.MaximumImageSize
P:CarPlay.CPNowPlayingButton.Selected
+P:CarPlay.CPNowPlayingSportsClock.Paused
+P:CarPlay.CPNowPlayingSportsTeam.Favorite
P:CarPlay.CPNowPlayingTemplate.IsAlbumArtistButtonEnabled
P:CarPlay.CPNowPlayingTemplate.IsUpNextButtonEnabled
P:CarPlay.CPPointOfInterestTemplate.PointOfInterestDelegate
diff --git a/tests/xtro-sharpie/api-annotations-dotnet/iOS-CarPlay.todo b/tests/xtro-sharpie/api-annotations-dotnet/iOS-CarPlay.todo
deleted file mode 100644
index 780f26fd87d0..000000000000
--- a/tests/xtro-sharpie/api-annotations-dotnet/iOS-CarPlay.todo
+++ /dev/null
@@ -1,36 +0,0 @@
-!missing-selector! +CPNowPlayingMode::defaultNowPlayingMode not bound
-!missing-selector! CPListTemplate::setShowsSpinnerWhileEmpty: not bound
-!missing-selector! CPListTemplate::showsSpinnerWhileEmpty not bound
-!missing-selector! CPNowPlayingModeSports::backgroundArtwork not bound
-!missing-selector! CPNowPlayingModeSports::eventStatus not bound
-!missing-selector! CPNowPlayingModeSports::initWithLeftTeam:rightTeam:eventStatus:backgroundArtwork: not bound
-!missing-selector! CPNowPlayingModeSports::leftTeam not bound
-!missing-selector! CPNowPlayingModeSports::rightTeam not bound
-!missing-selector! CPNowPlayingSportsClock::countsUp not bound
-!missing-selector! CPNowPlayingSportsClock::initWithElapsedTime:paused: not bound
-!missing-selector! CPNowPlayingSportsClock::initWithTimeRemaining:paused: not bound
-!missing-selector! CPNowPlayingSportsClock::isPaused not bound
-!missing-selector! CPNowPlayingSportsClock::timeValue not bound
-!missing-selector! CPNowPlayingSportsEventStatus::eventClock not bound
-!missing-selector! CPNowPlayingSportsEventStatus::eventStatusImage not bound
-!missing-selector! CPNowPlayingSportsEventStatus::eventStatusText not bound
-!missing-selector! CPNowPlayingSportsEventStatus::initWithEventStatusText:eventStatusImage:eventClock: not bound
-!missing-selector! CPNowPlayingSportsTeam::eventScore not bound
-!missing-selector! CPNowPlayingSportsTeam::initWithName:logo:teamStandings:eventScore:possessionIndicator:favorite: not bound
-!missing-selector! CPNowPlayingSportsTeam::isFavorite not bound
-!missing-selector! CPNowPlayingSportsTeam::logo not bound
-!missing-selector! CPNowPlayingSportsTeam::name not bound
-!missing-selector! CPNowPlayingSportsTeam::possessionIndicator not bound
-!missing-selector! CPNowPlayingSportsTeam::teamStandings not bound
-!missing-selector! CPNowPlayingSportsTeamLogo::initials not bound
-!missing-selector! CPNowPlayingSportsTeamLogo::initWithTeamInitials: not bound
-!missing-selector! CPNowPlayingSportsTeamLogo::initWithTeamLogo: not bound
-!missing-selector! CPNowPlayingSportsTeamLogo::logo not bound
-!missing-selector! CPNowPlayingTemplate::nowPlayingMode not bound
-!missing-selector! CPNowPlayingTemplate::setNowPlayingMode: not bound
-!missing-type! CPNowPlayingMode not bound
-!missing-type! CPNowPlayingModeSports not bound
-!missing-type! CPNowPlayingSportsClock not bound
-!missing-type! CPNowPlayingSportsEventStatus not bound
-!missing-type! CPNowPlayingSportsTeam not bound
-!missing-type! CPNowPlayingSportsTeamLogo not bound