gfx/message_box.h
The operating system's own message boxes, for an application: a message, an icon, and up to any number of buttons, answered synchronously or through a callback, and closable from code.
#include <sonore/gfx/message_box.h>- 3types
- 1other declaration
- Guides: The native editor
On this page
Design notes
Not inside a plugin
An OS modal dialog from inside a plugin blocks the HOST's message loop, can land behind the host's window, and leaves the user unable to reach the DAW to stop the transport. A plugin editor asks its questions with gfx/alert.h's AlertOverlay, which is drawn inside the editor and blocks nothing. This file is for programs that own their process: Application, DocumentWindow.
Per platform
Windows TaskDialogIndirect, which takes the buttons' own labels. It lives
in Common Controls 6, which a process gets only through an
activation context: when the program's manifest gave it none,
one is made from the manifest shell32 carries (resource 124).
Without it, MessageBoxW -- whose buttons cannot be relabelled,
so OK / OK-Cancel / Yes-No / Yes-No-Cancel are picked to suit.
macOS NSAlert, with the labels, through the Objective-C runtime.
Linux zenity, else kdialog, run as a child process -- the desktop's
own dialog without linking a toolkit.
Anywhere else, or when none of those can show this box (more than three
buttons for MessageBoxW or kdialog, no zenity or kdialog on the PATH): a
DRAWN box -- a small DocumentWindow of this SDK's holding an AlertOverlay.
Synchronous and asynchronous
show() waits, running the OS's modal loop on the calling thread (which keeps the message thread's queue moving: callAsync still runs). showAsync() returns at once and calls back on the message thread with the index of the button pressed; on Windows and Linux the box runs on a thread of its own, so nothing about the caller's loop is held. showScopedAsync() returns a ScopedMessageBox: destroying it, or calling close(), takes the box down and the callback is NOT called. Closing the box from its own close box or Escape answers with the LAST button (the cancel, as AlertOverlay has it). -1 means no box could be shown at all.
RUN on Windows: TaskDialog, MessageBoxW and the drawn box, each async and dismissed by a posted click; the sync form dismissed from another thread; ScopedMessageBox closing a box and suppressing its callback. NSAlert and zenity/kdialog are compiled only.
Types 3
What a box says and which buttons it has. Built by chaining, as in the reference: MessageBoxOptions().withTitle("Save?").withButton("Save")...
A box opened by showScopedAsync. Destroying it, or close(), takes the box down and its callback is not called. Movable, not copyable; an empty one does nothing.
The OS's message boxes. See the header for what runs where.
Enums 1
- enum
enum class MessageBoxIconTypeWhich icon a box shows. The reference's names. Windows shows each of the three; NSAlert, zenity and kdialog tell only a warning from the rest; the drawn box writes the word ("Warning", "Question", "Information") as its heading.gfx::MessageBoxIconType · message_box.h:97