A couple of weeks ago, Jacques-Alexandre showed us a prototype for a user interface that would make it a lot easier to create new applications, with a simple multi-step wizard. It came right at the time when I was giving some thoughts to the idea of a wizard-driven user interface for all our objects that could be used as a way to simplify the creation of new records. Some discussions ensued, and we agreed that it would be a good idea to implement it in order to dramatically simplify our overly sophisticated user interface.
The main goal is to simplify the creation of new records for any object, including objects themselves. The idea is to faciliate this creation by canonically generating multi-step wizards that would focus on an object’s required and important fields, with oversized forms. Such wizards would be stateful but non-persistent until the user would click on a Done button, allowing easy navigation through steps. And they would be defined using the exact same schema as the one used for screenflows, so that we could build a single graphical editor for both.
The canonical wizard would have three steps:
- Required Fields, with Next and Done buttons.
- Important Fields, with Previous, Next, and Done buttons.
- Preview, with Previous and Done buttons.
The steps would be shown on a straight-through flowchart setting the user’s expectation about the number of steps involved in the creation of the record. The Important Fields and Preview are optional and would be prominently indicated as such, allowing the user to complete the record creation as soon as all required fields would have been populated. At any time, the user could also switch to the full record view in order ot populate any other fields that are neither required nor important.
Additionally, developers of objects could create custom wizards, much like they can create custom forms and views. This would allow the creation of records for more complex objects such as applications, objects, or purchase orders, for which many parameters must be entered, and for which many fields are relational, including advanced relationships for which multiple relations need to be instantiated.
Right now, we’re not sure whether we will include this in our MVP or not. More on this soon…
Now that we’ve figured out how to create complex views and sophisticated charts, it’s time that we simplify our user interface so that all users could benefit from all this goodness, without having to fiddle through endless menus and cumbersome popups.
In such a context, Florian and I have decided to try something pretty radical: merging our grid perspective and our view editor, into a new grid perspective that would always display charts. The idea is that charts is another way to look at your data, hence our full collection of canonical charts could be considered as a perspective.
And because charts are intrinsically linked to the concept of views, and because views are best created when looking at data, either in raw form or through a pivot table, why not merging all three together? Raw data, view configuration, and charts, all tightly integrated together through the default grid perspective.
This approach would have the benefit of showing gorgeous charts immediately after importing any data (a spreadsheet usually), without having to click on any icon or menu item. And by doing so, we could refactor our grid perspective and get rid of its menus. Instead, we would just show the view’s name (All Records by default), and a set of icons, one for each perspective.
Down the road, we would apply the same principle to all other perspectives, showing different charts for different perspectives, according to the fields that are most relevant for a given perspective. For example, the Calendar perspective would show charts that have a chronological dimension, and the map perspective would show charts that have a locational dimension.
All the pieces are coming back together…
This could not come at a better time…
Next month, we’ll be done with the MVP (yeah!), and we’ll welcome teammate #9 (Zhipeng Jiang). His first assignment will be to refactor our mobile user interface using the new Ionic framework. As part of this exercise, we will test a lot of ideas that we would like to apply eventually to our web user interface. By testing them first on the mobile UI, we’ll give ourselves some time to refine them, in a smaller and totally safe context (the mobile UI is not part of the MVP). Some ideas will work, and some won’t. In the end, we’ll have learned a lot of lessons, and we’ll be in a much better position to apply them to the web UI. Here is what we’d like to test:
CircularJS server-side, AngularJS client-side
With the new architecture, CircularJS will generate and cache on the server-side pages which content will be processed client-side using AngularJS (Ionic is based on AngularJS, conveniently). The server-side processing will be limited to things like localization and theming. By having these two tiers, it will allow us to reduce the amount of data we need to send to the client, and the amount of processing that needs to happen there. By the same token, most of the extra processing taking place server-side for localization and theming can be fully cached, therefore won’t really create any significant overhead on the server.
With this architecture, all pages will be stored as records of the Pages object, instead of being stored as files directly on the filesystem. This will allow customers to make any changes they would like to our user interface, in a totally safe multi-tenant environment. While this is not something that we will actively encourage, for some use cases (like branding), it should be quite helpful. Of course, our mapping of object records to files (Cf. article) through STOIC Drive will soon give developers access to pages through the filesystem, allowing them to keep using their IDE of choice, and GitHub to manage their lifecycle (still trying to figure that one out).
Today, AngularJS has become a very powerful framework, with lots of features that we could take advantage of. But this will require quite a bit of upskilling if we want to use them well. In order to get there, we’ll watch movies, read books, and hire some consultants for a few sessions of pair programming. We’ll then apply our learnings to the mobile UI. This should give us a solid foundation to tackle the full refactoring of our web UI.
Currently, our implementation of UI controls is a little bit funky. Most controls are implicitly tied to specific datatypes, and we do not really have the ability to reuse the same control across multiple datatypes for datatypes that might be displayed through multiple controls (like Boolean, which could use a chackbox or radio buttons). In order to support this highly-desirable level of reuse, we need to properly define the input schemas of controls, then define schema bindings between the options of datatypes and the inputs of controls. This is something that we will prototype first with the mobile UI, then apply to our web UI. Knowing that we have 74 datatypes and 81 controls, it is not something that we can approach lightly…
Server-side D3.js Execution
Most of our visualization framework is based on the amazing D3.js. Unfortunately, it’s a pretty heavy framework, especially for mobile devices. In such a context, we’re considering to offer the option of running the D3.js code server-side in order to generate plain SVG vector images that can be rendered more easily by lightweight clients. This will be prototyped with the mobile UI for all our charts and some of our perspectives (Cf. this and that)
Bootstrap to Foundation Migration
Over the past couple of years, we’ve been slowly but surely reducing our reliance on Bootstrap, and the move from Bootstrap 2 to 3 did not particularly impress us. In fact, we’re still using Bootstrap 2.3.2, and we have no plans of ever migrating to Bootstrap 3. Instead, we’ve been using Foundation for more and more projects, and we really like it, because it’s lighter and more responsive (through the consistent use of rem CSS units). Therefore, we’re likely to use Foundation for our refactored web UI, and we’ll use it for our theming framework. Of course, Foundation will never offer as many themes as Bootstrap, but quality trumps quantity.
LESS to SASS Migration
So far, we’ve been using LESS to compile our CSS stylesheets. Both Foundation and Ionic are based on SASS, therefore we’re likely to move to this framework as well, but testing it first with the mobile UI should help us avoid any bad surprises.
Right now, our web user interface is tightly integrated within our core server. This is creating quite a few tricky issues that could be solved if we were to run it as a separate application, following the long-advocated recommendation of Hugues. It will require quite a bit of refactoring work on the server-side, but this is something that would benefit CircularJS, the mobile UI, the web UI, and any other server-side application built against the platform.
When developing CircularJS, we’ve been careful to start with Bower.io from day one to manage all our client-side libraries. This is something that we’ll do as well for our mobile UI, then apply the same lifecycle to our refactored web UI.
Icon fonts are great, but they also have their fair share of issues. We’re not sure what we’ll do there, but if we stick with icon fonts (instead of moving to plain SVG), we’re likely to integrate a full icon font generator (like grunt-webfont) into CircularJS, so that customers can easily add their own icons and discard the ones they don’t need. In fact, it should be fairly easy to detect which icons are being used by an application, and to dynamically generate a minimalist icon font for it. Right now, our icon font has about 3,500 icons in it, but I don’t think we’re using more than 500.
In order to automate the many tasks required to build our user interface, we will use the Grunt task runner. It should be especially useful for automating the packaging of our mobile UI with Cordova, by using something like grunt-cordovacli.
Our localization framework will be built for the mobile UI first. This will allow us to test it on a smaller scale before we apply it to the entire web UI. Translations will be managed with a dedicated object and will be applied server-side using CircularJS. Pages translated for a particular locale will then be cached on the server before being sent to the Ionic framework.
Theming and Rebranding
Similarly, our theming and rebranding framework will be tested on the mobile UI first. It will consist in a set of SASS resources for which a simple user interface powered by CircularJS will be developed. We will also make sure that we can support off-the-shelf Foundation themes.