Как реализовать компонент галереи с возможностью отображать или скрывать кнопку фотоаппарата в iOS?
Что проверяют
Умеете ли вы сделать компонент настраиваемым снаружи и не сломать его изнутри при переключении режима. На деле вопрос шире кнопки: доступ к фото и камере, разрешения, сетка миниатюр. Следом спрашивают, что делать, если камеры нет или пользователь запретил доступ.
Как отвечать
Видимость кнопки задаётся конфигурацией при создании: GalleryConfiguration(showsCameraButton: Bool) в инициализаторе контроллера или параметр у SwiftUI-вью. Тогда один компонент живёт на разных экранах без наследования.
Дальше важно, где находится кнопка:
- поверх сетки: отдельная кнопка в панели или в углу. В
UIStackViewскрытый элемент схлопывается сам, в обычных констрейнтах место под ним остаётся; - ячейкой в сетке: частый вариант, камера первой плиткой. Модель элементов описывается как
enum Item: Hashable { case camera; case asset(String) }, аUICollectionViewDiffableDataSourceполучает снапшот с камерой или без. Поправки индексов «плюс один» по всему коду не нужны; - SwiftUI:
LazyVGridи условиеif configuration.showsCameraButton.
Кнопку показывайте, только если режим включён и камера есть: UIImagePickerController.isSourceTypeAvailable(.camera), на симуляторе её нет. Разрешение проверяется через AVCaptureDevice.authorizationStatus(for: .video), при отказе кнопка ведёт в настройки приложения. В Info.plist обязательны NSCameraUsageDescription и NSPhotoLibraryUsageDescription, без них приложение падает при первом обращении.
Фото берутся через PhotoKit: PHAsset.fetchAssets и PHCachingImageManager для миниатюр нужного размера. С iOS 14 есть ограниченный доступ .limited, это отдельное состояние, а не отказ. В SwiftUI камеру оборачивают в UIViewControllerRepresentable.
Где спотыкаются
Пересчитывают индексы с поправкой на камеру вручную. После скрытия кнопки по тапу выбирается соседнее фото, и такой баг долго не замечают.
Забывают строки в Info.plist или не проверяют наличие камеры, и приложение падает на первом тапе.
Грузят в ячейки полноразмерные изображения. На библиотеке в десятки тысяч фото память заканчивается за несколько прокруток.