Bicing Barcelona with Qt

When I was living in Barcelona I saw that there is a OpenData service to get the information of the Bicing (bike public service). They provide the data in several formats such as CSV, XML and JSON. I wanted to write an app for Windows and Linux that retrieves the information from the stations and shows their current status. And for that, I chose JSON since I think the format is easier to read than XML.

After thinking a while I realised that it could be useful not just have every Bicing station data on demand but also a historic. To achieve that I split the app in two separated parts: “backend” that works as a deamon or service, and “frontend” that is the actual GUI app.

(more…)

Customization of a QCompleter

Time ago I had the task to create a QComboBox and a QLineEdit that open a completer so the user can select between all the suggested options. So far it seems a quite easy task by using the QCompleter that Qt provides.

The interesting part starts when I had to add customized styles for both the QComboBox and the QLineEdit, and make them match with the styles that I also had to add to the QCompleter. In addition I had a language constraint that initially I didn’t take into account but it impacted the performance of the widget. That’s the default filter implemented in QCompleter.

(more…)

Testing QTableWidget with QTest

In the last post I talked about how to integrate tests in the build environment. When we talk about testing I always think on unit testing for my classes and methods but I usually forget UI testing.

With Qt we have a really nice environment to test GUI as well. Widgets implement all the power of signals and slots, and Qt provides a wide range of signals so we can keep track of what happened and what’s currently happening. The fact that we can work with QSignalSpy makes all or testing easier. At least if we know what to test, because some times is not that straight-forward with widgets. Specially with QListWidget, QTableWidget and QTreeWidget classes.

In the Qt5 repository we can finde a lot of tests for those classes:

(more…)

Integrating Qt Test in Travis CI

For a long time I wanted to create a full Continuous Integration environment that uses Qt for both building apps and testing. In fact, one of the most important things for me was to find the right way to integrate Qt Test. For CI I’ve started to use Travis since it is one of the most widely used environments in GitHub. I took that decision after seeing other Qt projects (Musescore and Stellarium) using it.

The main difference between those projects and the one I wanted to set up, is that they’re using CTest as a testing tool. With that tool they can report when the tests are broken easily. But, how the hell I was going to do it with Qt?

(more…)

Drag and Drop in custom widgets with Qt

Implementing Drag and Drop for general widgets

This post is based on the one existing on Qt documentation. That is a great guide where you can find a lot of information and how to implement Drag&Drop in your widgets. However, when we want to apply that behavior into our widgets we might miss some useful information. Let’s write some requirements for our Drag&Drop widgets and then we will see how we implement it step by step.

  • Disable dropping widgets that are not the type we expect. We don’t want that anybody starts dropping any widget from other places like a view.
  • Change the background color when we’re moving over the widget we want to drop. If we change the color while we’re moving over the widget it will help us to know the drop area we have available.
  • Store an id (int) and a name (string) on our droppable widget from the widget we just dropped. Doing it this way we can save queries to the database asking for the information.

(more…)

Simple bugs that crashed my mind

This post is more about a memorial of my errors or those I found during the years than a tutorial or research entry. Even though, I’ll try to give an explanation about why it happened and what we try to take into account for the future. They’re usually simple errors but hard to find when you don’t know what you’re looking for. Some times it crashes but other times it just causes unexpected behavior.

I’ve some for C++ and other about Qt. I think it’s quite interesting to see both of them because their types and reasons are quite different. While in C++ we have full control about memory allocation and deallocation in Qt we have the re-parenting issue.

(more…)

CustomWindow in Qt (create your own QWindow)

Brief introduction

I’ve seen several questions in the Qt Forum about how to customize or create our CustomWindow predefined window title buttons or the styles of it. First of all is necessary to explain that this is not a trivial issue since the OS API defines these controls and styles.

In the case of Windows, the title bar is created by Windows Manager so it is impossible to modify it. If we want a personalized title bar or modify the styles of the border of the window or whatever, it is necessary to remove it and then, create our custom QWidget with our own title bar. Before we start to write our own custom QWindow we need to understand that is not an easy task. Our QWidget must fulfill the following requirements:

  • Catch some mouse events: press, release, move… In order to know where to move or how to resize the window.
  • Implement the top-right buttons behavior: close, minimize, maximize, restore…
  • Manage the include of the central widget that will has the main functionality.
  • We could want to add a top-left menu and the title of the window. It is necessary to implement too.
  • The good things that provide us a custom title bar is the possibility to add new buttons with extended functionality, customize the top-left menu with our own options and definitely, to have our application window style unified.

The best way to learn Qt goes trough code, code & code. In this case, create our custom window title and all the functionality it involves is a good way to learn the Qt window management.

(more…)

Logging with Qt

Logging with Qt

Logging messages is an important part of our app and sometimes we can’t find the right way to do so. It depends on how we want to work with that but of course that Qt provide us with some nice options.

Redirect QDebug to a file

Some times we prefer to analyse the our application debug messages in a separated file. It is useful when we want to work with Qt-Creator in full code window and we have two monitors (one for coding and another for application execution and debug file). To redirect the output we have to type in Qt:

Then, in main function we have to add the following line:

qInstallMessageHandler(customMessageHandler);

Redirect QDebug in our custom class

If we want to redirect the output of our custom class to QDebug, it is necessary to declare the operator << of QDebug type as a friend method:

friend QDebug operator << (QDebug d, const Protocol &p);

(more…)

Range-based loop in C++11

Since C++11 we have a new awesome range-based loop. It is an evolution of the always know for-loop but with implicit iterators management. In C++ we can write loops in a different way, for instance the do-while loop, the while loop and the for-loop. In this last case we take an initialization expression, a condition that must be fulfilled and finally a post-event sentence, almost always used for increment/decrement. When I started coding at the university I couldn’t use the STL containers. When I discover Qt I didn’t know anything about iterators and I kept iterating for-loops using the size/count method, that was totally aberrant as you may see. Some time ago I learned to work with iterators but with some laziness since I had to write the whole type.

For-loop before range-based loop

I know that I may by a bit basic but I like to show some old and wrong ways to write for loop. I think that sometimes in blogs we forgot that people with more basic knowledge may read this post and I like to give them the basic knowledge too. I’ve used lists because iterating them is the worst way we can do things. In a future post I’ll talk in-depth about containers and performance.

In this case it’s clear that we are looking up for a value in the list based in its position. The problem here is that a list is randomly allocated in memory so it’s really expensive to look for a value in a position. In addition we’re checking the size of a list that is not changing every iteration. We better move to iterators:

This code is almost good. The only problem is that we’re using the non-const iterator while we aren’t doing anything with the iterator neither the list. The best way would be to change for const_iterator in all sentences:

That’s righ but boring to write and tricky to remember that all iterators have to be const_iterator.

Range-based loop

Before C++11 there was no way to make the loops more readable so for that moment it was OK. Now, we have a new syntax we can use in this kind of loop called range-based loop. In addition we have auto keyword that will help us a lot. So instead of that loooooong iterator thing definition we have:

The reason we can work with that is because internally it takes the begin and end iterators and increments the iterator after the body of the loop. It allows us to work with iterators as well as const_iterators, work with object copies, const references or the reference itself. I think it’s simple and intuitive.

(more…)

My C++11 favorite features

Where I came from

I started developing C++ at university where I had my first contact with programming languages. I always had a computer at home since MS-DOS but I never knew or asked myself about how applications run until I started the university. When I started I found it difficult to think as a computer so my efforts where more oriented to memorize routines. Totally wrong, as you may see.

I’ve always worked with C++ during my university studies but it doesn’t mean that I knew how it works or how to use it properly. In fact, the first year I didn’t learn OOP at all, it was just structural programming to learn about loops, arrays and basic data structures. The main problem: not a single explanation of why we were using it in that way. Time after that I started with OOP, some templates and finally the conjunction of OOP with GUI applications. A total disaster as you will find out.

(more…)