From 6a77df04b8e00b55a07725b6a4d8e32896be938c Mon Sep 17 00:00:00 2001 From: Copilot Date: Sat, 31 Jan 2026 00:54:40 +0100 Subject: [PATCH 1/2] [UIKit] Enable nullability and clean up UICollectionView. This is file 5 of 30 files with nullability disabled in UIKit. * Enable nullability (#nullable enable). * Remove unused System.Threading.Tasks using directive. * Use ArgumentNullException.ThrowIfNull() instead of manual null checks. * Add nullable annotation for Source property (UICollectionViewSource?). * Simplify Source property getter with expression body. * Replace include file references with inlined XML documentation. * Remove inlined DocId entries from docs/api/UIKit/UICollectionView.xml. * Improve XML documentation comments: remove 'To be added.' placeholders, fix whitespace, add missing docs, add 'see cref' references. Contributes towards https://github.com/dotnet/macios/issues/17285. --- docs/api/UIKit/UICollectionView.xml | 107 +---------------- src/ObjCRuntime/Class.cs | 28 ++--- src/UIKit/UICollectionView.cs | 174 +++++++++++++++------------- 3 files changed, 112 insertions(+), 197 deletions(-) diff --git a/docs/api/UIKit/UICollectionView.xml b/docs/api/UIKit/UICollectionView.xml index 9b9525e9b6ec..317def4b3f7e 100644 --- a/docs/api/UIKit/UICollectionView.xml +++ b/docs/api/UIKit/UICollectionView.xml @@ -310,109 +310,4 @@ public class SimpleCollectionViewController : UICollectionViewController Introduction to Collection Views Apple documentation for UICollectionView - - To be added. - A non-empty string to be associated with the . - Specifies the type to be used to populate cells. - - The maintains a highly-efficient reuse queue for offscreen components. This requires that the be responsible for the lifecycle management of its component views. This method (and related methods such as ) provide the the knowledge of which types it needs to instantiate. - The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another type, in which case the old type will be "de-registered" and the new will be used. - It is very important that the type that you specify implements a public constructor that takes a parameter, this is used to initialize the class from an object allocated by Objective-C. The following example shows the constructor in use: - - - - Developers should not call this method if they have prototyped their type using a Storyboard. If they do so, they will overwrite the Storyboard-defined definition instantiation of the object's children. - - - - - - - - - - - - - - - A subtype of . - A non-empty string to be associated with the . - Specifies the type to be used to populate cells. - - The maintains a highly-efficient reuse queue for offscreen components. This requires that the be responsible for the lifecycle management of its component views. This method (and related methods such as ) provide the the knowledge of which types it needs to instantiate. - The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another type, in which case the old type will be "de-registered" and the new will be used. - It is very important that the type that you specify implements a public constructor that takes a parameter, this is used to initialize the class from an object allocated by Objective-C. The following example shows the constructor in use: - - - - Developers should not call this method if they have prototyped their type using a Storyboard. If they do so, they will overwrite the Storyboard-defined definition instantiation of the object's children. - - - - - - - - - - - - - - - A subtype of to be used for supplementary views - The type of supplementary view being registered. - A non-empty string to be associated with the . - Specifies the type to be used to populate supplementary views. - - The maintains a highly-efficient reuse queue for offscreen components. This requires that the be responsible for the lifecycle management of its component views. This method (and related methods such as ) provide the the knowledge of which types it needs to instantiate. - The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another type, in which case the old type will be "de-registered" and the new will be used. - - It is very important that you provide constructor that takes an IntPtr argument in any subclasses that you register. This is required because the classes are actually allocated by the Objective-C runtime, and you must initialize them. - - - - - - - - - - - - - - The to be used to populate the supplementary view. - The kind of supplementary view being registered. - A non-empty string to be associated with the . - Specifies the nib to be used for populating the supplementary view. - - The maintains a highly-efficient reuse queue for offscreen components. This requires that the be responsible for the lifecycle management of its component views. This method (and related methods such as ) provide the the knowledge of which types it needs to instantiate. - The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another nib, in which case the old nib will be "de-registered" and the new will be used. - - - - A specifying what kind of supplementary view is desired. - To be added. - The specifying the location of the supplementary view. - Returns a newly-allocated or reused supplementary . - A supplementary that is either newly allocated or recycled from the reuse queue.. - - The application developer must have registered a class or nib file using either or prior to calling this method. - If the is not newly allocated but is being recycled, this method will call that cell's method. - - - \ No newline at end of file + diff --git a/src/ObjCRuntime/Class.cs b/src/ObjCRuntime/Class.cs index 36c69c87e1a8..fcec98fd21f4 100644 --- a/src/ObjCRuntime/Class.cs +++ b/src/ObjCRuntime/Class.cs @@ -187,20 +187,22 @@ public static NativeHandle GetHandleIntrinsic (string name) return objc_getClass (name); } + /// Gets the Objective-C handle of the given type. /// Type for an NSObject-derived class - /// Gets the Objective-C handle of the given type. - /// The Objective-C handle to the object. - /// - /// - /// This method looks up the Objective-C handle for the specified type, or registers the specified type with the Objective-C runtime if it was not previously registered. - /// - /// - /// The class must be derived from NSObject. If the class is flagged with the [Register] attribute, the name specified in this Register attribute is the name that will be used for looking up or register the class. - /// - /// - /// - public static NativeHandle GetHandle (Type type) - { + /// The Objective-C handle to the object. + /// + /// + /// This method looks up the Objective-C handle for the specified type, or registers the specified type with the Objective-C runtime if it was not previously registered. + /// + /// + /// The class must be derived from . If the class is flagged with the attribute, the name specified in this Register attribute is the name that will be used for looking up or register the class. + /// + /// + public static NativeHandle GetHandle (Type? type) + { + if (type is null) + return NativeHandle.Zero; + return GetClassHandle (type, true, out _); } diff --git a/src/UIKit/UICollectionView.cs b/src/UIKit/UICollectionView.cs index 43dbaf4bc6c1..523a4d5e90af 100644 --- a/src/UIKit/UICollectionView.cs +++ b/src/UIKit/UICollectionView.cs @@ -7,134 +7,158 @@ // Miguel de Icaza // -using System.Threading.Tasks; - -// Disable until we get around to enable + fix any issues. -#nullable disable +#nullable enable namespace UIKit { public partial class UICollectionView { - /// To be added. - /// To be added. - /// Returns a new or reused . - /// To be added. - /// To be added. + /// Returns a new or reused . + /// The reuse identifier for the cell type to dequeue. + /// The index path specifying the location of the cell. + /// A that is either newly allocated or recycled from the reuse queue. public UICollectionReusableView DequeueReusableCell (string reuseIdentifier, NSIndexPath indexPath) { using (var str = (NSString) reuseIdentifier) return (UICollectionReusableView) DequeueReusableCell (str, indexPath); } - /// To be added. - /// To be added. - /// To be added. - /// Returns a . - /// To be added. - /// To be added. + /// Returns a for a supplementary view. + /// An specifying the kind of supplementary view to dequeue. + /// The reuse identifier for the supplementary view type to dequeue. + /// The index path specifying the location of the supplementary view. + /// A that is either newly allocated or recycled from the reuse queue. public UICollectionReusableView DequeueReusableSupplementaryView (NSString kind, string reuseIdentifier, NSIndexPath indexPath) { using (var str = (NSString) reuseIdentifier) return (UICollectionReusableView) DequeueReusableSupplementaryView (kind, str, indexPath); } - /// To be added. - /// To be added. - /// To be added. - /// Returns a . - /// To be added. - /// To be added. + /// Returns a for a supplementary view. + /// A specifying the kind of supplementary view to dequeue. + /// The reuse identifier for the supplementary view type to dequeue. + /// The index path specifying the location of the supplementary view. + /// A that is either newly allocated or recycled from the reuse queue. public UICollectionReusableView DequeueReusableSupplementaryView (UICollectionElementKindSection kind, string reuseIdentifier, NSIndexPath indexPath) { using (var str = (NSString) reuseIdentifier) return (UICollectionReusableView) DequeueReusableSupplementaryView (KindToString (kind), str, indexPath); } - /// To be added. - /// To be added. - /// Registers the Nib file that will be used for cell UI. - /// To be added. - public void RegisterNibForCell (UINib nib, string reuseIdentifier) + /// Registers the Nib file that will be used for cell UI. + /// The to be used to populate the cell. + /// A non-empty string to be associated with the . + public void RegisterNibForCell (UINib? nib, string reuseIdentifier) { using (var str = (NSString) reuseIdentifier) RegisterNibForCell (nib, str); } - /// - public void RegisterClassForCell (Type cellType, string reuseIdentifier) + /// Specifies the type to be used to populate cells. + /// A subtype of . + /// A non-empty string to be associated with the . + /// + /// The maintains a highly-efficient reuse queue for offscreen components. This requires that the be responsible for the lifecycle management of its component views. This method (and related methods such as ) provide the the knowledge of which types it needs to instantiate. + /// The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another type, in which case the old type will be "de-registered" and the new will be used. + /// It is very important that the type that you specify implements a public constructor that takes a parameter, this is used to initialize the class from an object allocated by Objective-C. + /// Developers should not call this method if they have prototyped their type using a Storyboard. If they do so, they will overwrite the Storyboard-defined definition instantiation of the object's children. + /// + public void RegisterClassForCell (Type? cellType, string reuseIdentifier) { using (var str = (NSString) reuseIdentifier) RegisterClassForCell (cellType, str); } - /// - public void RegisterClassForCell (Type cellType, NSString reuseIdentifier) + /// Specifies the type to be used to populate cells. + /// A subtype of . + /// A non-empty string to be associated with the . + /// + /// The maintains a highly-efficient reuse queue for offscreen components. This requires that the be responsible for the lifecycle management of its component views. This method (and related methods such as ) provide the the knowledge of which types it needs to instantiate. + /// The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another type, in which case the old type will be "de-registered" and the new will be used. + /// It is very important that the type that you specify implements a public constructor that takes a parameter, this is used to initialize the class from an object allocated by Objective-C. + /// Developers should not call this method if they have prototyped their type using a Storyboard. If they do so, they will overwrite the Storyboard-defined definition instantiation of the object's children. + /// + public void RegisterClassForCell (Type? cellType, NSString reuseIdentifier) { - if (cellType is null) - throw new ArgumentNullException ("cellType"); + ArgumentNullException.ThrowIfNull (cellType); RegisterClassForCell (Class.GetHandle (cellType), reuseIdentifier); } - /// To be added. - /// To be added. - /// To be added. - /// Specifies the type to be used to populate supplementary views. - /// To be added. - public void RegisterClassForSupplementaryView (Type cellType, NSString kind, string reuseIdentifier) + /// Specifies the type to be used to populate supplementary views. + /// A subtype of to be used for supplementary views. + /// The kind of supplementary view being registered (e.g., "UICollectionElementKindSectionHeader"). + /// A non-empty string to be associated with the . + public void RegisterClassForSupplementaryView (Type? cellType, NSString kind, string reuseIdentifier) { using (var str = (NSString) reuseIdentifier) RegisterClassForSupplementaryView (Class.GetHandle (cellType), kind, str); } - /// A subtype of to be used for supplementary views. - /// The type of supplementary view being registered (e.g., "UICollectionElementKindSectionHeader"). - /// A non-empty string to be associated with the . - /// Specifies the type to be used to populate supplementary views. - /// To be added. - public void RegisterClassForSupplementaryView (Type cellType, NSString kind, NSString reuseIdentifier) + /// Specifies the type to be used to populate supplementary views. + /// A subtype of to be used for supplementary views. + /// The kind of supplementary view being registered (e.g., "UICollectionElementKindSectionHeader"). + /// A non-empty string to be associated with the . + public void RegisterClassForSupplementaryView (Type? cellType, NSString kind, NSString reuseIdentifier) { RegisterClassForSupplementaryView (Class.GetHandle (cellType), kind, reuseIdentifier); } - /// To be added. - /// To be added. - /// To be added. - /// Specifies the type to be used to populate supplementary views. - /// To be added. - public void RegisterClassForSupplementaryView (Type cellType, UICollectionElementKindSection section, string reuseIdentifier) + /// Specifies the type to be used to populate supplementary views. + /// A subtype of to be used for supplementary views. + /// The kind of supplementary view being registered. + /// A non-empty string to be associated with the . + public void RegisterClassForSupplementaryView (Type? cellType, UICollectionElementKindSection section, string reuseIdentifier) { using (var str = (NSString) reuseIdentifier) RegisterClassForSupplementaryView (cellType, section, str); } - /// - public void RegisterClassForSupplementaryView (Type cellType, UICollectionElementKindSection section, NSString reuseIdentifier) + /// Specifies the type to be used to populate supplementary views. + /// A subtype of to be used for supplementary views. + /// The kind of supplementary view being registered. + /// A non-empty string to be associated with the . + /// + /// The maintains a highly-efficient reuse queue for offscreen components. This requires that the be responsible for the lifecycle management of its component views. This method (and related methods such as ) provide the the knowledge of which types it needs to instantiate. + /// The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another type, in which case the old type will be "de-registered" and the new will be used. + /// It is very important that you provide a constructor that takes an argument in any subclasses that you register. This is required because the classes are actually allocated by the Objective-C runtime, and you must initialize them. + /// + public void RegisterClassForSupplementaryView (Type? cellType, UICollectionElementKindSection section, NSString reuseIdentifier) { - if (cellType is null) - throw new ArgumentNullException ("cellType"); - RegisterClassForSupplementaryView (Class.GetHandle (cellType), KindToString (section), reuseIdentifier); } - /// To be added. - /// To be added. - /// To be added. - /// Registers the Nib file that will be used for UI in supplementary views. - /// To be added. - public void RegisterNibForSupplementaryView (UINib nib, UICollectionElementKindSection section, string reuseIdentifier) + /// Registers the Nib file that will be used for UI in supplementary views. + /// The to be used to populate the supplementary view. + /// The kind of supplementary view being registered. + /// A non-empty string to be associated with the . + public void RegisterNibForSupplementaryView (UINib? nib, UICollectionElementKindSection section, string reuseIdentifier) { using (var str = (NSString) reuseIdentifier) RegisterNibForSupplementaryView (nib, section, str); } - /// - public void RegisterNibForSupplementaryView (UINib nib, UICollectionElementKindSection section, NSString reuseIdentifier) + /// Specifies the nib to be used for populating the supplementary view. + /// The to be used to populate the supplementary view. + /// The kind of supplementary view being registered. + /// A non-empty string to be associated with the . + /// + /// The maintains a highly-efficient reuse queue for offscreen components. This requires that the be responsible for the lifecycle management of its component views. This method (and related methods such as ) provide the the knowledge of which types it needs to instantiate. + /// The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another nib, in which case the old nib will be "de-registered" and the new will be used. + /// + public void RegisterNibForSupplementaryView (UINib? nib, UICollectionElementKindSection section, NSString reuseIdentifier) { RegisterNibForSupplementaryView (nib, KindToString (section), reuseIdentifier); } - /// + /// Returns a newly-allocated or reused supplementary . + /// A specifying what kind of supplementary view is desired. + /// The reuse identifier for the supplementary view type to dequeue. + /// The specifying the location of the supplementary view. + /// A supplementary that is either newly allocated or recycled from the reuse queue. + /// + /// The application developer must have registered a class or nib file using either or prior to calling this method. + /// If the is not newly allocated but is being recycled, this method will call that cell's method. + /// public NSObject DequeueReusableSupplementaryView (UICollectionElementKindSection section, NSString reuseIdentifier, NSIndexPath indexPath) { return DequeueReusableSupplementaryView (KindToString (section), reuseIdentifier, indexPath); @@ -148,23 +172,17 @@ static NSString KindToString (UICollectionElementKindSection section) case UICollectionElementKindSection.Footer: return UICollectionElementKindSectionKey.Footer; default: - throw new ArgumentOutOfRangeException ("section"); + throw new ArgumentOutOfRangeException (nameof (section)); } } - /// An optional property that can substitute for the and properties - /// The default value is . - /// - /// Rather than specify separate classes and provide two objects for the and properties, one can provide a single class of type (which itself is simply defined as ). - /// - public UICollectionViewSource Source { - get { - var d = WeakDelegate as UICollectionViewSource; - if (d is not null) - return d; - return null; - } - + /// An optional property that can substitute for the and properties. + /// The that provides both data source and delegate functionality, or if not set. + /// + /// Rather than specify separate classes and provide two objects for the and properties, one can provide a single class of type . + /// + public UICollectionViewSource? Source { + get => WeakDelegate as UICollectionViewSource; set { WeakDelegate = value; WeakDataSource = value; From 473d98a240c7d3c1e9187315ab66198be90f86c6 Mon Sep 17 00:00:00 2001 From: Rolf Bjarne Kvinge Date: Mon, 2 Feb 2026 09:05:59 +0100 Subject: [PATCH 2/2] Copilot tweaks. --- src/UIKit/UICollectionView.cs | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/src/UIKit/UICollectionView.cs b/src/UIKit/UICollectionView.cs index 523a4d5e90af..6421fc9de333 100644 --- a/src/UIKit/UICollectionView.cs +++ b/src/UIKit/UICollectionView.cs @@ -73,14 +73,12 @@ public void RegisterClassForCell (Type? cellType, string reuseIdentifier) /// A non-empty string to be associated with the . /// /// The maintains a highly-efficient reuse queue for offscreen components. This requires that the be responsible for the lifecycle management of its component views. This method (and related methods such as ) provide the the knowledge of which types it needs to instantiate. - /// The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another type, in which case the old type will be "de-registered" and the new will be used. + /// The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another type, in which case the old type will be "de-registered" and the new will be used. /// It is very important that the type that you specify implements a public constructor that takes a parameter, this is used to initialize the class from an object allocated by Objective-C. /// Developers should not call this method if they have prototyped their type using a Storyboard. If they do so, they will overwrite the Storyboard-defined definition instantiation of the object's children. /// public void RegisterClassForCell (Type? cellType, NSString reuseIdentifier) { - ArgumentNullException.ThrowIfNull (cellType); - RegisterClassForCell (Class.GetHandle (cellType), reuseIdentifier); } @@ -143,7 +141,7 @@ public void RegisterNibForSupplementaryView (UINib? nib, UICollectionElementKind /// A non-empty string to be associated with the . /// /// The maintains a highly-efficient reuse queue for offscreen components. This requires that the be responsible for the lifecycle management of its component views. This method (and related methods such as ) provide the the knowledge of which types it needs to instantiate. - /// The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another nib, in which case the old nib will be "de-registered" and the new will be used. + /// The application developer may pass as the , in which case the will be "un-registered" and no longer instantiated. The application developer may pass in a previously associated with another nib, in which case the old nib will be "de-registered" and the new will be used. /// public void RegisterNibForSupplementaryView (UINib? nib, UICollectionElementKindSection section, NSString reuseIdentifier) {