C++ GUI – 3 Text Regions with Scrollbars

Last month, I discovered the software application I wrote atop FLTK would not render text at the proper size on 4K resolution monitors. The version of FLTK I used was designed for 1080p monitors and earlier. During the last 4 years, I looked at using C++ code libraries to build GUI applications. I came across numerous code libraries that would provide a means to produce a GUI in C++, but I had to try them out first to see if they would be a good fit. Two of the most popular ones, Qt and wxWidgets, I studied in-depth before I decided not to use them at all.

Several libraries seemed promising. I started with Win32 but that was not cross-platform. I looked at Allegro but decided it was not productive enough. SFML was a little more productive but had too many dependencies. Eventually, I settled on FLTK. The great thing about FLTK was it was nimble, compact, and fast to set up and deploy and required very little to get up and running. I built an application using FLTK and was satisfied with the result until I ran it on a system with a 4K monitor.

Reconsidering the results of using FLTK meant going back to the drawing board. Years passed since I last reviewed a multitude of code libraries and frameworks. I knew that I could get a thorough implementation of the software using Qt or wxWidgets as they were mature and feature complete solutions. I am just a tad on the bleeding edge in terms of core compilers, C++ language version, and depth of control I would prefer in the software and those toolkits are not designed to keep pace with that. I have other reasons not to prefer those toolkits. I began to consider Allegro again.

One thing I wanted that FLTK delivered was productive, high-level widgets that I could declare in code and just use. FLTK already has things like buttons, scroll bars, list boxes and such that I could just use and link to data. Using pre-built widgets such as you have in frameworks like .NET, Java, and HTML seemed like a productive way to go. I would gain the use of code I didn’t have to write. That point of view had a flaw.

As of 2016, code libraries such as Allegro and SFML do not have widgets. When using them as your primary graphics definition tool, you have to create any widgets you need from scratch. It was my hope over the last 4 years to avoid that and reap the benefits of productivity. I understood that if I made my own widgets, I would have more control and a greater ability to adapt to changes in technology and hardware. I also knew in the back of my mind that if I was wrong about using a high-level, productive framework like FLTK or something similar, that I would probably have to write the application-level interactive graphics solution from scratch.

October 2016 came around and it quickly became apparent that to support the latest compilers, C++ standards, display resolutions, and other aspects of an operating environment writing from scratch using libraries limits you less than assembling widgets using third-party frameworks. I still recommend widget frameworks for IT departments, but for true world software, even for personal use, I recommend going with code from scratch. Even with the hassles as the issues will be far less than waiting 6-months to a year or more for a framework to get updated.

C++ GUI using Allegro 5 Graphics, dlib Geometry, and GCC 6

One of the most promising aspects of the Allegro 5 Graphics Library is are high-level drawing routines. The great thing about that is that is very productive if you are comfortable with geometry. Since that was one of my favorite areas of mathematics, I was pleased to see the presence of such high level routines in Allegro. It sped up my definition of lines for the widgets I needed to create.

Drawing the squares and other angles needed was fairly straightforward. What was unclear was the interaction needed to achieve the appearance of movement across a geometric plane. My concern was the speed of the operations to detect mouse movements within a certain area. I needed fast algorithms to achieve this goal. That is where the dlib library becomes useful.

Before I decided to use dlib, I had defined my own geometric primitives. As I got further into the new solution, I realized I was writing too much code and was going too in-depth into areas that had less to do with the application and more with the mechanics of geometric translation. I decided to replace the geometric primitives I had defined with those from the dlib library. Once I did that, it actually became easier to visualize the high-level models I needed to create to produce a more algorithmic process to convert from mouse interactions to movement of lines of text on the screen.

In the past, I’ve used both GCC and Clang at the same time to make sure I was qualifying the code from the perspective of two compilers. This time, I decided to stay with GCC to speed up my code iterations a bit. I plan on exercising the code through Clang at some point, but for now, the code has been vetted only through GCC. I am pleased with the results so far with an executable that is 5.7 MB in size with a debug build.

C++ GUI at 4K Resolution

The series of screen shots that follow show the example application output to a monitor at 4K resolution. Even though I am on Linux and using open source technology, I have to thank Microsoft for the font scaling algorithm. They have a web page where they describe their method for font scaling. The web page does not show actual code for font scaling, but I translated the textual description to a formula. After a few revisions, the formula results in font scaling that appears to work well at different display resolutions.

Screen shot 1 shows the full window with example, auto-generated text. I auto-generated 100 lines of text. I wanted enough lines of text that I knew would not fit into any of the graphical regions I setup. I have 3 graphical regions and with truncated text, the conditions are such that I could examine both the size of lines of text and see how well scroll bar functionality operated.

gautierframe20161127_a_window4kresolution

Screen shot 2 shows the same window manually resized by mouse down to 1920 x 1080. The screen resolution is still 4K but this resized window shows the graphics layout automatically adjusted to the new window dimensions.

gautierframe20161127_b_window1080presolution

Screen shot 3 is where I clicked the mouse within the vertical bars on the right-side of each of the 3 graphical regions. The text scrolled in response. The final touch was to have so when I dragged the mouse down the vertical lane, the text scrolled continuously to correspond to the scrolling. The scroll functionality works, but one additional step is to put in logic so that when the visual scroll button reaches the end, scrolling continues bring text into view that is still beyond the upper bounds of the visual display region. However, the functionality that exist is an excellent start in that direction.

gautierframe20161127_c_scrolling

One question you may have is why Orange, Red, and Sea Green? The colors were chosen, not for any aesthetic reasons, but to create sharp contrasts between graphical regions so it was clear when things were working or not working. That way, when all the issues are ironed out, the visual design of those regions can simply be swapped out. When I eventually use this code in a real application, it will have a more refined and polished appearance. Today, however, the focus is on getting the foundation right so that any polish can occur in a context in which you are not troubleshooting both the form and the function.

C++ Code and GNU Makefile

You will notice that the code uses very few directly declared pointers. I was reading Kurt Guntheroth’s great book, Optimized C++ and I am near the end of the book at the 3rd chapter from the end. His insights into memory allocation has been influential in the decisions I’ve made in how I’ve designed the code. I’ve leaned more in a practical direction than I’ve been inclined in past versions of similar solutions.

The Makefile is how I compile and link the software. The following is the Makefile that I put together. You will notice that the libraries I use are several levels up from where I compile and link. If you try to compile the example software, it doesn’t matter where you put the libraries as long as they are reachable from where you compile and link.

The next two code files are the header and implementation for PrimaryDisplaySurfaceWindow. That is code that contains the main display window provided through Allegro in which changes to window size, mouse position, and other changes to the window are made available to the software application.

Next, we have the application-level solution. Others would call some of this the business logic. The C++ header followed by the C++ code. Whatever you call it, it is the merger of the graphics system (mouse clicks, window resizing, drag and drop) with the application (data in/data out, high-level rules, interaction response). This is the part most relevant to the end-user.

Finally, the main method from which the process starts when the application is launched.

This is the final example in this series and would be a great starting point for a GUI in C++ using Allegro and the geometry functions in the dlib library. I plan on moving forward with this code in rebuilding the 2015 version of the Gautier RSS Reader. Now, we have a GUI defined using video game technology in which there is great granular control over most if not all visual aspects of the interaction and rendering.

Allegro 5 C++ GUI on Fedora 25

Today, I did a clean install of Fedora 25 Workstation that was released a few days ago.  The installation went pretty well. One hiccup at the very end where it could not remove an old efi file in the boot partition, but that was not a real issue. The install screens are the same as for Fedora 24 and the process is fairly smooth. When running in Fedora 24, I did get an upgrade prompt but decided to download Fedora 25 Workstation to do a clean install.

Setup Fedora 25 Install USB Flash Drive from within Linux

The process I used to install Fedora 25 consisted of using the Disks GUI to write the .iso file to an external USB 3.0 flash drive. The menu option for the USB flash drive (most drives really) allow you to select a disk image (a .iso file qualifies) and write that image to a physical disk. This process allows me to apply the contents of the .iso to the USB flash drive in the correct manner that will result in a bootable flash drive in which the bootloader on the USB correctly finds the Fedora 25 operating system on the USB. The disks utility can be access from Ubuntu as well. This procedure can applied to most Linux distributions.

Installing Fedora 25 Workstation from Bootup

On an HP computer, when you boot up, you press the ESC key. Next, you press the F9 key which opens a menu from which you can select the appropriate boot image (in this case, image on the USB flash drive). After you select the image, the computer loads the operating system from the USB. The Fedora OS on the USB has an option to install the OS to the computer’s internal disk drive. Replace HP with the computer of your choice and the ESC and F9 keys with those that work for the bios of your computer and this is how you install Linux on a computer.

Fedora 25 Workstation Installed

The settings menu provides a Details applet that lists the overall summary of the distribution you are running. It is similar to the System window in Microsoft Windows that shows processor, memory, and version of windows. In this case, the details applet shows the version of Fedora installed along with a summary of primary hardware.
gautierfedora25upgrade20161125 Continue reading

C++ GUI Application with Allegro 5 – Drawing Text

Sometime around midnight I started down the road of drawing text using Allegro. It has been a few years since I last used a draw text routine and it was time to see my efforts to get better 4K monitor support was feasible. I ran into a few difficulties as I was linking the Allegro 5 library into my application in a modular way. The issue revolved around link-time symbols for the FreeType library. I quickly compiled a version of the FreeType library I had downloaded earlier and added that as an input into the linker. No good. I began to recognize my fatigue as I gave cmake another spin. I went to sleep around 1 AM … ish and decided to address it later.

I woke up hours later and was ready to re-engage the process from a fresh disposition. I looked more closely at the CMake options and decided to uncheck the box for share libraries and check the box for monolith library. I did the later hours before but realized I didn’t notice the former. After the adjustments, the monolith library would build without error.

Building Allegro 5 Library

The following is the basic output from the build system as it assembles the Allegro 5 library in binary form for me to incorporate into my application. In this case, instead of making 5 or 6 separate modules, I decided to merge them all into 1 library file as my preference in this situation.

buildallegro5_20161122a_monolithlibrary Continue reading

MacBook Pro 2016 Review

A balanced review of the 2016 MacBook Pro. An excellent laptop design. The review ponders the value of the touch bar. I like the touch bar concept.

Also, Microsoft is bringing Visual Studio to the Mac later this year. The Mac has the momentum. With iOS leading the shift to the cloud, Visual Studio on the Mac will provide a smoother transition to Azure and mobile apps defined in Xamarin.
http://money.cnn.com/2016/11/14/technology/macbook-pro-review-touch-bar/index.html?iid=ob_homepage_10-test_featured_pool

C++14 GUI with Allegro 5 Graphics Library (ScrollBar Outlines)

The previous article on building a cross-platform C++ application with Allegro showed a short snippet of code to erect a graphical window with 3 colored regeions. A file named main.cxx was used self-contained and encompassed all the code that produced the graphics window and 3 separate regions each with a different color using Allegro 5. The regions are arranged proportionally so they could work on nearly all display resolutions past and future. The choice to use Allegro means I’ve given up pre-packaged graphical widgets such as you have in Qt, wxWidgets, FLTK, Gnome and others. Rather, I have to define each and every graphical element myself using lines, geometry, and calculation of mouse position, etc. Just like in a video game, but geared towards a standard application. I made this choice because pre-built frameworks that have widgets have a tendency to stall for a good while in their support of minor things like language versions, compiler versions, display resolutions, and so the best way to get full support for the latest technology is to get granular. Allegro provides enough encapsulation and some good high-level drawing routines that it is productive enough to make progress.

The time I’ve put in so far on this is about 3 days (roughly 2 hours at night and an hour here or there on weekends). I started on this Nov. 2nd and so far I have a revision that not only present color regions but outputs scrollbars, or at least the lines and triangles where scrollbars would go. I also took most of the code in the single file, main.cxx and broke it out into C++ classes. I did this to get the RAII idiom on the display and event pointers returned by the Allegro 5 library and to start early decoupling the display handle from the drawing from the application level code.

Let’s start with the file named, PrimaryDisplaySurfaceWindow.hxx. It defines the interface to the Allegro 5 library to the rest of teh application. Unlike my earlier solutions, the goal is not to create a wrapper for the graphics library this time around. Instead, the goal is to have a clean division between the graphics library and the application to minimize or eliminate the co-mingling to specific elements from either graphics processing and application logic. Doing this also consolidates the logic for determining high-level events based on changes to window size, mouse position, and other attributes of the display and peripherals.

gautierrssallegro5201611051308 Continue reading

Build a C++ Cross-Platform Program with Allegro (2016)

The first time I wrote about the Allegro graphics library (see Build a C++ Cross Platform Program with Allegro) was Feb. 2013. I gave a walkthrough of building a basic application Window using Allegro on Microsoft Windows and Linux. Over time, I moved on from Allegro and explored SFML. As I clarified my goals more, I then embraced FLTK in which I completed a software application in C++ that uses FLTK, SQLite and Gnome Xml. All was well and I was looking forward to updating the program when the prospect of Hi-DPI became a reality. Higher resolution displays do not exactly prevent programs from running, but do pose productivity challenges.

I looked at the roadmap for FLTK and considered that it may be quite a ways out before version 2.0 arrives. I looked at the bug reports for FLTK 1.3.3 and realized that there may not be the kind of movement on Hi-DPI support that would be useful. I briefly made changes to the FLTK source code and decided that is not my path at this time. That began a brief journey of a few weeks in which I looked at various native graphics API.

I dusted off old books I had on OpenGl. Reviewed the status of C++14 support among various API. Examined some of the viewpoints out there for and against different API. After taking everything in, I saw that one API in particular seemed to quitely get a general nod of approval within the noise about graphics API. That was Allegro.

Allegro 5 Graphics Library

I was very familiar with Allegro a few years ago. A few days ago, I decided to give it a try and determine if things had improved from when I last used it. The problems I had with Allegro the last time around was in compiling it. I documented how to compile Allegro for various platforms in 2013 but I wanted a process that was more compact and to the point when creating a static library. At the time, the Allegro library was not easily inclined towards this approach. Today, it is … thankfully.

The other problem had to do with the way Allegro handled window creation. I found it uneven and oddly represented in some cases. I never expressed these misgivings until now, but I had some small trepidation about trying Allegro again given some of the issues with polish (that’s really what those issues are after all). I downloaded Allegro 5 (which I think was borderline unstable last time I tried it) and hoped for the best.

So far, I am pleasantly surprised. It works well. I still do not like the reliance on CMake for the build. I think a configure script is a smoother, more repeatable way to build API binaries from source, but CMake is a good alternative. Anyway, what really intrigued me about using Allegro is the various constructs in Allegro that improve productivity when creating a graphically detailed program. It is still more granular than FLTK, but I think it will do well once I evaluate its handling of fonts.

Compiling the Application

I put together a Makefile to compile the application I build with C++14 (compiler directives) and Allegro. The following Makefile is a minimum Makefile to build the source code shown further down. As you can see, my path to the Allegro library static binaries I emitted with CMake/make is a few levels up from where I keep source and make file. If you repeat this, it doesn’t matter where you put the Allegro 5 library static (or shared) binaries as long as the Makefile (and thus the compiler) can see them. All this for properly rendered fonts? Yes, it is worth it.

Allegro 5 Graphics Library Window – Initial Baseline

Continue reading