Transcript for:
Exploring iOS 16 Photos Picker in Swift UI

iOS 16 introduced a native photos picker in Swift UI and in this video I'm going to show you how to select a single image multiple image and filter out certain file types like screenshots because we all know our camera rules have gotten very out of hand over the years today's video is sponsored by Squarespace let's start by selecting a single image and I have some basic UI set up I'm simulating like a profile screen where you want to change your profile picture so that's what you see here with the hstack of the image which is our Avatar image that has the placeholder that you see there in the text for the name and profession iOS Developer in a vstack to the right of the image very simple Swift UI setup the first thing we have to do before we can use the photos picker is import photos UI so we'll do that under Swift UI photos UI so now we're going to have access to the photos picker now the way photos picker works is it's like a selector so we wrap it around something that we tap on to pull up the photos picker so in our example we want the user to be able to tap the profile image and that pulls up the Picker so we're going to wrap this image here in our photo photos picker and you'll see what I mean when I write this out so above our image here we'll do photos picker now look at all the auto completes here so title selection matching uh you know there's a lot of permutations here I'm not going to dive into every single option but we'll cover the main ones and for what we want we want the one with the label because the label is our custom button that we're going to use and our button I put that like in air quotes our button is going to be this image so I'm going to hit return in the label to give me the closure and bring our image up into where the label would be so again this can be anything this could be any type of view text view an SF symbol you know whatever you want to tap on to bring up the photos picker that's what goes here in this label and the selection this is what we're going to pick from the photos picker needs to be bound to a photos picker item so let me type that out and I'll explain to you what a photos picker item is so say State private VAR photos picker item and that is of type photos picker item and that's going to be optional because we only have this once we select it so now let me type out my binding two photos picker item now the way photos picker works is it gives you this photos picker item which to put it simple it's kind of like data it's not the fully rendered image or video or whatever you're selecting and that's just for like efficiency and performance reasons so what we have to do is we're going to get back a photos picker item and then we have to convert that data into an actual UI image in our case so that we can display it in the UI now before we get to that conversion let's talk about the parameter matching and this is a pH picker filter so we can just do images saying hey just give me images leave everything or we can do dot you know videos whatever file type you're looking for in your app you can specify it here but you can have some flexibility with this filter you can do any of and then you pass in an array you see any uh images okay the preview crashes when I do this filter so let's get rid to the preview for now any of the images comma dot you know slow-mo videos let me just do the dot so you can see all the different types images burst cinematic photos live photos screen recording screenshots right so all the types of you know things that are in your camera roll you can create a filter to give you specifically what you're looking for so you can do any of or you can do not right you can specify the negative so I could do dot not and then the filter I'll say just not screenshots right we just give me anything but all those pesky screenshots in our camera roll so we're going to keep it simple with just images but I wanted to Showcase how you can you know build a filter for whatever your app is specifically looking for all right so let me bring back my preview so we can see this in action again the preview was crashing as I was messing with my filter here but now that we have our photos picker item again we need to convert that data into the actual UI image that we're going to use to populate our UI here right you see I'm creating an image from a UI image so down here uh we do a modifier on the vstack we'll do it under the padding here do an onchange on change of and then the onchange we want to track here is the photos picker item so whenever this changes we're going to run this code and then we don't need old value new value so we can just do the underscores there we'll bring this up okay so whenever photos pi picker item change what do we want to do again we want to convert the data into a UI image and then set that UI image equal to our Avatar image which will then update our UI so we only want to run this code if we've actually selected a photos picker item so let's make sure that's not nil so we'll say if let photos picker item and then if we have a photos picker item we're going to say let data equal and I'm actually going to put this on the next line because it does get a little long and my code is super blown up big for the video we're going to say try await photos picker item so this is what I just unwrapped right here and a photos picker item has a load transferable where we just pass in the type so load transferable attempts to load an instance of the type you specify from the item provider so the type we're going to specify is going to be data. self because again the photos picker item is the data and that's what we are setting here on line 43 the data so again to review that code if photos picker item is not nil it's not going to be nil when we select it right it's n by default we select it it's no longer nil cool run this code let's make sure we have the photos picker item let's get the data from that photos picker item and know this error is telling me that I'm trying to use asyn we and I'm not in a task so let's wrap this in a task here that auto indents nicely Okay cool so I have a photos picker item I've got the data from that photos picker item so now I want to create an image from that data so say if let image equals UI image from data and the data I want to pass in is the data we just got up here on line 44 and the reason we're doing IFL is because this returns an optional because you may not be able to create an image or UI image from that data and if we do have a good image we will set Avatar image equal to image and to recap that Avatar image is what we have up here which is what we're showing in our UI Here Right image you from UI image of an avatar image saying image a lot so what's going to happen here when we tap on our Avatar it's going to pull up the photos picker item I'm only going to show images in there we're going to select it once we select it that sets the photos picker item to that photos picker item we selected which which will trigger the on change of and then it's going to trigger you know we're going to unwrap the optional we're going to create data from that photos picker item and then we're going to create a UI image from that data and we're going to set our Avatar image to that so that's the whole process one thing we want to do when we're done here is to set photos picker item equal to nil and that is so when we pull up the photos picker the next time our old selection doesn't persist okay so in our preview let's now tap on our Avatar brings up the photo picker and I can select one there you go select the waterfall it did what I just said it did and now we have our profile image I tap it again let's go with the red bushes there it is so tap it again cool so like I said whatever you want to tap on to pull up the photos picker that's where you wrap the photos picker in now that was an example of just selecting one image let's adjust our code to be able to handle multiple images now what sets this in motion if you will is what we're bound to so right now we're bound to a photos picker item which is one thing but if we change our photos picker item to an array so photos picker items it's no longer an option op we say this is an array of photos picker item and it's just an empty array so now we got a bunch of errors but we're going to fix those so again instead of one Avatar image we're going to have an array of images which is again an array of UI image so the main thing you want to do here is just change all your single stuff to an array and an array does not work with a curly brace there don't know what I was doing so now our photos picker is no longer bound to the photos picker item it's bound to the photos picker items which is our array that we just created so again to put this simply just change it to an array and then adjust your code that's what we're going to do here so so now I no longer want my photos picker to be wrapped around the UI image in our vstack let's just create another photos picker and I'll go through some other of these parameters here so we'll just do title selection give us Mac selection and give us Behavior as well so the title key will'll just say select photo so this is an example when you don't have like your own custom button or image and this is just going to be words on there I'm going to tap the words just like an old school button the selection again is bound to photos picker items Mac selection so maybe I have a restriction in my UI I don't want them to be able to select a thousand photos right so we'll do Max selection 5 this is optional you don't have to have that and then selection Behavior we'll say ordered so this will put it you know whatever order they selected and they'll be numbered when we select them you'll see that for the user so now I have my photos picker and I don't have to wrap it in a button or anything like that because it's going to be wrapped around the this text so this is a very simple version of it but now let me delete this photos picker because we're no longer using that and then get rid of the vstack of the text cuz we're just going to have the horizontal scroll view of the images so let me do that here let me do scroll view. horizontal and put the H stack of my images in there all right and then get rid of the spacer on the H stack I want to do four each and then we'll do zero. do less than images. count and the ID here is do self and I in and then we will do for each of my images in my images array we will have our image except we won't be on the Avatar image and have a default image there we will be on images at indexi I know I just whizzed that real quick I will explain it here in a second I'm trying to clear out airs so before we get to our unchange because that's stuff I actually want to pay attention to basically for the UI we have a photos picker button at the top of our vstack there just going to be text and then for each of the array of images because that's what we're creating when we select multiple items we're going to do a for each through that and then create an image you know from each of those index that basically has the same style that you see over there now okay so now let's clean up these there so we can see this in action now our onchange changes minimally right so instead of onchange of the single photos picker item just when our array changes and then in the task our photos picker item is no longer nil because we made it this empty array of photos picker items so we no longer need this first part of the IFL so we can say if let just go right into the data but we don't have one photos picker item right so we want to do this in a for Loop so four item in photos picker items right in our array there then we will say if let data you know we'll try to unwrap the item which again is just each individual item the same code that we just did and then instead of setting our Avatar image equal to the image that we created from that data we will do images. append image so we're iterating through our array of photos picker items we're converting the data into an image and then we're appending it to our array of images which again is what we're using to create our horizontal scroll view here we're iterating through that array of images and creating an image from each one and then instead of photos picker item equal nil we'll say photos picker items. remove all and again this just makes it so when we select our photos picker again our previous selections like aren't there anymore oh and I didn't initialize my images as an empty array so my initializer was expecting me to initialize it with something but I want to give it a default value of an empty array here on the images so again let's refresh my preview to see the new UI that we set up okay see this the select photos button that's what's going on here on the photos picker and we don't have anything in our horizontal hstack because there's no images in our images array yet we got to select those so so select the photos brings up the photos picker and you can see when I tap it 1 2 3 you can see it's in the order that I tapped it in and I have Max count five so I can't select a six one that's what this Max selection count does and the ordered selection behavior is what causes you know those numbers to pop up and it to appear in order so hit add now you see our horizontal scroll view again it doesn't look doesn't look great you can you know style the UI however you like but we got multiple images in the order we selected them in a scroll view but the key here in your app now you have an array of images you allow the user to select multiple images and you can style the UI however you like you want to put it into a grid like this or maybe into a scroll view like we did and then spice it up a little bit like we did in my scroll view video which I'll link in the description or if you want to put it into a card style UI you can style it however you like to make that beautiful UI and if you're building apps with beautiful user interfaces you're going to want a place to show them off and that brings me to today's sponsor Squarespace Squarespace is an all in one platform to help you get that iOS Developer portfolio blog or personal website up and running very quickly now I know we're all developers with the skills and the desire to build the web page ourself but I would argue There's an opportunity cost to your time if you're an iOS Developer trying to build a great product a great app maybe spending a lot of time learning the ins and outs of web development responsive design isn't the best way to spend your time that's why I recommend Squarespace to build that personal website the blog your portfolio or maybe a landing page for your app they have all kinds of beautiful themes and templates to get you started to handle all the analytics and the SEO for you again it just saves you so much time time so you can get back to doing what you want to do and that is building iOS apps so when you're ready to get started go to squarespace.com to start your free trial and when you're ready to launch go to squarespace.com Shan Allen to get 10% off your first purchase of a website or domain