Bond Tutorial: Bindings in Swift

Bond is a simple, powerful, type-safe binding framework for Swift. Learn how to use it with the popular MVVM architectural pattern in this Bond tutorial. By Tom Elliott.

Leave a rating/review
Save for later
Share

Note: Updated for Xcode 8.3, iOS 10.3, and Swift 3.1 by Tom Elliott. Original tutorial by Colin Eberhardt.

Almost any app you can think of needs to be able to fetch some sort of data from somewhere (disk, the network, the user) and display it somewhere else, possibly transforming or translating it along the way. Often you may want to show the same data in multiple ways.

The process of keeping all your UI elements in sync (often referred to as ‘wiring up’ your UI) is harder than it looks. Left unchecked it can rapidly lead to unmaintainable, difficult to modify spaghetti monstrosities. We’ve all been there :]

In this tutorial, you will use Bond to clarify and simplify the process of attaching what your users do to what they see on the screen.

Consider the seemingly trivial example of a slider with a text field.

Bond tutorial

In this example, you will update the text field to always show the same value as the slider. Updates made to the text field will also update the slider. For extra measure, you will connect buttons to set the slider to its maximum and minimum values.

With UIKit, you might commonly write code in an imperative manner – that is, by telling the program how it should do something, rather than declaring what it should do. In this example, you would tell the program “Hey! When somebody changes the slider, make the text field show the same value. And if they change the text field, make the slider show the same value. And while you’re at it, when somebody clicks the ‘Set to Minimum’ button set the slider down to zero. Oh, and don’t forget to set the text field to ‘0’ as well!”.

Instead, Bond allows us to write declarative code, focussing on the what without worrying about the how. “Hey! I want the slider and the text field to show the same value. And when somebody clicks the ‘Set to Minimum’ button, set the slider to zero”. In the language of Bond, you bind the value of the text field to the value of the slider.

Bond is a binding framework which sits on top of the ReactiveKit framework. ReactiveKit provides the base classes needed for functional reactive programming (FRP) in Swift. If you aren’t familiar with ReactiveKit, you may want to stop and review the project documentation on github.

Bond provides AppKit and UIKit bindings, reactive delegates and datasources to ReactiveKit. Bond makes it easy to bridge the FRP world with Apple’s APIs. Time to get binding with Bond … Swift Bond.

A Quick Bond Binding

To get started, download the starter project, which contains a ‘skeleton’ application. This will allow you to concentrate on Bond instead of fiddling with Interface Builder.

This project uses CocoaPods, so open the project using the BindingWithBond.xcworkspace file. (If you are not familiar with CocoaPods, check out this tutorial to help you get started.)

Now build and run. You will be greeted with the following:

Bond tutorial

All good? Then it’s time to create your first binding!

Open PhotoSearchViewController.swift and add the following to viewDidLoad():

_ = searchTextField.reactive.text.observeNext {
  text in
  if let text = text {
    print(text)
  }
}

The Bond framework adds various properties to UIKit controls, under the reactive proxy. In this case, reactive.text is a signal based on the text property of UITextField. Signals represent sequences of events that can be observed.

observeNext does just that, and executes its closure when the event occurs. Don’t worry, you’ll learn more about this shortly. For now, build and run, and then type “hello” to see what happens.

You will observe the following in the Xcode console:

h
he
hel
hell
hello

Each time you press a key, the closure in the code you just added executes; which results in the application logging the current state of the text field. This illustrates how events such as a property changing can be observed. Now you’re going to see what power that can bring.

Manipulating Data

Returning to PhotoSearchViewController.swift, update the code after super.viewDidLoad() as follows:

let uppercase = searchTextField.reactive.text
  .map { $0?.uppercased() }

_ = uppercase.observeNext {
  text in
  if let text = text {
    print(text)
  }
}

The map operation returns a signal by transforming the output of reactive.text into an uppercase string. The result is again printed in the observeNext closure, which is called as events arise.

Note: If you’re not familiar with map, check out Colin Eberhardt’s excellent tutorial on Functional Swift.

Note: If you’re not familiar with map, check out Colin Eberhardt’s excellent tutorial on Functional Swift.

Build and run. Then type “hello” again:

H
HE
HEL
HELL
HELLO

You might have noticed that the result of applying map is itself a signal. Therefore you don’t need the intermediate assignment. Update your code as follows:

_ = searchTextField.reactive.text
  .map { $0?.uppercased() }
  .observeNext {
    text in
    if let text = text {
      print(text)
    }
}

This gives rise to an elegant fluent syntax. Build and run your application to see the same behavior.

You’re probably only mildly impressed at the moment, so get ready to try something absolutely awesome.

Replace your current code with the following:

_ = searchTextField.reactive.text
  .map { $0!.characters.count > 0 }
  .bind(to: activityIndicator.reactive.isAnimating)

The map transforms each text string to a boolean, based on the presence of characters in the searchTextField. The bind, unsurprisingly, binds that boolean to the isAnimating property of activityIndicator.

Build and run your application. You will notice that the activity indicator animates only when the text field has text within it! That’s a pretty impressive feat with just three lines of code — perhaps even more impressive than a classic James Bond car chase :]

As you can see, Bond provides a fluent and expressive way to describe how data flows between your application and your UI. This makes your applications simpler, easier to understand, and ultimately gets the job done more quickly.

In the next section you’ll learn more about how bindings actually work. But for now, it’s worth appreciating the power of Bond … Bond.

I’ll drink to that!

Bond tutorial

I’ll drink to that!