-
Notifications
You must be signed in to change notification settings - Fork 142
Applications
Developping Geogram graphic applications is based on two components:
- The graphic user interface: we use the excellent Dear Imgui graphic user interface.
- 3D Rendering API: Geogram includes the GLUP API, that provides hardware-accelerated volumetric primitives, an easy-to-use OpenGL 2.x-like immediate mode, full-screen effects and much more. More on this here.
- Application: the bare minimum
- SimpleApplication: has a menu, viewer propeties, object properties and viewer controls (rotate, pan, clipping)
-
SimpleMeshApplication: a SimpleApplication with a
Mesh
object,MeshGfx
graphics and viewer propeties
It only has the bare minimum. It creates a window, a GLUP rendering context and initializes ImGui. The
functions draw_gui()
and draw_graphics()
can be overriden, one can refer to the
(super simple) example program.
In the example, the draw_gui()
function draws the demo window of Dear Imgui, and the draw_graphics()
function.
One can also override the xxx_callback()
functions to react to user input.
SimpleApplication
provides more services (it is in fact much more elaborate than Application
, it is called Simple
because it makes
life simpler to client code). It has the following functionalities:
- Console: Geogram logger messages are redirected to a console
- Viewer and viewer properties GUI: the built-in viewer has camera control, lighting and clipping control, and full-screen effects (cartoon and ambient-occlusion).
- Object properties GUI
- Embedded text editor
- Menu and commands
The example program demonstrates
how to draw your own graphics (override draw_scene()
), how to add your own menu and commands (override draw_application_menu()
),
how to load and save files (override load()
, supported_read_file_extensions()
, save()
, supported_write_file_extensions()
).
There are other example programs based on SimpleApplication
:
- geogram_demo_GLUP: demo of all rendering primitives
- geogram_demo_Evert: porting a nice mathematical app from the 90's
- geogram_demo_Delaunay2D and geogram_demo_Delaunay3D: demo of some Geogram geometric classes. Delaunay2D also has user input.
The commands are simply member functions of your class (that inherits SimpleApplication
). They are invoked in the draw_application_menus()
function. Suppose you have a command my_command(int, bool)
that takes an integer and a boolean as arguments. Adding the command to your
application works as follows:
class MyApp : public SimpleApplication() {
public:
...
void my_command(int x = 10, bool y = false) {
// do something !
}
void draw_application_menus() override {
if(ImGui::BeginMenu("Commands")) {
if(ImGui::MenuItem("my command")) {
Command::set_current(
"my_command(int x = 10, bool y = false)",
this,
&DemoApplication::my_command
);
}
}
}
}
And that's all ! It will create the dialog box for you. Note that the first argument of Command::set_current()
is the
prototype of the function with default values. It is necessary to do so, else Command
has no means of knowing the
names of the parameters and their default values (if no prototype is specified, then names will be arg1
... argn
and
there will be no default value). In addition, one can specify tooltips in the prototype string between square brackets
(the following code snippet is taken from the example program):
if(ImGui::MenuItem("compute")) {
Command::set_current(
"compute("
" index_t nb_iter=300 [number of iterations]"
") [pretends to compute something]",
this,
&DemoApplication::compute
);
}
Let us see now how to change the Object properties pane. It can be done by overriding draw_object_properties
:
void draw_object_properties() override {
SimpleApplication::draw_object_properties();
ImGui::ColorEdit3WithPalette(
"Surface", surface_color_.data()
);
ImGui::Checkbox("##MeshOnOff", &show_mesh_);
ImGui::SameLine();
ImGui::ColorEdit3WithPalette("mesh [m]", mesh_color_.data());
if(show_mesh_) {
ImGui::SliderFloat(
"wid.", &mesh_width_, 0.1f, 2.0f, "%.1f"
);
}
}
To understand what's going on, you need to learn a little bit more about Dear Imgui. It is an immediate mode GUI (note: it iscompletely unrelated with OpenGL immediate mode). It means that the code to draw the GUI and the code to handle the events is at the same place. To learn mode about Dear ImGui, one can refer to Dear ImGui website that has a gentle introduction.
Then, to know what can be done with it and how to do it, Dear Imgui's author Omar Cornut recommends to:
- show the demo window (you can do so either in
geogram_demo_Application
or ingeogram_demoSimpleApp
first entry of theWindows
menu (see video above) - find an example of what you are trying to do there
- lookup how it is done in the (heavily commented) source code of the demo window. To ease navigation in this 6K LOC file, there is an index at the beginning of the file. The find function of your text editor is your friend ! For instance, to find how what's shown in the video works, search "Plots Widgets" in
imgui_demo.cpp
.
There were three major versions of the GUI for Geogram:
- version 1: OSF Motif (98-early 2000's)
- version 2: Qt (2000-2010)
- version 3: Dear Imgui
The first one (OSF Motif) was an absolutely horrible programmer's experience: based on Xt Intrinsics, a C object-oriented framework, with lots of macros (if you develop Python extension packages manually without SWIG, you can have an idea of what it looks like).
The second one made things much easier, and brought Windows portability. However, as years passed, Qt became heavier and heavier, and was taking the lion's share of package weight when distributing binaries. In addition, Qt uses the (traditional) object-oriented description of the GUI, so you have somewhere some code that creates the buttons, windows, panes etc... and somewhere else event handlers (slots in Qt parlance) connected to your GUI elements, so in a certain sense you do the work twice.
With Dear Imgui it is completely different: you write this function that draws the GUI elements and that reacts to the events at the same time. Not only the code is incredibly shorter, but also the GUI can be made much mode dynamic, by chosing to display elements or not based on the current context. Not only it is much easier to program, but also in the end, the compiled packages weights virtually nothing.
SimpleMeshApplication inherits SimpleApplication. It has a mesh, graphics, mesh load and save. It is used to implement two programs bundled with Geogram: