Skip to content

[image_picker_ios] Convert the iOS example app and UI tests to Swift - #13570

Merged
auto-submit[bot] merged 4 commits into
flutter:mainfrom
victogomez-cs:pr6/image-picker-ios-swift-example
Nov 10, 2026
Merged

auto-submit[bot] merged 4 commits into
flutter:mainfrom
victogomez-cs:pr6/image-picker-ios-swift-example

Conversation

@victogomez-cs

Copy link
Copy Markdown
Contributor

Converts the image_picker_ios iOS example app and UI tests from Objective-C to Swift:

  • AppDelegate is now Swift. @main replaces main.m, and AppDelegate.h becomes Runner-Bridging-Header.h.
  • ImagePickerFromGalleryUITests and ImagePickerFromLimitedGalleryUITests are now Swift.
  • The example still seeds the photo library from jpgImageTall.jpg, and logs when that fixture is missing.
  • Drops the @available(iOS 14, *) checks in the UI tests. The example already requires iOS 15.

The plugin implementation is unchanged from #13493.

Bumps image_picker_ios to 0.8.13+16.

Follow-up to the Obj-C → Swift migration, following #13493. Part of flutter/flutter#119107

Pre-Review Checklist

If you need help, consider asking for advice on the #hackers-new channel on Discord.

Note: The Flutter team is currently trialing the use of Gemini Code Assist for GitHub. Comments from the gemini-code-assist bot should not be taken as authoritative feedback from the Flutter team. If you find its comments useful you can update your code accordingly, but if you are unsure or disagree with the feedback, please feel free to wait for a Flutter team member's review for guidance on which automated comments should be addressed.

Footnotes

  1. Regular contributors who have demonstrated familiarity with the repository guidelines only need to comment if the PR is not auto-exempted by repo tooling. ↩ ↩2

…to library seeding and increase deployment target to iOS 15. Refactor tests to remove deprecated checks and streamline permission handling.

@gemini-code-assist gemini-code-assist Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Code Review

This pull request converts the iOS example application and its UI tests from Objective-C to Swift, including updates to the Xcode project file, bridging header, and application delegate. Feedback suggests refactoring the photo library seeding logic in AppDelegate.swift to verify authorization status and perform asset creation asynchronously rather than using a synchronous, blocking call.

Comment on lines +24 to +35
if !photoAdded {
PHPhotoLibrary.requestAuthorization(for: .addOnly) { _ in
do {
try PHPhotoLibrary.shared().performChangesAndWait {
PHAssetChangeRequest.creationRequestForAssetFromImage(atFileURL: jpgImageTall)
}
UserDefaults.standard.set(true, forKey: photoAddedKey)
} catch {
os_log(.error, "%{public}@", error.localizedDescription)
}
}
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

medium

Instead of ignoring the authorization status and using the synchronous performChangesAndWait method, it is more robust and efficient to check if the authorization status is .authorized and perform the changes asynchronously using performChanges(_:completionHandler:). This avoids blocking the background thread unnecessarily and prevents attempting to perform changes if authorization was denied.

    if !photoAdded {
      PHPhotoLibrary.requestAuthorization(for: .addOnly) { status in
        guard status == .authorized else { return }
        PHPhotoLibrary.shared().performChanges {
          PHAssetChangeRequest.creationRequestForAssetFromImage(atFileURL: jpgImageTall)
        } completionHandler: { success, error in
          if success {
            UserDefaults.standard.set(true, forKey: photoAddedKey)
          } else if let error = error {
            os_log(.error, "%{public}@", error.localizedDescription)
          }
        }
      }
    }

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Keeping this as a port of the Objective-C example. That code also ignored the authorization status and used performChangesAndWait, so the fixture is saved before the authorization handler returns. requestAuthorization(for:) already calls its handler off the main queue, so launch is not blocked. An async performChanges would leave a gap before the photo exists, and the gallery UI tests need that photo. A denied save is already logged

@victogomez-cs victogomez-cs added the triage-ios Should be looked at in iOS triage label Nov 5, 2026
@jmagman
jmagman requested a review from hellohuanlin November 5, 2026 18:02
repository: https://github.com/flutter/packages/tree/main/packages/image_picker/image_picker_ios
issue_tracker: https://github.com/flutter/flutter/issues?q=is%3Aissue+is%3Aopen+label%3A%22p%3A+image_picker%22
version: 0.8.13+15
version: 0.8.13+16

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Drive-by comment: this PR doesn't need a version or changelog change, as none of the changes here are relevant to package clients.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Done!

) -> Bool {
// Seed the photo library with at least one image for tests to operate on.
let photoAddedKey = "PhotoAdded"
let photoAdded = UserDefaults.standard.bool(forKey: photoAddedKey)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

nit: these 2 can be moved after the guard statement

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Done!

@hellohuanlin hellohuanlin left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

just 1 nit

…e app. Moved UserDefaults checks for photo seeding to improve clarity and maintainability.
@victogomez-cs victogomez-cs added the autosubmit Merge PR when tree becomes green via auto submit App label Nov 10, 2026
@auto-submit
auto-submit Bot merged commit 75094a6 into flutter:main Nov 10, 2026
12 checks passed
@victogomez-cs
victogomez-cs deleted the pr6/image-picker-ios-swift-example branch November 10, 2026 21:56
opensource-fork-sync Bot pushed a commit to cla7aye15I4nd/opensource-flutter__flutter that referenced this pull request Nov 11, 2026
…er#196381)

flutter/packages@08faf64...653628e

2026-11-11 [email protected] Roll Flutter from
fffd8c2 to b98afb5 (31 revisions) (flutter/packages#13623)
2026-11-11 [email protected] [material_ui] Document how to
programmatically clear DropdownMenu selection (flutter/packages#13266)
2026-11-11 [email protected] [pigeon] Fix basePath resolution when
paths share a string prefix with basePath (flutter/packages#13342)
2026-11-11 [email protected]
[cupertino_ui] Fix CupertinoSheetRoute throwing when a drag ends during
a pending relayout (flutter/packages#13316)
2026-11-11 [email protected] [shared_preferences] Updates Pigeon to
30.0.1 to support multi-engine registration and deregistration.
(flutter/packages#13617)
2026-11-11 [email protected]
[vector_graphics] Catch any throwable in useHtmlRenderObject() and cache
HTML fallback (flutter/packages#13545)
2026-11-11 [email protected] [cupertino_ui]
Include selectionHandleColor in NoDefaultCupertinoThemeData equality
(flutter/packages#13450)
2026-11-11 [email protected] [flutter_svg] Remove failed async loads
from Cache._pending (flutter/packages#13604)
2026-11-11 [email protected] [pigeon] Adds Native Interop FFI codec
serialization for NS types (flutter/packages#13616)
2026-11-10 [email protected] [pigeon] Support multi-engine Native
Interop registration and instance-aware unregistration
(flutter/packages#13576)
2026-11-10 [email protected] [image_picker_ios] Convert the
iOS example app and UI tests to Swift (flutter/packages#13570)
2026-11-10 [email protected]
[cupertino_ui] Localize CupertinoActionSheet semantics label
(flutter/packages#13377)
2026-11-10 [email protected] [camera_android]
Fix stopVideoRecording returning JPEG when takePicture runs during
recording (flutter/packages#13070)
2026-11-10 [email protected] [google_sign_in_android] Rename keep.xml
to google_sign_in_keep.xml (flutter/packages#13475)
2026-11-10 [email protected] [web_benchmarks] Fix benchmark stalling
when only repainting views that are dirty (flutter/packages#13089)
2026-11-10 [email protected] Roll Flutter from
d463821 to fffd8c2 (21 revisions) (flutter/packages#13614)

If this roll has caused a breakage, revert this CL and set the roller
to dry run mode using the controls here:
https://autoroll.skia.org/r/flutter-packages-flutter-autoroll
Please CC [email protected] on the revert to ensure that a
human
is aware of the problem.

To file a bug in Flutter:
https://github.com/flutter/flutter/issues/new/choose

To report a problem with the AutoRoller itself, please file a bug:
https://issues.skia.org/issues/new?component=1389291&template=1850622

Documentation for the AutoRoller is here:
https://skia.googlesource.com/buildbot/+doc/main/autoroll/README.md
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

autosubmit Merge PR when tree becomes green via auto submit App CICD Run CI/CD p: image_picker platform-ios triage-ios Should be looked at in iOS triage

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants