Responsive Ui Layouts Flashcards
iOS
What are the challenges in working with UI on iOS?
Show them that you are aware of the responsive and adjustable nature of iOS UI. There are several things you as a developer need to be concerned with when developing UI for iOS:
- Multiple screen sizes/dimensions for iPhone 5, 6, 6 Plus, etc.
- Multiple screen sizes/dimensions for iPads
- Potential reusability of UIViews between iPhone and iPad
- Adaptability of your UI to resizable views used for multi-tasking feature on iPad (i.e., size classes)
- UI performance, especially with dynamic content of various sizes in UITableViews and UICollectionViews Mentioning all of the concerns above show that you are aware of the issues.
Also, it is good if you mention here that Apple has AutoLayout to address a lot of the challenges related to UI scalability and that it is a replacement of the previously used Frames and auto-resizing masks approach. These answers will likely make your interviewer steer toward a Frames versus AutoLayout discussion.
Table views and collection views’ performance is especially important for social networking applications, for example. They typically have content of arbitrary size posted by users that need to be displayed in lists.
The challenge there is to quickly calculate cell and other UI elements’ sizes when the user scrolls the content quickly. Mentioning that will most likely prompt your interviewer to ask probing questions about Frames, AutoLayout, and UITableView/UICollectionView.
What do you use to layout your views correctly on iOS?
Go-to options for laying out views on the screen are good old CGRect Frames and AutoLayout. Frames, along with auto-resizing masks, were used in the past before iOS 6 and are not a preferred option today. Frames are too error-prone and difficult to use because it’s hard to calculate precise coordinates and view sizes for various devices.
Since iOS 6 we have AutoLayout, which is the go-to solution these days and is preferred by Apple. AutoLayout is a technology that helps you define relationships between views, called constraints, in a declarative way, letting the framework calculate precise frames and positions of UI elements instead.
There are other options for laying out views, such as ComponentKit and LayoutKit, that are more or less inspired by React.
These alternatives are good in certain scenarios when, for example, you need to build highly dynamic and fast table views and collection views. AutoLayout is not always perfect for that and knowing there are other options is always good.
What are CGRect Frames? When and where would you use them?
The simplest way to position views on the screen is to give them specific coordinates and sizes with CGRects.
CGRect is a struct that represents a rectangle that a view is placed at. It has origin with x and y values, and size with width and height values. They represent the upper - left corner where the view starts to draw itself and the width and height of that view respectively.
Frames are used to explicitly position views on the screen and have the most flexibility in terms of what and how you position views on the screen. But the disadvantage is that you have to take care of everything yourself (with great power comes great responsibility, you know), meaning even though you’re in full control of how your UI is drawn on the screen, you will have to take care of all the edge cases and the different screen sizes and resolutions.
A better option these days is AutoLayout. It helps you with layout positioning through constraints and sets specific frames for views for you. It makes your views scalable and adaptive to different screen sizes and resolutions.
What is AutoLayout? When and where would you use it?
AutoLayout is a technology that helps you define relationships between views, called constraints, in a declarative way, letting the framework calculate precise frames and positions of UI elements instead.
AutoLayout came as an evolution of previously used Frames and auto-resizing masks. Apple created it to support various screen resolutions and sizes of iOS devices.
In a nutshell, using AutoLayout instead of setting view frames, you’ll create NSLayoutConstraint objects either in code or use nibs or storyboards.
NSLayoutConstraints describe how views relate to each other so that at runtime UIKit can decide what specific CGRect frames to set for each view. It will adjust to different screen sizes or orientations based on the “rules” you defined using constraints. The main things you’ll be using working with AutoLayout are NSLayoutRelation, constant, and priority.
- NSLayoutRelation defines the nature of a constraint between two UI items/views. It can be lessThanOrEqual, equal, or greaterThan- OrEqual.
- Constant defines constraint value. It usually defines things like the distance between two views, or the width of an item or margin, etc.
- Priority defines how high of a priority a given constraint should take. Constraints with a higher priority number take precedence over the others. Priority typically is used to resolve conflicting constraints. For example, when there could be an absence of content, we may want to align elements differently. In that scenario we’d create several constraints with different priority.
What are Compression Resistance and Content Hugging Priorities for?
Compression resistance is an AutoLayout constraint that defines how your view will behave while under the pressure of other constraints demanding its resizing. The higher compression resistance is, the less chance it’s going to “budge” under the other constraint’s pressure to compress it.
Hugging priority is the opposite of compression resistance. This constraint defines how likely it it the view will grow under pressure from other constraints.
How does AutoLayout work with multi-threading?
All UI changes have to be done on the main thread. Just like working with Frames, working with AutoLayout is UI work and it needs to be performed on the main UI thread. Every AutoLayout constraint’s addition or removal or constant change needs to be done on the main thread.
After you change constraints, call the setNeedsLayout method. Saying you can change AutoLayout constraints in any thread will raise a red flag.
What are the advantages and disadvantages of creating AutoLayouts in code versus using storyboards?
Working with AutoLayout in storyboards is considered to be more typical, and Apple pushes a lot of examples showing how to do that.
The advantages are that it’s visual, drag-and-drop/plug-and-playable, and you can, in some scenarios, actually render your UI in Interface Builder without actually running the app and waiting for the entire build process to happen.
Neat. But the disadvantages are very apparent when you need to debug your constraints or work in a team of more than two people. It is difficult to tell what constraints need to be there and what constraints need to be removed at a glance. And quite often, teams working with one storyboard modify it in different git branches, causing merge conflicts.
Also, the advantages of defining AutoLayout in code are that it’s very explicit, clear, and merge- and conflict-free. Disadvantages, on the other hand, are that it’s difficult to work with Apple’s AutoLayout constraints API in code (it can be helped if you use a library like Masonry) and you have to compile your app to see the results of rendering.
How do you work with storyboards in a large team?
The main problem when working with storyboards in a big team is dealing with .storyboard file merge conflicts. When two developers change the same storyboard in different branches, they most likely will have a merge conflict. The benefits a unified monolith storyboard gives are quickly outweighed by the struggle teams experience with those merge conflicts.
There are two solutions:
- Don’t use storyboards and define your AutoLayout in code.
- Split your monolithic storyboard into multiple storyboards, typically one per view controller. That way, storyboard changes will happen only when one view controller is modified, which likely will help you avoid most of the merge conflicts.
How do you mix AutoLayout with Frames?
AutoLayout and Frames can coexist together only in scenarios when you’re not mixing them up directly. Basically, you can have a superview layout itself and its subviews using constraints and have one or all of those subviews position themselves with frames. Views that need to use frames will have to override the layoutSubviews() method where they can do the precise calculations for CGRects necessary to align things in them.
Never say that you can just simply change frames of views that use AutoLayout. That would not work because with AutoLayout, frames are set by the system based on the constraints you’ve created.
What options do you have with animation on iOS?
There are three major things you can use on iOS to animate yourUI: UIKit,Core Animation, and UIKit Dynamics.
- UIKit is the basic animation that is used the most often. It can be triggered by running the UIView.animateWithDuration() set of methods. Things that are “animatable” this way are frame, bounds, center, transform, alpha, and backgroundColor.
- Core Animation is used for more advanced animation, things that UI-Kit isn’t capable of doing. With Core Animation, you will manipulate the view’s layer directly and use classes like CABasicAnimation to set up more complex animations.
- UIKit Dynamics is used to create dynamic interactive animations.These animations are a more complex kind where the user can interact with your animation half-way through and potentially even revert it. With UIKit Dynamics you’ll work with classes like UIDynamicItem.
Note: there’s also a very handy dynamics animation library by Facebook called Pop that can help with it.
How do you do animation with Frames and AutoLayout?
Most likely talking about how to animate views with UIKit is sufficient enough. With frame-based views you simply change frames in UIView.animateWithDuration:animations: and then assign new frames to your views and that’s it - the animation will be performed.
It’s almost the same thing with AutoLayout, but instead of changing frames directly you change your constraints and their constants in the animations: block of the UIView.animateWithDuration:animations: method and then call layoutIfNeeded() on the views you’ve changed.
How do you work with UITableView?
UITableView is one of the most used and important UI classes in iOS applications. UITableView is a class that lets you display a list of static or dynamic content of variable or set heights with optional section grouping.
Each row in a table is a UITableViewCell class or subclass. Table views and cells can be as complex or as simple as the application demands. Two of the biggest constraints on mobile devices are memory and performance.
This is why table views are designed to dequeue and reuse UITableViewCells they are displaying instead of creating new objects as user scrolls. It helps avoid memory bloat and improves performance. When you work with UITableView you usually instantiate an instance of it and then implement UITableViewDelegate and UITableViewDataSource protocols.
- UITableViewDelegate is responsible for calculating cells’ and sections’ heights (unless it’s done automatically with UITableViewAutomatic- Dimension) and for the other cell and section life cycle callbacks like tableView(UITableView, willDisplay: UITableViewCell, forRowAt: IndexPath) and tableView(UITableView, did- SelectRowAt: IndexPath). It also dequeues section views.
- UITableViewDataSource is the source of data for the table. It pro- vides the model data your table is displaying. It is also responsible for dequeuing cells for specific indexPath.
How do you optimize table views performance for smooth, fast scrolling?
Scrolling performance is a big issue with UITableViews and quite often can be very hard to get right. The main difficulty is cell height calculation.
When the user scrolls, every next cell needs to calculate its content and then height before it can be displayed. If you do manual Frame view lay- outs then it is more performant but the challenge is to get the height and size calculations just right.
If you use AutoLayout then the challenge is to set all the constraints right. But even AutoLayout itself could take some time to compute cell heights, and your scrolling performance will suffer.
Potential solutions for scrolling performance issues could be:
- Calculate cell height yourself
- Keep a prototype cell that you fill with content and use to calculate cell height.
Alternatively, you could take a completely radical approach, which is to use different technology like ComponentKit. ComponentKit is made specifically for list views with dynamic content size and is optimized to calculate cell heights in a background thread, which makes it super performant.
How do you work with UICollectionView?
UICollectionView is the next step from UITableView and it was made to display complex layouts for lists of items - think a grid where you have two or more items in a row or a grid where each item could be a different size.
Each item in a UICollectionView is a subclass of UICollectionViewCell. UICollectionView mimics UITableView in its API and has similar UICollectionViewDelegate and UICollectionViewDataSource to perform the same functions.
A very distinct feature of UICollectionView is that unlike UITableView it is using UICollectionViewLayout to help it lay out views it is going to display in its list.
How do you work with UIScrollView?
UIScrollView is responsible for displaying content that is too big and cannot be fully displayed on the screen. It could be a big picture that the user can pinch to zoom or it could be a list where all of the items cannot be displayed on the screen at the same time.
UIScrollView is a superclass of UITableView, UICollectionView, and UITextView; therefore, all of them get the same features as UIScrollView.
When you work with UIScrollView, you define yourself as its delegate by adopting the UIScrollViewDelegate protocol.
There are a lot of methods that you get with that delegate but the main one you usually work with is scrollViewDidScroll(UIScrollView). In this method, you can do additional work when the user scrolls table view content, for example.