namespace Msp {
+GetOpt::~GetOpt()
+{
+ for(list<OptBase *>::iterator i=opts.begin(); i!=opts.end(); ++i)
+ delete *i;
+}
+
/**
Generates a single line that gives an overview about the known options.
if(!(*i)->get_long().empty())
line<<'|';
else if((*i)->get_arg_type()==OPTIONAL_ARG)
- line<<"[ARG]";
+ line<<'['<<(*i)->get_metavar()<<']';
else if((*i)->get_arg_type()==REQUIRED_ARG)
- line<<" ARG";
+ line<<' '<<(*i)->get_metavar();
}
if(!(*i)->get_long().empty())
{
line<<"--"<<(*i)->get_long();
if((*i)->get_arg_type()==OPTIONAL_ARG)
- line<<"[=ARG]";
+ line<<"[="<<(*i)->get_metavar()<<']';
else if((*i)->get_arg_type()==REQUIRED_ARG)
- line<<"=ARG";
+ line<<'='<<(*i)->get_metavar();
}
line<<']';
}
*/
string GetOpt::generate_help() const
{
- string result;
+ bool any_short=false;
+ for(list<OptBase *>::const_iterator i=opts.begin(); (!any_short && i!=opts.end()); ++i)
+ any_short=(*i)->get_short();
+
+ string::size_type maxw=0;
+ list<string> switches;
for(list<OptBase *>::const_iterator i=opts.begin(); i!=opts.end(); ++i)
{
- ostringstream line;
- line<<" ";
+ ostringstream swtch;
if((*i)->get_short())
{
- line<<'-'<<(*i)->get_short();
+ swtch<<'-'<<(*i)->get_short();
if(!(*i)->get_long().empty())
- line<<", ";
+ swtch<<", ";
else if((*i)->get_arg_type()==OPTIONAL_ARG)
- line<<"[ARG]";
+ swtch<<'['<<(*i)->get_metavar()<<']';
else if((*i)->get_arg_type()==REQUIRED_ARG)
- line<<" ARG";
+ swtch<<' '<<(*i)->get_metavar();
}
+ else if(any_short)
+ swtch<<" ";
if(!(*i)->get_long().empty())
{
- line<<"--"<<(*i)->get_long();
+ swtch<<"--"<<(*i)->get_long();
if((*i)->get_arg_type()==OPTIONAL_ARG)
- line<<"[=ARG]";
+ swtch<<"[="<<(*i)->get_metavar()<<']';
else if((*i)->get_arg_type()==REQUIRED_ARG)
- line<<"=ARG";
+ swtch<<'='<<(*i)->get_metavar();
}
+ switches.push_back(swtch.str());
+ maxw=max(maxw, switches.back().size());
+ }
- line<<" "<<(*i)->get_help()<<'\n';
-
- result+=line.str();
+ string result;
+ list<string>::const_iterator j=switches.begin();
+ for(list<OptBase *>::const_iterator i=opts.begin(); i!=opts.end(); ++i, ++j)
+ {
+ result+=" "+*j;
+ result+=string(maxw+2-j->size(), ' ');
+ result+=(*i)->get_help();
+ result+='\n';
}
return result;
args.push_back(argv[i]);
}
-GetOpt::~GetOpt()
-{
- for(list<OptBase *>::iterator i=opts.begin(); i!=opts.end(); ++i)
- delete *i;
-}
-
GetOpt::OptBase &GetOpt::get_option(char s)
{
for(list<OptBase *>::iterator i=opts.begin(); i!=opts.end(); ++i)
// See if the argument contains an =
unsigned equals=0;
- for(; arg[equals] && arg[equals]!='='; ++equals);
+ for(; arg[equals] && arg[equals]!='='; ++equals) ;
OptBase &opt=get_option(string(arg, equals));
return 1;
}
+
+GetOpt::OptBase::OptBase(char s, const std::string &l, ArgType a):
+ shrt(s),
+ lng(l),
+ arg_type(a),
+ seen_count(0),
+ metavar("ARG")
+{ }
+
+GetOpt::OptBase &GetOpt::OptBase::set_help(const string &h)
+{
+ help=h;
+ return *this;
+}
+
+GetOpt::OptBase &GetOpt::OptBase::set_help(const string &h, const string &m)
+{
+ help=h;
+ metavar=m;
+ return *this;
+}
+
+void GetOpt::OptBase::process()
+{
+ if(arg_type==REQUIRED_ARG)
+ throw UsageError("--"+lng+" requires an argument");
+ ++seen_count;
+
+ store();
+}
+
+void GetOpt::OptBase::process(const string &arg)
+{
+ if(arg_type==NO_ARG)
+ throw UsageError("--"+lng+" takes no argument");
+ ++seen_count;
+
+ store(arg);
+}
+
} // namespace Msp