All posts by Dominik

Dominik is a PhD student at the Control Theory and Robotics Lab, TU Darmstadt, as part of the Research Training Group GKMM (GRK1362). My research focuses on state estimation in distributed systems. As hobby, I contribute to the KDE project and work on the Kate application and editor component.

Kate in 4.12

Since the KDE SC 4.12 release a month ago, it’s about time to look at the changes of Kate in 4.12:

What comes next?

Kate will get more polishing in the next 4.x releases, for instance, in KDE SC 4.13 Kate optionally supports animated bracket matching.

However, as already mentioned in Kate in 4.11the main efforts are put into making Kate on Qt5 and Frameworks 5 rock solid. Already now Kate, KWrite and Kate Part are fully ported, i.e. all are free of KDE4support libraries. A preview (already one month old!) can be found here.

Besides that, Kate and KDevelop again join forces and there is a developer meeting from 18th to 25th of January 2014. So expect quite some blogs about Kate on 5 then!

Current State of Kate on 5

Just a quick update on the frameworks 5 port: KTextEditor,  Kate Part and KWrite build and run. Kate is not yet ported and does not compile. These changes were already committed:

  • made KTE::Cursor and KTE::Range non-virtual for maximum speed
  • removed KTE::EditorChooser, since Kate Part is the only implementation since over 10 years. Just use KTE::Editor* editor = KTE::editor(); to get KatePart.
  • new signal KTE::Document::readWriteChanged()
  • removed KTE::LoadSaveFilterCheckPlugin, was unused since years
  • removed all KTE::Smart* classes in favor of KTE::Moving* classes
  • merged KTE::CoordinatesToCursorInterface into KTE::View
  • new: KTE::Range KTE::Document::wordRangeAt(KTE::Cursor)
  • new: QString KTE::Document::wordAt(KTE::Cursor)
  • new: KTE::DocumentCursor
  • ported lots of KSharedPtr to QSharedData
  • updated Mainpage.dox to reflect porting notes
  • some small interface cleanups and additions

Please feel free to join the porting fun. Just follow the Frameworks compile guide and checkout the git branch “frameworks” in the Kate git module.

Kate: “C++/boost Style” Indenter

Greetings from the Kate land again. This time, Alex Turbov will spend a few words about his “C++/boost Style” indenter that is part of Kate Part for several releases.

The Initial Motivation

This indenter (initially) was designed to help code typing in a “boost::mpl” style (i.e. with leading comma in formatted (template) parameters list). One may read the rationale of such approach in the “C++ Template Metaprogramming: Concepts, Tools, and Techniques from Boost and Beyond” by David Abrahams and Aleksey Gurtovoy. It is really easy to miss a comma when invoke metafunctions and it usually leads to a lot of complicated compile errors. The indenting technique should help to visualize the control syntax and prevent stupid errors like missed commas.

Small example:

typedef typename boost::mpl::fold<
    typename boost::mpl::transform_view<
        Seq
      , boost::remove_pointer
      >::type
  , boost::mpl::long_
  , boost::mpl::eval_if<
        boost::mpl::less
      , boost::mpl::_2
      , boost::mpl::_1
      >
  >::type type;

In practice I’ve noticed that this style can be used to format long function calls or even `for` statements. Actually everything that can be split into several lines could be formatted that way. And yes, it is convenient to have a delimiter (comma, semicolon, whatever) as a leading character to make it visually noticeable.

// Inheritance list formatting
struct sample
  : public base_1
  , public base_2
  , ...
  , public base_N
{
    // Parameter list formatting
    void foo(
        const std::string& param_1                      ///< A string parameter
      , double param_2                                  ///< A double parameter
      , ...
      , const some_type& param_N                        ///< An user defined type parameter
      )
    {
        // Split `for` parts into few shorter lines
        for (
            auto first = std::begin(param_1)
          , last = std::end(param_1)
          ; it != last && !is_found && !is_exit_requested
          ; ++it
          )
        {
            auto val = check_some_condition()
              ? get_then_value()
              : get_else_value()
              ;
        }
    }
};

It looks unusual for awhile :) but later it becomes (quite) normal and easy to read and edit :) Really! When you want to add one more parameter to a function declaration it takes less typing if compare to a “traditional” way :) (especially if you have some help from an editor, like move/duplicate the current line or a selected block up/down by a hot-key or having an indenter like this :)

Next improvements was designed to simplify typing C++ code, using most common syntactic rules, like:

  • add spaces around operators and after a comma
  • add space after control keywords, but not after a function name in a call expression
  • etc.

Further improvements bring to the indenter some cute features and nowadays I’d prefer to consider it similar to a T9 (input method) for C++ coding, but not as a “real indenter” in contrast to others, shipped with kate out of the box :) Particularly this indenter “exploit” can see “impossible” syntax and (try to) transform it to something “reasonable” — i.e. just like T9 it tries to be a predictive.

For example, if you have autobrackets plugin turned ON, when typing `some(nested(` gives you `some(nested(|))` w/ `|` indicating a current cursor position. If you press `,` at this position, it gives you the following snippet `some(nested(), |)` supposing that you want to add one more parameter to a `some()` call. While typing `;` looks like you’ve done with that nested calls and gives you the `some(nested());|` snippet. Both cases help you to avoid couple of redundant key presses ;)

… but do not even try to use this indenter to (re)format blocks of code! :) It can do some really simple/primitive formatting, but far from good — as I’ve mentioned above: this “not quite indenter”™ designed to help you to __”do little more with less typing”__ for C++ ;)

Some of the Features

  • to start a C-style comment block type `/*` and press ENTER key — it gives you
    /*
     * |
     */

    to start `doxygen` comment block use `/**` + ENTER. Every following ENTER just extend the current block.

  • to start C++ style comment just type `//` it will add a one space after ;)
  • I prefer to have on-line-comments (i.e. C++-style comments after some expression) to be aligned at 60th position. So typing `//` will automatically move comment to that position if there was some code before. Moreover the indenter tries to keep that comments when you use ENTER key to break some complex expressions into a few lines
    // Before pressing ENTER at position marked by '|'
    some_call_with_long parameters_list(|param1, ..., paramN);  // Comment starts here...
    // After pressing ENTER: keep comment at the original line
    some_call_with_long parameters_list(                        // Comment starts here...
        |param1, ..., paramN);

    Also try to use _ENTER_ in the middle of a comment text ;-)

  • typing `///` gives you `/// ` (with a space) or `///< ` depending on presence of code at the current line
  • from time to time I use grouping in a doxygen documentation, so typing `//@` gives you:
    //@{
    |
    //@}
  • always add a space after `,` character — simple, but really convenient! really soon you’ve stopped typing a space after any comma and feel yourself inconvenient with other indenters ;)
  • typing `<` without a space after some identifier adds a closing angle bracket (like notorious autobrackets plugin do for other bracket types), because template instantiation guessed. So typing `std::vector<|` gives you `std::vector<|>`. But `std::cout<|>` turns into `std::cout << |` after pressing one more `<` ;-)
  • a lot punctuation characters being typed withing parenthesis is a some operator (or at least part of), so will be moved out of parenthesis (most likely call expression). Try to type various punctuators at marked position in the following snippet `some(|)`…
  • typing a backslash in on a line of a long `MACRO` definition cause realign all others to fit to a longest line:
    #define PP_FORM_A_ROW(State, Data, Elem)    \
      {                                         \
        {                                       \
            field_path(                         \
                BOOST_PP_TUPLE_ELEM(2, 0, Data) \
              , BOOST_PP_TUPLE_ELEM(2, 1, Data) \
              , BOOST_PP_TUPLE_ELEM(2, 0, Elem) \
              )                                 \
          , BOOST_PP_TUPLE_ELEM(2, 1, Elem)     \
        }                                       \
      , manage_config_keys::action::GET         \
      },
  • * typing `R”` will initiate a raw string literal

This advanced indenter  has some other (smaller) features to reduce typing. Hope, you’ll like them if found! ;)

PS: The other things I’ve found useful when typing C++ code can be plugged with some Python plugins dedicated to C++.

Kate on 5: The Future of KTextEditor and Kate Part

Recently, there was a dot story about Frameworks 5: Started in spring of 2011, the KDE software stack is undergoing a heavy split. The idea is to modularize the KDE libraries into lots of rather small units. Each unit has well-defined dependencies, depending on whether it’s in the tier 1, tier 2, or tier 3 layer, and depending on whether it provides plain functionality, integration, or a solution. If you haven’t yet, please read the article on the dot for a better understanding.

With this modularization, the question arises about what will happen to the KTextEditor interfaces and its implementation Kate Part – and of course all the applications using Kate Part through the KTextEditor interfaces, namely Kate, KWrite, KDevelop, Kile, RKWard, and all the others… The purpose of this blog is to give an answer to these questions, and to start a discussion to get feedback.

A Bit of History (Funny Read Here)

Since not everyone is familiar with “Kate & friends” and its sources, let’s have a quick look at its software architecture:

From this figure, we can see that the software stack has 3 layers: the application layer, the interfaces layer and the backend layer. KTextEditor provides an interface to all functions of an advanced editor component: Documents, Views, etc. (see also the API documentation). However, KTextEditor itself does not implement the functionality. So it’s just a thin layer that is guaranteed to stay compatible for a long time (for the KDE 4 line, KTextEditor is compatible since  2007, so as of now 7 years). This compatibility, or better yet interface continuity is required, since applications in the Application layer use the KTextEditor interfaces to embed a text editor component. The implementation of the text editor itself is completely hidden in Kate Part. Think of a backend library implementing all the KTextEditor interfaces. When an application queries KDE for a KTextEditor component, KDE loads a Kate Part behind the scenes and returns a pointer to the respective KTextEditor classes. This has the advantage, that Kate Part itself can be change without breaking any applications, as long as the interfaces stay the same. Now, with KDE Frameworks 5, this principle will not change. However, interfaces will undergo a huge cleanup, as will be explained now. As a consequence, all nodes that point to or from the KTextEditor node, namely Kate Part on the backend layer as well as applications, will need to adapt to these interfaces.

Milestone 1: KTextEditor and Kate Part on 5

KTextEditor will be a separate unit in the frameworks split. Therefore, the KTextEditor interfaces will not come bundled with one monolithic ‘kdelibs’ as it was the case for that last 10 years. Instead, the KTextEditor interfaces are developed and provided in a separate git repository. This is already now the case: The KTextEditor interfaces exist as a copy in Kate’s git repository, and relevant changes were merged into kdelibs/interfaces/ktexteditor in the KDE 4.x line. For “KTextEditor on 5,” the first milestone will be to get KTextEditor compile with the libraries and tools from the frameworks 5 branch. Along with this port, the KTextEditor interfaces have a lot of places that are annotated with “KDE 5 todos.” That is, the KTextEditor interfaces will undergo a huge cleanup, providing an even better API for developers than before.

Currently, the KTextEditor and therewith also its implementation Kate Part use the KParts component model. The KParts model allows to easily embed Kate Part in other applications along with Kate Part’s actions and menus. Further, Kate Part internally uses KIO to load and save files to support network transparent text editing. KParts itself and KIO are both Tier 3 solutions. This implies that KTextEditor along with its implementation Kate Part are a Tier 3 solution.

In other words, a straight port and cleanup of KTextEditor and Kate Part will depend on a lot of high level frameworks. This solution will provide all the features the KTextEditor interfaces provides right now in the KDE SC 4.x line.

Currently, we plan one major change in the KTextEditor on 5: We will remove KTextEditor plugins. Over the last 10 years, we got close to no contributions to the KTextEditor plugins. Existing KTextEditor plugins partly clash with code in Kate Part (for instance the Auto Brackets with the Autobrace plugin), and merging the plugin’s xml gui into the KTextEditor::Views always requires some hacks to avoid flickering and make it work correctly. Besides, if the KTextEditor plugins are removed, for instance the Kate config dialog only shows one “Plugins” item instead of two. This is much cleaner to the user. Existing functionality, like for instance the “Highlight Selected Text” plugin, will be included into Kate Part directly. The same holds true for the HTML export feature. This is a bold change. So if you want to discuss this, please write to our mailing list kwrite-devel@kde.org.

The time frame for the KTextEditor port & cleanup is rather short: We want to provide rather stable KTextEditor interfaces so that other applications can rely on it. Therefore, we will probably create a frameworks branch in the Kate git repository in December (current proposal on kwrite-devel). Binary and source incompatible changes will be allowed until other applications like KDevelop or Kile are ported to Frameworks 5. Then, the KTextEditor interfaces will again stay binary compatible for years.

Milestone 2: KWrite and Kate on 5

KWrite is just a thin wrapper around the KTextEditor interfaces and therewith Kate Part. Therefore, KWrite will mostly support just the same functionality as it provides now. The same holds true for Kate. However, Kate itself provides quite a lot of advanced features, for instance to have multiple main windows (View > New Window), or sessions, and a good plugin infrastructure. Of course, Kate itself will also undergo cleanups: i) cleanups due to changes in the KTextEditor interfaces, and ii) cleanups like for instance moving the Projects plugin Kate itself, making it more easily accessible to other plugins like the Search & Replace or Build plugin. We will also remove support for multiple main windows through “View > New Window.” This is due to the fact, that many Kate plugin developers were not aware of this feature, and therefore completely messing up their code by not separating the logic from the view, resulting in crashes or broken behavior when using multiple main windows. Removing the support for multiple main windows, we will loose this feature. However, we get simpler and more maintainable code.

There are other small details that will change. For instance, as it looks right now, the Python pate host plugin in Kate on 5 will only support Python 3 (current discussion on kwrite-devel). Python developers, you are welcome to contribute here, as always! :-)

Milestone 3: More Modularization in the KTextEditor Interfaces?

Milestone 1 & milestone 2 will happen rather sooner than later (fixed dates will follow once we’re sure we can satisfy them). Since the transition to Frameworks 5 allows us to change KTextEditor interfaces, it is the right time to think how we can improve the KTextEditor interfaces and its implementation Kate Part even further. For instance, on the mailing list, the idea was raised to make the KParts model optional. This could be achieved for instance by deriving KTextEditor::Document from QObject directly, and create a thin KParts wrapper, say KTextEditor::DocumentPart that wraps KTextEditor::Document. This would be a major change, though, and possibly require a lot of changes in applications using the KTextEditor interfaces. As of now, it is unclear whether such a solution is feasible.

Another idea was raised at this year’s Akademy in Bilbao: Split Kate Part’s highlighting into a separate library. This way, other applications could use the Kate Part’s highlighting system. Think of a command line tool to create highlighted html pages, or a syntax highlighter for QTextEdits. The highlighting engine right now is mostly internal to Kate Part, so such a split could happen also later after the initial release of KTextEditor on 5.

Join Us!

The Kate text editor only exists thanks to all its contributors. Moving to frameworks, it is the perfect time to follow and contribute to the development of Kate. In fact, you can learn a lot (!) in contributing. In case you are interested, have ideas or want to discuss with us, please join our mailing list kwrite-devel@kde.org.