summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKjell Ahlstedt <kjell.ahlstedt@bredband.net>2011-02-14 16:24:27 +0100
committerMurray Cumming <murrayc@murrayc.com>2011-02-15 12:41:59 +0100
commit94a1f3d568decbde9c3fab84c34db5741ffcad62 (patch)
tree7b25ba17b002e06ea7d8642a4ebe61cfe3038be9
parentefa5be64159016d2b9cc4ac8d1cc5a6176703ce7 (diff)
downloadglibmm-94a1f3d568decbde9c3fab84c34db5741ffcad62.tar.gz
OptionGroup: Add add_entry() that takes a slot with callback function.
* glib/src/optiongroup.[hg|ccg]: Add add_entry() and add_entry_filename() that take a slot. Add protected option_arg_callback(). An exception thrown by on_pre_parse() or on_post_parse() is propagated to the error argument of g_callback_pre_parse() or post_parse_callback(). * glib/src/optionentry.hg: Add description of set_flags(). * examples/options/main.cc: Add more OptionEntries and callback functions for parsing command option values. Bug 589197 (Hubert Figuiere)
-rw-r--r--ChangeLog13
-rw-r--r--examples/options/main.cc94
-rw-r--r--glib/src/optionentry.hg8
-rw-r--r--glib/src/optiongroup.ccg273
-rw-r--r--glib/src/optiongroup.hg15
5 files changed, 365 insertions, 38 deletions
diff --git a/ChangeLog b/ChangeLog
index e2243aea..ce458d43 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,16 @@
+2011-02-14 Kjell Ahlstedt <kjell.ahlstedt@bredband.net>
+
+ OptionGroup: Add add_entry() that takes a slot with callback function.
+
+ * glib/src/optiongroup.[hg|ccg]: Add add_entry() and add_entry_filename()
+ that take a slot. Add protected option_arg_callback().
+ An exception thrown by on_pre_parse() or on_post_parse() is propagated
+ to the error argument of g_callback_pre_parse() or post_parse_callback().
+ * glib/src/optionentry.hg: Add description of set_flags().
+ * examples/options/main.cc: Add more OptionEntries and callback functions
+ for parsing command option values.
+ Bug #589197 (Hubert Figuiere)
+
2011-02-15 Murray Cumming <murrayc@murrayc.com>
Dealt with several TODOs.
diff --git a/examples/options/main.cc b/examples/options/main.cc
index 0ba5372b..ee524dac 100644
--- a/examples/options/main.cc
+++ b/examples/options/main.cc
@@ -28,7 +28,12 @@ public:
virtual bool on_pre_parse(Glib::OptionContext& context, Glib::OptionGroup& group);
virtual bool on_post_parse(Glib::OptionContext& context, Glib::OptionGroup& group);
virtual void on_error(Glib::OptionContext& context, Glib::OptionGroup& group);
-
+
+ bool on_option_arg_string(const Glib::ustring& option_name,
+ const Glib::ustring& value, bool has_value);
+ bool on_option_arg_filename(const Glib::ustring& option_name,
+ const std::string& value, bool has_value);
+
//These members should live as long as the OptionGroup to which they are added,
//and as long as the OptionContext to which that OptionGroup is added.
int m_arg_foo;
@@ -37,6 +42,8 @@ public:
bool m_arg_boolean;
Glib::OptionGroup::vecustrings m_arg_list;
Glib::OptionGroup::vecustrings m_remaining_list;
+ Glib::ustring m_arg_x_string;
+ std::string m_arg_x_filename;
};
ExampleOptionGroup::ExampleOptionGroup()
@@ -73,6 +80,22 @@ ExampleOptionGroup::ExampleOptionGroup()
entry5.set_description("A List");
add_entry(entry5, m_arg_list);
+ Glib::OptionEntry entry6;
+ entry6.set_long_name("x-string");
+ entry6.set_short_name('x');
+ entry6.set_description("A string with custom parsing");
+ entry6.set_flags(Glib::OptionEntry::FLAG_OPTIONAL_ARG);
+ m_arg_x_string = "not specified";
+ add_entry(entry6, sigc::mem_fun(*this, &ExampleOptionGroup::on_option_arg_string));
+
+ Glib::OptionEntry entry7;
+ entry7.set_long_name("x-filename");
+ entry7.set_short_name('X');
+ entry7.set_description("A filename with custom parsing");
+ entry7.set_flags(Glib::OptionEntry::FLAG_OPTIONAL_ARG);
+ m_arg_x_filename = "not specified";
+ add_entry_filename(entry7, sigc::mem_fun(*this, &ExampleOptionGroup::on_option_arg_filename));
+
Glib::OptionEntry entry_remaining;
entry_remaining.set_long_name(G_OPTION_REMAINING);
entry_remaining.set_arg_description(G_OPTION_REMAINING);
@@ -103,6 +126,66 @@ void ExampleOptionGroup::on_error(Glib::OptionContext& /* context */, Glib::Opti
std::cout << "on_error called" << std::endl;
}
+bool ExampleOptionGroup::on_option_arg_string(const Glib::ustring& option_name,
+ const Glib::ustring& value, bool has_value)
+{
+ if(option_name != "-x" && option_name != "--x-string")
+ {
+ m_arg_x_string = "on_option_arg_string called with unexpected option_name: " + option_name;
+ throw Glib::OptionError(Glib::OptionError::UNKNOWN_OPTION, m_arg_x_string);
+ }
+
+ if(!has_value)
+ {
+ m_arg_x_string = "no value";
+ return true;
+ }
+
+ if(value.empty())
+ {
+ m_arg_x_string = "empty string";
+ return true;
+ }
+
+ m_arg_x_string = value;
+ if(value == "error")
+ {
+ throw Glib::OptionError(Glib::OptionError::BAD_VALUE,
+ "on_option_arg_string called with value = " + m_arg_x_string);
+ }
+ return value != "false";
+}
+
+bool ExampleOptionGroup::on_option_arg_filename(const Glib::ustring& option_name,
+ const std::string& value, bool has_value)
+{
+ if(option_name != "-X" && option_name != "--x-filename")
+ {
+ m_arg_x_filename = "on_option_arg_filename called with unexpected option_name: " + option_name;
+ throw Glib::OptionError(Glib::OptionError::UNKNOWN_OPTION, m_arg_x_filename);
+ }
+
+ if(!has_value)
+ {
+ m_arg_x_filename = "no value";
+ return true;
+ }
+
+ if(value.empty())
+ {
+ m_arg_x_filename = "empty string";
+ return true;
+ }
+
+ m_arg_x_filename = value;
+ if(value == "error")
+ {
+ throw Glib::OptionError(Glib::OptionError::BAD_VALUE,
+ "on_option_arg_filename called with value = " + m_arg_x_filename);
+ }
+ return value != "false";
+}
+
int main(int argc, char** argv)
{
@@ -111,7 +194,10 @@ int main(int argc, char** argv)
//./example --help
Glib::init();
-
+
+ //Set up the current locale.
+ setlocale(LC_ALL, "");
+
Glib::OptionContext context;
ExampleOptionGroup group;
@@ -130,7 +216,9 @@ int main(int argc, char** argv)
" foo = " << group.m_arg_foo << std::endl <<
" filename = " << group.m_arg_filename << std::endl <<
" activate_something = " << (group.m_arg_boolean ? "enabled" : "disabled") << std::endl <<
- " goo = " << group.m_arg_goo << std::endl;
+ " goo = " << group.m_arg_goo << std::endl <<
+ " x-string = " << group.m_arg_x_string << std::endl <<
+ " x-filename = " << group.m_arg_x_filename << std::endl;
//This one shows the results of multiple instance of the same option, such as --list=1 --list=a --list=b
std::cout << " list = ";
diff --git a/glib/src/optionentry.hg b/glib/src/optionentry.hg
index 74d74ded..5bab0e5c 100644
--- a/glib/src/optionentry.hg
+++ b/glib/src/optionentry.hg
@@ -75,20 +75,20 @@ public:
_MEMBER_SET(short_name, short_name, gchar, gchar)
_MEMBER_GET(flags, flags, int, int)
+ /** Set one or more OptionEntry::Flags.
+ * Do not set FLAG_FILENAME. Character encoding is chosen when the OptionEntry
+ * is added to an OptionGroup.
+ */
_MEMBER_SET(flags, flags, int, int)
- //TODO: G_OPTION_ARG_CALLBACK,
-
_MEMBER_GET(description, description, Glib::ustring, const char*)
void set_description(const Glib::ustring& value);
-
_MEMBER_GET(arg_description, arg_description, Glib::ustring, const char*)
void set_arg_description(const Glib::ustring& value);
-
GOptionEntry* gobj() { return gobject_; }
const GOptionEntry* gobj() const { return gobject_; }
diff --git a/glib/src/optiongroup.ccg b/glib/src/optiongroup.ccg
index ed5e45a6..358d8661 100644
--- a/glib/src/optiongroup.ccg
+++ b/glib/src/optiongroup.ccg
@@ -31,25 +31,79 @@ namespace Glib
namespace //anonymous
{
+//A pointer to an OptionArgCallback instance is stored in CppOptionEntry::cpparg_
+//when a callback function shall parse the command option's value.
+class OptionArgCallback
+{
+public:
+ OptionArgCallback(const OptionGroup::SlotOptionArgString& slot)
+ : slot_string(new OptionGroup::SlotOptionArgString(slot)), slot_filename(0)
+ { }
+
+ OptionArgCallback(const OptionGroup::SlotOptionArgFilename& slot)
+ : slot_string(0), slot_filename(new OptionGroup::SlotOptionArgFilename(slot))
+ { }
+
+ bool is_filename_option() const { return slot_filename != 0; }
+ const OptionGroup::SlotOptionArgString* get_slot_string() const { return slot_string; }
+ const OptionGroup::SlotOptionArgFilename* get_slot_filename() const { return slot_filename; }
+
+ ~OptionArgCallback()
+ {
+ delete slot_string;
+ delete slot_filename;
+ }
+
+private:
+ //One of these slot pointers is 0 and the other one points to a slot.
+ OptionGroup::SlotOptionArgString* slot_string;
+ OptionGroup::SlotOptionArgFilename* slot_filename;
+
+ //Not copyable
+ OptionArgCallback(const OptionArgCallback&);
+ OptionArgCallback& operator=(const OptionArgCallback&);
+};
+
extern "C"
{
-static gboolean g_callback_pre_parse(GOptionContext* context, GOptionGroup* /* group */, gpointer data, GError** /* TODO error */)
+static gboolean g_callback_pre_parse(GOptionContext* context,
+ GOptionGroup* /* group */, gpointer data, GError** error)
{
OptionContext cppContext(context, false /* take_ownership */);
- //OptionGroup cppGroup(group, true /* take_copy */); //Maybe this should be option_group.
OptionGroup* option_group = static_cast<OptionGroup*>(data);
- if(option_group)
- return option_group->on_pre_parse(cppContext, *option_group);
- else
+ if(!option_group)
+ {
+ OptionError(OptionError::FAILED, "Glib::OptionGroup: g_callback_pre_parse(): "
+ "No OptionGroup pointer available").propagate(error);
return false;
+ }
+
+ try
+ {
+ return option_group->on_pre_parse(cppContext, *option_group);
+ }
+ catch(Glib::Error& err)
+ {
+ err.propagate(error);
+ }
+ catch(...)
+ {
+ Glib::exception_handlers_invoke();
+ }
+ return false;
}
-static void g_callback_error(GOptionContext* context, GOptionGroup* /* group */, gpointer data, GError** /* TODO error*/)
+static void g_callback_error(GOptionContext* context,
+ GOptionGroup* /* group */, gpointer data, GError** /* TODO error */)
{
+ // TODO GError** error is input data containing information on an error that
+ // has occurred before this function is called. When API can be broken,
+ // the function prototype of on_error ought to be changed to
+ // void on_error(OptionContext& context, Error& error).
+
OptionContext cppContext(context, false /* take_ownership */);
- //OptionGroup cppGroup(group); //Maybe this should be option_group.
OptionGroup* option_group = static_cast<OptionGroup*>(data);
if(option_group)
@@ -86,33 +140,133 @@ static void OptionGroup_Translate_glibmm_callback_destroy(void* data)
//static
gboolean OptionGroup::post_parse_callback(GOptionContext* context,
- GOptionGroup* /* group */, gpointer data, GError** /* TODO error */)
+ GOptionGroup* /* group */, gpointer data, GError** error)
{
OptionContext cppContext(context, false /* take_ownership */);
- //OptionGroup cppGroup(group, true /* take_copy */); //Maybe this should be option_group.
OptionGroup* option_group = static_cast<OptionGroup*>(data);
- if(option_group)
+ if(!option_group)
{
- //The C args have now been given values by g_option_context_parse().
- //Convert C values to C++ values:
+ OptionError(OptionError::FAILED, "Glib::OptionGroup::post_parse_callback(): "
+ "No OptionGroup pointer available").propagate(error);
+ return false;
+ }
- for(type_map_entries::iterator iter = option_group->map_entries_.begin();
- iter != option_group->map_entries_.end(); ++iter)
- {
- CppOptionEntry& cpp_entry = iter->second;
- cpp_entry.convert_c_to_cpp();
- }
+ //The C args have now been given values by g_option_context_parse().
+ //Convert C values to C++ values:
+ for(type_map_entries::iterator iter = option_group->map_entries_.begin();
+ iter != option_group->map_entries_.end(); ++iter)
+ {
+ CppOptionEntry& cpp_entry = iter->second;
+ cpp_entry.convert_c_to_cpp();
+ }
+
+ try
+ {
return option_group->on_post_parse(cppContext, *option_group);
}
+ catch(Glib::Error& err)
+ {
+ err.propagate(error);
+ }
+ catch(...)
+ {
+ Glib::exception_handlers_invoke();
+ }
+ return false;
+}
+
+//static
+gboolean OptionGroup::option_arg_callback(const gchar* option_name, const gchar* value,
+ gpointer data, GError** error)
+{
+ const Glib::ustring cpp_option_name(option_name);
+ const OptionGroup* const option_group = static_cast<const OptionGroup*>(data);
+ if(!option_group)
+ {
+ OptionError(OptionError::FAILED, "Glib::OptionGroup::option_arg_callback(): "
+ "No OptionGroup pointer available for option " + cpp_option_name).propagate(error);
+ return false;
+ }
+
+ //option_name is either a single dash followed by a single letter (for a
+ //short name) or two dashes followed by a long option name.
+ OptionGroup::type_map_entries::const_iterator iterFind = option_group->map_entries_.end();
+ if(option_name[1] == '-')
+ {
+ //Long option name.
+ const Glib::ustring long_option_name = Glib::ustring(option_name+2);
+ iterFind = option_group->map_entries_.find(long_option_name);
+ }
else
+ {
+ //Short option name.
+ const gchar short_option_name = option_name[1];
+ for(iterFind = option_group->map_entries_.begin();
+ iterFind != option_group->map_entries_.end(); ++iterFind)
+ {
+ const OptionGroup::CppOptionEntry& cppOptionEntry = iterFind->second;
+ if (cppOptionEntry.entry_ &&
+ cppOptionEntry.entry_->get_short_name() == short_option_name)
+ break;
+ }
+ }
+
+ if(iterFind == option_group->map_entries_.end())
+ {
+ OptionError(OptionError::UNKNOWN_OPTION, "Glib::OptionGroup::option_arg_callback(): "
+ "Unknown option " + cpp_option_name).propagate(error);
+ return false;
+ }
+
+ const OptionGroup::CppOptionEntry& cppOptionEntry = iterFind->second;
+ if (cppOptionEntry.carg_type_ != G_OPTION_ARG_CALLBACK)
+ {
+ OptionError(OptionError::FAILED, "Glib::OptionGroup::option_arg_callback() "
+ "called for non-callback option " + cpp_option_name).propagate(error);
return false;
+ }
+
+ const bool has_value = (value != 0);
+ const OptionArgCallback* const option_arg =
+ static_cast<const OptionArgCallback*>(cppOptionEntry.cpparg_);
+ try
+ {
+ if (option_arg->is_filename_option())
+ {
+ const OptionGroup::SlotOptionArgFilename* the_slot = option_arg->get_slot_filename();
+ const std::string cpp_value(value ? value : "");
+ return (*the_slot)(cpp_option_name, cpp_value, has_value);
+ }
+ else
+ {
+ const OptionGroup::SlotOptionArgString* the_slot = option_arg->get_slot_string();
+ const Glib::ustring cpp_value(value ? value : "");
+ return (*the_slot)(cpp_option_name, cpp_value, has_value);
+ }
+ }
+ catch(Glib::Error& err)
+ {
+ err.propagate(error);
+ }
+ catch(...)
+ {
+ Glib::exception_handlers_invoke();
+ }
+ return false;
}
OptionGroup::OptionGroup(const Glib::ustring& name, const Glib::ustring& description, const Glib::ustring& help_description)
-: gobject_( g_option_group_new(name.c_str(), description.c_str(), help_description.c_str(), this, 0 /* destroy_func */) ),
+: gobject_( g_option_group_new(name.c_str(), description.c_str(), help_description.c_str(),
+ this /* user_data */, 0 /* destroy_func */) ),
has_ownership_(true)
{
+ //g_callback_pre_parse(), post_parse_callback(), g_callback_error(), and
+ //option_arg_callback() depend on user_data being this. The first three
+ //functions get a GOptionGroup*, but it would not be correct to use it for
+ //creating a new OptionGroup. They must call their virtual functions in the
+ //original OptionGroup instance.
+
//Connect callbacks, so that derived classes can override the virtual methods:
g_option_group_set_parse_hooks(gobj(), &g_callback_pre_parse, &post_parse_callback);
g_option_group_set_error_hook(gobj(), &g_callback_error);
@@ -191,7 +345,30 @@ void OptionGroup::add_entry_filename(const OptionEntry& entry, vecstrings& arg)
{
add_entry_with_wrapper(entry, G_OPTION_ARG_FILENAME_ARRAY, &arg);
}
-
+
+// When the command argument value is to be parsed by a user-supplied function
+// (indicated by G_OPTION_ARG_CALLBACK), the FLAG_FILENAME in 'entry' is ignored.
+// set_c_arg_default() clears or sets it as required in a copy of 'entry'.
+//
+// The glib API is inconsistent here. The choice between UTF-8 and filename
+// encoding is done with G_OPTION_ARG_STRING, G_OPTION_ARG_FILENAME,
+// G_OPTION_ARG_STRING_ARRAY, and G_OPTION_ARG_FILENAME_ARRAY, which in glibmm
+// are set by OptionGroup::add_entry[_filename]. But when a callback function
+// is chosen, there is only G_OPTION_ARG_CALLBACK, and the encoding is chosen
+// with G_OPTION_FLAG_FILENAME. Other option flags are set by OptionEntry::set_flags().
+
+void OptionGroup::add_entry(const OptionEntry& entry, const SlotOptionArgString& slot)
+{
+ //The OptionArgCallback is deleted in release_c_arg().
+ add_entry_with_wrapper(entry, G_OPTION_ARG_CALLBACK, new OptionArgCallback(slot));
+}
+
+void OptionGroup::add_entry_filename(const OptionEntry& entry, const SlotOptionArgFilename& slot)
+{
+ //The OptionArgCallback is deleted in release_c_arg().
+ add_entry_with_wrapper(entry, G_OPTION_ARG_CALLBACK, new OptionArgCallback(slot));
+}
+
void OptionGroup::add_entry_with_wrapper(const OptionEntry& entry, GOptionArg arg_type, void* cpp_arg)
{
const Glib::ustring name = entry.get_long_name();
@@ -199,6 +376,10 @@ void OptionGroup::add_entry_with_wrapper(const OptionEntry& entry, GOptionArg ar
if( iterFind == map_entries_.end() ) //If we have not added this entry already
{
CppOptionEntry cppEntry;
+ //g_option_group_add_entry() does not take its own copy, so we must keep the instance alive.
+ cppEntry.entry_ = new OptionEntry(entry);
+ //cppEntry.entry_ is deleted in release_c_arg(), via the destructor.
+
cppEntry.carg_type_ = arg_type;
cppEntry.allocate_c_arg();
cppEntry.set_c_arg_default(cpp_arg);
@@ -206,10 +387,6 @@ void OptionGroup::add_entry_with_wrapper(const OptionEntry& entry, GOptionArg ar
cppEntry.cpparg_ = cpp_arg;
//Give the information to the C API:
-
- cppEntry.entry_ = new OptionEntry(entry); //g_option_group_add_entry() does not take its own copy, so we must keep the instance alive. */
- //cppEntry.entry_ is deleted in release_c_arg(), via the destructor.
-
cppEntry.entry_->gobj()->arg = arg_type;
cppEntry.entry_->gobj()->arg_data = cppEntry.carg_;
@@ -256,7 +433,8 @@ void OptionGroup::CppOptionEntry::allocate_c_arg()
//Create an instance of the appropriate C type.
//This will be destroyed in the OptionGroup destructor.
//
- //We must also call set_c_arg_default() to give these C types the specified defaults based on the C++-typed arguments.
+ //We must also call set_c_arg_default() to give these C types the specified
+ //defaults based on the C++-typed arguments.
switch(carg_type_)
{
case G_OPTION_ARG_STRING: //The char* will be for UTF8 strins.
@@ -303,6 +481,13 @@ void OptionGroup::CppOptionEntry::allocate_c_arg()
break;
}
+ case G_OPTION_ARG_CALLBACK:
+ {
+ //The C arg pointer is a function pointer.
+ carg_ = reinterpret_cast<void*>(&OptionGroup::option_arg_callback);
+
+ break;
+ }
default:
{
break;
@@ -389,6 +574,22 @@ void OptionGroup::CppOptionEntry::set_c_arg_default(void* cpp_arg)
}
break;
}
+ case G_OPTION_ARG_CALLBACK:
+ {
+ //No value to set here. The arg pointer is a function pointer.
+
+ //Set or clear FLAG_FILENAME in *entry_.
+ const OptionArgCallback* const option_arg = static_cast<const OptionArgCallback*>(cpp_arg);
+ if (option_arg->is_filename_option())
+ {
+ entry_->set_flags(entry_->get_flags() | OptionEntry::FLAG_FILENAME);
+ }
+ else
+ {
+ entry_->set_flags(entry_->get_flags() & ~OptionEntry::FLAG_FILENAME);
+ }
+ break;
+ }
default:
{
break;
@@ -440,11 +641,18 @@ void OptionGroup::CppOptionEntry::release_c_arg()
break;
}
+ case G_OPTION_ARG_CALLBACK:
+ {
+ //Delete the OptionArgCallback instance that was allocated by add_entry()
+ //or add_entry_filename().
+ OptionArgCallback* option_arg = static_cast<OptionArgCallback*>(cpparg_);
+ delete option_arg;
+ cpparg_ = 0;
+
+ break;
+ }
default:
{
- /* TODO:
- G_OPTION_ARG_CALLBACK,
- */
break;
}
}
@@ -560,11 +768,14 @@ void OptionGroup::CppOptionEntry::convert_c_to_cpp()
*(static_cast<bool*>(cpparg_)) = *(static_cast<gboolean*>(carg_));
break;
}
+ case G_OPTION_ARG_CALLBACK:
+ {
+ //Nothing to convert here. That's a task for the callback function
+ //(the SlotOptionArgString or SlotOptionArgFilename).
+ break;
+ }
default:
{
- /* TODO:
- G_OPTION_ARG_CALLBACK,
- */
break;
}
}
diff --git a/glib/src/optiongroup.hg b/glib/src/optiongroup.hg
index 8d687b25..f31015dc 100644
--- a/glib/src/optiongroup.hg
+++ b/glib/src/optiongroup.hg
@@ -51,6 +51,16 @@ public:
*/
typedef sigc::slot<Glib::ustring, const Glib::ustring&> SlotTranslate;
+ /** For example bool on_option_arg_string(const Glib::ustring& option_name,
+ * const Glib::ustring& value, bool has_value);.
+ */
+ typedef sigc::slot<bool, const Glib::ustring&, const Glib::ustring&, bool> SlotOptionArgString;
+
+ /** For example bool on_option_arg_filename(const Glib::ustring& option_name,
+ * const std::string& value, bool has_value);.
+ */
+ typedef sigc::slot<bool, const Glib::ustring&, const std::string&, bool> SlotOptionArgFilename;
+
OptionGroup(const Glib::ustring& name, const Glib::ustring& description, const Glib::ustring& help_description = Glib::ustring());
/** This always takes ownership of the underlying GOptionGroup,
@@ -81,6 +91,8 @@ public:
void add_entry_filename(const OptionEntry& entry, std::string& arg);
void add_entry(const OptionEntry& entry, vecustrings& arg);
void add_entry_filename(const OptionEntry& entry, vecstrings& arg);
+ void add_entry(const OptionEntry& entry, const SlotOptionArgString& slot);
+ void add_entry_filename(const OptionEntry& entry, const SlotOptionArgFilename& slot);
/** Sets the function which is used to translate user-visible strings, for
* --help output. Different groups can use a different SlotTranslate. If a
@@ -128,6 +140,9 @@ protected:
static gboolean post_parse_callback(GOptionContext* context,
GOptionGroup* group, gpointer data, GError** error);
+ static gboolean option_arg_callback(const gchar* option_name, const gchar* value,
+ gpointer data, GError** error);
+
//Map of entry names to CppOptionEntry:
typedef std::map<Glib::ustring, CppOptionEntry> type_map_entries;
type_map_entries map_entries_;