Categories

Meta

KRunner, the framework, is the backend behind the ‘krunner’ UI, as well as being used for search operations within the Plasma shell. Backends (or ‘runners’) are written as plugins, which can come from a range of sources and loaded by both the plasmashell and krunner process.

This works fine for simple tasks like calculators, dictionaries and listing applications. However, if we want to search through data that’s available in an already running application, this approach isn’t ideal.

What’s changing

In addition to the current plugin structure, runners can have their results fetched from another process via DBus.

To work, apps supply a .desktop file with the DBus service name of a search provider. The apps then implements a couple of DBus methods to return a list of matches for a given search query, and another method called when a match is invoked. Depending on the situation, you might want to make this DBus-activatable, or just silently do nothing if the service is not running.

Example of a query being performed:

Results are presented identically.

Benefits:

Reduce code re-implementations

The original motivation for writing this was plasma-browser-integration writing a runner. Kai ended up writing both a DBus API on the client, and a runner to read from it. A common standard cuts that in half for any future apps wanting runners.

Memory saving

Instead of data being in 3 places: the app with the data, plasma shell and krunner, data is only stored in one place and then fetched by the two UIs.

Robustness

Plasma shell is a very core process. We want that to stay alive even if the included plugins fail. One of our more problematic runners was moved out of process to solve this in Plasma/5.11

Portability

By not being linked inside the same binary, we solve a lot of portability issues.

* I can make runners in python (example) or potentially any other language with no extra dependencies

* We’ll be able to handle the ineviatible Qt6 changeover in a few years without runners having to all be ported at the same time.

This was a big problem for KTp, which had the main USP of having tight Plasma integration. We caused a big problem for ourselves resulting in a rushed port.

* It’s a step towards next gen where more apps and services are sandboxed.

Conclusion

Hopefully this will improve Plasma and make it easier to write runners.

I hope to see runner support to kde-connect and search active konversation tabs. Personally, I’m already using the python support for custom code to talk to my home-automation server which had a python lib.

If this has inspired you to write a runner and documentation is unclear, ping me (d_ed) on #plasma.

Marco Martin recently posted about some of the improvements in krunner, today I want to show some of the effort into navigating the Plasma panels.

This video shows a user navigating the plasma panel using voice and keyboard. A shortcut focusses the panel, and then one can use tab and cursor keys as normal. In future we will improve our key-focus visual indicators, and allow for richer interaction.

What makes Plasma different to existing apps

Plasma in general has been a sore point with regards to accessibility as it doesn’t follow some of the exact same concepts as a traditional toolkit. Some of these convention breakages are by design, in krunner you wouldn’t want to have to tab to a list of results in order to navigate results with the cursor keys. Unfortunately these changes, if done non-optimally, really conflict with core concepts of focus and screen reader parsing. On top of that, we have the issues of an emerging toolkit, which needs that extra push to get right.

Why is this work useful?

Blind people aside, the work here has multiple other advantages.

We need better keyboard navigation, regardless. You often hear people say they prefer console apps; it’s not because they’re inherently better, but because being “handicapped” forces them to have good keyboard handling. We should be matching or beating that.

Also, approaching a large code base from a completely different angle has helped to tidy up some complex code that has built up over the years. Kickoff key handling is now not only better but the code is 2/3 the size.

Apps and window decoration to work across multiple screens at different DPI

Consistent mouse speed and input across monitors of different DPI

What we want to see:

What we need to render

How it works:

In order to have a normalised co-ordinate system between monitors and to support apps that can’t scale themselves the system is defined as follows:

* KWin pretends all monitors are ~96dpi and handles all communication and input co-ordinates as such. Final output is then scaled up if applicable

* Clients which support high DPI, when relevant, will provide a buffer (the picture of their contents) which is twice the resolution of their window size.

This covers all the different scenarios:

If we have a 1x window on a 2x screen, the compositor will draw the window twice the size.

If we have a 2x window on a 1x screen, the window contents will be drawn implicitly downsized.

If we have a 2x window on a 2x screen, the window will be drawn twice the size, but because it’s at twice the resolution, we end up painting the contents at the native resolution.

Clients without scaling now work as intended, I can use ardour or xfig on my high DPI screen and can read and interact with it normally (albeit obviously at standard resolution)

The mouse even moves at a consistent speed across monitors and even if you had two touch screens at different DPI showing the same content, both will work perfectly.

The changes to kwin were therefore really small, and mostly was not about implementing features but more about removing an assumed coupling between a texture size and the rendered size.

FAQ

When?

The code to do all of this is in Plasma 5.10 as a hidden feature whilst we get more testing with everything except a UI to configure it. This is ready to land for 5.11 An extra problem is that Qt < 5.9 has a bug if the screen scale changes dynamically.

What’s left?

Using this technique means everything is at the right size, but some adjustments are needed to make sure everything appears at native DPI not normal DPI. This is something being fixed over time.

What about fractional scaling?

The wayland protocol specifies a scaling in integers. We can’t really go against the protocol. However, there’s absolutely nothing against kwin scaling to a different amount to the protocol. It’s something we can expand on later.

Binding loops suck, and they can be hard to fix. I wrote a tool that prints a backtrace of the bindings being updated when a loop occurs. See link at bottom.

About:

QML bindings are a very fast and easy way to write a declarative UI. However it’s quite easy to accidentally write an infinite loop.
This can happen if we bind propertyA to affect propertyB and also bind propertyB to affect propertyA, they would constantly update each other.

The Rectangle width changes on startup, that changes the text’s size, which in turn changes the Rectangle’s width. If this was undetected the application would loop forever and eventually crash.
QML prints a warning, and ceases processing, but it’s an indication that something is wrong with the logic of your code, and it needs fixing.

However, whilst the loop here is obvious to spot, it can be considerably more complicated when looping through tens of bindings over many many components.

Creating a Tool

The problem with this warning is that on its own is rather unhelpful – trying to find the loop then becomes a manual task of tracing all possible combinations through every bindings that could lead to a short circuit. GDB on its own doesn’t help as the C++ backtrace tells us absolutely nothing we can use.

I’ve created a small script that, using gdb, unwinds the backtrace detecting where the properties changed and then showing the QML code which is responsible.

The Randa meeting starts this week, and I’ll be working with the KDE multi-platform group, being led by Aleix Pol, and will be spending my time working on both flatpak (formerly xdg-app) and Snappy.

During this past week I have been brought into some technical discussions about deployment on both platforms; so I intend to spend my time working closely with other interested developers solving problems that affect either platform as there is a lot of overlap. Tackling these independently doesn’t make sense.

These two emerging technologies both have a lot of potential to revolutionise Linux packaging and distribution with either being a huge boost over the current state.
Both are going to become relevant in the Linux world over the next few years, and the important thing is making sure our software works best for our users whatever the platform.

So far over this week I’ve spent some time fixing KDE flatpak applications, in particular fixing multiple problems we’ve encountered with Dolphin; namely being able to load plugins and making kio slaves work.

In the meantime I’ve been testing out packaging some Snappy apps, packaging and running a few applications.

Over the week I’ll write some more in depth blog posts, exploring the state of each, where we have problems deploying our apps, and hopefully some concrete solutions 🙂

Be sure to sponsor the sprint to help pay for developers from around the world to come together to work on important projects and be sure to follow PlanetKDE for blog posts about software developments from the people here.

Since Plasma 5, the main shell is powered by QtQuick, which till now brings a requirement on a working OpenGL setup. This causes problems for Plasma in situations where we can’t run OpenGL; either extremely cheap hardware, xrdc or when a user upgrades and breaks their nvidia setup (a seemingly common occurence).

Qt 5.6 brings a new module which opens some interesting possibilities; the QtQuick 2D renderer, which avoids that.
This has existed for a while, but it has only recently been open sourced as GPL3.

QtQuick Internals

Each graphical item updates a tree containing nodes containing either transformations or content. That content being either a rectangle, a picture or a custom openGL shader from the application. The important part is that it stores a tree of items in an way optimised for rendering, but also acts somewhat as an layer between any QtQuick component and the underlying OpenGL renderer.

Using the QtQuick 2D renderer

The QtQuick 2D renderer still uses the same scenegraph, so all custom QQuickItem’s which use the standard QtQuick SceneGraph nodes still work, but instead of calling OpenGL functions, calls are mapped to a raster backend instead.

The Result

My personal desktop, running Plasma using the QtQuick 2D renderer. The screenshot shows some of the parts working, but also highlights some of the bugs

Performance is surprisingly fast, not faster than the OpenGL backend, but plasmashell still remains perfectly usable on my desktop.

Most of the basic scene graph nodes have a 2d renderer implementation, however any node that does custom openGL, such as QtGraphicalEffects or certain parts of Plasma, will simply fail.

What’s broken

There are plenty of known limitations with using the 2D renderer, some cosmetic, some more fundametnal.
Qt provides their own list.

In terms of Plasma, the list of broken items are:

We have our own GL check in the shell that needs adapting

Icons were broken. We implemented our own shader whilst animating between states rather than uploading a new pixmap per frame. I fixed this by simply turning that off.

Our load monitor plasmoids are pure GL. I’ve made a patch that makes it not crash. Making it actually work would mean having two implementations…which isn’t a route I really want to go down.

Widget explorer is broken, again we have our own shader for some effects

We are missing a lot of minor graphical effects. Fewer shadows and alike, but that’s a hit I think we will just have to accept

Summary

In general it seems that with a relatively small amount of work this might be a valid option for users without working openGL.

It will always be a second class citizen, but it should be do-able to support without hindering progress for the vast majority of users.

What’s interesting is to see how easy it is to support a different scene graph backend, as it is a clear indication of what we will encounter when it comes to Vulcan in a few years time.

As we saw neon, a new and fresh Linux distribution was launched last week. This project is incubated by the KDE Community, sharing KDE’s hosting and community. Hopefully we’ll see neon flourish into an awesome distribution over time.

However, I have seen some potential confusion in an article reaching a conclusion that this might be in some way problematic for other distributions to deploy KDE software. To make sure we’re all on the same page I wanted to give a clarifying statement from the Plasma mantainer.

Plasma is and remains distro-agnostic. It’s in our interest to help all of our distribution channels. As long as distributions continue to keep up with the dependencies we need and work well with us, we support everyone as best as we can.

One of the new features coming to Frameworks 5.15 is my new widget KCollapsibleGroupBox.

Acting like QGroupBox it allows you to hide some of the more advanced options out the way till the user expands the header revealing the rest. A common web pattern, but lacking in Qt or KF5.

Good for making a long list of pages navigable or hiding features that only a small fraction of users will find useful.

simple by default, powerful when needed

Handy, but mundane. Why the blog post?

There’s no point in writing a new class in a library if no-one knows about it.

Also I wanted to highlight two more interesting topics:

Working with the VDG

The main reason I wrote it was because every mockup given to me to by the VDG, especially from the usability expert Heiko Tietze, invariably featured this widget somewhere.

Our resources need to match what’s being requested from our design team as described by Thomas in his recent blog post.

Bringing our QWidget library forwards

Another important aspect that’s worth broadcasting is how we’re still moving our QWidget libraries forwards. Whilst there’s talk about them being outdated or replaced, that’s really not the case; and still definitely the best candidate for building any serious desktop application.

This isn’t the only new change; there’s still a lot of areas that can and should be improved to modernise our platforms for the current set of applications.