signal_ungrab_pointer.emit();
}
-void Dialog::button_release(int x, int y, unsigned button)
-{
- Panel::button_release(x, y, button);
- check_stale();
-}
-
-bool Dialog::key_release(unsigned key, unsigned mod)
-{
- bool result = Panel::key_release(key, mod);
- check_stale();
- return result;
-}
-
-bool Dialog::navigate(Navigation nav)
-{
- bool result = Panel::navigate(nav);
- check_stale();
- return result;
-}
-
void Dialog::response(int code)
{
on_response(code);
signal_response.emit(code);
- stale = true;
-}
-
-void Dialog::check_stale()
-{
- if(stale)
- delete this;
+ set_visible(false);
}
/**
A Dialog is used for temporary interaction with the user. When any of the
-Dialog's action buttons are clicked, it will emit a signal and delete itself.
+Dialog's action buttons are clicked, it will emit a signal and hide itself.
*/
class MSPGLTK_API Dialog: public Panel
{
sigc::signal<void, int> signal_response;
-private:
- bool stale = false;
-
-public:
const char *get_class() const override { return "dialog"; }
/** Adds an action button to the dialog. Pressing the button will invoke
away from the dialog. */
void set_modal(bool);
- void button_release(int, int, unsigned) override;
- bool key_release(unsigned, unsigned) override;
- bool navigate(Navigation) override;
protected:
void response(int);
- void check_stale();
/** Called when an action button is pressed. */
virtual void on_response(int) { }
};
+
+/**
+A dialog which automatically deletes itself after being responded to.
+*/
+template<typename D>
+class MSPGLTK_API AutoDialog: public D
+{
+private:
+ struct StaleChecker
+ {
+ AutoDialog *dialog;
+
+ StaleChecker(AutoDialog &d): dialog(&d) { }
+ ~StaleChecker() { if(dialog->stale) delete dialog; }
+ };
+
+ bool stale = false;
+
+ template<typename... Args>
+ AutoDialog(Args &&... args): D(std::forward<Args>(args)...) { }
+
+public:
+ // Ensure that AutoDialog is always created with new.
+ template<typename... Args>
+ static AutoDialog *create(Args &&... args) { return new AutoDialog(std::forward<Args>(args)...); }
+
+ void button_release(int x, int y, unsigned b) override { StaleChecker sc(*this); D::button_release(x, y, b); }
+ bool key_release(unsigned k, unsigned m) override { StaleChecker sc(*this); return D::key_release(k, m); }
+ bool navigate(Navigation n) override { StaleChecker sc(*this); return D::navigate(n); }
+
+protected:
+ void on_response(int c) override { D::on_response(c); stale = true; }
+};
+
} // namespace GLtk
} // namespace Msp