The course is part of this learning path
This course explores the concepts of threading, async, and await in iOS and how you can employ them in your app builds.
- Understand how to implement threading (aka concurrency) in your iOS apps
- Learn about the concepts of async image and await and how to use them
This course is intended for anyone who wants to learn how to develop apps on iOS.
To get the most out of this course, some basic knowledge of iOS development would be beneficial. We recommend that you take this course as part of the Developing Mobile Apps for iOS learning path.
Hi. Within this lecture, we're going to go ahead and write our View model. So, if you remember the MVVM structure that we have done in previous sections. We have used a View and a ViewModel and also a model. Right now, we have written our model and also a web service that we're going to use in the ViewModel. So, it's time to write our ViewModel. If you remember all those things are too separate or distinct the business logic from the UI logic. So, everything related to UI, User Interface, will be done in the MainView over here. However, downloading something or parsing the data is not related with the user. The user doesn't, you need to know about this, okay? So, what we're going to do? We're going to create a new swift file in the ViewModel and we will write our ViewModel inside of this file. So, you can call this anything like crypto ViewModel, okay? And here you go. Right now we have our file over there. So, what I'm going to do? I'm going to create like a crypto ViewModel in which we will actually implement the model that we have created. And then later on, we're going to create another ViewModel for the list of that particular model. So, let me just do it and show you what I mean. First I'm going to say struck CryptoViewModel, okay? And this will be only for to implement the model that we have created in this file. So, what I'm going to do. I'm going to bring in the crypto model that we have created. So, this will be Cryptocurrency and then I'm going to write every parameter, every property of this model one by one and just assign the values to it. So, if you remember how we did that, so we have the ID, we have the currency, and we have the price. Now, we need to make sure that we assign the values to those parameters inside of this struct as well. So, I'm going to save our ID UUID optional. And of course, this is very easy to just implement, very easy to understand how it's done. It's crypto.ID. And it's the same for the currency and the price as well. Crypto.currency and you can write var price and this will be a string as well. And crypto.price. Here you go. And by the way, since our price is string, I'm just writing this as a string. If this had been like a double or something, then I would have to write this as a double or another particular situation in that case. So, anyway right now, I'm going to create another class over here, not a struct but a class. I'm going to explain why I'm doing that, don't worry. And I'm going to call this crypto list ViewModel. So, what we're going to do? The main idea of the ViewModel will be executed in this class, okay? And this class will be an observable object, Okay? So, as you can see observable object comes from the combined framework and this will enable us to publish some variables and observe them in our View. So, maybe you don't know what it is, I'm going to explain, don't worry about it. Right now, know that we are creating this as a class because it needs to implement this observable object. It needs to inherit from this observable object and we cannot do that in structs, but we can do that in classes. That's why I'm creating this as a class. Now under this class, we're going to create a list and just store the crypto ViewModels in that list. So, let me just write the web service over here, create an object out of the web service. And let me just write a function called download Cryptos and call the download function that we have created in the web service class. So, as you can see, it asks for an URL. So, again you can just give the URL or ask for it and give it later on. I'm just going to give it later on. And for the completion block, I'm going to hit 'Enter'. And as you can see once we did do that, it gives us a result back and not the type result, but the variable result over here, you can call it anything you want. And now, if you look at this result, as you can see, we either get a Cryptocurrency optional or an error, a downloader error over here. So, what we can do? We can do an if else or switch case. So, I'm going to switch the result. So, we have two cases over here, first of which is success. And then, failure. As you can see, if I say case.failure, it gives me an error. I can say let error and print down that error. So, this error will come from the enum that I have created. For example, it can say bad URL or no data and in the case of success, it will give us the Cryptocurrency. So, I'm going to say let's cryptos. And in that case of course, I'm not going to print the cryptos over here. Right now, I have the list, even though it's optional, I can just unwrap it. I can say if let cryptos = cryptos. And here you go, now I have the cryptos. Right? So, I have the Cryptocurrency list right now. So, what I want to do at this point is to store this in kind of a variable, like a list of cryptocurrencies and then I'm just going to send it to the MainView, right? That's all what we're going to do. So, that's why we have created this function. But how do we pass this to the view. So, let me just first create a crypto list array over here. So, it will be an array containing the crypto ViewModel, okay? So, this is the crypto ViewModel and it actually consists of crypto ViewModels. Now, if I want to put these cryptos into that crypto list, will it work? Let me just try this. So, I'm going to say self.cryptoList = cryptos. So, will it work? It won't work because they are not the same type, right? One of them is crypto ViewModel and other type is Cryptocurrency itself. However, as you can see, we are just implementing the crypto currency model inside of this ViewModel. So, we can easily convert them. Just we have to know how to do that, right? They have all the same parameters. So, all we got to learn about this thing is the map. Map is a function that converts one type to another if they are compatible with each other. So, map is not only for swift, you can find it in any language like Java, Kotlin, Python, Java script, anything you might imagine. And over here, what we're going to do, we're going to say cryptos.map. It will transform the cryptos into crypto ViewModels. All you got to do is just say CryptoViewModel.init. Of course, if it wasn't compatible, then it wouldn't have worked. But we know that they are compatible with each other, right? So, crypto ViewModel actually implements the crypto. It has all the same parameters and the same structure. So, we can easily do that. And right now, the main logic, the main idea over here comes into play. Why did we do this as an observable object? Why did we inherit from this? The reason we want to make this variable, the crypto list variable accessible from the main View and more importantly accessible in a way than when the list changes. When the list changes the main updates itself. For example, we did that with at state, inside of the main View before in the swift UI section. However, this crypto list isn't even there, right? So, that's why we have created this as an observable object. Observable means we're going to make this observable by saying that it's published. Okay, use that wrapper to publish this like Youtube, you publish something over here and in another location you can subscribe to it and just see the changes. In order to do that, you need to make this observable object and it's published. Keep in mind that this is a very, very important concept. Once we do that, we can come over here to the main view and we can create a variable that will observe, that will observe what's happening in the crypto list. So, whenever we update the crypto list, like maybe we download data from scratch again, maybe we just do it every one minute or something like that. Whenever this crypto list changes, main View will update itself automatically and we won't have to deal with it again. This is a great feature of combined framework. So, this is observable pattern and we're going to use this a lot. And one implication that we might think of is that we're going to have to do DispatchQueue.main.async over here. Why? Because this crypto list now will update the main UI, right? So, we are downloading the data in the background and we are updating in the main thread and that's exactly what we want. And by the way, in some cases you may need to import the combined framework over here. So, we needed that before but they have just taken care of this. So, right now I believe we are good to go without importing it. But if you get any errors, make sure you import the combined framework. Now, what we're going to do? We're going to just observe what's going on inside of the ViewModel in the View and we're going to do that in the next lecture.
Atil is an instructor at Bogazici University, where he graduated back in 2010. He is also co-founder of Academy Club, which provides training, and Pera Games, which operates in the mobile gaming industry.