Getting Down to the Nitty Gritty of Android Development

At this year’s IO Google introduced a new layout – the ConstraintLayout – and also presented it’s totally revamped layout editor. I am not going into how to use the layout. Google itself has done a good job in explaining it with its code lab “Using ConstraintLayout to design your views”.

In this post I am going to highlight what I like about the new layout and the new editor.

What’s to like about the new ConstraintLayout

With the new layout there’s a lot to like. Here are my favorite things about it:

If you have a complex layout, things can get pretty difficult to manage. Moving stuff around in a RelativeLayout is bound to break a lot of other stuff. That’s what they cited at IO. And it is true. So if this new layout help us with this, I’m all for it.

On the other hand things are currently not as bad, as they made them out to be. And the nesting can actually help you understand certain parts of the layout better since they are grouped and broken down into smaller parts. More practice with the new layout will show, if this really makes that much of a difference when maintaining screens.

In my opinion more important is the second motivation: To improve the performance. As users we all want the apps on our devices to run as smoothly as possible. And as developers we want to deliver this experience to our users. Thus, I’m all for it.

When it comes to performance improvements there is never any limit for additional improvements. So if Google helps us, I’m more than happy. Maybe this way the ConstraintLayout also reduces the need for some custom views or layouts.

A bit down I’m going to have a look at the actual performance of the ConstraintLayoutas it is today. It definitely needs more work. But the goal is laudable and the final implementation surely will fare much better than the current one. Mind you, we are talking about an alpha version here!

The availability of the stretched width/height of its children

The new stretched (or “any size”) appearance is better than match_parent in the context of this new layout. By stretching to it’s constraints this new mode is not limited to the enclosing container but can be used for arbitrary areas of the screen. You could achieve this with other means before – but now we have a unified concept for everything, which sounds more logical to me. It’s not that big a change, but a nice one nonetheless.

Guidelines are great additions

In addition to the layout and the editor we also have guidelines. These only make sense in the context of the ConstraintLayout – but they are actually proper views. They show up as separate view items in the hierarchy and get rendered at runtime.

But fear not. The decompiled Guildeline class is not only a mere 44 lines short – it also is as simple as a view can get. It doesn’t draw anything, always sets the dimension to zero width and zero height in its onMeasure() method and on top of that sets itself to View.GONE in the constructors. So no problems here.

What this means is, that the guidelines can work as any other view, when it comes to constraints.

For the placement of the guidelines you can use fixed values (say always 100 dp from the left edge) or percent values (say always at 33% of the whole screen width).

Later on in this post I am going to show you a sample for how to make good use of guidelines.

Not as weird as Auto Layout

When I first heard about the new layout during the IO keynote, my first thought was: “Oh no! Auto Layout is coming”. I have not done much with iOS, but what I have seen of Auto Layout, well, let’s put it this way: I do not necessarily like it. It breaks to easily whenever you try to do something with the screen. It’s only partially intuitive. In short it’s nothing you like to work with.

Right now I do not have these negative thoughts when it comes to ConstraintLayout. Maybe Google learned something from what Apple did wrong. But it could as well be, that it’s just because ConstraintLayout is not (yet?) as powerful as Auto Layout. I don’t know – all I can say is, that ConstraintLayout seems to behave quite reasonably. But seasoned iOS devs might think about this issue very differently 🙂

What’s to like about the new editor?

The new editor of course is also part of Google’s plans to make life for us developers easier. Actually it might end up to be also quite useful for sketching and prototyping. Who knows.

I especially like these things:

The properties pane has improved a lot

The editor shows lint warnings and errors prominently

The editor supports all kind of ViewGroups – not only ConstraintLayout

Everything is still XML backed

The screen is easily resizeable

The editor lets you select an image for all ImageViews right away

The improved properties pane

Do you remember the old properties pane? All kind of attributes were listed in an alphabetical way. Only very few more important properties were at the top:

The properties pane of the old layout editor

Now this has changed significantly – and it is much more usable that way:

The properties pane of the new layout editor

Android Studio by default lists only important and often used properties in this pane. Though, if you feel like it, you can always go back to the old list by clicking on the "Show expert properties" button on the top right.

Some attributes probably should be added (like layout_weight for LinearLayout children or layout_gravity), but all in all this is much better than before.

Also note that for views that extend other views the properties pane lists the properties grouped by the class they originate from. In this case first those of Button and afterwards those of the inherited TextView.

The error hints

Another nice addition we haven’t had before is the prominent display of lint errors and warnings in glaring red, so that you can’t miss them:

Indicator showing that the layout contains problems

And if you click on the number, it expands to show the problems:

Popup showing details about the problems

And as you can see, it also shows the content of the view in question, so that you know right away which view has a problem. Nice!

The new editor supports all kind of ViewGroups

When Google introduced the new layout editor it only showed it with the ConstraintLayout. But you will be able to use it for all existing layouts as well. For Linearlayout this works well, for RelativeLayout not so much. For RelativeLayout some magic of the ConstraintLayout like dragging to which other view the new view should be relative to would make sense as well.

I guess Google puts more emphasis on correctly supporting ConstraintLayout than supporting the other layouts like RelativeLayout. Actually: I hope so. I very rarely used the designer with those older layouts. I preferred the XML view and expect this to remain unchanged for those. And for those “legacy” ViewGroup types I wouldn’t mind if it stayed like that. After all the idea is to get rid of them anyway.

Everything is still XML backed

Obviously the aim of Google is for us to use the layout editor instead of the XML editor in the future. So why then is XML still a big deal?

In my opinion there are a few reasons:

XML is better to fix fiddly things
Sometimes working with a graphical editor has its drawbacks and it can become pretty difficult to access the correct handle and drag it onto the correct drop target. Or you made a mistake and marked some views as invisible or gone – or made them ridiculously small.

XML is ideal for version control
With a simple diff you can quickly see what changed over time. This is nice for yourself (using your local history or comparing changes to previous versions). But is even more important when collaborating with other. Code reviews and reasoning and discussing about pull requests is so much easier with XML and line numbers than having to throw screenshots around or having to run stuff just to understand even the simplest changes.

Easy resizability of screen

At the bottom right corner of the screen you have this handle. Nearly too unobstrusive:

Resize handle at the bottom right corner

You can use this handle to drag and resize the current preview screen and see which influence this has on your layout. Probably not often needed, but it can come in handy – while creating your layout, but also during presentations and trainings.

The editor lets you select an image for all ImageViews right away

Whenever you drag an ImageView or ImageButton onto the layout, the editor pops open a dialog in which you can choose the image to show or the color to use. That might not save that much work, but it’s still a nice detail, that I appreciate:

Dialog for image selection

Note that this screen also shows the more likely ones (the images of your project) at the top.

What about Performance?

Since performance improvements are among the main reasons to create this new layout, I did some performance tests to check if this goal is met.

I compared a layout used within a RecyclerView. Nothing too fancy, just some nested LinearLayout and RelativeLayout containers. I moved this layout manually over to ConstraintLayout and did some rather sloppy performance tests.

Comparing those two on an emulator as well as on an Nexus 5 yielded overall a performance penalty when using the new ConstraintLayout.

Performing worst is the measurement. The onMeasure() method takes roughly ten times as long as the one of the LinearLayout I used for comparison. And it uses up the bulk of the time with taking about 60 times as long as onLayout(). Thus the 30 per cent hit of the onLayout() method of ConstraintLayout compared to the one of the LinearLayout in question is nearly irrelevant. Finally layout inflation also took longer with ConstraintLayout than with LinearLayout.

The ConstraintLayout does lots of calculations to find out where and how to display each of its children. Internally (at least) three rather lengthy classes are working together to get the results: LinearSystem, ConstraintWidget and ConstraintWidgetContainer. To fully understand the performance behaviour I would have to dig into the depth of these classes (and for this I prefer the commented classes when their sources are released by Google). But just by having a cursory look at the decompiled code it looks like those classes have to do a lot.

Right now it looks like the performance improvements that Google hopes to achieve are far off. But at the Google IO talk John and Nicolas mentioned that they are working hard on improving the performance. So we can expect this to get better over time. And since the ConstraintLayout comes as a separate library, further improvements are likely even after the final release. If the result will be good enough in the end – well, that remains to be seen. We have to wait for future releases. And we have to do some more (and more thorough) testing with multiple layouts. Right now I’m more than willing to give Google the benefit of the doubt.

Additional note (as of July, 9th): This post was written based on the third alpha of ConstraintLayout. In the meantime a fourth has been released. Which, according to Nicolas Rouard, should be performing much better. I will give it a try and let you know about improvements in future posts. As I’ve written above: Google is hard at work on improving performance – and even this fourth release is still an alpha release!

Additional note (as of July, 22th): I have used the same layout for testing the fourth alpha build. It is indeed much better – but still needs improvements. With the performance imporvements of this build, onLayout() takes roughly a third of the time it took before. And onMeasure() now roughly twice as fast as before.

In one thread on twitter, Nicolas Rouard mentioned that – performancewise – ConstraintLayout is best for complex layouts for which you would have needed deeply nested layouts before. Keep this in mind, when deciding what layout to use. If time allows, I will try to find a suitable deeply nested layout to verify this in future add-ons to this post.

Some annoyances

Not all is working perfectly at the moment, though. Right now these things bother me the most:

Noticable lag between blueprint changes and design preview changes

On bigger screens it’s quite useful to open the blueprint view and the preview next to each other. But especially if you use lots of stretched views or many views that make use of the bias you will notice a growing lag in the preview.

This has already improved a bit with the latest updates, but is still noticeable and sometimes a bit irritating. Also while calculating those new positions the editor makes heavy use of your CPU. Luckily only for short bursts.

Preview is not always correct

When you miss some constraints, the preview view shows an incorrect screen. This actually is by design and has been different in the very first version of the layout editor. Back then (due to the aforementioned lag) things jumped around seemingly haphazardly, which of course was very disturbing. But apart from the lag the other reason for this was, that you can use the preview to drag things around. Which I strongly advocate against (see below). There’s no reason for that. We have the blueprint editor to edit constraints. Let the preview do what its name implies.

Blueprint view doesn’t heed text layout constraints

This is a fairly minor issue – yet one I would like to see corrected. In a TextView setting the gravity doesn’t change the location of the text in the blueprint view. The setting is reflected correctly in the design preview, but when working with the blueprint only, it feels odd that changing this setting doesn’t have any effect. Switching between the design and blueprint view just to verify that this setting did indeed work as expected is a bit cumbersome. Nothing that makes life really hard, but something that requires an extra step and makes one wonder at first.

Constraints do not always work as expected

The following screenshot admittedly show a very weird and pretty useless screen – but it shows that constraints might not work as you would expect them to work:

Screen showing constraints not working properly

Never mind that this screen is among the weirdest app screen you might ever stumble upon. It still should be correct 🙂

As you can see the bottom button is left aligned to the right button in the second row. That’s at least how the button should be. And you can also see, that this button is stretched. So why then does it stretch that far to the left? What makes this calculation go that wrong? My guess is, that the problem is not so much with the button at the bottom, but the buttons of the second row.

What worries me is not that this specific screen isn’t working. The problem is, that I do not know why it’s not working and what makes views appear so wrongly aligned. As long as things like this can happen, you are bound to run into this problem with a real screen on a real device eventually. And then it is really bothersome.

Undo works very unreliably

On one screen I accidentally moved one view around after I set some button’s visibility to gone and to visible again. I hit Ctrl-Z and the button’s visibility changes to gone again. What I had expected, of course, was to undo the last step – which was the accidental dragging of another view.

Trying to reproduce exactly these steps for this post I was not only not able to reproduce this particular problem. Instead I was now not able to undo the moving around step. Alas, very unpredictable again.

One of the earlier versions also behaved differently when using Undo via the menu or hitting Ctrl-Z. This appears to be fixed in the current version. But since Undo is so unreliable in general I do not know for sure.

I think this is the worst problems the editor has right now. When working graphically to quickly test stuff, moving items around should be easily – and reliably – reversible. Otherwise this editor hampers experimentation and is not useful for quickly sketching and for trying things out.

The editor undos or changes stuff in unexpected ways

This is even harder to describe properly since this seems to be even more haphazard than the undo issues. I do not have many proper examples.

On the screen I have worked with while checking and re-checking some stuff for this post I had a button. I changed the visibility to gone, then to invisible and then to visible. Afterwards the view was still drawn as if it were invisible. Reproducible: Of course not 🙁

The editor also tends to ignore size changes (or to revert them when switching between the the XML and then back to the design tab). But nothing of this is easy to pin down and reproducing these issues is unreliable as well 🙂 I do not envy the Googlers having to fix these type of arbitrary issues. And I am sorry for not being able to be more specific. But whoever uses the editor will stumble upon the undo and unreliability issues pretty quickly.

Suggestions for additions

Currently I have two suggestions for the layout and three for the editor:

Add width constraints based on other views

Add an aspect-ratio constraint

Add Ctrl-Mousewheel scrolling to the layout editor

Allow changes in the blueprint view only

Make the guideline’s orientation indicator select the guideline

Of course there might be more suggestions in the future when I’m actually going to use ConstraintLayout for productive projects. But right now I think those additions would help a lot.

Now let me tell a bit about why I would like to see those items realized.

Add width and height constraints based on other views

For some screens I would like to ensure that neighbouring elements use the same width (or height) – but not a fixed width. For example you want buttons to divide up all of the width available. Or two images next to each other.

With LinearLayout you would simply set the layout’s width to match_parent and then use layout_width="0" and layout_weight="1" on its children and they would divide up the available space.

When I first experimented with ConstraintLayout I thought, that would be easy. Simply use three buttons next to each other, align each of the right ones to the one left of it and finally the left button to the left edge of the screen and the right one to the right edge of the screen. And then make all of them stretch. But this didn’t work as expected:

Three buttons not taking up equal space

What you see here is that the first two are as they would be with a width of wrap_content and only the last one is actually stretched. In a bug report I filed, a Googler remarked that this works as designed. Stretch doesn’t divide up the remaining space between all stretching views. Keep this in mind!

But not all is lost: The team plans to add some constraints that would allow us to do this in the future. Meaning after the first release of ConstraintLayout. The bad part is, that we do not have this right away. The good part is, that they have much more plans for this layout and that we can expect it to get better over time.

Guidelines to the rescue

But even with the first release not having width constraints, we might be able to achieve this, depending on the specific layout at hand.

For the layout shown above the solution is to use Guildeline objects to divide up the space and then align the buttons to it. Here’s what the workaround looks like (click on the image to see its original size):

Three buttons now equally spaced

And since sometimes code is easier to understand, you can find the code for this layout in this gist. The gist contains the correctly sized buttons as well as the first attempt without guidelines.

Add an aspect-ratio constraint

Romain Guy pointed out in the comments that the ConstraintLayout indeed has this feature. I’m going to add some more information about how to use it soon. Stay tuned!

Even though I never published it, I once made a board game. For things like this it would be nice to have the ability to ensure that this view always has the same height as it’s width. And I can also imagine other use cases where elements should use a certain height depending on the device width. Say half the height as the view’s width.

You can achieve this with custom views (and in the case of game boards that’s the most logical thing to use anyway), but I still guess this addition could make a lot of sense. Especially for ImageView objects.

Make the guideline’s orientation indicator select the guideline

If you add guidelines they get an indicator at the top (or on the left for horizontal guidelines) which show whether a guideline is positioned at a fixed margin or at a percentage of the total width. Here’s the indicator for a percentage:

The position indicator for a guideline

It would feel more natural if I could select the guideline by clicking on this indicator. Right now I first have to select the guideline by clicking somewhere on the line itself. Afterwards I can use the indicator to drag the guideline around or to change the type of indicator. Why not directly so?

Add Ctrl + Mouse Wheel scrolling to the layout editor

The layout editor can get very crowded – depending on the amount of views, how close they are and how they are constrained. In some cases it would be convenient to quickly zoom into the screen, do some designing, and then quickly zoom out again. It also would be really helpful while presenting about the editor and the ConstraintLayout 🙂

This is what we’re used to when using graphics software. And Android Studio has a setting to allow this way of zooming for text:

Ctrl + Mouse Wheel setting for text in Android Studio

Thus I would like to see, the zooming to work for the layout editor whenever this setting is checked in Android Studio.

Allow changes to be made in the blueprint view only

Currently it’s possible to change layout settings in the blueprint view – but also in the preview view. I think the latter should not be possible at all. Restrict designing to the blueprint. If you do so, the preview would be less cluttered – and also might perform better.

The most important reason in my opinion though is, that we are then free to actually use the preview as it should be: A realistic preview. I have already mentioned that the preview is not correct in all cases. And this has to do with the fact that you should be able to drag views around there as well. But if we drop the need for this, we actually can see problems like missing constraints right away.

What about LinearConstraintLayout and TableConstraintLayout

I just had a cursory look at both. Thus I do not have an opinion on them. Maybe in some later post. Depends on how they turn out.

One thing is worth mentioning, though: Those two layouts exist, but Google doesn’t explain them at all. I think they didn’t even mention them during their IO talk. So that’s the one thing I can say: Please let us know what you intend to do with these ConstraintLayout children and what they should be useful for. I actually have a hard time seeing much use of LinearConstraintLayout for example – but hopefully Google proves me wrong.

Does Anko support ConstraintLayout?

For those that use Kotlin and like to use Anko as an alternative to XML, the answer right now is: No! Anko doesn’t support ConstraintLayout.

Yan Zhulanow opened issue #210 within the Anko project to add support for ConstraintLayout to Anko. Right now, no further comments have been added. But most likely this will be fixed soon.

To sum things up

The new layout and the new layout editor both show promise. They are currently in alpha (the layout) or preview (the editor), so we can expect to see many – if not all – of the problems ironed out until the final release of both of them.

It’s definitely worth getting yourself accustomed with the new layout. I’m quite confident that it is the future.

Having said that, I currently don’t use the ConstraintLayout for real projects. But I expect to be able to do so pretty soon.

Please note that everything I have written here is based on what I currently think about the ConstraintLayout and the design editor. There have been lots of improvements during the last iterations of both the ConstraintLayout and the editor and I expect this to go on.

Also keep in mind, that we are only starting to understand the possibilities of ConstraintLayout! The more we use it the more we will know how to do stuff. I’m actually quite excited about it – despite some of the problems the alpha still has.

I very much appreciate what the Googlers are doing there! Keep up the good work – and thanks!

Let me finally thank those nice folks of the Dutch Android User Group. I had the opportunity to speak about ConstraintLayout at their Google IO Extended Extended. Many of the thoughts in here are the result of my preparations for the talk and feedback about the demo afterwards.

If you’re not doing so already, I thoroughly recommend to go to the meetups and devfests of your local Google Developer Group. Here’s a map of Google Developer Groups worldwide, if you’re not sure where the next one is.

Ratio will work (for now) only to set one dimension from the other — i.e. if you have a fixed dimension (wrap_content or literal value), you can set the other dimension using the ratio attribute (the ratio is expressed as a string formatted like “3:2”). The dimension that is set by the ratio need to be set to “0dp” (“match constraints”). What’s missing currently, which is why we haven’t yet surfaced the attribute in the UI, is the ability of having both dimensions to 0dp, with one of them driven by connection constraints and the other driven by the ratio attribute. Future version!

“It doesn’t feel as weird as Auto Layout”? This portion of the article felt a little like fluff. Could you go into more details here? As someone with a few years of iOS dev experience, I’m really not sure what you’re talking about – I enjoy Auto Layout for the most part.

Not much, yet. I have to give a talk next week about Android Things. So I had to flash the Android Things dev preview 2 and improve on my demo today.

With regards to ConstraintLayout beta5 I especially like the improvements they made to to the aspect ratio constraint. That’s the only thing I tested today, since it was giving me grieve before. And it now works exactly as I had hoped 🙂