Releasing TableViewKit 1.0
We are excited to release TableViewKit 1.0 – an open source framework which is a core part of our apps: eDreams, Opodo, GO Voyages (and soon Travellink). The framework allowed the eDreams ODIGEO iOS mobile team to set up a complex layout easily, while improving the modularity of our codebase.
TableViewKit was developed to improve our apps architecture, to spend less time doing tedious work such as layout composition and manual diffs, so that our team could spend more time on building a state of the art travel app.
TableViewKit is heavily based on UITableView – why?
UITableView is one of the most used component for us, we use it for showing information, editing data and setting up layouts. It’s a pretty mature API, solid and very fast compared to Auto Layout or other solutions.
But we had a couple of problems with our current implementation: there was a lot of boilerplate for setting up a view, the responsibilities were not very clear between cells/items/sections, and showing or hiding specific elements was over complicated (i.e. we had to write specific code each time we wanted to insert an element in a position).
Let’s consider a simple example. We would like to create a fold/unfolded feature, so that our users can have a glance of the most important information and check extra details if they want.
The idea is pretty simple, we have an array of “items” we want to show for the “Folded” state and for the “Unfolded” one.
Using what we had, we would have written something like this:
One of the problems here is that we couldn’t just change the position of a cell without rewriting all the logic. A lot of boilerplate, a small change required rewriting a lot of code, low reusability – those were not the things we wanted to have. We sat down and we found a solution.
We separated each concern and responsibility into its own protocol. Those were mainly:
- TableViewManager, coordinating with its own sections
- Section, declares the layout composed by a header, items and a footer and manage its state
- Header, Item, Footer, have logic specific properties and connects to its drawer
- Drawer, an implementation of the strategy pattern with a mix of generics that helps define how to paint a view
Now defining a layout became as simple as defining an array of sections, which means we could easily move or exchange sections and it’s also very useful for A/B testing.
We integrated the Longest Common Subsequence algorithm, so that a Section could automatically understand the “diff” between states and automatically add, remove or move any element together with a build-in animation.
Also, Swift compiler features helped to clean up code and to be more safe: for example Height is an enumeration property that differentiates between static or dynamic height, the protocols are bounded with the working-with type, i.e. a CellDrawer can only work with UITableViewCell objects.
Our code is now cleaner and less error prone, and many of the assertions that we were manually writing are now checked by the compiler, automatically. Cool right?
If you are curious to know how much will change the folded/unfolded example, this would be the result with the framework:
When refactoring using TableViewKit we got:
- an average of 60% less code
- making changes went from few days to few hours
- testing got much easier because of the separation of concerns
Those benefits mean we can ship great new features to our users faster and better.
We wanted to give back the help that the open source community has been giving to us during the journey of developing our apps. We hope you will love TableViewKit as much as we do, as it has been a strong companion for our iOS engineers.
If you want to know more or start contributing, have a look at our repo on Github.