Skip to content

Add get_indexed() to ParmValueList and AttrDelegate. #2526

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Mar 25, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 27 additions & 0 deletions src/include/OpenImageIO/attrdelegate.h
Original file line number Diff line number Diff line change
Expand Up @@ -149,6 +149,33 @@ template<class C> class AttrDelegate {
return m_obj->getattribute(m_name, TypeString, &s) ? T(s) : defaultval;
}

// `Delegate->get_indexed<T>(int index, defaultval=T())` retrieves the
// index-th base value in the data as type T, or the defaultval if no
// such named data exists or is not the designated type.
template<typename T,
typename std::enable_if<!pvt::is_string<T>::value, int>::type = 0>
inline T get_indexed(int index, const T& defaultval = T()) const
{
T result;
if (!m_obj->getattribute_indexed(m_name, index,
TypeDescFromC<T>::value(), &result))
result = defaultval;
return result;
}

// Using enable_if, make a slightly different version of get_indexed<>
// for strings, which need to do some ustring magic because we can't
// directly store in a std::string or string_view.
template<typename T = string_view,
typename std::enable_if<pvt::is_string<T>::value, int>::type = 1>
inline T get_indexed(int index, const T& defaultval = T()) const
{
ustring s;
return m_obj->getattribute_indexed(m_name, index, TypeString, &s)
? T(s)
: defaultval;
}

// `Delegate->as_string(defaultval="")` returns the data, no matter its
// type, as a string. Returns the defaultval if no such data exists at
// all.
Expand Down
9 changes: 9 additions & 0 deletions src/include/OpenImageIO/paramlist.h
Original file line number Diff line number Diff line change
Expand Up @@ -368,6 +368,15 @@ class OIIO_API ParamValueList : public std::vector<ParamValue> {
bool getattribute(string_view name, std::string& value,
bool casesensitive = false) const;

/// Retrieve from list: If found its data type is reasonably convertible
/// to `type`, copy/convert the value into val[...] and return true.
/// Otherwise, return false and don't modify what val points to.
bool getattribute_indexed(string_view name, int index, TypeDesc type,
void* value, bool casesensitive = false) const;
/// Shortcut for retrieving a single string via getattribute.
bool getattribute_indexed(string_view name, int index, std::string& value,
bool casesensitive = false) const;

/// Sort alphabetically, optionally case-insensitively, locale-
/// independently, and with all the "un-namespaced" items appearing
/// first, followed by items with "prefixed namespaces" (e.g. "z" comes
Expand Down
8 changes: 4 additions & 4 deletions src/include/OpenImageIO/typedesc.h
Original file line number Diff line number Diff line change
Expand Up @@ -222,9 +222,9 @@ struct OIIO_API TypeDesc {
/// ignoring whether it's an array).
size_t elementsize () const noexcept { return aggregate * basesize(); }

// /// Return just the underlying C scalar type, i.e., strip out the
// /// array-ness and the aggregateness.
// BASETYPE basetype () const { return TypeDesc(base); }
/// Return just the underlying C scalar type, i.e., strip out the
/// array-ness and the aggregateness.
constexpr TypeDesc scalartype() const { return TypeDesc(BASETYPE(basetype)); }

/// Return the base type size, i.e., stripped of both array-ness
/// and aggregateness.
Expand All @@ -240,7 +240,7 @@ struct OIIO_API TypeDesc {
/// Shortcut: is it UNKNOWN?
constexpr bool is_unknown () const noexcept { return (basetype == UNKNOWN); }

/// if (typespec) is the same as asking whether it's not UNKNOWN.
/// if (typedesc) is the same as asking whether it's not UNKNOWN.
constexpr operator bool () const noexcept { return (basetype != UNKNOWN); }

/// Set *this to the type described in the string. Return the
Expand Down
43 changes: 43 additions & 0 deletions src/libutil/paramlist.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -597,6 +597,49 @@ ParamValueList::getattribute(string_view name, std::string& value,



bool
ParamValueList::getattribute_indexed(string_view name, int index, TypeDesc type,
void* value, bool casesensitive) const
{
auto p = find(name, TypeUnknown, casesensitive);
if (p != cend()) {
if (index >= int(p->type().basevalues()))
return false;
TypeDesc basetype = p->type().scalartype();
return convert_type(basetype,
(const char*)p->data() + index * basetype.size(),
type, value);
} else {
return false;
}
}



bool
ParamValueList::getattribute_indexed(string_view name, int index,
std::string& value,
bool casesensitive) const
{
auto p = find(name, TypeUnknown, casesensitive);
if (p != cend()) {
if (index >= int(p->type().basevalues()))
return false;
TypeDesc basetype = p->type().scalartype();
ustring s;
bool ok = convert_type(basetype,
(const char*)p->data() + index * basetype.size(),
TypeString, &s);
if (ok)
value = s.string();
return ok;
} else {
return false;
}
}



void
ParamValueList::sort(bool casesensitive)
{
Expand Down
3 changes: 3 additions & 0 deletions src/libutil/paramlist_test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -347,6 +347,9 @@ test_delegates()
OIIO_CHECK_EQUAL(pl["bar4"].get<std::string>(), "barbarbar?");
OIIO_CHECK_EQUAL(pl["red"].get<Imath::Color3f>(),
Imath::Color3f(1.0f, 0.0f, 0.0f));
OIIO_CHECK_EQUAL(pl["red"].get_indexed<float>(0), 1.0f);
OIIO_CHECK_EQUAL(pl["red"].get_indexed<float>(1), 0.0f);
OIIO_CHECK_EQUAL(pl["red"].get_indexed<float>(2), 0.0f);
OIIO_CHECK_EQUAL(pl["xy"].get<Imath::V3f>(), Imath::V3f(0.5f, 0.5f, 0.0f));
OIIO_CHECK_EQUAL(pl["Tx"].get<Imath::M44f>(),
Imath::M44f(1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 42, 0, 0,
Expand Down