The Wayback Machine - https://web.archive.org/web/20130517213432/http://mikhas.posterous.com/tag/maliit

Thoughts 'n Stuff

Maliit Status Update

We’ve been busy! The result is our latest release, Maliit 0.99, with a massive amount of changes. While the framework has mostly seen code cleanups (:~/source/maliit/fw$ git diff 0.94.0..0.99.0 --stat: 389 files changed, 3612 insertions(+), 30081 deletions(-)), we’ve been adding tons of features to the reference plugins (:~/source/maliit/plugins$ git diff 0.94.0..0.99.0 --stat: 324 files changed, 32499 insertions(+), 12799 deletions(-)).

After (finally!) getting official Debian and Ubuntu packages, the next big step is our Maliit 1.0 release, which we expect sometime later this year.

Maliit 0.99 works with applications using GTK+2/3 or Qt4/5, though Qt4 still works best. Maliit’s framework and reference plugins strictly require Qt5 as build dependency, allowing us to get rid of Qt4 and Xlib legacy code. Maliit can run on Wayland but at this point only EFL applications support Wayland input methods. For Qt5 applications wanting to use Maliit together with Wayland, a Qt5 platform plugin for Wayland input methods would be needed.

Who is using Maliit?

The best Maliit showcase is still the Nokia N9. No other device got anywhere near to the demonstrated input method integration level. The haptic feedback of its virtual keyboard remains unchallenged. I think it’s a major success for our old Harmattan text input method team that we see Maliit being used in other projects. It was hard work to get to this point and yet it feels as if this was only the beginning of Maliit as an open-source project.

We have the friendly folks beind the OLPC project who were one of the first to go with Maliit. Few of us will probably make the new XO their primary device and therefore, won’t see the results of the collaboration. But from the very beginning, they worked with us in the open, provided official Fedora packages and helped us test-driving the then-new styling engine of Maliit Keyboard. The XO is one of the use-cases where Maliit has to run without a compositing window manager, which made them an early adopter of our windowed mode.

Plasma Active is another project that — for its size — invested significant development time improving and testing Maliit’s reference plugins. They’ve been (and hopefully remain!) a huge help whenever we faced problems with QML. I wish we could find a sponsor however to work on improving their input method integration, which is the “invisible” and challenging part that easily gets forgotten.

Ubuntu Touch is choosing Maliit as well. Canonical sponsored significant work in Maliit Keyboard, especially in terms of Qt5 support and replacing QGraphicsView with QtQuick2.

SailfishOS is happy user of Maliit, too. They are the main consumers of our 0.80 branches that still offer full support for Qt4 and X11. We always considered 0.80 our latest “stable” release branch, so it’s good to know that at least someone is also using it.

OpenEmbedded has integrated Maliit into their meta layer. This makes it easier to build custom Linux distros for embedded with Maliit on board. My understanding of OpenEmbedded is still limited at this point so I cannot explain all the real benefits this collaboration provides. Luckily there’s the always friendly Samuel Stritzel who’s following our official mailing list, waiting to answer all your OpenEmbedded related questions.

Gnome3. Just kidding. But once Gnome3 properly integrates with Wayland input methods, we can just plug in Maliit, too. Of course to be of any interest for Gnome3, we need to demonstrate working CJK input methods too. Luckily, we got the opportunity to just do that: IBus working with Wayland input methods. If things pan out I’ll be talking about this at GNOME.Asia.

I would like to get the chance to improve input method support for Firefox and Chrome/Chromium. There is one nasty bug around password fields that’s been quite a blocker for us. Some day, we’ll hopefully be able to convince the browser guys to just “do the right thing”.

And then there’s yours project of course. You just didn’t tell me about it yet ;–)

Architecture

There is an influx of new developers showing interest in Maliit which is why I feel that reiterating the basic architecture behind Maliit doesn’t hurt.

Maliit is split into three parts: framework, reference plugins and input method modules (GTK+, Qt4, Qt5).

The framework provides maliit-server, a process that can load reference plugins (such as VKBs) and allows applications to connect to it through input method modules. The input method modules are UI toolkit specific and are loaded dynamically by the applications. For each UI toolkit Maliit wishes to support, a separate input method module is required.

Input method modules and framework are designed as client-server architecture, with applications behaving as clients. The default IPC is QDBus but it can be replaced by other mechanisms, for instance the Wayland IPC.

In a follow-up blog post I will provide an outlook of where Maliit goes next and which parts of it we might have to rethink, now that the leviathan of Linux DEs is quickly moving towards Wayland.

People

Those are the people who have contributed to Maliit, but you wouldn’t know if you only checked commit messages:

  • Łukasz Zemczak, Thomas Möricke and Kevin Wright: You guys have been great. Would work together again.
  • Iain Lane, Michał Zajac, Peter Robinson: Without you, we still wouldn’t have proper Debian/(K)Ubuntu/Fedora packaging. Thanks!
  • Samuel Stritzel: Thanks for bringing Maliit to OpenEmbedded! Hopefully we’ll see more use of your work soon.
  • Simon Schampijer, Daniel Drake, Gary Martin, Jennifer Amaya and Martin Langhoff: Thanks for the opportunity to work on OLPC. I know most of us are not in the target audience which makes it hard for you guys to motivate others to help you. Your work is important, please never give up.
  • Pekka Vuorela: I am just glad to have you back in the team. Maliit just isn’t the same without you.
  • Aaron Seigo, Marco Martin: Thanks for all your enthusiasm about Maliit and Plasma Active. Your motivation is infectious.
  • Jan Arne Petersen, Krzesimir Nowak: I am impressed by your motivation and dedication that you still have for input methods, even though none of us ever planned to become an “input method expert”.
Filed under  //   Gnome   Input methods   Maliit   Openismus   Qt  
Posted April 2, 2013

Concrete problems and generic solutions

Maliit-gnome-vkb-comparison
For the Maliit Keyboard, we need the ability to style it for different form factors. As our focus is mostly on mobile devices (where the form factor is known), we got away with pixel-based styling that — while being resolution dependent — makes it easy to place and size the buttons in exactly the way needed. It’s what designers call pixel perfect, and the difference can be very noticable. Let’s take a look at the comparing screenshot, with the Gnome3 virtual keyboard on top (taken from the 3.2 release notes) and the Gnome3-styled Maliit Keyboard at the bottom (video). The former uses a generic layout engine and generic styling, whereas the latter allows to style pixel-perfect layouts.

For the official Gnome3 virtual keyboard, one can notice how the space bar is strangely sized, how the regular keys are unpleasantly square and how the enter and backspace keys are way too small. They all use the same graphical asset. For the Gnome3 styled Maliit Keyboad, the letters d-j, x-n, together with the space bar and its neighboring keys, form a neatly aligned center area, with a staircase pattern to each side of the keyboard. If you look in the last row, you will notice that the space bar is just a few pixels too large. This happens because the only non-pixel-perfect elements in the Maliit Keyboard are stretched keys and spacer elements, and I somehow still compute their width incorrectly. From a designer perspective, that “pixel bug” in the layout destroys the immersion of an otherwise good design. Pixel perfectness — whilst having a poor reputation among us developers perhaps — is actually quite a challenge to get right!

Maliit Keyboard is a reimplementation of the MeeGo Keyboard that was shipped on the Nokia N9. It doesn’t share any code with it, but it does reuse the ideas and the XML layout files. The format for the layout files evolved from programmer-friendly to designer-friendly over time, which I think was a good change. Instead of using the complex and pretty generic styling system of libmeegotouch (which was intended to fit the needs of any mobile application), I use a concrete style class that reads a styling profile folder, looks into into the two INI files (one for the main keyboard area, one for the extended keys) and fills a model with style attributes. In the given context of virtual keyboard styling, the concrete solution offers the same flexibility as the generic solution but comes with a fraction of the implementation complexity and remains simple to extend. This is because the concrete solution fits the intended use-case perfectly, whereas a generic solution will always acrue overhead.

The trade-off, of course, is that for a new use-case, I’d probably have to write a new style class and create new style attributes. It is very unlikely, however, that the styling requirements of a fairly specific “application” would fit the the styling requirements of a regular application, so why burden myself with a generic enough abstraction that I will never use? Inversely, why try to make a generic solution fit a specialised problem? Jokingly, that’s precisely what I call Java programming: Instead of solving the problem at hand, write a framework that can solve all similar problems. I have started to grow a strong aversion against that, not because I like reinventing the wheel (I don’t), but because I think that understanding the concepts behind an idea is far more valuable than clinching to an implementation of it.

For the Maliit Keyboard, I took the concepts of the libmeegotouch styling system and mixed my understanding of CSS with the XML layout files. The result feels pretty clean and easy to use, but that’s because I based the implementation on well-understood concepts, not because of the implementation itself. Who knows, if I keep myself busy with implementing virtual keyboards for just a bit longer, I should eventually be able to write a pretty decent book about VKB design patterns ;–)

Filed under  //   Design patterns   Gnome   Input methods   Maliit   Openismus  
Posted June 19, 2012

Multi word ribbon UI for Maliit (video)

Motivated by the new Blackberry 10 virtual keyboard, I decided to spent a couple of hours on a proof of concept, this video being the result.

I had to hack the Presage engine a bit to provide word prediction in a similar fashion to what you see in the 2-3 seconds of the Blackberry video. Then I added some space between the rows of the keyboard, so that I could place additional word ribbons there. The word candidates appear next to their starting letters, though it’s only one candidate per letter. I need to find a better solution here, but then again Blackberry guys also haven’t solved it either ;–) Tapping on the word candidates inserts then into the text editor (no gestures, for now).

The code is very hackish, certainly nothing I would publish. I am going to put it onto a tablet so that I can show it around to you guys at the TiZen Developer Conference or the Ubuntu Developer Summit.

Jon is going to bring a camcorder on Sunday, so perhaps we can actually record a real, youtube-worthy video then.

Filed under  //   Blackberry   Input methods   Maliit   Presage   TiZen   Ubuntu  
Posted May 4, 2012

Maliit Keyboard now with word prediction and error correction (video)

This is a feature that I personally wanted for a long time. Interrupted by FOSDEM, some Wayland research and many other things, I finally managed to get word prediction and error correction beyond prototype quality. The video shows just how amazingly good the Presage word prediction can be, even without extensive training (in fact, for the video we used the minimal language model training that comes with a regular Presage installation). The second part of the video shows how combining Presage with a spellchecker such as Hunspell further improves the provided word candidates.

Presage uses a very scalable approach called text n-grams. There is a lot of research in that area, but language models of contemporary language usage are either well guarded or cannot be freely distributed. Luckily, Presage comes with training tools such as text2ngram. Users can feed arbitrary language corpora to it, though one should be careful to perhaps not mix different languages too much.

Matteo Vescovi, the author of Presage (formerly known as Soothsayer), started the work as part of his master thesis a couple of years ago. The heart of Presage are the different predictors. They can be queried in parallel and the result lists are merged, using probability analysis.

Presage certainly has a lot of potential. It comes with an easy to use C++ API but also provides bindings for C and Python. In fact, it even provides a D-Bus API, which would make it possible to run it as a system service. The user could then benefit from (and train!) the same language models from different applications.

Hunspell probably doesn’t need much introduction. It is used in many Linux desktops. It’s a fine library and comes with many dictionaries. However, one should be aware that Hunspell itself cannot provide word prediction, which is why it wasn’t enough for mobile text input. As a fallback for Presage, it works very well though.

Of course there are a couple of things we could do from here. As Jon mentioned in the video, the virtual keyboard’s word ribbon UI could host word suggestions from other applications, such as the Google search in the browser. For Unity’s dasher input or Gnome Shell’s search, the application names could be shown instead. Or we could hook it up to Bash completion.

PS: Anyone up to package Presage for Fremantle or Nemo? It could be pretty interesting to see the next release of Maliit running on the N900.

Filed under  //   Hunspell   Input methods   Maemo   Maliit   Openismus   Presage  

Getting rejected as GSoC organization

Last week I submitted an application on behalf of the Maliit project to participate in this year’s Google Summer of Code, as a mentoring organization. Today I got the rejection mail in my inbox.

Maybe I am too European to understand this, but what I find disappointing is the lack of any reason given in that e-mail, other than that too many applications were received. I mean, how am I supposed to learn from that? How will I know whether a project like Maliit has any chance at all, or whether I should even try to submit a project next year? Even for the list of accepted organizations, such as KDE or GNOME (of which both are pretty much doing the same stuff, so why do we need both here?) no reasons are given of why they were accepted.

Having had a bad experience with opaque decision making in the MeeGo project, this tastes just as bad. Sure, not giving reasons so that you don’t have to argue about them later on has apparently become a standard procedure, but I am not willing to accept such behaviour. After all, I also spend time in writing the proposal, and I find it disrespectful to only receive an empty, canned response.

If you are on the other side of a similar process, be it for a conference or because you work in the HR department of a company, please do think about whether it’s really too much to ask for the extra five minutes it takes to provide the reasoning behind your decision, and whether you would like to be treated the same way as you treat others.

Google can certainly do less evil than that.

PS: This blog post about the rejected WordPress project mentions a follow-up meeting, but I was unable to find any concrete information on the GSoC website.

PPS: On the list of accepted organizations, you’ll find entries such as “Name: Pidgin, Finch, and libpurple. Tags: pidgin, finch, libpurple, instant messaging, im, networking, gtk, glib, c, amazing, awesome, a+++++ would do business with again, space mice, team edward” (emphasis mine) – is that supposed to be taken seriously? Or shall I conclude that the submissions are not thoroughly reviewed?

Update: There are some who try hard to misread what I wrote. I think I should clarify what a successful application as a GSoC organization means.

You will:

  • spend a lot of time mentoring students during your typical holiday and travel season;
  • not get paid for that (the students will); (update: mentors get 500USD, thanks to lucianafujii for pointing that out)
  • receive a GSoC T-Shirt;
  • be invited to the Googleplex later the year (you will usually have to take extra holiday for that though, so there goes more of your spare time, if you accept the invite);
  • increase the visibility of your project.

Heavily simplified, GSoC consists of one entity providing the money, another entity providing time and a third entity consuming both. There’s also a big deal of knowledge transfer happening between the entities, but the flow is less clear than for time and money.

However, my point is: I would have been part of the time spending entity and without that entity, GSoC simply does not happen. So think again before you essentially reduce me to a loudly complaining free-rider who should STFU and get over himself.

Filed under  //   GSoC   Gnome   Google   KDE   Maliit  

Designing an input method system for Wayland

As mentioned before, Jon and I met with Kristian Høgsberg and Peter Hutterer during FOSDEM 2012. The discussion quickly revolved around Wayland and input methods. Kristian and I basically picked up from where we left after the Qt Contributor Summit last year in Berlin.

Right now, there is no explicit input method support in Wayland, and it’s the responsibility of the applications to provide such. But we came to the conclusion that moving it into Wayland provides several benefits.

That is why I spent some time during February to write down an initial design proposal, using the two years of experience from working in the application framework team for the Nokia N9. It has gotten longer than expected, but hopefully it is structured well enough to still be accessible.

From the introduction:

Currently, Wayland has no explicit text input method support and relies entirely on toolkit-specific or platform-specific solutions. This is awkward for platforms that support multiple toolkits. The resulting fragmentation and re-implementation would make it hard to attract developers of high-quality text input methods. These developers would generally prefer a unified architecture that lets them ignore application-specific or platform-specific details. This would let them simultaneously target all platforms that support Wayland.

We believe this goal can be reached by adding two new Wayland protocols, of which only one requires adaptation by toolkit providers.

The idea is not new, XIM has been around since the dawn of time. Because of the protocol’s daunting complexity, it apparently never became popular among application toolkit providers. That is why I decided to split up the envisioned Wayland input method protocol up into two:

  • The Wayland text protocol, to be used between the Wayland compositor and its clients. It tries to keep input method knowledge to a minimum and therefore can be used for any kind of (hardware) input that results in text input.
  • The Wayland input method protocol, to be used between the Wayland compositor and the input method system, which can either run as a stand-alone process or inside the compositor process.

In the proposal, I explain my ideal solution where applications and input method system are completely separated from each other and where the compositor acts as a mediator between them. I continue with alternative solutions that are feasible but have several drawbacks. Towards the end, there is a comparison matrix that features all discussed solutions.

There is an important aspect though: The alternative solutions provide an iterative implementation approach to reach the ideal solution. The obvious idea here is that already in early stages, we get testable prototypes. The solutions with a compositor-hosted input method system for instance allow others to think about window management policies that take input methods into account, whereas I could continue my iterations towards the ideal solution.

Anyhow, the next steps are now to discuss the proposal in a wider public (feedback from developers of exotic input methods especially welcome!), possibly also at upcoming conferences, and to come up with a prototype implementation so that we can iron out protocol bugs.

I would probably target Qt 5 as the first application toolkit to support the Wayland text protocol, followed by GTK+ and perhaps Enlightment. One also needs to take the popular desktop shells into account, such as Gnome Shell, Unity and Plasma Active.

Maliit could fill the role of a reference input method system, but we should have at least one more implementation, at some stage (IBus comes to mind, naturally).

Looks as if this could keep me busy for the better part of 2012, but it would be great if we could get at least the Wayland text protocol into Wayland 1.0. It’ll require some luck though.

Filed under  //   Gnome   Input methods   Maliit   Openismus   Qt   Wayland  
Posted March 5, 2012

Maliit as your remote control (video)

There is seemingly a trend (in ideas) to use your mobile device as a remote control for stationary devices such as your TV.

We thought that experimental support for remote text input should be easy to add to Maliit, as it already comes with a server-client architecture. As soon as client and server can run on different host machines, we’d have network transparency and it should basically just work. Luckily, we use D-Bus as our IPC, and it turns out that D-Bus understands remote host addresses. If you check the README in maliit-framework you will recognize that – with the latest release (0.90.0) – it only takes an additional environment variable, MALIIT_SERVER_ADDRESS, to connect a client (that is, an application that uses the Maliit input context) to the input method server. The scary part is perhaps that one has to disable D-Bus authentication. Therefore it's a good idea to only use this inside a trusted network.

Jon created a video which demonstrates the new feature in a better way, using a laptop that is connected to a projector as a TV replacement. The great thing about this feature is that it requires no changes to the applications, nor to the Maliit input method plug-ins, it’s the framework that handles this internally (or not so internally, now that Qt 5 turned our D-Bus API into a public one).

However, to make Maliit truly useful as a remote control, at least two additional features are required:

  • Have a proxy text editor widget on mobile device that allows text interactions such as copy and paste, cursor positioning and rich text formatting.
  • Emulate and transmit mouse or touch events, possibly through a dedicated touch area on the touch screen of the mobile device.

The second feature requires an extension to the Maliit protocol, whereas the first is already filed as bug MALIIT#84. After that, I could use my N9 (or my N900, as Maliit also runs there) to remote control my Gnome or Ubuntu Unity desktop, which would work perfectly for my movie watching habits. Kudos goes to Krzesimir and Jon for their work on this feature.

Filed under  //   Gnome   Input methods   Maemo   Maliit   N9   N900   Nokia   Openismus   Qt   Ubuntu  
Posted March 5, 2012

FOSDEM 2012

FOSDEM is only real with Belgian Waffles FOSDEM in 2012 was an exciting (and naturally, exhaustive) conference again. It's great to have so many relevant people who are all active in the free software world together in one place. It's also a great opportunity to discuss radical new ideas, ideally while experimenting with Belgium beer. Which is what we usually did when we weren't at the conference site.

It was nice to see Jarno and Esko at the conference, too. We even stayed in the same hotel. I hope they enjoyed the Ethiopian lunch as much as I did. And perhaps they're not too angry any more that we lead them to drink Absinthe ;-)

Jon and I gave two talks. Jon's talk (slides) was about Maliit as a project, explaining what Maliit is (and what it is not), combined with a short history lesson about the project. I tried to outline the difficulties of mobile text input in general (slides), picking some use-cases that are known from the desktop world and showing why simply copying the use-cases and their known interaction models does not work very well. I honestly liked Jon's talk more though.

Neither of us two actually managed to visit other talks, even though we wanted to. We had to ask Jarno, Esko and others about what great talks we missed. Apparently there were quite a few :-(

Our Maliit T-Shirts were well received, though we usually only handed them out when someone listened to our Maliit ramblings long enough.

We were asked about accessibility several times, which is currently not within the scope of Maliit but perhaps something to think about in the future.

We also got to talk with the people working on (text) input in Redhat and Intel, mostly in the context of Wayland. There are some interesting opportunities to get things (more) right this time around.

Thanks to our employer, Openismus, for sending us there!

Filed under  //   Brussels   FOSDEM   Input methods   Maliit   Openismus  

How we enable others to write 3rd party plugins with Maliit

We finally published a video about Maliit - an input method framework including a virtual keyboard - and 3rd party plugins. Kudos goes to Jon for making time for that.

This video highlights one of Maliit's key features: pluggable input methods which come with their very own user interfaces. The Chinese input methods show how Maliit offers support for composed characters. The video is proof that 3rd party development for Maliit (open-source and proprietary) is not only possible but also happening.

maliit.org states that "it should be easy to customize existing input methods or develop powerful new input methods, whether for profit, research or fun", we actually mean it.

The harder question is of course how to motivate others to actually get started on input method development with Maliit. For that, we have a multipronged strategy:

  1. Provide sufficiently polished reference plugins that can show off Maliit capabilities but also serve as inspiration for new plugins (hence the BSD license for reference plugins). Our reference plugins are currently using Qt/C++ (Maliit Keyboard) and QML (Nemo Keyboard). We also have PySide support, but no one contributed a reference plugin yet. This gives choice to interested input method developers, and we think that's important. The reference plugins serve another role when it comes to designing new API: They become our testbed, allowing us to verify our API proposals.

  2. Ship Maliit with a bunch of example plugins and example applications. None of them try to be complete. They are all self-contained though and usually show one feature at a time. This can be tedious to maintain, but we believe that examples need to stay small and focused, otherwise developers won't look at them.

  3. Documentation that is easy to consume. Our documentation is not as concise and clear as we'd like it to be, but it's slowly improving. We also experiment with videos that can serve as an introduction to more in-depth (text) documentation.

  4. Packages for most common Linux distributions. This one seems obvious, but sadly, it's quite a lot of work for us to keep up with it (and we already use automated services such as Launchpad and OpenSuse Build Service). In the hope to attract dedicated packagers we wrote down some packaging guidelines

  5. An architecture that had 3rd party plugins and multiple toolkit support in mind from the start. The plugin developer facing API needs to be easy to use and clearly documented. This will be the focus of the upcoming 0.9x series.

We will demo Maliit @ FOSDEM 2012, hope to see you there!

Filed under  //   C++   Debian packaging   Documentation   FOSDEM   Fedora packaging   Input methods   Maliit   Nemo   OpenSuse Build Service   Openismus   QML   Qt  

Into the Wild

We kicked off the new 0.81 release series together with a nice announcement: We have our own bugtracker now!

This means that Maliit has a near complete project infrastructure, all available under *.maliit.org, and all that thanks to Karsten, the always professional and very experienced hostmaster here at Openismus.

There is one more thing that we need (as demonstrated by me when I made my first broken release), and that's a simple build bot setup for continuous integration. Right now, we still rely on Nokia's infrastructure. I am confident that buildbot will fit all of our requirements, as long as it is trivial to maintain.

I am also happy that we improved our documentation significantly, thanks to Dave. He translated the important documentation bits into proper English and made it more accessible, demonstrating his doxygen skills. As a bonus, he also updated the project's README files, something we had neglected for a long time.

Future development

Regarding the Maliit development, I think we have simplified things a lot. D-Bus activation for the Maliit server (which finally means one server instance per user session) and the new support for plain QML plugins makes it almost trivial to get started with Maliit. We also let go of the critically acclaimed MeeGo Keyboard in Maliit upstream, which made me a bit sad of course.

Still, it probably was the right decision: MeeGo Keyboard is heavily fine-tuned for Nokia's N9 and it has some dependencies that are hard to satisfy outside of Harmattan. Over time, with ever changing requirements, the code has naturally evolved into a rather complex design. The result, however, is a very polished product, and ultimately, that's the only thing that matters (even though many opensource developers will disagree, strangely enough). Everyone in the team is proud of what we have achieved.

At the same time, I can understand how new contributors will be put off by all the complexity. So Maliit upstream will instead focus on the very basic but almost trivial to build Maliit Keyboard. For new contributors, that's a good thing. For us, it means the possibility to fix shortcomings in the plugin API. This is important, as one of our main goals has always been to enable others to write great input method plugins for Maliit, which will then run on any platform that Maliit supports. The Swype VKB plugin and the Japanese VKB plugin for example both demonstrate that we are on a good way, but I think we can do better.

Maliit itself still needs a good reference plugin, of course, even if only as a showcase (though I want it to be more). All this doesn't mean that MeeGo Keyboard goes away; its development will continue in the MeeGo Touch repositories, just as before (effectively degraded as just another Maliit plugin). But what we can take over, hopefully, is our experience when it comes to creating one of the best virtual keyboards currently available.

Filed under  //   Documentation   Input methods   Maliit   N9   Nokia   Openismus