root/OpenSceneGraph/trunk/examples/osgviewerGTK/osgviewerGTK.cpp @ 12292

Revision 12292, 6.9 kB (checked in by robert, 4 years ago)

Ran svn propset -R svn:eol-style native . on the OpenSceneGraph

  • Property svn:eol-style set to native
RevLine 
[8810]1#include <string.h>
2
[8290]3#include <iostream>
4#include <string>
5#include <osg/Stats>
6#include <osgDB/ReadFile>
7
8#include "osggtkdrawingarea.h"
9
10const char* HELP_TEXT =
[8294]11    "Use CTRL or SHIFT plus right-click to pull up a fake menu.\n"
12    "Use the standard TrackballManipulator keys to rotate the loaded\n"
13    "model (with caveats; the model won't keep rotating).\n"
14    "\n"
15    "<b>OpenSceneGraph Project, 2008</b>"
[8290]16;
17
18// If you want to see how to connect class method to callbacks, take a look at the
19// implementation of OSGGTKDrawingArea. It's dirty, but it's the only way I could
20// come up with.
21bool activate(GtkWidget* widget, gpointer) {
[8294]22    GtkWidget* label = gtk_bin_get_child(GTK_BIN(widget));
[8290]23
[8294]24    std::cout << "MENU: " << gtk_label_get_label(GTK_LABEL(label)) << std::endl;
[8290]25
[8294]26    return true;
[8290]27}
28
29// Our derived OSGGTKDrawingArea "widget." Redraws occur while the mouse buttons
30// are held down and mouse motion is detected.
31//
32// This is the easiest way to demonstrate the use of OSGGTKDrawingArea. We override
33// a few of the event methods to setup our menu and to issue redraws. Note that an
34// unmodified OSGGTKDrawingArea never calls queueDraw, so OSG is never asked to render
35// itself.
36class ExampleOSGGTKDrawingArea : public OSGGTKDrawingArea {
[8294]37    GtkWidget* _menu;
38   
39    unsigned int _tid;
[8290]40
[8294]41    // A helper function to easily setup our menu entries.
42    void _menuAdd(const std::string& title) {
43        GtkWidget* item = gtk_menu_item_new_with_label(title.c_str());
44       
45        gtk_menu_shell_append(GTK_MENU_SHELL(_menu), item);
[8290]46
[8294]47        g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(activate), 0);
48    }
[8290]49
[8294]50    bool _clicked(GtkWidget* widget) {
51        const char* text = gtk_label_get_label(
52            GTK_LABEL(gtk_bin_get_child(GTK_BIN(widget)))
53        );
[8290]54
[8810]55        if(not strncmp(text, "Close", 5)) gtk_main_quit();
[8294]56   
[8810]57        else if(not strncmp(text, "Open File", 9)) {
[8294]58            GtkWidget* of = gtk_file_chooser_dialog_new(
59                "Please select an OSG file...",
60                GTK_WINDOW(gtk_widget_get_toplevel(getWidget())),
61                GTK_FILE_CHOOSER_ACTION_OPEN,
62                GTK_STOCK_CANCEL,
63                GTK_RESPONSE_CANCEL,
64                GTK_STOCK_OPEN,
65                GTK_RESPONSE_ACCEPT,
66                NULL
67            );
[8290]68
[8294]69            if(gtk_dialog_run(GTK_DIALOG(of)) == GTK_RESPONSE_ACCEPT) {
70                char* file = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(of));
[8290]71
[8294]72                osg::ref_ptr<osg::Node> model = osgDB::readNodeFile(file);
[8290]73
[8294]74                if(model.valid()) {
75                    setSceneData(model.get());
76               
77                    queueDraw();
78                }
[8290]79
[8294]80                g_free(file);
81            }
82           
83            gtk_widget_destroy(of);
84        }
[8290]85
[8294]86        // Assume we're wanting FPS toggling.
87        else {
88            if(not _tid) {
89                _tid = g_timeout_add(
90                    15,
91                    (GSourceFunc)(ExampleOSGGTKDrawingArea::timeout),
92                    this
93                );
[8290]94
[8294]95                gtk_button_set_label(GTK_BUTTON(widget), "Toggle 60 FPS (off)");
96            }
[8290]97
[8294]98            else {
99                g_source_remove(_tid);
100                gtk_button_set_label(GTK_BUTTON(widget), "Toggle 60 FPS (on)");
[8290]101
[8294]102                _tid = 0;
103            }
104        }
[8290]105
[8294]106        return true;
107    }
[8290]108
109protected:
[8294]110    // Check right-click release to see if we need to popup our menu.
111    bool gtkButtonRelease(double, double, unsigned int button) {
112        if(button == 3 and (stateControl() or stateShift())) gtk_menu_popup(
113            GTK_MENU(_menu),
114            0,
115            0,
116            0,
117            0,
118            button,
119            0
120        );
[8290]121
[8294]122        return true;
123    }
[8290]124
[8294]125    // Our "main" drawing pump. Since our app is just a model viewer, we use
126    // click+motion as our criteria for issuing OpenGL refreshes.
127    bool gtkMotionNotify(double, double) {
128        if(stateButton()) queueDraw();
[8290]129
[8294]130        return true;
131    }
[8290]132
133public:
[8294]134    ExampleOSGGTKDrawingArea():
135    OSGGTKDrawingArea (),
136    _menu             (gtk_menu_new()),
137    _tid              (0) {
138        _menuAdd("Option");
139        _menuAdd("Another Option");
140        _menuAdd("Still More Options");
[8290]141
[8294]142        gtk_widget_show_all(_menu);
[8290]143
[8294]144        getCamera()->setStats(new osg::Stats("omg"));
145    }
[8290]146
[8294]147    ~ExampleOSGGTKDrawingArea() {}
[8290]148
[8294]149    // Public so that we can use this as a callback in main().
150    static bool clicked(GtkWidget* widget, gpointer self) {
151        return static_cast<ExampleOSGGTKDrawingArea*>(self)->_clicked(widget);
152    }
[8290]153
[8294]154    //static gboolean timeout(GtkWidget* widget) {
155    static bool timeout(void* self) {
156        static_cast<ExampleOSGGTKDrawingArea*>(self)->queueDraw();
[8290]157
[8294]158        return true;
159    }
[8290]160};
161
162// Our main() function! FINALLY! Most of this code is GTK stuff, so it's mostly boilerplate.
163// If we wanted to get real jiggy with it we could use Glade and cut down about 20 lines of
164// code or so.
165int main(int argc, char** argv) {
[8294]166    gtk_init(&argc, &argv);
167    gtk_gl_init(&argc, &argv);
[8290]168
[8294]169    ExampleOSGGTKDrawingArea da;
[8290]170
[8294]171    if(da.createWidget(640, 480)) {
172        if(argc >= 2) {
173            osg::ref_ptr<osg::Node> model = osgDB::readNodeFile(argv[1]);
[8290]174
[8294]175            if(model.valid()) da.setSceneData(model.get());
176        }
[8290]177
[8294]178        GtkWidget* window    = gtk_window_new(GTK_WINDOW_TOPLEVEL);
179        GtkWidget* vbox1     = gtk_vbox_new(false, 3);
180        GtkWidget* vbox2     = gtk_vbox_new(false, 3);
181        GtkWidget* hbox      = gtk_hbox_new(false, 3);
182        GtkWidget* label     = gtk_label_new("");
183        GtkWidget* buttons[] = {
184            gtk_button_new_with_label("Open File"),
185            gtk_button_new_with_label("Toggle 60 FPS (on)"),
186            gtk_button_new_with_label("Close")
187        };
[8290]188
[8294]189        gtk_label_set_use_markup(GTK_LABEL(label), true);
190        gtk_label_set_label(GTK_LABEL(label), HELP_TEXT);
[8290]191
[8294]192        for(unsigned int i = 0; i < sizeof(buttons) / sizeof(GtkWidget*); i++) {
193            gtk_box_pack_start(
194                GTK_BOX(vbox2),
195                buttons[i],
196                false,
197                false,
198                0
199            );
[8290]200
[8294]201            g_signal_connect(
202                G_OBJECT(buttons[i]),
203                "clicked",
204                G_CALLBACK(ExampleOSGGTKDrawingArea::clicked),
205                &da
206            );
207        }
[8290]208
[8294]209        gtk_window_set_title(GTK_WINDOW(window), "osgviewerGTK");
[8290]210
[8294]211        gtk_box_pack_start(GTK_BOX(hbox), vbox2, true, true, 2);
212        gtk_box_pack_start(GTK_BOX(hbox), label, true, true, 2);
[8290]213
[8294]214        gtk_box_pack_start(GTK_BOX(vbox1), da.getWidget(), true, true, 2);
215        gtk_box_pack_start(GTK_BOX(vbox1), hbox, false, false, 2);
[8290]216
[8294]217        gtk_container_set_reallocate_redraws(GTK_CONTAINER(window), true);
218        gtk_container_add(GTK_CONTAINER(window), vbox1);
[8290]219
[8294]220        g_signal_connect(
221            G_OBJECT(window),
222            "delete_event",
223            G_CALLBACK(gtk_main_quit),
224            0
225        );
[8290]226
[8294]227        gtk_widget_show_all(window);
228        gtk_main();
229    }
[8290]230
[8294]231    else return 1;
[8290]232
[8294]233    return 0;
[8290]234}
Note: See TracBrowser for help on using the browser.