Weekend Reading for July 15, 2016

Weekend Reading for July 15, 2016, click here

Happy Weekend fellow Clean Swifters. I’ve been spending all week in “sprint.” Not the agile software kind, but instead it’s a format proposed by Jake Knapp of Google Ventures. It’s designed to learn what product you should build based on your customer needs in a short period of time (one week). I’m looking forward to some downtime over the weekend. Here’s what I’ll be catching up on.

Get “Weekend Reading” delivered in your email, as well as every other cleanswifter.com post, and receive a free screencast on iOS automated testing by signing up here. “Weekend Reading” is created through AWeber’s app, Curate, which I helped create and is entirely written in Swift.

Happy cleaning

Swift Playground Books

Swift Playground Books are going to usher in an entirely new interactive experience to learning a programming language. There have been various creative ways to learn new programming languages for years, but nothing like what Swift Playground Books will provide. I see two key factors that will enable Swift Playground Books to revolutionize the way that programming languages are learned, while also making Swift mega popular:

  1. Apple controls the whole ecosystem – iPad, IDE, and language. Well ya okay technically Swift is open source, but at least Apple controls the hardware and the IDE. The hardware being the iPad, and the IDE being the Swift Playgrounds app. Just like they’ve done for years, by controlling the whole ecosystem, Apple gets to ensure a top notch experience.
  2. iPad learning – Learning on a tablet, an iPad to be specific, will appeal to a much wider audience in a much wider set of circumstances. Ya the iPad has lost some appeal lately, but despite that, I foresee huge sections of people in new age groups using Swift Playground Books to learn the Swift programming language (not just “kids”).

Why Playground Books?

The new iOS 10 iPad app, Swift Playgrounds, is pretty cool on its own. Awesome autocompletion, touching and dragging brackets around, immediate feedback on written code, and more all contribute to a whole new way of programming. I’m not going to rehash the app in detail, this blog has a nice summary, and I also suggest watching the WWDC 2016 session “Introducing Swift Playgrounds”. (The last 10 minutes are super cool where a Sphero robot is controlled from an iPad, live on stage).

We can’t actually create apps in Swift Playgrounds yet, so until then, Swift Playgrounds is pretty much designated an exploratory and educational tool, and I’m okay with that. Regarding informal exploration of the Swift language, I see a lot of this happening in one-off playgrounds themselves. A standalone playground file is the perfect resource to try things out, learn about a specific topic, and just have fun. Swift Playground Books though is a giant step forward in organized and collated learning. Rather than just consuming a single playground, Swift Playground Books allow authors to aggregate content into an actual book-like, yet interactive experience.

Playground Books support a nested chapter and page structure, just like a real book. Additionally, there’s a cool new type of “page” called a cut-scene. Imagine that you complete a chapter in the book, and as a reward get to watch a little animation celebrating your victory, while also setting up the next challenge. As an author, you can also programmatically designate assessments on a chapter – did the user complete it successfully? This shows up in the Table of Contents as a green checkmark.

swift playground books

Striving to get all the green checkmarks like that are what make me so prone to get sucked into compulsively completing something, and in this case learning. 🙂

In addition to the assessments, there is built in support for the following:

  • Glossary – You can link terms at the tap of a finger.
  • Regions – Annotate pieces of code so that the user literally only needs to fill in specific parts to complete the challenge.
  • Shortcuts – Control what shows in the Helper Bar.
  • Hints – After the user has provided a response, if it isn’t quite correct you can code a “hint” to be displayed.
  • Resetting – The reader can either reset a page, or the entire document to start all over.
  • Live View – You can trigger a Live View to interact with that takes up half the screen. The idea is that the user writes code on the left hand side of the window – the Contents View, while interactive results are displayed on the right hand side – the Live View.

swift playground books

(There are actually some specific APIs to use in order to pass data back and forth between the Contents View and the Live View. See PlaygroundLiveViewMessageHandler, PlaygroundValue, and PlaygroundRemoteLiveViewProxy.

Playground Book Format

Swift Playground Books are easy to create. They are literally just a folder, with a particular structure, and a couple configuration files. Check Apple’s official documentation for details on setting up the directory and file structure, it’s dead simple. And since it’s all just text and folders, it can be version managed just like any other code or project!

Despite it being simple, I’ve had some issues getting it actually working on iOS 10 Developer Beta 1 and 2. For some reason, Swift Playgrounds isn’t recognizing my Swift Playground Books as something it can read. Instead, it just lets me browse the directory hierarchy, never actually opening it as a Swift Playground Book.

swift playground books

This folder should be detected as a Swift Playground Book that may be opened. Apple even recognizes the .folder extension in their documentation as something expected, and something that should be there. Maybe it’s just too early of a beta, or maybe I’m having problems since I’m trying to create these on OS X El Capitan rather than Sierra? I’ll continue to dig and post and update when I figure it out.

Playground Book Store?

One thing on my mind is whether Apple will provide some sort of store front for the Swift Playground Books. I could see significant effort and time spent on developing complex books that could provide hours of entertainment and learning for end users through discovery within a Swift Playground Book. It’s certainly a ripe business opportunity. Right now, there are only two tabs in the Swift Playground app: Featured, and My Playgrounds. I wonder if they will eventually create a store front to purchase Swift Playground Books through? And if so, will be be protected my DRM at all?

Learning More

I have so many ideas for content to create and distribute in Swift Playground Books. And besides that, I can’t wait to sit on the couch with my kids and reveal the amazing world of computer programming to them through Swift Playgrounds. How about you?

Happy cleaning.

VIDEO: Inline Method Refactoring in Swift

In “Refactoring, Improving the Design of Existing Code” by Martin Fowler, he presents the Inline Method refactoring. It is the opposite of Extract Method, which I’ve already covered.

Here’s a video walkthrough of the Inline Method refactoring in Swift and its benefits:

Video Transcription

Hey, what’s up everybody, it’s Andy from cleanswifter.com, and I’m back here to talk about another refactoring in my video series covering Martin Fowler’s book, Refactoring, Improving the Design of Existing Code. This week we’re going to talk about Inline Method and it’s a refactoring which is actually the exact opposite of the refactoring we talked about last time, Extract Method. With Extract Method, it was all about taking common functionality from a larger piece of code and extracting it into a new method. With Inline Method, it’s doing the exact opposite. You’re going to take code in a method and delete that method, and move the functionality back to where’s it’s called from.

Why Inline Method Is Useful

This is useful for a couple reasons. In one case, if the code being called is so simplistic that putting it in another method just distracts you, you might as well just put it back in the original place and delete the simple method.

Another reason you may want to do it, is that, if you have a series of different methods that are all called from a bigger method, and those other methods being called are smaller, you can then move that functionality back to the original method, delete all those other smaller methods, and then once the functionality is back together in the calling method, then extract that as one method, that then serves a better purpose in being a cohesive unit of code that actually does something.

We’re not going to do that right now. First we’re going to look at inline method all by itself. Let’s take a look at an example.

The Example

Here we have some code that calculates the length of a hypotenuse according to the Pythagorean Theorem. This code right here adds the squares of two numbers, the base and height of a right triangle, then takes the square root of the result. That’s the length of the hypotenuse of the right triangle. Reading this line of code by itself is pretty decent. I can read this and understand what it’s doing. But then I look at all these methods being called, and all of these are just doing a single line of code, which is just built in math. I want to propose an Inline Method refactoring to delete all three of these methods and move this functionality to be directly included with this method. Let’s do this one by one.

Starting in the middle we have the numbers being squared. That’s going to be my target method to first delete. I can see that this is just multiplying two numbers together, simple enough. I can come down here and square the numbers directly, and now since square is no longer being called, I’ll delete that. Voilah, that is the Inline Method refactoring.

I’m going to do this again for add. I can then delete add, and the call to it, and instead, just put that functionality directly in this line. Now you can see that I’m adding the result of the methods being squared. Add is no longer called, so delete that custom method. And the same square root, which just wraps the Foundation function for doing the same thing, I can then delete this and instead call the Foundation function directly. You can see the refactored result.

This example is kind of simplistic, but I think the simplisticness of it is a good example of when you would want to do this refactoring. In each of these cases and methods that I deleted, there was one line of code that called a function right from Foundation: add, multiply, and square root. When looking at this code, I think it’s much more obvious what it does, and there’s not these extraneous methods that cause my eyes to jump around. Now, imagine you’re doing this in a class, or series of classes, where those methods being called actually existed in a different place. Now, not only do you need to look somewhere else, but where you have to look is in a totally different file. For me, that jumping around, especially when the method is so simple, I think it’s better served to have it right inline with the code that is performing the function.

Again, it’s just a tool to add to your toolbox. Inline Method appears in Martin Fowler’s book, Refactoring, Improving the Design of Existing Code. You can buy it in the description for this video. Again, check out the original post on my blog, cleanswifter.com. Thanks a lot for watching, and I’ll see you next time.

Weekend Reading, July 1, 2016

Weekend Reading for July 1, 2016, click here

Happy Friday fellow Clean Swifters. We’re looking at a 3-day weekend here in the United States, I can’t wait. More time to catch up on WWDC sessions! Here’s some other suggested reading if you find yourself with free time this weekend.

Get “Weekend Reading” delivered in your email, as well as every other cleanswifter.com post, and receive a free screencast on iOS automated testing by signing up here. “Weekend Reading” is created through AWeber’s app, Curate, which I helped create and is entirely written in Swift.

Happy cleaning

Xcode UI Tests Review

After writing Xcode UI tests for the first time today, immediately some things formed my initial impression. I wanted to pass along my Xcode UI tests review here on cleanswifter.com in effort to help educate others. For at least the pass year, if not longer, I’ve been using KIF for writing my functional UI tests. I love KIF. KIF is a third party, open source tool. That brings both benefits and drawbacks. Right off the bat, due to changes in the iOS 10/Xcode 8 Accessibility Inspector, KIF was broken in the beta versions of our tools. It was quickly fixed, and the impact was low, but it does make you wonder about what’s in store for the future when there are less people available to maintain it? This wasn’t the only thing that drove me towards Xcode UI tests for this project, but it was certainly a concern. I still love KIF and will continue to use it on other projects for the foreseeable future.

Background

Xcode UI tests build on an older tool from Apple called UI Automation. UI Automation enabled the iOS developer to write UI tests for their apps, and it was officially supported by Apple. “Officially supported” is certainly a loaded term, especially with UI Automation. The documentation was pretty bad. While there was some light guides on developing UI Automation tests, the actual API documentation had very little information. Combine that with the fact that the tests were written in JavaScript and run with Instruments (outside of Xcode), I was never happy with the tool.

Then last year, in WWDC 2015, Apple announced a reimagined solution for writing UI tests, Xcode UI tests. Here’s my Xcode UI tests review.

Pros

Officially Supported by Apple

This shouldn’t be underplayed. I’d live through a lot of crappy documentation just to use an officially supported tool. Apple officially supports Xcode UI tests, and that means a lot to me. It means you get WWDC videos on the subject. You get subtle integration with Xcode that only Apple could have access to. It means that your tests are less likely to break in future versions of iOS and Xcode.

Tests Written In Swift

Unlike UI Automation tests, Xcode UI tests can be written in either Objective-C or Swift. This could be the single best improvement. This means that you get everything from code completion, to compile-time syntax checking, to full Xcode integration.

Integration with Xcode

It was really annoying with UI Automation that you needed to switch to Instruments just to run your UI tests. Furthermore, JavaScript support in Xcode is pretty bad too, so one was left searching for a good editor experience when writing tests. Xcode UI tests change this. Now, the tests are first-class citizens right in the same IDE that we are using to write our actual application code. There’s even a “New File template” for Xcode UI tests.

Xcode UI Tests Review

XCTestCase subclasses

Buliding on the integration with Xcode, Xcode UI tests subclass XCTestCase just like unit tests. This means the full API of XCTest is available. Methods like XCTestAssertEqual and XCTestAssertTrue can be leveraged for writing your tests. Additionally, things like Scheme integration into your Test action enable execution of your Xcode UI tests when running tests, right from Xcode. Also, all those others niceties of running unit tests and the wonderful keyboard shortcuts can also be used with your Xcode UI tests.

Xcode UI Tests Review

UI Recording

UI Recording for Xcode UI tests is pretty cool. You can click a “Record” button in Xcode, and your app will launch in the simulator. Then, as you tap and navigate through your app, actual code will be generated in a test reflecting the path through your app that you took. It’s not perfect though, and more importantly, it doesn’t actually generate any assertions. Also, to prevent your test from being really brittle, you do need to consider breaking your tests up into cohesive chunks, and not one giant test.

Cons

Xcode UI tests aren’t without their flaws.

Documentation Is Still Light

The documentation for Xcode UI tests is still light. It’s not as bad as UI Automation was, but it’s still not perfect. KIF has been around for years. There are tons of stackoverflow.com questions and answers for it, the GitHub repository is mature, and you’ll find plenty of tutorials. I still can’t find an official piece of web-hosted API documentation for Xcode UI tests.

See the end of the article for a list of resources that I’ve been using as reference for Xcode UI testing.

Slow

Obviously all UI tests are going to be slow, regardless of whatever platform and tools you are using. Something uniquely slow jumps out at me about Xcode UI tests though. As a developer, you are required to call XCUIApplication().launch() from your tests when you want the app to launch. Each test must call this. The common pattern from what I’ve seen is to place the call to XCUIApplication().launch() in setUp(). setUp() is an overridden method from the XCTestCase base class, and is executed by the XCTest framework before each test. The thing is, XCUIApplication().launch() is REALLY SLOW. It triggers a fresh launch of your app. Now I guess this is useful from the context of resetting state in your app, but if you aren’t careful about structuring your tests, you could inadvertently introduce a lot of overhead in the speed of your tests.

iOS9 and Up

One of the main advantages of a suite of automated tests, regardless of the platform or type of tests, is to be able to run those tests in all places that your code base is supported. If you are writing a web application, this might be different browsers at different screen resolutions and window sizes. In iOS development, you can exponential benefit from running the same suite of tests across different devices of different form factors and different iOS versions. Unfortunately, Xcode UI tests put a major hamstring in this, in that they will only run on devices with iOS 9 and greater. To me, this is a big deal. We don’t all have the luxury of requiring the minimum iOS version to be the latest on the market. At the time of this post, iOS 9 is the latest iOS version, so that means I can’t even run my automated UI test suite on one version back, iOS 8. There have been so many times in my testing career in which UI tests identify and/or verify a bug that is present on one iOS version and not another. I’m really disappointed that Xcode UI tests don’t work on anything older than iOS 9. I guess I just have to hope for my applications, we’ll soon be able to require iOS 9 and greater.

XCUIElement != UIView

One of the most awesome things about KIF is the overlap between the KIF APIs and UIKit. When writing KIF tests, there are many methods like:

func waitForViewWithAccessibilityLabel(label: String!) -> UIView!

It’s so useful to have a UIView returned. This can be cast to more specialized subclasses that actually represent the object returned. And once you do that, you have full access to all the methods available on that object as defined in the actual code. Code like this is possible:

let saveButton = tester().waitForViewWithAccessibilityLabel("Save") as! UIButton
XCTAssertEqual(UIColor.blue(), saveButton.currentTitleColor)

This code is really useful because once you have a handle on the UIView, you can access so many APIs to verify behavior.

Unfortunately, there is no such intersection in Xcode UI tests. In Xcode UI tests, the object returned from similar method calls is a XCUIElement, and there’s no way to translate this to UIView (that I’ve found). As such, you are limited to the limited API available through Xcode UI tests and XCUIElement – none of which translates to a UIKit equivalent.

Final Thoughts

Despite the drawbacks, I’m still excited to use Xcode UI tests and I hope this Xcode UI tests review conveys that. It’s always fun to learn something new, and I think there are plenty of positives to using the tool. Have you used Xcode UI tests? What’s your Xcode UI tests review?

Happy cleaning.

Useful Resources

IBOutlet Local Reasoning: What, why, and how

Did you watch Protocol and Value Oriented Programming in UIKit Apps from WWDC 2016 yet? I did and it’s one of my favorite sessions yet. It was essentially a part 2 from the WWDC 2015 session, Protocol-Oriented Programming in Swift. It even included a cameo of Crusty. I really liked the session because it gives some plain talk explanation towards improving your Swift code through basic functional programming techniques, and it was specifically attractive to me because of this year’s session’s focus on UI code. UIKit code is filled with object-oriented techniques and patterns like MVC and subclassing that it’s hard for a chiseled object-oriented veteran to learn new tricks like functional programming.

State is Bad

Relying on instance variables in your objects leads to buggy code. Furthermore, it leads to code that’s not just buggy, but also simply hard to debug. You should strongly consider any case where you introduce an instance variable that will be used for state management. Consider the following view controller:

class ViewController: UIViewController {

  var total = 0

  override func viewDidAppear(_ animated: Bool) {
    super.viewDidAppear(animated)
    if (total > 0) {
      print("total bigger than 0")
    }
  }

  func incrementTotal() {
    total = total + 1
  }
}

This code has an outrageous example of relying on an instance variable to determine state of the object. total is an Int. The major problem I have with code like this is the conditional if-statement in viewDidAppear(_:). This is a simple example, so it may not seem problematic to you. Imagine if the view controller had significantly more code, where total was referenced all over the code. Imagine there were numerous places where total was getting assigned to. Imagine there were numerous places where total was being used for conditional checks. Imagine that even external classes were reading and modifying total. Imagine all the places you would have to check and be aware of to ensure that total behaved correctly such that the view controller properly functioned. It quickly grows out of control. Code like this has been the source of more bugs than I can count in my UIKit programming. It’s why functional programming is so attractive to me, despite how hard it is for my head to wrap around some of the concepts.

Local Reasoning

One of the absolute most attractive things about functional programming in my mind is the lack of “side effects” of your code. Essentially, you strive to write code that does not have side effects, where there is a single “source of truth.” This is one of the cores of value oriented programming. When working towards this, you begin to write code that is much easier to debug and much less buggy to begin with. It’s much easier to understand code just by looking at it. One of the biggest anti-patterns of object oriented code is managing state of an object through a instance variable.

In the WWDC 2016 session Protocol and Value Oriented Programming in UIKit Apps the concept of “Local Reasoning” is introduced. It’s a semi-official computer science term that describes code which contains little to no side effects. Local reasoning is that “when you look at the code right in front of you, you don’t have to look at the rest of the code or project to know how it behaves.” This is really attractive because when you look at a piece of code, you can quickly have confidence that you understand what it does because you don’t need to look in many places. Instance variables that control object state are the enemy of local reasoning. For example, looking at the code above, any reference to total contains the caveat that there could be any number of things modifying total throughout program execution. You can never rely on the value of total to actually make a decision about the state of the program.

IBOutlet Local Reasoning

Of course you can’t actually remote all instance variables from your code. You’ll inevitably find certain scenarios where some state must be stored. One common such example are IBOutlets. IBOutlets are special snowflakes in the software design world. Pretty much any rule about software design may not apply when using IBOutlets. When using a Interface Builder file or a Storyboard, you’ll need to subclass UIView or UIViewController and link user interface elements from Interface Builder to the code through IBOutlets. The thing is, IBOutlets take the form of instance variables in code.

class ViewController: UIViewController {
  @IBOutlet weak var toggleSwitch: UISwitch!
}

So how can you apply IBOutlet local reasoning to improve your code? My coworker Mike Stanziano had a really useful idea on how to do this: use a property observer on the IBOutlet.

Let’s say that you want to create a UISwitch in your storyboard. The state of this switch will correspond to a boolean value in a persistence layer, the example will use UserDefaults. Initializing the value usually would happen in viewDidLoad() like:

override func viewDidLoad() {
  super.viewDidLoad()
  let keep = UserDefaults.standard().bool(forKey: "ToggleValue") ?? false
  toggleSwitch!.setOn(keep, animated: false)
}

Maybe you could use the Extract Method refactoring to move those two lines to their own method, but my point is that this code immediately violates local reasoning and starts you off on the wrong foot in using your IBOutlet. I’d consider this code part of initialization of the UISwitch, so it doesn’t make sense to put it in viewDidLoad() aside from the semi-artificial rule put in place by UIKit in that views should be setup in viewDidLoad().

Inspired by Protocol and Value Oriented Programming in UIKit Apps, my colleague Mike came up with something better:

@IBOutlet weak var toggleSwitch: UISwitch! {
  didSet {
    let keep = UserDefaults.standard().bool(forKey: "ToggleValue") ?? false
    toggleSwitch!.setOn(keep, animated: false)
  }
}

This code moves the initialization of the UISwitch‘s state out of viewDidLoad() to a place that I argue is much more appropriate, where the IBOutlet is defined. Since IBOutlets don’t get init’d in code, their definition is the closest thing we have towards an actual instantiation. Now, when you look at the definition of the IBOutlet, you immediately know how it’s initial state is configured. This is right in line with the local reasoning – “when you look at the code right in front of you, you don’t have to look at the rest of the code to know how it behaves.”

And of course, writing a unit test for this code is extremely straightforward.

func testSwitch_DisplaysStoredSwitchState_WhenToggled() {
  // Start the switch on
  UserDefaults.standard().set(true, forKey:"ToggleValue")
  UserDefaults.standard().synchronize()

  let toTest = ViewController()
  let testSwitch = UISwitch()
  toTest.toggleSwitch = testSwitch

  XCTAssertTrue(toTest.toggleSwitch.isOn)
}

No need to call viewDidLoad() from your test. Simply set the desired value on the UISwitch and verify the behavior.

Clean Code is Clear Code

I love the principle of local reasoning in your code. I’m all about writing clean code, I even named this blog after it. Give IBOutlet local reasoning a try and I think you’ll like it. Clean code is enabled by clear code, and local reasoning leads you to clearer code. Give it a try. Here’s a project on GitHub with this code all wired up using Swift 3 and Xcode 8.

Happy cleaning.

VIDEO: Extract Method Refactoring

In “Refactoring, Improving the Design of Existing Code” by Martin Fowler, he presents the Extract Method refactoring. It is one of the best refactorings out there. It’s one of the most common ones that I use.

Here’s a video walkthrough of the Extract Method refactoring and its benefits:

Video Transcription

Hey, what’s up everybody, it’s Andy from cleanswifter.com, and I’m back this week to actually continue our series on reading “Refactoring, Improving the Design of Existing Code” by Martin Fowler. This week for the first time, we’re going to look at an actual refactoring in code. The refactoring we’re going to look at is called “Extract Method.” Extract Method is actually a really easy refactoring, it’s often supported by IDEs and the benefit of it is that it increases the opportunity for code reuse, you’ll have less duplication of your code, it enables smaller units of code, so it helps you get rid of those really long methods. And it also reduces the semantic distance between the method name and method purpose. I really like that wording that Fowler actually used in the book. That means your method names will be very clear and close to what the method actually does. As a result, for that to happen, your method needs to be succinct and cohesive. Extract method refactoring enables this. Let’s take a look at it.

Here’s a class, AccountViewController that subclasses UIViewController. Right here in viewDidLoad() is some simple code that creates two UILabels. Three properties are set on each label: the text color, the text alignment, and the number of lines. There are actually two different labels on which these properties are being set. But what’s in common between these two pieces of code, is that, the three properties are being set on the label are exactly the same. This is a prime opportunity to leverage the Extract Method refactoring. For Extract Method, all we’re going to do is create a new method called setUpLabel. In there, I’ll add a parameter that is the label to be set, and on that label, I’ll take this code, remove it from viewDidLoad() and add it to this new method that we’re extracting, and then down in viewDidLoad(), call the new method by providing the label. Down where the second label is setup, I can also then delete this code and call that same method with the addressLabel. Now you can see we’ve removed the redundant code that is setting up the label, and now we have a dedicated method that is named very clearly for what it does: sets up a label. The redundant code for addressLabel has also been consolidated.

Let’s make the example a little more complicated. In this example we see the similar three lines of code setting up the label that configure the text color, the text alignment, and the number of lines. To make it a little more complicated, we’re actually going to set the text on the two labels as well. nameLabel will be set to “Andy” and addressLabel will be set to “Philadelphia.” Now we want to perform a refactoring that removes redundancy while also preserving the ability to set the test on the labels. We’ll start off in the same way as before, creating the new method setUpLabel. Move forward with the refactoring to get to the same point we were at in the last example. Now that a baseline for setUpLabel is extracted, we need to update it to be able to accept a String such that the text on the label may be set, and the redundant use of temporary variables in viewDidLoad() can be removed. Add a parameter to setUpLabel of type String called text. Set the text on the UILabel‘s text. Update the method call to setUpLabel in viewDidLoad to actually pass in the text to be set. Do the same thing for addressLabel. At this point, we’ve removed redundancy and consolidated the code which includes setting the label’s text based on a provided parameter. There’s one more level of complication that we can add while leveraging the Extract Method refactoring.

Increasing the complexity of the example towards something even more real-life is to add properties on the view controller for each label so the values that are created are stored. After setUpLabel is called, we’re now storing the label in the property on the class. To further reduce the redundant code, I’m going to extract the label creation into setUpLabel. That will cause me to return the created label so that it can be set on the property. The goal of what I want to do here, is delete the creation of the UILabel in viewDidLoad() and move it to setUpLabel(). I will no longer need to pass the created label in to setUpLabel(). Instead, I will create a new UILabel each time setUpLabel is called. Then using that new label, set it’s properties, and return it. Now you can see the final result of the refactoring where all the redundant code has been consolidated into one place, a method dedicated to setting up labels. viewDidLoad() now reads very clearly.

You just saw an example of the Extract Method refactoring. Just to recap it’s benefits: it increases the opportunity for code reuse by reducing duplication, it enables smaller pieces of code (as you saw viewDidLoad and setUpLabel become small). And finally, decreases the semantic distance between the method name and method purpose – which means you can create a nice small method with a nice clear name that reflects what the method does.

I hope you liked this screencast on the Extract Method refactoring from “Refactoring, Improving the Design of Existing Code” by Martin Fowler.

Weekend Reading, June 24, 2016

Weekend Reading for June 24, 2016, click here

Happy Friday fellow Clean Swifters. It’s been a crazy week of watching and writing about WWDC videos and new technology for me. Xcode 8 beta has been fairly stable for me, and it’s really fun digging into some of the new frameworks.

I’d love to hear from you, what topics are you interested in hearing about on cleanswifter.com? Just reply to this email and let me know.

Get “Weekend Reading” delivered in your email, as well as every other cleanswifter.com post, and receive a free screencast on iOS automated testing by signing up here. “Weekend Reading” is created through AWeber’s app, Curate, which I helped create and is entirely written in Swift.

Happy cleaning

iOS 10 UICollectionView Highlights

Did you get a chance to watch the WWDC 2016 session, “What’s New in UICollectionView in iOS10″ yet? I watched it today. There is some good stuff in the session, and I want to recap it for you in this post. The session is broken into three segments that capture everything that’s new for an iOS 10 UICollectionView :

Improvements to:

  • Smooth Scrolling
  • Self-Sizing Cells
  • Interactive Reordering

There is a special bonus fourth segment as well, but I’ll save that for later.

Smooth Scrolling Enhancements

In iOS 10, there are several enhancements that will improve the performance of your UICollectionViews – some of which you will manually need to leverage, and some you will get for free. Before dropping into the new features of iOS 10 UICollectionView, the presenter gives a nice overview of what it means to “drop frames” and what it’s bad.

Don’t Drop Frames

In order for your app to have “buttery smooth” performance, a hallmark of iOS apps, you must strive for app animation that performs at 60 frames per second. This means that a given frame of the user interface must be displayed in less than 16.67ms in order for the animation to appear “smooth.” Otherwise, when the frame rate drops lower than that, it’s apparent to the user in the form of a choppy animation. The easiest way to make the frame rate drop, is to do things like add blocking, long running method calls on the main thread in the middle of your animation. Here’s an in-depth article from Facebook on how they measure and ensure a highly performant news feed in their app.

Less Aggressive Loading and Unloading Cells

In a UICollectionView, the lifecycle of a cell is as follows:

  1. prepareForReuse
  2. cellForItemAtIndexPath – The heavy lifting of populating your cell’s data from your model happens here.
  3. willDisplayCell – Lightweight preparation for when you cell is about to go onscreen.
  4. Cell comes on screen, and as scrolling continues starts to move offscreen.
  5. didEndDisplayingCell

In general, this flow is unchanged between iOS 9 and iOS 10. The different is when these methods are called. Apple has optimized when willDisplayCell is called. In iOS 10, it’s now called at the very last minute before the cell goes on screen. This helps to balance out the CPU performance in drawing cells, but not executing that code too early. Additionally, another enhancement Apple has made in iOS 10 UICollectionView is that cells are not put on the reuse queue as aggressively as in the past. Instead, after a cell leaves the screen, it is kept around a little longer in case the user decides to swipe the cell back on screen.

Cell Pre-fetching

Apple also enhanced UICollectionView such that by default, cells are pre-fetched. This means that you can get even earlier awareness of when data for a cell is needed such that you can retrieve it. For example, if you are building a UICollectionView full of remote images. Leveraging the UICollectionViewDataSourcePrefetching, UIKit will call:

collectionView(_:prefetchItemsAt:)

to allow for you to start downloading the images with Grand Central Dispatch of an NSOperationQueue such that when the cells containing the images comes on screen, the images will be downloaded and ready to go.

If you need to, you can opt out of this behavior by setting isPrefetchingEnabled to false, but why would you?

As part of pre-fetching, realizing that cellForItemAtIndexPath may be called for cells that never end up coming on screen – because the user stopped scrolling before they were shown. Also, it’s really important that you keep the work in willDisplayCell and didEndDisplayingCell really light. All the heavy lifting goes in cellForItemAtIndexPath. Apple described pre-fetching as an “adaptive technology” which I assume to mean that it’s level of “predictiveness” varies by use case for a given application.

And as bonus, this exact same pre-fetching API is also available on UITableView via UITableViewDataSourcePrefetching.

Self Sizing Enhancements

Prior to iOS 10, estimatedItemSize has existed on UICollectionViewFlowLayout in order for you to provide an estimate size for the items in your collection view. Sometimes it’s hard to predict the size of items in your UICollectionView. Realizing this, Apple has introduced automatic item sizing for your UICollectionViewFlowLayout. Simple set the item size to the constant UICollectionViewFlowLayoutAutomaticSize and UIKit will make smart guesses based on past measurements of your items in order to automatically predict item sizes for future items.

According to Apple:

It will keep a running tally of all the cells it’s already sized, and use that to influence its future sizing estimates…making the sizing much more accurate…leading to better performance and a more accurate layout.

Interactive Reordering Enhancements

Reordering a iOS 10 UICollectionView has also undergone some improvements as well. Prior to iOS 10, if you didn’t already know (and I only learned recently), it’s really easy to enable reordering on your UICollectionView – in your UICollectionViewDelegate, simply implement:

func collectionView(_ collectionView: UICollectionView, targetIndexPathForMoveFromItemAt originalIndexPath: IndexPath, toProposedIndexPath proposedIndexPath: IndexPath) -> IndexPath

There are some additional methods on UICollectionView that you should take a peak at too that enable you to add more advanced animation and update your data model if appropriate.

New in iOS 10 UICollectionView is the ability to reorder with paging!

collectionView.isPagingEnabled = true

That’s it! The presenter describes it as an interaction that feels just like moving icons between pages on your home screen.

The Bonus

Finally, the big reveal happens. It’s as if this is such exciting news worthy of a WWDC reveal, but there is no other session appropriate for it. The presenters reveal that pull to refresh will be supported on:

  • UIScrollView
  • UITableView
  • UICollectionView

If it wasn’t awesome enough that UIScrollView and UICollectionView got the control, but you are also no longer constrained to needing a UITableViewController if you want an out of the box pull to refresh control (which was a pretty annoying prior limitation in my opinion).

Final Thoughts

I have plans to do an in-depth example of how to use pre-fetching with Grand Central Dispatch in order load remote images in a UITableView sometime in the future. I recently ran into a problem in one of my apps that this exact thing would have solved. Essentially I had cells in a UITableView that were of varied height based on a remote UIImage being loaded. I ended up needing to set a static height on the cells to achieve a high frame rate and scaling the images, instead of properly sizing the cells according to the natural height of the image. It wasn’t the end of the world, but there was some extra white space in the cells that wasn’t needed. How do you plan on using these new changes to iOS 10 UICollectionView?

Happy cleaning.

UIPasteboard iOS 10 Example

I just finished watching What’s New in Cocoa Touch today from WWDC 2016, it was an awesome session. My coworker called it “the index for the rest of WWDC.” Olivier Gutknect basically goes on rapid fire for an hour citing change after change in UIKit for iOS 10. For each thing he mentions, he covers varied levels of detail, and usually references a different WWDC session where the framework or topic will be covered in more detail. The UIPasteboard iOS 10 API made an appearance in this session, just like the keynote. When I heard about the Universal Clipboard changes for iOS 10 and macOS Sierra, I was so excited to actually be able to use this new feature as an end user. It’s so cool, leveraging Handoff and continuity, iOS and macOS will intelligently share your clipboard across devices. This means I can copy something on my laptop, and then pickup my iPhone and have that most recent thing copied available for pasting.

As a developer, I was also curious to see what new changes were in store in the UIPasteboard iOS 10 API.

In order to take advantage of the new Universal Clipboard in your apps, you don’t need to do anything differently than you’ve been doing, just use the UIPasteboard API. That being said, in order to provide the best user experience, there’s two changes to the UIPasteboard iOS 10 API that are related to the Universal Clipboard:

  1. Methods to help understand what is in the clipboard.
  2. Methods to designate the lifetime of the clipboard item.

Understanding the Clipboard Contents

Some of the changes to the UIPasteboard iOS 10 API enable you to inspect the contents of the clipboard to understand what type of contents are in the clipboard. Is it a color? Is it an image? Is it a string? Is it a URL? As a developer, you can intelligently take advantage of this. For example, say your app contains a color picker. You could provide a standard looking color picker, while also observing that the clipboard contains a color and show it as well.

Here’s an example:

// Setup, let's put some stuff in the UIPasteboard

let pasteboard = UIPasteboard.general()
pasteboard.string = "andy"
pasteboard.url = URL(string: "http://cleanswifter.com")
pasteboard.image = UIImage()
pasteboard.color = UIColor.red()

// Understanding the UIPasteboard contents

if pasteboard.hasStrings {
    print("The pasteboard has Strings!")
}
if pasteboard.hasURLs {
    print("The pasteboard has URLs!")
}
if pasteboard.hasImages {
    print("The pasteboard has images!")
}
if pasteboard.hasColors {
    print("The pasteboard has colors!")
}

Designating The Lifetime of Clipboard Contents

With the changes to the UIPasteboard iOS 10 API that introduce Universal Clipboard, it also opens a slight security vulnerability in that an end user could copy a sensitive piece of data and inadvertently make it available across all their devices. The UIPasteboard iOS 10 API provides a way to lock this down. As a developer, you can either:

  • Flag a piece of data as “local only” in which it will not appear in the Universal Clipboard across devices, and
  • Set an expiration date on a piece of data such that it isn’t available after that date.

Here’s an example of flagging a pasteboard item as “local only”:

// Add a string
let aLocalOnlyStringKey = "Local only string key"
let aLocalOnlyStringValue = "Local only string value"

// Set the string in the LOCAL pasteboard
pasteboard.setItems([[aLocalOnlyStringKey: aLocalOnlyStringValue]], options: [UIPasteboardOption.localOnly : true])

In one line, you set the item in the UIPasteboard with an option localOnly as true.

Here’s an example of adding something to the pasteboard with an expiration date:

let aExpiringStringKey = "Local only string key"
let aExpiringStringValue = "Local only string value"
// Create a date 24 hours from now
let expirationDateOfTomorrow = Date().addingTimeInterval(60*60*24)

// Add the string and mark it to expire 24 hours from now
pasteboard.setItems([[aExpiringStringKey: aExpiringStringValue]], options: [UIPasteboardOption.expirationDate: expirationDateOfTomorrow])

Again, in one line you get to pass an expiration date for when the UIPasteboard item should expire. You can also use these together.

Gonna Needa Pasteboard

James Dempsey is going to need to update the lyrics to his song “Gonna Needa Pasteboard” to account for the Universal Clipboard and these new UIPasteboard iOS 10 API features. In the meantime, I absolutely can’t wait to use the Universal Clipboard, and all the while knowing that if developers properly take advantage of these new UIPasteboard iOS 10 API features, my data will be safe and my applications will be snappy.

The code from this post is available in GitHub as a playground, here.

Don’t forget, this UIPasteboard iOS 10 API is still in beta and could change between now and the public release.

Happy cleaning.