Basics of Swift optionals

Some time ago I’ve read Stack Overflow Developer Survey Results and it wasn’t a big surprise for me that Swift had the sixth place in “Most Loved” category beating such popular languages like JavaScript or C#. The main reason for that situation is that Swift is very easy to use and at the same time less error prone than some of the most popular languages. Imagine the scenario that you published brand new application and users don’t report any bugs – it just works great. After some time you decide to launch an update with minor changes like an update of the third-party library. Unfortunately this time something went terribly wrong and the application starts to crash. At first sight, it shouldn’t even happen but in logs, there is “NullPointerException” entry related to the updated library – some method had changed and as default, it returns null instead of empty String. Sounds familiar to you? 🙂 If yes, you probably already know how inconvenient error it can be. Hopefully Swift comes to the rescue!

Icons made by Good Ware from www.flaticon.com is licensed by CC 3.0 BY

 

In a nutshell Optional is like a box, it can contain a value or it is empty. Under the hood it’s an enum with two cases:

You may wonder why we even need another type to wrap existing ones?  We could check in a runtime if the property is nil but many examples from other languages show that it’s a huge source of problems. Sometimes even experienced developer can miss such error not mentioning beginners. Fortunately, Swift prevents assigning nil value to type which isn’t Optional. It almost completely eradicates the problem of unexpected nil values, and make code less error-prone.

Declaration

Let’s consider a real-life example which will help you understand the concept of optional values. We want to create a simple gallery of photos, first of all, we need to know the number of photos to display. Depending on the source of this photos type of “numberOfPhotos” property may be different.

  1. If photos are the static content in application we don’t need optional, because at the moment of writing the code we already know the number of photos.
  2. What if photos are stored on the remote server? We could use some default value like “0” and refresh it after server response, but there is a catch. Sometimes there is no value which could be assigned as a default (for example integer in a calculator app). It can be negative, positive or zero so default value could introduce some nasty errors. Optional is handy because it tells that numberOfPhotos is an integer but could be not available at the moment (contains nil).
  3. The example above is a valid declaration of Optional integer, but it’s very unpopular. There is a lot simpler way to achieve the same result – just add a question mark after the type and that’s it! 🙂
  4. The last example shows unconditional unwrapped optional. To put it simply, it’s optional which is already unwrapped at the moment of accessing its value. Use this type of optionals as a last resort, because it will crash the application if the instance of optional contains nil. Personally, I try not to use force unwrapped optionals, in larger projects you don’t have a guarantee that changes made by someone else won’t affect your code and make optional nil.

Safe unwrapping

Safe unwrapping is the simple way of accessing a value of optional without the risk of error. It’s extremely easy task and after a short period of time, it will become something natural and almost unnoticeable during writing the code. There are 3 methods of safe unwrapping which I want to show you:

  1. If numberOfPhotos is integer this code will execute “if block” and assign value wrapped by numberOfPhotos to constant unwrappedNumberOfPhotos in the scope of this block. If numberOfPhotos is nil, “else block” will be executed.
  2. Guard statement is reversed if let statement. Else block will be executed if numberOfPhotos is nil otherwise it will assign it’s value to unwrappedNumberOfPhotos in the whole scope below guard statement. Using guard statement often help to avoid many nested if blocks which makes code easier to read.
  3. As I’ve mentioned before Optional is an enum with two cases, so it can be handled by switch statement.

You can also use “while let” statement instead of “if let” but it’s so uncommon that I’ve decided to skip this method. Generally, I use a combination of first two methods depending on the scope in which I need unwrapped value.

Optional chaining

Optional chaining is a very useful feature that drastically reduces the amount of code if there is a complex structure. Instead of many nested „if” blocks, we can chain calls of optional and non-optional values like I’ve done it above  „ server.user?.storage?.numberOfPhotos”. Such call will return an integer which represents the number of photos or nil if there is any nil value in the chain of calls. In OOP (Object Oriented Programming) it’s very common to access properties of nested structures so I use that feature a lot. 🙂

Force unwrapping

As I’ve mentioned earlier when you are 100% sure that instance of Optional is not nil you can use an exclamation mark in order to force unwrap optional. It’s very quick method, but laziness can lead to runtime errors. In many teams, such code won’t be accepted in Code Review so try not to use force unwrapping when it’s not necessary.

Nil-Coalescing Operator

Sometimes you can face the situation in which you must provide some default value. Instead of safe unwrapping which involves a lot of additional code, you can use nil coalescing ternary operator „??”.  It works very simply – if Optional is nil, it returns the default value instead. In our case if “server.user?.storage?.numberOfPhotos” is nil we assume that we have 0 photos available.

Summary

I hope that I’ve managed to show you how simple and useful are optional values. This concept isn’t new and other languages like Kotlin, Java etc. also have it. Swift stands out, because none of them managed to make optionals so simple, intuitive and well integrated like Swift does. There are many different ways to achieve exact same results using optionals so I have one advice. Don’t take my word which solution is the best, but check on your own, which one of them suits your needs the most. You will be shocked how powerful tool you’ve just discovered. 🙂

First iOS App – ECTS Calc

About month ago I’ve made a promise to write next post in April. To fulfill this promise I will show you how easily you can create your own iOS application.
Every great tutorial starts with hello world example so I’ve decided to start this series with a simple application for the beginners. My purpose is to show you how quick and fun iOS development can be. In future posts i will dive into details, good practices etc. , so be patient and treat this one as a warm-up. 🙂

Prerequisites

In order to start creating your first app you’ll need a certain set of tools:

  • Computer with macOS system installed (unfortunately iOS is a very closed platform and Windows OS users won’t be able to build iOS apps)
  • Apple Developer account – you can create it here. If you’re not going to publish applications in AppStore, a free membership will be sufficient for you.
  • Xcode 9.3 IDE (or higher) – you can download it from here

ECTS Calc

As an example of a simple iOS application, I will create a calculator for ECTS credits. For all of you who aren’t familiar with this acronym, ECTS stands for “European Credit Transfer and Accumulation System“. It may sound complicated but in higher education system it requires from every student across EU to collect 60 ECTS points per year. It becomes really relevant for students when they cannot collect them and they must pay money for taking again courses which they couldn’t pass. At the Lodz University of Technology, it’s on average 55 PLN per point. I wish that none of you will need this calculator but real life shows that it can be very useful tool. 🙂

1. Create new Xcode project

2. Pick Single View App

3. Provide application info

In this step we must provide basic information like:

  • Project name
  • Team – Apple Developer team which in free membership is Personal Team
  • Organization Name
  • Organization identifier which usually is reversed domain like in Java projects.
  • Language – In my posts I will only cover Swift language.
  • Core data – SQLite data persistence
  • Include UI/Unit Tests – when checked, it automatically creates unit tests targets.

4. Choose project directory

After the wizard is finished we have 6 files in our project directory:

  • AppDelegate.swfit – In this file we can manage application lifecycle events.
  • ViewController.swift – View controller class which will hold all application logic. It’s worth to mention that in production apps it is considered as a bad practice but it’s good for educational purposes.
  • Main.storyobard – User Interface builder is a graphical tool which enables us to create quickly and easily even more complicated views. It is also possible to create all views in the code but is less common than using storyboards.
  • Assets.xcassets – Assets catalog which holds all of the graphical assets like images.
  • LaunchScreen.storyboard – In this file we create splash screen which is shown at the startup before the application is completely loaded.
  • Info.plist – configuration file which defines application version, name etc.

5. Create User Interface

When you click on Main.storyboard file, interface builder shows up. It’s very complex tool, but basic components which you must be aware of are:

  1. View hierarchy window which helps to understand how views are organized.
  2. Storyboard editor which enables you to create user interfaces using drag and drop.
  3. View configuration that shows all possible configuration options for selected UIView.
  4. Object library with all available UI components. If you want to use any of them, just drag and drop selected item on storyboard.

1. Add image asset

On the first (and only) screen of application I will use an image as a header so before that, I need to add this image to assets. To achieve this I only need to drag my image from Finder window to Assets.xcassets catalog. From now I can use that image across the whole project just by referencing it by its name “ects_logo”.

2. Change background color

We must to go back to Main.storyboard file and then click on View Controller window which is only visible UI component so far. On the right side of screen background, the color picker will show up. I will change this color from white to dark red.

3. Add UIImageView to storyboard

After you drop imageView on the storyboard, click it once to show the context menu. Type in “ects_logo” which is a name of our asset in the “Image” text field. Under this text field, there is also “Content Mode” combo box in which we must change the current mode from default “Scale To Fill” to “Aspect Fit”. This change will guarantee us that image will keep its aspect ratio.

4. Add UITextField to storyboard

Similar to UIImageView we drag and drop UITextField on the storyboard and then set “Placeholder” field to provide a hint about what type of data user should enter. The second parameter which I’ve changed is a keyboard type, it should be “Number Pad” to ensure numeric input. It won’t prevent the user from typing all incorrect values but in this post, I will skip this topic. Just keep it in your mind that in production apps It won’t be sufficient solution.

5. Add UIButton to storyboard

Last UI component is UIButton, which will trigger calculating amount of money to pay for missing points. In this case, I’ve changed default title from “Button” to “Calculate”, Text color to dark gray and background color to white.

6. Setting up constraints

One of the most powerful tools for creating User Interface for iOS platform is the auto layout. Instead of calculating dimensions of view for every possible device we just set necessary constraints.

The first step for our layout will be to close all of the current components in a container called UIStackView. It will help in distributing evenly all of the elements. In order to achieve this, we must press command + shift and select all of the components. When all elements are selected press stack button on the bottom of the screen.

After this action, all elements should be closed in stack view container. It’s very easy to maintain even many elements. For example, if we want to set some space between elements, we don’t have to set padding for each element. There is “Spacing” option which provides us such functionality. Set this value to 40 to distribute those elements.

Click on UIStackView and click Constraints button which is situated on the bottom of the screen nearby “Stack” button. Select side constraints and set them to 70 points, then press “Add 2 Constraints”.

Click once more on stack view and click “Alignment Constraint” button on the bottom of the screen. Pick “Vertically in Container” and press “Add 1 Constraint button”.

If you managed to finish all of these steps, you just created your first iOS User Interface! 🙂

7. Connect IBOutlets

Comparing to Android development referencing UI elements in code is extremely easy.
Just click split view button, which will show storyboard UIViewController on the left side and UIViewController swift class on another.

Next step is to click UITextField in hierarchy view and press Control button. This will make possible to drag it on Swift class file. When pop-up window will show up, choose “Connection” and pick Outlet. You must fill “Name” field because this will be also the name of this element in code.

Next step is to connect button click action. It is very similar to connecting text field but we must choose “Action” instead of “Outlet” connection type. There is also a difference in the name field because it will be the name of the method instead of the variable. This method will be invoked every time user press calculate button.

6. Implement logic of calculator

As you can see whole logic is pretty simple and it’s no longer than 50 lines of code.
I will guide you through this code line by line.

  • Line 13: IBOutlet provides us the reference to UITextField component.
  • Line 14: Immutable variable which stores what is a cost of one missing ECTS point.
  • Line 20: calculatePressed method which runs every time user taps calculate button
  • Line 21: In this line “missingPointsText” variable stores text from UITextField. Because text property can be nil there is “??” operator. In this case, operator sets empty String value if it found nil.
  • Line 23: “guard let” is also a way to safe unwrapping optional values. If Integer cannot be constructed from missingPointsText variable (it returns nil) else block is executed. It is a very clean solution for checking if variable crucial for our logic isn’t nil.
  • Line 28: costOfMissingPoints variable stores result of number of ECTS points and it’s cost multiplication.
  • Line 30: When calculated amount of money is greater than zero then we show user alert with this amount.
  • Line 31: You may be curious why there are brackets inside of the message.
    \(costOfMissingPoints) “. It is called String interpolation which is used to place value of given variable inside String.
  • Line 32: If the amount of money is negative it means that user typed in a negative number of ECTS points which is an invalid value.
  • Line 34: If else block is executed it means that student completed all required ECTS points and he doesn’t have to pay any money.
  • Line 39: This method shows an alert popup with ECTS calculator message.

Summary

I hope that the recipe for a simple iOS application which I presented helped some of you to dive into iOS development. I’ve realized that next topics shouldn’t be based so much on user interface operations like this one. Text and images aren’t so great medium for such type of content. Next time I will try to avoid it or record some video to help you out understand what is happening.

Complete ECTS Calc application is available on my GitHub repository.

As I’ve mentioned earlier I will be happy if you provide me any kind of feedback. It will help me improve next posts.

I’ll be back! 🙂

 

Let the adventure begin!

Credit: LUCASFILM /20TH CENTURY FOX

Hello everyone!

Personally, it is very important moment for me, because it took over a year to finally write down my first post. At daily basis I’m software developer, and I’m going to cover topics related to iOS development. If you think that this post will contain any technical topics you are wrong 🙂 . I had more than plenty of time to think about what and in which order I want to write about. I’ve decided that this post will be good opportunity to introduce myself to all of you – my potential future readers.

I am aware that there is a chance that no one will ever read this post, but publicity is not my main goal. I’ve started this blog because of two reasons:

First one is to improve my skills in writing articles. It was always one of my weaknesses so I hope that at the end of this year I will be able to say „I’ve managed to write down one article per month and my writing style is more approachable then it was when I wrote down my first post”.

The second one is way more demanding than the first one. My technical knowledge is fairly wide, but not well structured. I’ve come to the conclusion that there is no better solution for this problem then trying to explain my daily struggles in iOS development to another person. In my opinion, there is no better place for such experiment than the internet. I haven’t made my mind yet if I’m going to start series of post for beginners or more advanced developers. I will take into consideration every possible feedback and adapt my posts as dynamically as it is possible.

What is this all about?

Some of you may be wondering why I choose to start a blog if nobody knows that it even exists. The answer is very simple – lack of motivation. 🙂 Once you publish something on the internet it’s out forever. I’ve got one resolution:

I will write at least one post per month in the year 2018.

Now it is officially too late to back off. All of you saw this statement and I have the motivation to keep that promise. Probably most of you are my family and friends which I forced to read that post but maybe in the future, there will be someone from outside that group :D.

My background

My journey with programming started in 2012 when I’ve became student of Łódź University of Technology on Faculty of Electrical, Electronic, Computer and Control Engineering. To be honest, it wasn’t love from the first sight, because C and later C++ wasn’t easy to learn for me. I thought that electronics is an area which I should explore but everything had changed in the year 2014 when I’ve participated in the Java-based project at my faculty. It provided me chance to take part in trainee program in one of leading IT companies in my city. My task was to explore capabilities of Android platform and it was something that started my passion which lasts to this day. I thought that there is no better mobile platform till I encountered iOS. For a long period of time I was laughing at iPhone users. I was convinced that everyone who buys Apple products is doing this just because of trend and there is no explanation why they pay so much money for this devices. A few years later, exactly in March 2016, I was asked to write an iOS version of the app which I was already developing for Android platform. At the very beginning I was very upset that I received this task, but now I’m grateful for this opportunity. I can’t imagine to create mobile apps for platform which isn’t iOS in near future. Why it is so good? I will try to explain it’s phenomenon in next post.

I hope that reading that text wasn’t a painful experience, I promise that I will improve!

PS. I would be grateful for any feedback, don’t hesitate to write down a comment or send me an e-mail. I’m here to learn 🙂