How to use Built-in Dialogs in wxWidgets
By Luke
Where wxWidgets shines as a multi-platform UI library is its consistent native look and feel across different operating systems.
Dialogs are no exception. The library offers methods and classes to display system-specific dialogs for everyday tasks, like opening a file, choosing a font, etc.
Let’s dive in and explore these options. For those who prefer video format, my YouTube channel features a tutorial that covers the built-in and custom dialogs, including how to transfer data between them and other parts of your application.
File Dialogs
The file dialog is one of the most commonly used built-in dialogs in wxWidgets. It allows users to choose a file to open, a directory to work in, or a destination to save their work. To create a file dialog in your wxWidgets application, you can use the wxFileDialog
class. The wxFileDialog
class provides various options to customize the dialog’s behavior and appearance, such as the file type filters, default file name, and the starting directory.

File Open Dialog
Here’s an example of an Open File dialog. The code asks the user to select an image file and then loads its contents to a wxImage
object.
wxImage image;
wxFileDialog dialog(this,
"Open Image File",
"",
"",
"Image Files (*.png;*.jpg;*.jpeg;*.bmp)|*.png;*.jpg;*.jpeg;*.bmp", wxFD_OPEN | wxFD_FILE_MUST_EXIST);
if (dialog.ShowModal() == wxID_CANCEL)
{
return;
}
if (!image.LoadFile(dialog.GetPath()))
{
wxMessageBox("Failed to load image file", "Error", wxOK | wxICON_ERROR);
return;
}
Check the documentation for all possible styles and parameters.
Messages and Text Input
Sometimes we need something even more fundamental. The wxMessageBox
lets us display a simple message, while wxTextEntryDialog
allows the user to input text.
wxMessageBox("Hello World", "Message", wxOK | wxICON_INFORMATION);
As is always the case with wxWidgets, our control has a native look and feel. Here’s an example on Mac:

MessageBox on Mac
The wxTextEntryDialog
allows for more interactions:
wxTextEntryDialog dialog(this, "Enter your name", "Name", "John Doe");
if (dialog.ShowModal() == wxID_OK)
{
textView->SetLabel(dialog.GetValue());
}
else
{
textView->SetLabel("You cancelled the dialog");
}

Text Input
If the user confirms the dialog (by clicking OK), we can get the text they typed using dialog.GetValue()
.
Color Picker and Font Chooser
wxWidgets also provides built-in dialogs for selecting colors and fonts. The wxColourDialog
class allows users to choose a color, while the wxFontDialog
class lets users choose a font. Both dialogs are straightforward to use, and developers can customize their appearance and behavior by setting different options.
Here’s an example that displays the color dialog, setting the initial color value to the current control’s background color (assuming this
points to a wxWindow
). After the user clicks ok, we update the background color.
wxColourData data;
data.SetColour(this->GetBackgroundColour());
wxColourDialog dialog(this, &data);
if (dialog.ShowModal() == wxID_OK)
{
auto backgroundColor = dialog.GetColourData().GetColour();
this->SetBackgroundColour(backgroundColor);
this->Refresh();
}

Color Picker on Mac
This example shows a font dialog and changes the textView
font to the one the user chose. The textView
variable is a pointer to wxStaticText
.
wxFontData data;
data.SetInitialFont(textView->GetFont());
wxFontDialog dialog(this, data);
if (dialog.ShowModal() == wxID_OK)
{
auto font = dialog.GetFontData().GetChosenFont();
textView->SetFont(font);
this->Fit();
this->Layout();
}

Font Dialog on Mac
The Progress Dialog
The progress dialog is a useful built-in dialog in wxWidgets that allows developers to display the progress of a long-running task to the user. The wxProgressDialog
class provides a customizable dialog that shows the progress bar, a message, and an optional cancel button. Developers can use this dialog to keep the user informed about the progress of a time-consuming operation, like downloading a file or processing a large dataset.
Using the Progress Dialog lets us perform our time-consuming task directly on the main thread, as long as we call Update
or Pulse
during our long-running task.
Let’s start with the long-running task. Here’s a slow sorting algorithm that accepts a callback to decide if the function should be aborted.
void BubbleSort(std::vector<int> &data, std::function<bool(int)> shouldQuit)
{
for (int i = 0; i < data.size(); i++)
{
if (shouldQuit(i * 100 / data.size()))
{
return;
}
for (int j = 0; j < data.size() - i - 1; j++)
{
if (data[j] > data[j + 1])
{
std::swap(data[j], data[j + 1]);
}
}
}
}
Now we can use it like this:
void OnClick(wxCommandEvent &event)
{
const int MaxProgress = 100;
std::vector<int> data;
for (int i = 0; i < 30000; i++)
{
data.push_back(rand());
}
wxProgressDialog dialog(
"Progress Dialog",
"Doing work",
MaxProgress,
this,
wxPD_AUTO_HIDE | wxPD_APP_MODAL | wxPD_CAN_ABORT |
wxPD_ELAPSED_TIME | wxPD_ESTIMATED_TIME | wxPD_REMAINING_TIME);
BubbleSort(data, [&dialog](int progress)
{ return !dialog.Update(progress); });
dialog.Update(MaxProgress);
textView->SetLabel("First Item: " + std::to_string(data[0]));
}
In the callback, we call the Update
method of our dialog
, which accomplishes two goals:
- the framework can update the UI so that our time-consuming does not hinder the user experience,
- we react to the
false
result of this call by returning from theBubbleSort
method. This happens when the user cancels the progress dialog.
Note the long list of flags passed to the dialog’s constructor - among them are constants like wxPD_ELAPSED_TIME
or wxPD_REMAINING_TIME
, which do all the time calculations and estimations for you.
Summary
In conclusion, wxWidgets provides a rich set of built-in dialogs that can save developers time and effort in creating native-looking dialogs for their applications. These dialogs allow developers to provide a consistent user experience across multiple platforms without worrying about system-specific code.