6 #include "../conversion/stringconversion.h" 7 #include "../conversion/stringbuilder.h" 8 #include "../io/path.h" 9 #include "../io/ansiescapecodes.h" 44 ArgumentReader::ArgumentReader(
ArgumentParser &parser,
const char *
const *argv,
const char *
const *end,
bool completionMode) :
46 args(parser.m_mainArgs),
51 argDenotation(nullptr),
52 completionMode(completionMode)
86 const vector<Argument *> &parentPath = parentArg ? parentArg->
path(parentArg->
occurrences() - 1) : vector<Argument *>();
89 vector<const char *> *values =
nullptr;
99 bool abbreviationFound =
false;
102 abbreviationFound =
false;
112 abbreviationFound =
false;
120 size_t argDenotationLength;
123 for(argDenotationLength = equationPos ? static_cast<size_t>(equationPos -
argDenotation) : strlen(
argDenotation); argDenotationLength; matchingArg =
nullptr) {
127 if(arg->abbreviation() && arg->abbreviation() == *
argDenotation) {
129 abbreviationFound =
true;
135 if(arg->name() && !strncmp(arg->name(),
argDenotation, argDenotationLength) && *(arg->name() + argDenotationLength) ==
'\0') {
144 matchingArg->m_occurrences.emplace_back(
index, parentPath, parentArg);
147 values = &matchingArg->m_occurrences.back().values;
149 values->push_back(equationPos + 1);
159 argDenotation =
nullptr;
175 for(
auto parentArgument = parentPath.crbegin(), pathEnd = parentPath.crend(); ; ++parentArgument) {
176 for(
Argument *sibling : (parentArgument != pathEnd ? (*parentArgument)->subArguments() :
parser.m_mainArgs)) {
177 if(sibling->occurrences() < sibling->maxOccurrences()) {
179 || (sibling->name() && !strncmp(sibling->name(),
argDenotation, argDenotationLength))) {
184 if(parentArgument == pathEnd) {
200 if(arg->denotesOperation() && arg->name() && !strcmp(arg->name(), *
argv)) {
201 (matchingArg = arg)->m_occurrences.emplace_back(
index, parentPath, parentArg);
213 if(arg->isImplicit() && !arg->isPresent() && !arg->wouldConflictWithArgument() && (!uncombinableMainArgPresent || !arg->isMainArgument())) {
214 (matchingArg = arg)->m_occurrences.emplace_back(
index, parentPath, parentArg);
222 if(lastArgInLevel == matchingArg) {
227 values = &matchingArg->m_occurrences.back().values;
232 argDenotation =
nullptr;
245 switch(
parser.m_unknownArgBehavior) {
247 cerr <<
"The specified argument \"" << *
argv <<
"\" is unknown and will be ignored." << endl;
254 throw Failure(
"The specified argument \""s % *argv +
"\" is unknown and will be ignored."s);
279 inline bool notEmpty(
const char *str)
302 Argument::Argument(
const char *name,
char abbreviation,
const char *description,
const char *example) :
304 m_abbreviation(abbreviation),
305 m_environmentVar(nullptr),
306 m_description(description),
311 m_denotesOperation(false),
312 m_requiredValueCount(0),
316 m_preDefinedCompletionValues(nullptr)
334 if(!m_occurrences.empty() && !m_occurrences.front().values.empty()) {
335 return m_occurrences.front().values.front();
336 }
else if(m_environmentVar) {
337 return getenv(m_environmentVar);
350 if(notEmpty(
name())) {
351 os <<
'-' <<
'-' <<
name();
361 unsigned int valueNamesPrint = 0;
363 os <<
' ' <<
'[' << *i <<
']';
370 os <<
" [value " << (valueNamesPrint + 1) <<
']';
376 os <<
'\n' << Indentation(indentation) <<
description();
379 os <<
'\n' << Indentation(indentation) <<
"particularities: mandatory";
381 os <<
" if parent argument is present";
385 os <<
'\n' << Indentation(indentation) <<
"default environment variable: " <<
environmentVariable();
388 os <<
'\n' << Indentation(indentation) <<
"\nusage: " <<
example();
392 arg->printInfo(os, indentation);
404 if(arg != except && arg->
isPresent() && !arg->isCombinable()) {
429 arg->m_parents.erase(
remove(arg->m_parents.begin(), arg->m_parents.end(),
this), arg->m_parents.end());
432 m_subArgs.assign(secondaryArguments);
436 if(find(arg->m_parents.cbegin(), arg->m_parents.cend(),
this) == arg->m_parents.cend()) {
437 arg->m_parents.push_back(
this);
451 if(find(m_subArgs.cbegin(), m_subArgs.cend(), arg) == m_subArgs.cend()) {
452 m_subArgs.push_back(arg);
453 if(find(arg->m_parents.cbegin(), arg->m_parents.cend(),
this) == arg->m_parents.cend()) {
454 arg->m_parents.push_back(
this);
468 for(
const Argument *parent : m_parents) {
469 if(parent->isPresent()) {
502 if(sibling !=
this && sibling->isPresent() && !sibling->isCombinable()) {
518 arg->resetRecursively();
541 m_executable(nullptr),
543 m_defaultArg(nullptr)
557 if(mainArguments.size()) {
558 for(
Argument *arg : mainArguments) {
559 arg->m_isMainArg =
true;
561 m_mainArgs.assign(mainArguments);
563 if(!(*mainArguments.begin())->requiredValueCount()) {
564 bool subArgsRequired =
false;
565 for(
const Argument *subArg : (*mainArguments.begin())->subArguments()) {
566 if(subArg->isRequired()) {
567 subArgsRequired =
true;
571 if(!subArgsRequired) {
572 m_defaultArg = *mainArguments.begin();
589 argument->m_isMainArg =
true;
590 m_mainArgs.push_back(argument);
599 if(applicationName && *applicationName) {
601 if(applicationVersion && *applicationVersion) {
605 if(applicationVersion && *applicationVersion) {
608 if((applicationName && *applicationName) || (applicationVersion && *applicationVersion)) {
612 if(!m_mainArgs.empty()) {
613 os <<
"Available arguments:";
614 for(
const Argument *arg : m_mainArgs) {
619 if(applicationUrl && *applicationUrl) {
620 os <<
"\nProject website: " << applicationUrl << endl;
653 IF_DEBUG_BUILD(verifyArgs(m_mainArgs, std::vector<char>(), std::vector<const char *>());)
657 m_executable = *argv;
662 bool completionMode = !strcmp(*++argv,
"--bash-completion-for");
663 unsigned int currentWordIndex;
667 currentWordIndex = (--argc ? stringToNumber<unsigned int, string>(*(++argv)) : 0);
670 currentWordIndex =
static_cast<unsigned int>(argc - 1);
675 ArgumentReader reader(*
this, argv, argv + (completionMode ? min(static_cast<unsigned int>(argc), currentWordIndex + 1) : static_cast<unsigned int>(argc)), completionMode);
679 if(!completionMode) {
685 printBashCompletion(argc, argv, currentWordIndex, reader);
691 m_defaultArg->m_occurrences.emplace_back(0);
695 m_executable =
nullptr;
706 arg->resetRecursively();
716 for(
const Argument *arg : m_mainArgs) {
717 if(!arg->isCombinable() && arg->isPresent()) {
739 void ApplicationUtilities::ArgumentParser::verifyArgs(
const ArgumentVector &args, vector<char> abbreviations, vector<const char *> names)
741 vector<const Argument *> verifiedArgs;
742 verifiedArgs.reserve(args.size());
743 abbreviations.reserve(abbreviations.size() + args.size());
744 names.reserve(names.size() + args.size());
745 bool hasImplicit =
false;
747 assert(find(verifiedArgs.cbegin(), verifiedArgs.cend(), arg) == verifiedArgs.cend());
748 verifiedArgs.push_back(arg);
749 assert(arg->isMainArgument() || !arg->denotesOperation());
750 assert(!arg->isImplicit() || !hasImplicit);
751 hasImplicit |= arg->isImplicit();
752 assert(!arg->abbreviation() || find(abbreviations.cbegin(), abbreviations.cend(), arg->abbreviation()) == abbreviations.cend());
753 abbreviations.push_back(arg->abbreviation());
754 assert(!arg->name() || find_if(names.cbegin(), names.cend(), [arg] (
const char *name) {
return !strcmp(arg->name(), name); }) == names.cend());
755 assert(arg->requiredValueCount() == 0 || arg->subArguments().size() == 0);
756 names.emplace_back(arg->name());
759 verifyArgs(arg->subArguments(), abbreviations, names);
778 return strcmp(arg1->
name(), arg2->
name()) < 0;
788 bool onlyCombinable =
false;
789 for(
const Argument *sibling : siblings) {
790 if(sibling->isPresent() && !sibling->isCombinable()) {
791 onlyCombinable =
true;
795 for(
const Argument *sibling : siblings) {
796 if((!onlyCombinable || sibling->isCombinable()) && sibling->occurrences() < sibling->maxOccurrences()) {
797 target.push_back(sibling);
807 void ArgumentParser::printBashCompletion(
int argc,
const char *
const *argv,
unsigned int currentWordIndex,
const ArgumentReader &reader)
810 list<const Argument *> relevantArgs, relevantPreDefinedValues;
811 bool completeFiles =
false, completeDirs =
false, noWhitespace =
false;
815 size_t lastDetectedArgIndex;
816 vector<Argument *> lastDetectedArgPath;
817 if(lastDetectedArg) {
819 lastDetectedArgPath = lastDetectedArg->
path(lastDetectedArg->
occurrences() - 1);
823 const char *
const *lastSpecifiedArg;
824 unsigned int lastSpecifiedArgIndex;
826 lastSpecifiedArgIndex =
static_cast<unsigned int>(argc) - 1;
827 lastSpecifiedArg = argv + lastSpecifiedArgIndex;
828 for(; lastSpecifiedArg >= argv && **lastSpecifiedArg ==
'\0'; --lastSpecifiedArg, --lastSpecifiedArgIndex);
832 bool nextArgumentOrValue;
833 if(lastDetectedArg && lastDetectedArg->
isPresent()) {
834 if((nextArgumentOrValue = (currentWordIndex > lastDetectedArgIndex))) {
836 auto currentValueCount = lastDetectedArg->
values(lastDetectedArg->
occurrences() - 1).size();
837 if(currentValueCount) {
838 currentValueCount -= (currentWordIndex - lastDetectedArgIndex);
840 if(lastDetectedArg->
requiredValueCount() ==
static_cast<size_t>(-1) || (currentValueCount < lastDetectedArg->requiredValueCount())) {
842 relevantPreDefinedValues.push_back(lastDetectedArg);
853 if(subArg->occurrences() < subArg->maxOccurrences()) {
854 relevantArgs.push_back(subArg);
859 for(
auto parentArgument = lastDetectedArgPath.crbegin(), end = lastDetectedArgPath.crend(); ; ++parentArgument) {
860 insertSiblings(parentArgument != end ? (*parentArgument)->subArguments() : m_mainArgs, relevantArgs);
861 if(parentArgument == end) {
868 relevantArgs.push_back(lastDetectedArg);
873 nextArgumentOrValue =
true;
878 const char *opening =
nullptr;
879 string compoundOpening;
880 size_t openingLen, compoundOpeningStartLen = 0;
881 unsigned char openingDenotationType =
Value;
882 if(argc && nextArgumentOrValue) {
883 if(currentWordIndex < static_cast<unsigned int>(argc)) {
884 opening = argv[currentWordIndex];
890 size_t minCurrentWordIndex = (lastDetectedArg ? lastDetectedArgIndex : 0);
891 if(currentWordIndex > minCurrentWordIndex && !strcmp(opening,
"=")) {
892 compoundOpening.reserve(compoundOpeningStartLen = strlen(argv[--currentWordIndex]) + 1);
893 compoundOpening = argv[currentWordIndex];
894 compoundOpening +=
'=';
895 }
else if(currentWordIndex > (minCurrentWordIndex + 1) && !strcmp(argv[currentWordIndex - 1],
"=")) {
896 compoundOpening.reserve((compoundOpeningStartLen = strlen(argv[currentWordIndex -= 2]) + 1) + strlen(opening));
897 compoundOpening = argv[currentWordIndex];
898 compoundOpening +=
'=';
899 compoundOpening += opening;
901 if(!compoundOpening.empty()) {
902 opening = compoundOpening.data();
905 opening = *lastSpecifiedArg;
907 *opening ==
'-' && (++opening, ++openingDenotationType)
908 && *opening ==
'-' && (++opening, ++openingDenotationType);
909 openingLen = strlen(opening);
915 cout <<
"COMPREPLY=(";
917 for(
const Argument *arg : relevantPreDefinedValues) {
918 if(arg->preDefinedCompletionValues()) {
920 if(argc && currentWordIndex <= lastSpecifiedArgIndex && opening) {
921 if(openingDenotationType ==
Value) {
922 bool wordStart =
true, ok =
false, equationSignAlreadyPresent =
false;
923 size_t wordIndex = 0;
924 for(
const char *i = arg->preDefinedCompletionValues(), *end = opening + openingLen; *i;) {
926 const char *i1 = i, *i2 = opening;
927 for(; *i1 && i2 != end && *i1 == *i2; ++i1, ++i2);
928 if((ok = (i2 == end))) {
933 }
else if((wordStart = (*i ==
' ') || (*i ==
'\n'))) {
934 equationSignAlreadyPresent =
false;
940 }
else if(*i ==
'=') {
941 equationSignAlreadyPresent =
true;
944 if(!compoundOpeningStartLen || wordIndex >= compoundOpeningStartLen) {
953 case ' ':
case '\n':
case '\0':
954 if(appendEquationSign && !equationSignAlreadyPresent) {
957 equationSignAlreadyPresent =
false;
969 }
else if(
const char *i = arg->preDefinedCompletionValues()) {
970 bool equationSignAlreadyPresent =
false;
980 equationSignAlreadyPresent =
true;
982 case ' ':
case '\n':
case '\0':
983 if(appendEquationSign && !equationSignAlreadyPresent) {
985 equationSignAlreadyPresent =
false;
1000 for(
const Argument *arg : relevantArgs) {
1001 if(argc && currentWordIndex <= lastSpecifiedArgIndex && opening) {
1002 switch(openingDenotationType) {
1004 if(!arg->denotesOperation() || strncmp(arg->name(), opening, openingLen)) {
1011 if(strncmp(arg->name(), opening, openingLen)) {
1017 if(opening && openingDenotationType ==
Abbreviation && !nextArgumentOrValue) {
1018 cout <<
'\'' <<
'-' << opening << arg->abbreviation() <<
'\'' <<
' ';
1020 if(reader.
argv == reader.
end) {
1021 cout <<
'\'' << *(reader.
argv - 1) <<
'\'' <<
' ';
1023 }
else if(arg->denotesOperation() && (!
actualArgumentCount() || (currentWordIndex == 0 && (!lastDetectedArg || (lastDetectedArg->
isPresent() && lastDetectedArgIndex == 0))))) {
1024 cout <<
'\'' << arg->name() <<
'\'' <<
' ';
1026 cout <<
'\'' <<
'-' <<
'-' << arg->name() <<
'\'' <<
' ';
1031 string actualDir, actualFile;
1032 bool haveFileOrDirCompletions =
false;
1033 if(argc && currentWordIndex == lastSpecifiedArgIndex && opening) {
1035 string unescapedOpening(opening);
1036 findAndReplace<string>(unescapedOpening,
"\\ ",
" ");
1037 findAndReplace<string>(unescapedOpening,
"\\,",
",");
1038 findAndReplace<string>(unescapedOpening,
"\\[",
"[");
1039 findAndReplace<string>(unescapedOpening,
"\\]",
"]");
1040 findAndReplace<string>(unescapedOpening,
"\\!",
"!");
1041 findAndReplace<string>(unescapedOpening,
"\\#",
"#");
1042 findAndReplace<string>(unescapedOpening,
"\\$",
"$");
1043 findAndReplace<string>(unescapedOpening,
"\\'",
"'");
1044 findAndReplace<string>(unescapedOpening,
"\\\"",
"\"");
1045 findAndReplace<string>(unescapedOpening,
"\\\\",
"\\");
1047 string dir =
directory(unescapedOpening);
1051 if(dir[0] ==
'\"' || dir[0] ==
'\'') {
1054 if(dir.size() > 1 && (dir[dir.size() - 2] ==
'\"' || dir[dir.size() - 2] ==
'\'')) {
1055 dir.erase(dir.size() - 2, 1);
1057 actualDir = move(dir);
1060 string file =
fileName(unescapedOpening);
1061 if(file[0] ==
'\"' || file[0] ==
'\'') {
1064 if(file.size() > 1 && (file[dir.size() - 2] ==
'\"' || dir[file.size() - 2] ==
'\'')) {
1065 file.erase(file.size() - 2, 1);
1067 actualFile = move(file);
1073 entryTypes |= DirectoryEntryType::File;
1076 entryTypes |= DirectoryEntryType::Directory;
1079 const string replace(
"'"), with(
"'\"'\"'");
1080 if(argc && currentWordIndex <= lastSpecifiedArgIndex && opening) {
1083 for(
string &dirEntry : entries) {
1086 if(actualDir !=
".") {
1090 cout << dirEntry <<
'\'' <<
' ';
1091 haveFileOrDirCompletions =
true;
1097 cout <<
'\'' << dirEntry <<
'\'' <<
' ';
1098 haveFileOrDirCompletions =
true;
1105 if(haveFileOrDirCompletions) {
1106 cout <<
"; compopt -o filenames";
1111 cout <<
"; compopt -o nospace";
1124 const auto occurrences = arg->occurrences();
1125 if(arg->isParentPresent() && occurrences > arg->maxOccurrences()) {
1126 throw Failure(
"The argument \""s % arg->name() %
"\" mustn't be specified more than "s % arg->maxOccurrences() + (arg->maxOccurrences() == 1 ?
" time."s :
" times."s));
1128 if(arg->isParentPresent() && occurrences < arg->minOccurrences()) {
1129 throw Failure(
"The argument \""s % arg->name() %
"\" must be specified at least "s % arg->minOccurrences() + (arg->minOccurrences() == 1 ?
" time."s :
" times."s));
1131 Argument *conflictingArgument =
nullptr;
1132 if(arg->isMainArgument()) {
1133 if(!arg->isCombinable() && arg->isPresent()) {
1139 if(conflictingArgument) {
1140 throw Failure(
"The argument \""s % conflictingArgument->
name() %
"\" can not be combined with \""s + arg->name() +
"\"."s);
1142 for(
size_t i = 0; i != occurrences; ++i) {
1143 if(!arg->allRequiredValuesPresent(i)) {
1144 stringstream ss(stringstream::in | stringstream::out);
1145 ss <<
"Not all parameter for argument \"" << arg->name() <<
"\" ";
1147 ss <<
" (" << (i + 1) <<
" occurrence) ";
1149 ss <<
"provided. You have to provide the following parameter:";
1150 size_t valueNamesPrint = 0;
1151 for(
const auto &name : arg->m_valueNames) {
1152 ss <<
' ' << name, ++valueNamesPrint;
1154 if(arg->m_requiredValueCount != static_cast<size_t>(-1)) {
1155 while(valueNamesPrint < arg->m_requiredValueCount) {
1156 ss <<
"\nvalue " << (++valueNamesPrint);
1179 if(arg->m_callbackFunction) {
1180 for(
const auto &occurrence : arg->m_occurrences) {
1181 arg->m_callbackFunction(occurrence);
1199 Argument(
"help",
'h',
"shows this information")
bool isMainArgument() const
Returns an indication whether the argument is used as main argument.
CPP_UTILITIES_EXPORT const char * applicationUrl
Specifies the URL to the application website (used by ArgumentParser::printHelp()).
bool startsWith(const StringType &str, const StringType &phrase)
Returns whether str starts with phrase.
ValueCompletionBehavior
The ValueCompletionBehavior enum specifies the items to be considered when generating completion for ...
const char * preDefinedCompletionValues() const
Returns the assigned values used when generating completion for the values.
bool denotesOperation() const
Returns whether the argument denotes the operation.
void resetArgs()
Resets all Argument instances assigned as mainArguments() and sub arguments.
ArgumentVector & args
The Argument instances to store the results. Sub arguments of args are considered as well...
std::initializer_list< Argument * > ArgumentInitializerList
#define IF_DEBUG_BUILD(x)
Wraps debug-only lines conveniently.
std::size_t requiredValueCount() const
Returns the number of values which are required to be given for this argument.
Argument * conflictsWithArgument() const
Checks if this arguments conflicts with other arguments.
const char * description() const
Returns the description of the argument.
const char * argDenotation
The currently processed abbreviation denotation (should be substring of one of the args in argv)...
bool isParentPresent() const
Returns whether at least one parent argument is present.
ArgumentParser()
Constructs a new ArgumentParser.
ValueCompletionBehavior valueCompletionBehaviour() const
Returns the items to be considered when generating completion for the values.
void readArgs(int argc, const char *const *argv)
Parses the specified command line arguments.
void setStyle(std::ostream &stream, TextAttribute displayAttribute=TextAttribute::Reset)
CPP_UTILITIES_EXPORT std::list< std::string > directoryEntries(const char *path, DirectoryEntryType types=DirectoryEntryType::All)
Returns the names of the directory entries in the specified path with the specified types...
The ConversionException class is thrown by the various conversion functions of this library when a co...
Contains currently only ArgumentParser and related classes.
const char *const * argv
Points to the first argument denotation and will be incremented when a denotation has been processed...
void setMainArguments(const ArgumentInitializerList &mainArguments)
Sets the main arguments for the parser.
Argument(const char *name, char abbreviation='\0', const char *description=nullptr, const char *example=nullptr)
Constructs an Argument with the given name, abbreviation and description.
bool isRequired() const
Returns an indication whether the argument is mandatory.
Argument CPP_UTILITIES_EXPORT * firstPresentUncombinableArg(const ArgumentVector &args, const Argument *except)
This function return the first present and uncombinable argument of the given list of arguments...
void parseArgs(int argc, const char *const *argv)
Parses the specified command line arguments.
const char * firstValue() const
Returns the first parameter value of the first occurrence of the argument.
CPP_UTILITIES_EXPORT const char * applicationVersion
Specifies the version of the application (used by ArgumentParser::printHelp()).
void invokeCallbacks()
Invokes all assigned callbacks.
~Argument()
Destroys the Argument.
The Indentation class allows printing indentation conveniently, eg.
#define CMD_UTILS_START_CONSOLE
void addMainArgument(Argument *argument)
Adds the specified argument to the main argument.
#define FALLTHROUGH
Prevents clang from warning about missing break in switch-case.
void checkConstraints()
Checks whether contraints are violated.
const char * name() const
Returns the name of the argument.
const std::vector< const char * > & valueNames() const
Returns the names of the requried values.
HelpArgument(ArgumentParser &parser)
Constructs a new help argument for the specified parser.
unsigned char argDenotationType
The type of the currently processed abbreviation denotation. Unspecified if argDenotation is not set...
const ArgumentVector & subArguments() const
Returns the secondary arguments for this argument.
Contains utility classes helping to read and write streams.
ArgumentParser & parser
The associated ArgumentParser instance.
void printHelp(std::ostream &os) const
Prints help text for all assigned arguments.
void findAndReplace(StringType &str, const StringType &find, const StringType &replace)
Replaces all occurences of find with relpace in the specified str.
const std::vector< const char * > & values(std::size_t occurrence=0) const
Returns the parameter values for the specified occurrence of argument.
Contains several functions providing conversions between different data types.
CPP_UTILITIES_EXPORT void(* exitFunction)(int)
Specifies a function quit the application.
Argument * wouldConflictWithArgument() const
Checks if this argument would conflict with other arguments if it was present.
std::size_t occurrences() const
Returns how often the argument could be detected when parsing.
void read()
Reads the commands line arguments specified when constructing the object.
The Argument class is a wrapper for command line argument information.
void setCallback(CallbackFunction callback)
Sets a callback function which will be called by the parser if the argument could be found and no par...
const std::vector< Argument * > & path(std::size_t occurrence=0) const
Returns the path of the specified occurrence.
bool isCombinable() const
Returns an indication whether the argument is combinable.
ApplicationUtilities::ArgumentReader & reset(const char *const *argv, const char *const *end)
Resets the ArgumentReader to continue reading new argv.
ArgumentDenotationType
The ArgumentDenotationType enum specifies the type of a given argument denotation.
UnknownArgumentBehavior
The UnknownArgumentBehavior enum specifies the behavior of the argument parser when an unknown argume...
void printInfo(std::ostream &os, unsigned char indentation=0) const
Writes the name, the abbreviation and other information about the Argument to the give ostream...
const char *const * lastArgDenotation
Points to the element in argv where lastArg was encountered. Unspecified if lastArg is not set...
CPP_UTILITIES_EXPORT std::string directory(const std::string &path)
Returns the directory of the specified path string (including trailing slash).
void addSubArgument(Argument *arg)
Adds arg as a secondary argument for this argument.
The ArgumentOccurrence struct holds argument values for an occurrence of an argument.
CPP_UTILITIES_EXPORT const char * applicationName
Specifies the name of the application (used by ArgumentParser::printHelp()).
bool isPresent() const
Returns an indication whether the argument could be detected when parsing.
bool completionMode
Whether completion mode is enabled. In this case reading args will be continued even if an denotation...
The Failure class is thrown by an ArgumentParser when a parsing error occurs.
const ArgumentVector & mainArguments() const
Returns the main arguments.
bool isUncombinableMainArgPresent() const
Checks whether at least one uncombinable main argument is present.
char abbreviation() const
Returns the abbreviation of the argument.
const char * example() const
Returns the usage example of the argument.
void reset()
Resets occurrences (indices, values and paths).
const char *const * end
Points to the end of the argv array.
CPP_UTILITIES_EXPORT std::string fileName(const std::string &path)
Returns the file name and extension of the specified path string.
size_t index
An index which is incremented when an argument is encountered (the current index is stored in the occ...
CPP_UTILITIES_EXPORT const char * applicationAuthor
Specifies the author of the application (used by ArgumentParser::printHelp()).
DirectoryEntryType
The DirectoryEntryType enum specifies the type of a directory entry (file, directory or symlink)...
const char * environmentVariable() const
Returns the environment variable queried when firstValue() is called.
Argument * lastArg
The last Argument instance which could be detected. Set to nullptr in the initial call...
void setSubArguments(const ArgumentInitializerList &subArguments)
Sets the secondary arguments for this arguments.
unsigned int actualArgumentCount() const
Returns the actual number of arguments that could be found when parsing.
bool compareArgs(const Argument *arg1, const Argument *arg2)
Returns whether arg1 should be listed before arg2 when printing completion.
The ArgumentParser class provides a means for handling command line arguments.
void resetRecursively()
Resets this argument and all sub arguments recursively.
void insertSiblings(const ArgumentVector &siblings, list< const Argument *> &target)
Inserts the specified siblings in the target list.
std::vector< Argument * > ArgumentVector