cmArgumentParser: support storing a context value with parsing
This allows for parsing of contextual keywords. For example: ``` some_command( ARG_WITH_CONTEXT foo CONTEXT bar ARG_WITH_CONTEXT quux) ``` will be able to store that `foo` happened without context (or, rather, its default value) and `quux` was provided in a `bar` context.
This commit is contained in:
parent
c9ca5f6326
commit
93993c7ad4
@ -7,6 +7,7 @@
|
||||
#include <cassert>
|
||||
#include <cstddef>
|
||||
#include <functional>
|
||||
#include <iterator>
|
||||
#include <map>
|
||||
#include <string>
|
||||
#include <utility>
|
||||
@ -176,6 +177,17 @@ public:
|
||||
void Bind(MaybeEmpty<std::vector<std::string>>& val);
|
||||
void Bind(NonEmpty<std::vector<std::string>>& val);
|
||||
void Bind(std::vector<std::vector<std::string>>& val);
|
||||
template <typename U>
|
||||
void Bind(NonEmpty<std::vector<std::pair<std::string, U>>>& val,
|
||||
U const& context)
|
||||
{
|
||||
this->Bind(
|
||||
[&val, &context](cm::string_view arg) -> Continue {
|
||||
val.emplace_back(std::string(arg), context);
|
||||
return Continue::Yes;
|
||||
},
|
||||
ExpectAtLeast{ 1 });
|
||||
}
|
||||
|
||||
// cm::optional<> records the presence the keyword to which it binds.
|
||||
template <typename T>
|
||||
@ -187,6 +199,15 @@ public:
|
||||
this->Bind(*optVal);
|
||||
}
|
||||
|
||||
template <typename T, typename U>
|
||||
void Bind(cm::optional<T>& optVal, U const& context)
|
||||
{
|
||||
if (!optVal) {
|
||||
optVal.emplace();
|
||||
}
|
||||
this->Bind(*optVal, context);
|
||||
}
|
||||
|
||||
template <typename Range>
|
||||
void Parse(Range const& args, std::size_t pos = 0)
|
||||
{
|
||||
@ -232,6 +253,17 @@ public:
|
||||
return *this;
|
||||
}
|
||||
|
||||
template <typename T, typename U>
|
||||
cmArgumentParser& BindWithContext(cm::static_string_view name,
|
||||
T Result::*member, U Result::*context)
|
||||
{
|
||||
this->Base::Bind(name, [member, context](Instance& instance) {
|
||||
auto* result = static_cast<Result*>(instance.Result);
|
||||
instance.Bind(result->*member, result->*context);
|
||||
});
|
||||
return *this;
|
||||
}
|
||||
|
||||
cmArgumentParser& Bind(cm::static_string_view name,
|
||||
Continue (Result::*member)(cm::string_view),
|
||||
ExpectAtLeast expect = { 1 })
|
||||
|
Loading…
Reference in New Issue
Block a user