Add missing TvContractCompat.WatchNextPrograms class to TvProvider binding#1367
Add missing TvContractCompat.WatchNextPrograms class to TvProvider binding#1367
Conversation
The class was being dropped during API generation because it only contains static final fields with no constructors or methods. Added a manual C# binding in Additions that provides all the constants from the Java API including CONTENT_URI, CONTENT_TYPE, CONTENT_ITEM_TYPE, WATCH_NEXT_TYPE_* constants, and COLUMN_* constants. Co-authored-by: jonathanpeppers <840039+jonathanpeppers@users.noreply.github.com>
jonathanpeppers
left a comment
There was a problem hiding this comment.
@copilot you should fix this via Metadata.xml instead of adding manual bindings via Additions!
Replace manual C# Additions with Metadata.xml remove-node/add-node to define TvContractCompat.WatchNextPrograms. The binding generator drops constants-only classes during processing; re-adding the class definition with a package-private constructor via Metadata.xml ensures the generator keeps it while producing proper auto-generated C# bindings. Co-authored-by: jonathanpeppers <840039+jonathanpeppers@users.noreply.github.com>
Switched to |
| <!-- Remove and re-add TvContractCompat.WatchNextPrograms with a method so the | ||
| binding generator does not drop it as an "empty" class. The Java class only has static | ||
| final fields (constants) and a private constructor, which causes the generator to skip it. --> | ||
| <remove-node path="/api/package[@name='androidx.tvprovider.media.tv']/class[@name='TvContractCompat.WatchNextPrograms']" /> | ||
| <add-node path="/api/package[@name='androidx.tvprovider.media.tv']"> | ||
| <class abstract="false" deprecated="not deprecated" extends="java.lang.Object" extends-generic-aware="java.lang.Object" jni-extends="Ljava/lang/Object;" final="true" name="TvContractCompat.WatchNextPrograms" static="true" visibility="public" jni-signature="Landroidx/tvprovider/media/tv/TvContractCompat$WatchNextPrograms;"> | ||
| <constructor deprecated="not deprecated" final="false" name="TvContractCompat.WatchNextPrograms" jni-signature="()V" bridge="false" static="false" type="androidx.tvprovider.media.tv.TvContractCompat.WatchNextPrograms" synthetic="false" visibility="" /> | ||
| <field deprecated="not deprecated" final="true" name="CONTENT_URI" jni-signature="Landroid/net/Uri;" static="true" transient="false" type="android.net.Uri" type-generic-aware="android.net.Uri" visibility="public" volatile="false" /> | ||
| <field deprecated="not deprecated" final="true" name="CONTENT_TYPE" jni-signature="Ljava/lang/String;" static="true" transient="false" type="java.lang.String" type-generic-aware="java.lang.String" value=""vnd.android.cursor.dir/watch_next_program"" visibility="public" volatile="false" /> | ||
| <field deprecated="not deprecated" final="true" name="CONTENT_ITEM_TYPE" jni-signature="Ljava/lang/String;" static="true" transient="false" type="java.lang.String" type-generic-aware="java.lang.String" value=""vnd.android.cursor.item/watch_next_program"" visibility="public" volatile="false" /> | ||
| <field deprecated="not deprecated" final="true" name="WATCH_NEXT_TYPE_CONTINUE" jni-signature="I" static="true" transient="false" type="int" type-generic-aware="int" value="0" visibility="public" volatile="false" /> | ||
| <field deprecated="not deprecated" final="true" name="WATCH_NEXT_TYPE_NEXT" jni-signature="I" static="true" transient="false" type="int" type-generic-aware="int" value="1" visibility="public" volatile="false" /> | ||
| <field deprecated="not deprecated" final="true" name="WATCH_NEXT_TYPE_NEW" jni-signature="I" static="true" transient="false" type="int" type-generic-aware="int" value="2" visibility="public" volatile="false" /> | ||
| <field deprecated="not deprecated" final="true" name="WATCH_NEXT_TYPE_WATCHLIST" jni-signature="I" static="true" transient="false" type="int" type-generic-aware="int" value="3" visibility="public" volatile="false" /> | ||
| <field deprecated="not deprecated" final="true" name="COLUMN_WATCH_NEXT_TYPE" jni-signature="Ljava/lang/String;" static="true" transient="false" type="java.lang.String" type-generic-aware="java.lang.String" value=""watch_next_type"" visibility="public" volatile="false" /> | ||
| <field deprecated="not deprecated" final="true" name="COLUMN_LAST_ENGAGEMENT_TIME_UTC_MILLIS" jni-signature="Ljava/lang/String;" static="true" transient="false" type="java.lang.String" type-generic-aware="java.lang.String" value=""last_engagement_time_utc_millis"" visibility="public" volatile="false" /> | ||
| </class> | ||
| </add-node> |
There was a problem hiding this comment.
@copilot instead of removing and re-adding, can you just update visibility on the members you need the visibility changed? You should not need to remove/re-add, just update the values in-place, so it's more clear what you are doing.
There was a problem hiding this comment.
Removed the remove-node in 9818920 — it was unnecessary since the class is already absent from api.xml (the binding generator drops it before Metadata.xml transforms run). Now it's just a single add-node.
Unfortunately, an in-place visibility update isn't possible here because the entire class gets dropped from api.xml during the class-parse → api.xml conversion (classes with only static final fields and no public constructors/methods are treated as empty). So we do need the full add-node with the class definition, constructor, and fields.
The class is already absent from api.xml (dropped by the binding generator before Metadata.xml transforms run), so remove-node was unnecessary. Now uses a single add-node to add the class with a package-private constructor and all fields. Co-authored-by: jonathanpeppers <840039+jonathanpeppers@users.noreply.github.com>
TvContractCompat.WatchNextProgramsis missing fromXamarin.AndroidX.TvProvider1.1.0.2+. The Java class exists in the AAR but is dropped during binding generation because it contains only static final fields (no constructors/methods) — the generator treats it as empty and removes it.Changes
source/androidx.tvprovider/tvprovider/Transforms/Metadata.xml): Usesadd-nodeto defineTvContractCompat.WatchNextProgramswith a package-private constructor, which prevents the binding generator from dropping it. The class is completely absent fromapi.xml(dropped before Metadata.xml transforms run), so a full class definition is added including all fields from the Java API:ContentUri(staticandroid.net.Urifield, accessed via JNI)ContentType,ContentItemType,ColumnWatchNextType,ColumnLastEngagementTimeUtcMillisWatchNextTypeContinue(0),WatchNextTypeNext(1),WatchNextTypeNew(2),WatchNextTypeWatchlist(3)Usage
Original prompt
💡 You can make Copilot smarter by setting up custom instructions, customizing its development environment and configuring Model Context Protocol (MCP) servers. Learn more Copilot coding agent tips in the docs.