That’s not an optional!

Announcement

I vividly remember being so excited at WWDC when Image Playground was announced. It was a perfect fit for Please Don’t Rain and I couldn’t wait to get my hands on it.

I did encounter one issue that I wasn’t sure how to handle.

Usage

I started off by using a basic implementation of Image Playground’s sheet.

.imagePlaygroundSheet(
    isPresented: Binding<Bool>,
    concept: String,
    onCompletion: (URL) -> Void
)

In the completion block you’ll get back a URL that points to the generated image in a temporary location.

In the future it would be great for accessibility reasons if we also got back some information about the generated image. Inside of Image Playground the user can decide not to use the concept that was passed in and also add additional concepts. It would be great if a return value could give us some information about the created Image when possible. What I ended up doing was giving the user the option to enter a VoiceOver description of the Image since I have no way of knowing what the generated image looks like.

There’s also a variation of imagePlaygroundSheet where you can pass in an Image? (optional) for a source Image. Image Playground will use that source Image as a factor in what final Image it ends up creating.

.imagePlaygroundSheet(
    isPresented: Binding<Bool>,
    concept: String,
    sourceImage: Image?,
    onCompletion: (URL) -> Void
)

Here’s what the documentation says about NOT providing a source Image.

If you don’t provide a starting image, the system creates the new image using only the contents of the concepts parameter.

Adding More Functionality

After I had my base UI for creating weather images working I wanted to add more functionality. I was thinking of the scenario where the user launched Image Playground and then exited it but then decided they wanted to change the image a little more before they were happy with it. At that point I have a URL that points to their first creation in a temporary location. So I’ll want to pass that to imagePlaygroundSheet as a starting point for creating another image.

In looking at my options I did see that imagePlaygroundSheet had a variation where you could pass in a source Image URL. So my thinking was that I would pass in a nil for the URL when the user is creating an image from scratch, and then when they want to further refine that image before finalizing it I’ll pass in the URL to the tmp location as the source Image URL.

.imagePlaygroundSheet(
    isPresented: Binding<Bool>,
    concept: String,
    sourceImageURL: URL,
    onCompletion: (URL) -> Void
)

But then I noticed something. The source Image URL is NOT an optional. How do I deal with that?

I could of course try to have two different instances of imagePlaygroundSheet in my View but I wanted to try and avoid dealing with two different State variables for deciding whether or not to present an Image Playground sheet. If there’s a way to launch a single sheet if you do/don’t have a source Image it felt like there had to be a way to do it if you did/didn’t have a source Image URL.

So what do I pass in for the source URL for the first pass when the user is creating an Image from scratch and there is no source? A friendly AI told me to use this for the URL:

URL(string: "")!

That ended up causing a crash when it gets forced unwrapped. 🙄

After some more research I ended up trying this URL:

URL(string: "about:blank")! 

That worked! So when the user creates the initial image (that shouldn’t have a source image) I pass in that as the URL and if the user wants to iterate further then I pass in the URL to the temporary file location that holds the previous creation.

Does this work? Yes. Does this feel clunky and do I suspect there was a better way to handle this? Also yes.

I posted on the Apple developer forums about this but didn’t get any responses. My hope is that this will help someone having the same question that I did.

Contact

If this post was helpful to you I’d love to hear about it! I’m @chriswu.com on Bluesky, @MuseumShuffle@mastodon.social on Mastodon, and my email is museumshuffle at gmail dot com.

iOS Dev Happy Hour

Also, whether you’re interested in becoming an iOS developer or you’re a veteran of the App Store, iOS Dev Happy Hour is a great place to meet and connect with other iOS Developers. Join us at our monthly event!

Social Media:

iOS Dev Happy Hour banner