Cross-platform frameworks that don’t use native controls have suffered from problems...
- They inevitably don’t look or work like native apps in ways both big and small, frustrating and annoying users. (... the spell-checker doesn’t work right or text selection is janky or unavailable where it should be, certain short-cuts work differently or have different gestures or keys, etc.)
- they don’t get updates to native controls... e.g. if the OS adds some new drag-and-drop capability to text fields the framework doesn’t get it unless and until the framework is updated (and the app is updated to use the newer version of the framework). Of course, some things are never deemed important enough to be adopted by the framework.
- Ambitious frameworks that really try to minimize the gaps between apps build with the framework vs native app grow to be very large. They take on the role of the entire app-facing OS API, which is truely massive in today’s systems. This leads to slow-loading/building, resource-hungry apps. Each app becomes a mini-OS unto itself.
- there are cross-platform issues, like fonts that fit on one host OS get cut off in another, or differences in volume control etc.
- dealing with the cross-platform issues the framework doesn’t solve becomes very difficult for the app developer. They’ve got to find a way in, through, or around the framework (in an area it already isn’t handling well).
- devs have yet another set of tech and tools they have to master. And I mean devs in the wide sense here, designers, coders, testers, etc. Some also have to become masters of how the framework and each host OS interact, in order to debug the inevitable problems.
- many potential third-party tools will have native support and bindings but most won’t make accommodations for your framework, so you end up having to support that yourself, or do without.
Building and maintaining an app twice is a very serious expense. But the expense of dealing with the issues with crosss-platform frameworks can be pretty big as well. Of course it depends on what you’re doing (shorter term and longer term) whether or not it makes sense. But go in with your eyes open. Consider other options (like examining your app architecture and see if you can’t find a way to factor some of your naturally cross-platform stuff into a shared library usable by the native apps of each platform you support).
>- They inevitably don’t look or work like native apps in ways both big and small, frustrating and annoying users.
We're way past that in the mobile world, where both Google, Facebook, and other top dogs use non-native cross platform frameworks and looks (e.g. Material UI).
To be fair, just because bigs use their own frameworks doesn't mean they produce great UX. There's an added learning curve to any non-native app that users incur when this happens - things are out of place, don't work as expected, features don't exist, etc. For example:
- Facebook doesn't use standard share sheets or web views. So if you're viewing an article, you can't use reader mode and you lose the (considerable) power of share sheets to do things like sending an article to another app or take an action on it.
- Gsuite doesn't register left swipe as back even though 99% of apps on iOS do. Icons for common actions are subtly different and make you double-take while you understand what they do. Accessibility options like larger text do not work, so if you're vision impaired good luck trying to figure out what you're looking at. And there's a ton of other quirks that have existed over the years including scaling to new resolutions/ipads, problematic text selection, performance, etc. It's not as bad as it used to be, but it's still not a pleasure to use Gsuite or any material design on iOS.
While many apps may use cross-platform frameworks solely for saving developer/designer time, the bigs use them for an additional strategic purpose that is detrimental to users.
- Google wants you to be familiar with their apps regardless of platform, so that its easier to get you to switch to Android or Chromebooks.
- Facebook wants to keep you in the app as long as possible, limit social sharing outside of their app, and spy on your browsing activity, so they add friction and don't use modern iOS web views that prevent that.
I wouldn't take cues from the bigs and just assume because they do it, it's the best course of action.
For us, we want to use the web stack so our stuff works across all platforms. So we use Cordova. We realize that over 90% of users just want to use the main interface and not some fancy OS feature. All our effort goes into making the product rock solid stable, engaging and easy to use. We aren’t actually interested in making it feel exactly like a native iOS or Android app.
Well, such things are causing subtle annoyance for users. This works as long as the value you provide is good, but the more and app is just a bad we view the more likely it becomes that people uninstall it or look for alternatives. Unsurprising consistent behavior is a value.
They do care. Try writing a DOS or Blackberry-style app today and see what happens. Software today has internalized the idioms so much that its developers don't even realize it.
"My app is a snowflake and needs a custom design language and UI." You're vim or Photoshop or AutoCAD or Excel: you're targeting dedicated users who are prepared to invest in learning a specialized UI. Fair enough.
But if you're not one of these highly professional apps, then custom control just makes the app less predictable, harder to use, and often inaccessible for users with disabilities. Not good.
>They do care. Try writing a DOS or Blackberry-style app today and see what happens.
Nothing much. Some of the most downloaded and bought apps (desktop and mobile) have horrible custom UIs. As long as the app has the crucial functionality, few care. And I'm talking for average users.
As for pros? Well, vim and Emacs are DOS style apps (well, in that they use curses and totally un-native GUI paradigms), and they're still strong.
UI concerns of that level only matter when apps otherwise have marginal utility and small other differences with competitors.
Sure but lets not forget the single most successful consumer product in history (iPhone) owes much of its success to it's clean, consistent UX across a suite of built-in apps. More people probably use those than downloaded apps.
1. People regularly complain about inconsistent web UI.
2. Even web apps often have similar idioms and patterns to their UI that they've settled on. It's their own patterns that are different from desktop OS, it's basically another category.
3. Most web apps are used on desktop, not mobile. On mobile, it's mostly native apps that are used. So they're not substitutes.
Honestly, I expect from a web page to be shitty. I'm surprised when some web page aren't slow, unresponsive, or doesn't distract me with million designer quirks.
My expectations are different with mobile apps. If I'm spending some time to find the app on the app store (and maybe pay for it) and giving the app a place and a storage on my phone, I'm expecting from the app to be polished and give me pleasant experience.
Agreed - I never could quite understand that argument and what is so intuitive and familiar with native UI controls when looking from perspective of a new app to the user. Depending on the app functionality, achieving good UX could be very hard and sub-optimal using only native controls, and impact of a well-thougth-out flow through the app, specialized controls where helpful and polished design should not be underestimated...I'd say that, if someone puts enough attention into it, custom design / controls are probably mostly superior to the native UI, in terms of UX. Not to mention how often people want something different and fancy over "boring" bland look of native controls...Granted, there are a lot of small usability aspects and behaviors to consider, as pointed out by others.
> I never could quite understand that argument and what is so intuitive and familiar with native UI controls when looking from perspective of a new app to the user
Consider the humble popup button. A user may open the menu via touch, or with a mouse click, or tab to it and open it with spacebar, or via accessibility support, or via scripting support. Once the menu is open, the user may choose to select an item via touch, or trackpad, or key equivalent, or arrow keys and return, or accessibility, or scripting...
When the control is obviously normal, all of these interaction modes are available. If it's something custom, then probably only a few work and I don't want to subject myself to the frustrations of figuring out which one.
Native UI controls allow the user to exercise their built-up vocabulary.
> I'd say that, if someone puts enough attention into it, custom design / controls are probably mostly superior to the native UI, in terms of UX.
Broadly false, but true in highly specialized apps where the investment in custom flows is worth it. (vim, Photoshop, etc). If you're building one of these apps, by all means, think deeply about a specialized interaction vocabulary. But if your app isn't designed to be absolutely central to a specialized workflow, PLEASE leverage the ecosystem and use the native stuff.
> Not to mention how often people want something different and fancy over "boring" bland look of native controls
Same in the desktop world - Qt emulates the widgets, but can theme them, then QML is another story. Also WPF (from what I've heard) uses (skia?) to paint own widgets. IMGUI is another example.
Then using the native wrappers, like wxWidgets is often cumbersome to create customized control, and if you do you end up with some platform specific version (not end of the world, but pretty much why not use the OS toolkit directly). Also any wrapper soon or later suffers from "leaky abstraction" - where you hide things behind interfaces, but can't hide different performance characteristics, and getting the current line in a log dialog might just kill you, because underneath it might be scanning all '\n', '\r' until your cursor position.
Given the usage of e.g. and offering the most charitable interpretation of coldtea’s comment, I guess it wasn’t supposed to be an exhaustive list, just the first (or most pervasive?) thing that came to mind.
There's one place where none of this matters: Games engines.
Games have the same, consistent (hopefully) easy to use interface across every platform they support. They either accomplish this, or they simply don't survive on the market.
It has to be said that most modern UI frameworks ARE game engines, anyway. Or maybe its a tautology: game engines eventually become platforms, which become "OS's on other OS's".
Which means that in this scenario:
> devs have yet another set of tech and tools they have to master. And I mean devs in the wide sense here, designers, coders, testers, etc. Some also have to become masters of how the framework and each host OS interact, in order to debug the inevitable problems.
.. It becomes moot whether you're using an engine or an OS's own specific platform. You have either an 'engine developer' or a 'user-facing developer', where the former does everything needed on the target OS to support the latter.
My personal preference: treat onboard native UI frameworks as a plug-out interface to the engine, port the engine everywhere, have my apps look and feel and function the same, no matter where they are running. Screw the OS vendors and their UI's - they change their frameworks so frequently and for no good reason other than to lock in the poor developer who thinks he has to learn their framework, or else not be competitive.
That may be true, but the real competition is in building an app that functions - and functions well - wherever you port it. To accomplish that, you've gotta be willing to be both an expert at the native framework, while also abandoning it ...
Game engines are a place where it makes sense to roll your own UI framework many times, so on that point I agree with you. The purpose of a game is generally immersion and escape, so makes sense to remove users from their device's UI in many instances. Game UIs tend to have their own conventions so frequent players don't have much of a learning curve. But in general players accept some learning curve because games are about taking on a challenge.
However, apps are not games. They're tools. And tools are not about giving your users challenges. They're about fulfilling a purpose as easily as possible. UI frameworks and conventions matter here because they lower the learning curve and cognitive switching cost, and they respect a user's preferences for how they wish to engage with their device (including valuable OS-wide capabilities like accessibility).
Companies that choose to use their own UI frameworks or avoid the platform's guidelines are doing so to the detriment of their user experience.
- Some do it accidentally, because they don't know the UX guidelines or subtleties of the platform
- Some do it for expedience, because they need to put out a product quickly with few resources
- Some do it strategically, because they want the user experience worse since it serves other purposes for them
Yes, UI frameworks change as OSes change, but it's rarely for 'no reason'. Stepping back, devices have gotten way more capable and their UX way more sophisticated... which does necessitate change. Though that's some extra work for developers, it's not about you. It's about your users.
There are so many aspects of modern UI that are not functional, and serve only to distinguish one platform from another in the wider market-place - so I feel that your statement that the OS-provided UI is a 'tool' is misguided. There is nothing tool-like about making me wait for a swipe scroll to complete - this is a game mechanic designed to entertain.
And in that sense, its quite possible to make a non-native UI that is more productive than the OS-provided UI - you merely have to take responsibility for the user experience, obviously.. So yes, its about the user. One reason for going non-native and rolling-your-own, is to ensure that your user has a positive experience, no matter what platform they are using - and this directly competes with the platform-vendors ability to woo new users with fancy, game-like, UI elements.
So I don't think this point is quite correct:
>Companies that choose to use their own UI frameworks or avoid the platform's guidelines are doing so to the detriment of their user experience.
Developers that choose to use their own UI framework win or lose on the basis of how responsible they are for making sure the user has a good time with their UI. This has nothing to do with whether the app is a game or a tool or whatever. Its a matter of competence.
Let me restate what you're saying to see if I understand it:
A product that looks the same across platforms is better than a product that adapts itself to the platform it is on, in part because platforms have a lot of UX that isn't good.
My argument for why its better to adapt a product to the platform is threefold:
1. Users have made the choice to use a particular platform and either like or at least tolerate that platform's approach to UX.
When in Rome.
2. Users are using many apps not just the one you made.
This is about scope. You can't just optimize your app in isolation, you have to take into consideration the entire scope of usage on a platform. It's certainly possible to create the perfect UX for a given set of tasks a user has to perform in an app, but drop that into a platform and its likely you've just added a huge learning curve and ongoing cognitive load.
3. Users mostly do not use your app on different platforms.
Users probably own either iOS or Android. If they own one, they aren't even aware of how the other one works. And on desktop, who cares because screen size and pointing device differences necessitate different UX anyway.
----
I think there are some instances where having the exact same UX on very different platforms is more ideal UX for the user, but only after it's acknowledged that a) its not just a proxy argument for being easier on the developer/designer, b) its not just the result of developer/company tunnel vision which leads to the assumption that users care about the app as much as the developer/company does, c) users actively want a different experience (e.g. immersive game), and/or d) users are moving more frequently between platforms than different apps on platforms (e.g. a business use case).
From a business perspective it's certainly fine to choose to use a cross-platform kit as there's many reasons to do so, I'm just arguing that it's not ideal for the user the majority of the time.
As far as whether platforms have not-good UX, I mostly disagree. I'd need to see examples of what you're talking about. If by swipe scroll you mean momentum scrolling I disagree. That has great utility on small screens to traverse large lists and it grounds the device in physical metaphors. It's a fantastic UX innovation.
I share your concern regarding text fields. That's the one area where I never want to mess with native behavior. The search results for "flutter ios text field copy paste" aren't encouraging.
These are all excellent points. I'm curious how Flutter stands to address these risks/issues in the early days.
I'd imagine it will take much more than 1.0 to get close to parity with the OS. Even if we assume it will always be 90% of the full OS experience (which is fine for the vast majority of use cases).
It helps that the Flutter and Android teams can talk to each other (they're both part of Google). So atleast for Android, you might be able to expect Android platform features appearing on Flutter in sync'd release cycles.
And in cases where you're using platform-specific feature that Flutter doesn't support yet, then your experience will be no different -- the burden remains on you to write platform-specific code.
Only one team needs to sync with another in this scenario.
It's also assuming that the Flutter team wouldn't consider do that considering they have that kind of information available to them -- it's in their best interest, after all.
If only one team needs to sync, how is it any advantage for Flutter and Android to be within the same company? How is the situation any different from Flutter and iOS?
I agree with the other commenter -- don’t expect any close cooperation between Flutter and Android because that’s just not how Google (and other huge companies) tends to work.
> "devs have yet another set of tech and tools they have to master. And I mean devs in the wide sense here, designers, coders, testers, etc. Some also have to become masters of how the framework and each host OS interact, in order to debug the inevitable problems."
Good product is a team effort. The question is: Can you find the right people - not just any people but the right people - to come on-board, use / learn the tools you've chosen, and make magic happen?
Sheer technical prowess of tools and/or people is not enough.
That aside, to your points, there are __always__ tradeoffs. Some more detrimental than others. But again, preserving is a function of team. Someone somewhere is doing what your team is doing, and doing it better. They have the same technologies. So then the question is: why.
These seem like valid concerns at first glance, but I feel these are not really issues in practice (only in theory).
>> - They inevitably don’t look or work like native apps in ways both big and small, frustrating and annoying users. (... the spell-checker doesn’t work right or text selection is janky or unavailable where it should be, certain short-cuts work differently or have different gestures or keys, etc.)
as `coldtea` points out below, this is not really an issue in today's ecosystem. Branding themes are more prevelant on most apps people are using than not.
>> they don’t get updates to native controls... e.g. if the OS adds some new drag-and-drop capability to text fields the framework doesn’t get it unless and until the framework is updated (and the app is updated to use the newer version of the framework). Of course, some things are never deemed important enough to be adopted by the framework.
If people are writing cross-platform apps and want to use new platform-specific features, wouldn't they have to write platform-specific code anyway if they were native? I'm not sure this is a newly introduced problem in any sense.
>> - Ambitious frameworks that really try to minimize the gaps between apps build with the framework vs native app grow to be very large. They take on the role of the entire app-facing OS API, which is truely massive in today’s systems. This leads to slow-loading/building, resource-hungry apps. Each app becomes a mini-OS unto itself.
I guess that's valid; but I'm curious about cases where code-heavy app sizes have actually hindered app downloads. I don't really know, but I haven't heard that this has been a big problem? For reference, a hello world flutter apk clocks in at 5 MB.
>> - there are cross-platform issues, like fonts that fit on one host OS get cut off in another, or differences in volume control etc.
Flutter renders all of its fonts itself natively, using the same way Chrome does it. Has this been a problem?
>> - dealing with the cross-platform issues the framework doesn’t solve becomes very difficult for the app developer. They’ve got to find a way in, through, or around the framework (in an area it already isn’t handling well).
>> - many potential third-party tools will have native support and bindings but most won’t make accommodations for your framework, so you end up having to support that yourself, or do without.
Is this a remark on an incomplete cross platform framework (i.e., flutter needs more features) and that it hasn't reached enough popular usage, or that cross platform frameworks have this problem? If not, it feels like the alternative to not using a cross platform framework is to write everything for each platform in a platform-specific way, which might be considered much worse. What's the issue at hand here?
>> - devs have yet another set of tech and tools they have to master. And I mean devs in the wide sense here, designers, coders, testers, etc. Some also have to become masters of how the framework and each host OS interact, in order to debug the inevitable problems.
This feels like an emotional assessment of having to learn something new. If this technology is meant to simplify/remove problems that people have today, then isn't it worth learning?
I guess you might feel this way if you felt that flutter isn't adding anything of value to other popular solutions today.
> as `coldtea` points out below, this is not really an issue in today's ecosystem. Branding themes are more prevelant on most apps people are using than not.
On iOS, the extent of "branding themes" end up is often limited.
> Flutter renders all of its fonts itself natively, using the same way Chrome does it. Has this been a problem?
There is no Chrome on iOS. So Flutter is different from everything else out there.
> Is this a remark on an incomplete cross platform framework (i.e., flutter needs more features) and that it hasn't reached enough popular usage, or that cross platform frameworks have this problem? If not, it feels like the alternative to not using a cross platform framework is to write everything for each platform in a platform-specific way, which might be considered much worse. What's the issue at hand here?
Flutter, and almost every other cross-platform framework, have this problem.
>... but I feel these are not really issues in practice (only in theory).
Ha, I wish! I've been down this road a few times and this list came from contemplating some of my old battle scars.
> ...as `coldtea` points out below, this is not really an issue in today's ecosystem.
That's not quite the same thing as it not being a problem. I know it can be done, but it's harder than when using native controls. This is something the "big dogs" can handle (they can bring massive resources to high-profile projects if need be) -- especially if they control the framework.
> ...cases where code-heavy app sizes have actually hindered app downloads...
Well, look around for people complaining about bloat. It's not usually the download itself, by the way. Memory is filled and runtimes have to initialize, buffers allocated, etc. It all takes time and uses runtime resources. This is fine to a point, but once you use too many resources or take too much time, it has a negative impact on the app (and as the developer, you have to deal with it in some way... e.g., perhaps spend time to alleviate the issues or perhaps walk away from lower-end devices). Any app, no matter the tech used to develop it can face these issues as it grows. But with an engine you start off closer to the limits and have less control over resource usage, so you generally reach them more quickly.
> Flutter renders all of its fonts itself natively, using the same way Chrome does it. Has this been a problem?
Hey, if flutter solves cross-platform text in 1.0 as you suggest, then good for them. Believe me, that's a massive accomplishment. (Though I'll note: if they aren't using native facilities, they'll have to duplicate them, which goes back to the point on bloat.)
> Is this a remark on an incomplete cross platform framework...?
No, I'm saying apps -- at some point -- generally eventually need to incorporate third-party libraries/tools to best accomplish their purpose. A PDF generator, a .csv parser, an image processor, an AI library, whatever. (A framework can't include an API for everything and shouldn't try, so it's not a matter of an incomplete framework). However whatever third-partly library you're interested in probably won't provide direct support for your framework, so you'll have to figure it out and do it yourself. It really depends on the library and the framework and how/whether they overlap how much harder this is.
E.g., suppose you want to incorporate an image rendering library of some sort into your app. The library supports iOS and Android and can output to UIImage on iOS and Bitmap on Android and their site provides samples showing how each of these work. But you're using a framework that has "XImage" and "XImageView". So now you need to delve into the platform's "XImage" to figure out how to load a UIImage into it on iOS and a Bitmap on Android. Maybe you find it works in terms of OpenGL textures and you realize going through a UIImage/Bitmap is an extra, inefficient step, so now you're learning about how to load directly from the library output into an OpenGL texture and you learn OpenGL textures can have different color formats so you start using the complicated low-level API of the image library to get output in the color format of the OpenGL texture. Whew! What would have been a few lines of code in each native app turned into a couple days of work, but you're done and release it.... and shortly thereafter, you start getting reports that the images are flipped on certain devices. Uh Oh... Now, maybe flutter doesn't have this particular problem, but this is just an example. This kind of thing will pop up as you integrate the third-party libraries you use with the UI platform. The more "opinionated" the UI platform is, the more quickly you'll run into these kinds of problems.
> This feels like an emotional assessment of having to learn something new.
Oh, come on. I'm pointing out an additional cost to adopting this kind of platform. That's a real concern to anyone developing apps, not something you can dismiss as an "emotional assessment" (Not sure even what that means -- laziness?). Note, this is an additional cost since you'll need native expertise in any case.
- They inevitably don’t look or work like native apps in ways both big and small, frustrating and annoying users. (... the spell-checker doesn’t work right or text selection is janky or unavailable where it should be, certain short-cuts work differently or have different gestures or keys, etc.)
- they don’t get updates to native controls... e.g. if the OS adds some new drag-and-drop capability to text fields the framework doesn’t get it unless and until the framework is updated (and the app is updated to use the newer version of the framework). Of course, some things are never deemed important enough to be adopted by the framework.
- Ambitious frameworks that really try to minimize the gaps between apps build with the framework vs native app grow to be very large. They take on the role of the entire app-facing OS API, which is truely massive in today’s systems. This leads to slow-loading/building, resource-hungry apps. Each app becomes a mini-OS unto itself.
- there are cross-platform issues, like fonts that fit on one host OS get cut off in another, or differences in volume control etc.
- dealing with the cross-platform issues the framework doesn’t solve becomes very difficult for the app developer. They’ve got to find a way in, through, or around the framework (in an area it already isn’t handling well).
- devs have yet another set of tech and tools they have to master. And I mean devs in the wide sense here, designers, coders, testers, etc. Some also have to become masters of how the framework and each host OS interact, in order to debug the inevitable problems.
- many potential third-party tools will have native support and bindings but most won’t make accommodations for your framework, so you end up having to support that yourself, or do without.
Building and maintaining an app twice is a very serious expense. But the expense of dealing with the issues with crosss-platform frameworks can be pretty big as well. Of course it depends on what you’re doing (shorter term and longer term) whether or not it makes sense. But go in with your eyes open. Consider other options (like examining your app architecture and see if you can’t find a way to factor some of your naturally cross-platform stuff into a shared library usable by the native apps of each platform you support).