WebEngine Recipe Browser#
A small hybrid application based on the WebEngineView QML type and Qt Quick Controls 2.
Running the Example#
main.cpp, we use the
QQmlApplicationEngine classes to set up and load the main QML file. We call
initialize so we can use WebEngineView in our QML code. We set the default Qt Quick Controls 2 style to the Material style, so we do not have to specify it for each new item we add. Finally, we use a C++ define to check whether the application is compiled for an embedded platform. The value will be used in the main QML code to determine the window size.
main.qml file, we first create a top-level window and set a title for it. We also set up the size of the window depending on its primary orientation as well as the platform, so that the application is usable on both desktop and embedded platforms. On desktop, the size is constrained by a minimum of 320x480 pixels up to the maximum size that the screen supports. The default window size is 1024 pixels wide and 768 pixels high in landscape orientation. On embedded devices, the window will occupy the whole screen.
Next, we add a RowLayout item so we can divide the window into two parts: one being a custom
RecipeList item containing the recipe titles, and the other being the WebEngineView , which shows the recipe details. The spacing is set to zero so the items are positioned directly next to each other.
RecipeList item has a few attached Layout properties , in order to scale the item to a maximum of one third of the layout width. We give the item focus, so that the keyboard can be used to navigate the recipes, in addition to using mouse and touch. We also add a handler for the custom
recipeSelected signal, to tell the WebEngineView to load the URL of the selected recipe.
The WebEngineView has similar layout properties, to make it occupy two thirds of the layout width.
We then disable the focusOnNavigationEnabled setting to make sure that the WebEngineView does not steal focus from the
RecipeList item every time its URL is changed. This allows the user to continue navigating through the recipes using the keyboard. We also disable the default context menu by accepting the ContextMenuRequest .
Once the first page in the view is loaded, we start a Timer that will hide the placeholder and show the actual page. The delay provides more time for the recipe images to load, so that when the view is shown, the page is completely rendered. The timer also shows a help ToolTip that informs the user on how to navigate the recipes.
Let’s see what the
RecipeList item looks like from the inside. The root item is a FocusScope to allow transferring focus to the child ListView whenever the root item receives focus. We also declare a custom
recipeSelected signal, which will be emitted when the current item of the ListView changes.
The second item inside the layout is a ListView , whose contents will fill the remaining space in the layout. We set clip to true, so that the delegates that are scrolled up are not seen under the ToolBar item. We set focus to true, so the ListView gains focus when the FocusScope does. We add a vertical scroll bar, so the user can scroll through the recipes if the window size is small. We also specify the recipe model to be used by the ListView as described later in this topic.
We have an ItemDelegate set as the ListView delegate, which displays the recipe title. The contentItem is a Text item, customized with a few properties to adjust the visual appearance and position of the text. We create a binding to the current delegate’s model URL, so we can access the respective URL outside the delegate itself. We set the highlighted property to
true whenever the item is the current one in the ListView to provide visual feedback. And we set the focus on the ListView whenever a delegate is clicked, so that keyboard navigation works in case the focus was previously in the WebEngineView .
A handler is defined for the
currentItemChanged signal to emit our own
recipeSelected signal with the URL that the WebEngineView should load.
We use a ListModel with seven ListElements, each of which contains a recipe title and the URL to an HTML page contained in a resource file. The model is used to populate the ListView with the recipes and to show the recipe details in the WebEngineView .
We use a ToolTip item that is displayed on application startup to inform the users how they can navigate and view the details of each recipe. The ToolTip is shown using the
showHelp method, which is invoked by the Timer in the main.qml file.
markdown.css is a markdown-friendly stylesheet created by Kevin Burke
marked.min.js is a markdown parser and compiler designed for speed written by Christopher Jeffrey
custom.css makes some small styling adjustments to the final recipe page
custom.js is used to invoke the conversion of the recipe content (which is written in markdown syntax) into HTML
The images on the pages are loaded from the compiled resource file.
Files and Attributions#
The example bundles the following code with third-party licenses:
Apache License 2.0