Skip to content

Commit

Permalink
nested VariantSet support W.I.P.
Browse files Browse the repository at this point in the history
  • Loading branch information
syoyo committed Oct 1, 2023
1 parent 3ddb495 commit 43f5d01
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 21 deletions.
31 changes: 19 additions & 12 deletions src/ascii-parser.cc
Original file line number Diff line number Diff line change
Expand Up @@ -4287,7 +4287,7 @@ bool AsciiParser::IsStageMeta(const std::string &name) {
bool AsciiParser::ParseVariantSet(const int64_t primIdx,
const int64_t parentPrimIdx,
const uint32_t depth,
std::map<std::string, VariantContent> *variantSetOut) {
VariantSetContent *variantSetOut) {

if (depth > 1024 * 1024) {
PUSH_ERROR_AND_RETURN_TAG(kAscii, "[InternalError] too deep nested call.");
Expand All @@ -4311,7 +4311,7 @@ bool AsciiParser::ParseVariantSet(const int64_t primIdx,
return false;
}

std::map<std::string, VariantContent> variantContentMap;
VariantSetContent variantSetContent;

// for each variantStatement
while (!Eof()) {
Expand Down Expand Up @@ -4361,6 +4361,10 @@ bool AsciiParser::ParseVariantSet(const int64_t primIdx,

VariantContent variantContent;

int64_t variantPrimIdx = _prim_idx_assign_fun(parentPrimIdx);
//variantContent.variantPrimIdx = variantPrimIdx;
DCOUT("primIdx for variant = " << variantPrimIdx);

while (!Eof()) {

if (!SkipCommentAndWhitespaceAndNewline()) {
Expand Down Expand Up @@ -4416,8 +4420,9 @@ bool AsciiParser::ParseVariantSet(const int64_t primIdx,
return false;
}

std::map<std::string, VariantContent> child_vmap;
if (!ParseVariantSet(primIdx, parentPrimIdx, depth+1, &child_vmap)) {

VariantSetContent child_vmap;
if (!ParseVariantSet(variantPrimIdx, primIdx, depth+1, &child_vmap)) {
PUSH_ERROR_AND_RETURN("Failed to parse `variantSet` statement.");
}

Expand Down Expand Up @@ -4476,16 +4481,15 @@ bool AsciiParser::ParseVariantSet(const int64_t primIdx,

DCOUT(fmt::format("variantSet item {} parsed.", variantName));

int64_t idx = _prim_idx_assign_fun(parentPrimIdx);
DCOUT("primIdx for variant = " << idx);

variantContent.variantPrimIdx = idx;

variantContent.metas = metas;
variantContentMap[variantName] = variantContent;
variantSetContent.variantSets[variantName] = variantContent;
}

(*variantSetOut) = std::move(variantContentMap);
variantSetContent.variantPrimIdx = primIdx;

(*variantSetOut) = std::move(variantSetContent);

return true;
}
Expand Down Expand Up @@ -4704,12 +4708,15 @@ bool AsciiParser::ParseBlock(const Specifier spec, const int64_t primIdx,
return false;
}

std::map<std::string, VariantContent> vmap;
if (!ParseVariantSet(primIdx, parentPrimIdx, depth, &vmap)) {
int64_t variantPrimIdx = _prim_idx_assign_fun(parentPrimIdx);

VariantSetContent vs;
if (!ParseVariantSet(variantPrimIdx, primIdx, depth, &vs)) {
PUSH_ERROR_AND_RETURN("Failed to parse `variantSet` statement.");
}

variantSetList[variantName] = vmap;
vs.variantPrimIdx = variantPrimIdx;
variantSetList[variantName] = vs;

continue;
}
Expand Down
24 changes: 19 additions & 5 deletions src/ascii-parser.hh
Original file line number Diff line number Diff line change
Expand Up @@ -187,20 +187,34 @@ class AsciiParser {
using PrimMetaMap =
std::map<std::string, std::pair<ListEditQual, MetaVariable>>;

struct VariantContent;

//
// variantSet "keyname" = {
// "key0" : { ... }
// "key1" : { ... }
// }
//
struct VariantSetContent {
int64_t variantPrimIdx{-1}; // Pseudo Prim Idx for `variantSet`. -1 = no variantSet node
std::map<std::string, VariantContent> variantSets;
};

struct VariantContent {
PrimMetaMap metas;
std::vector<int64_t> primIndices; // primIdx of Reconstrcuted Prim.
std::map<std::string, Property> props;
std::vector<value::token> properties;

// for nested `variantSet`
int64_t variantPrimIdx{-1}; // Pseudo Prim Idx for `variantSet`. -1 = no variantSet node
std::map<std::string, std::map<std::string, VariantContent>> variantSets;
std::map<std::string, VariantSetContent> variantSets;
};



// TODO: Use std::vector instead of std::map?
using VariantSetList =
std::map<std::string, std::map<std::string, VariantContent>>;
std::map<std::string, VariantSetContent>;

AsciiParser();
AsciiParser(tinyusdz::StreamReader *sr);
Expand Down Expand Up @@ -779,10 +793,10 @@ class AsciiParser {
const int64_t parentPrimIdx, const uint32_t depth,
const bool in_variant = false);

// Parse `varianntSet` stmt
// Parse `variantSet` stmt
bool ParseVariantSet(const int64_t primIdx, const int64_t parentPrimIdx,
const uint32_t depth,
std::map<std::string, VariantContent> *variantSetMap);
VariantSetContent *variantSetMap);

// --------------------------------------------

Expand Down
10 changes: 6 additions & 4 deletions src/usda-reader.cc
Original file line number Diff line number Diff line change
Expand Up @@ -356,7 +356,7 @@ class USDAReader::Impl {
const prim::ReferenceList &references,
T *out);

bool ProcessVariantSetContent(const uint32_t depth, const std::map<std::string, std::map<std::string, ascii::AsciiParser::VariantContent>> &in_variants, std::map<std::string, std::map<std::string, VariantNode>> &dst) {
bool ProcessVariantSetContent(const uint32_t depth, const std::map<std::string, ascii::AsciiParser::VariantSetContent> &in_variants, std::map<std::string, std::map<std::string, VariantNode>> &dst) {
if (depth > 1024 * 1024) {
PUSH_ERROR_AND_RETURN("Too deep.");
}
Expand All @@ -372,7 +372,7 @@ class USDAReader::Impl {

// Convert VariantContent -> VariantNode
std::map<std::string, VariantNode> variantNodes;
for (const auto &item : variantContext.second) {
for (const auto &item : variantContext.second.variantSets) {

// process child variantSet first.
std::map<std::string, std::map<std::string, VariantNode>> childVariantSets;
Expand All @@ -383,7 +383,7 @@ class USDAReader::Impl {

VariantNode variant;

variant.variantPrimIdx = item.second.variantPrimIdx;
variant.variantPrimIdx = variantContext.second.variantPrimIdx;
variant.variantSets = std::move(childVariantSets);

if (!ReconstructPrimMeta(item.second.metas, &variant.metas)) {
Expand Down Expand Up @@ -629,7 +629,7 @@ class USDAReader::Impl {

// Convert VariantContent -> VariantNode
std::map<std::string, VariantNode> variantNodes;
for (const auto &item : variantContext.second) {
for (const auto &item : variantContext.second.variantSets) {
VariantNode variant;
if (!ReconstructPrimMeta(item.second.metas, &variant.metas)) {
return nonstd::make_unexpected(fmt::format("Failed to process Prim metadataum in variantSet {} item {} ", variant_name, item.first));
Expand Down Expand Up @@ -1449,6 +1449,7 @@ bool ConstructPrimTreeRec(const size_t primIdx,
Prim prim(node.prim);
prim.prim_type_name() = node.typeName;

DCOUT("prim[" << primIdx << "].name = " << prim.element_name());
DCOUT("prim[" << primIdx << "].type = " << node.prim.type_name());
DCOUT("prim[" << primIdx << "].variantNodeMap.size = " << node.variantNodeMap.size());
//prim.prim_id() = int64_t(idx);
Expand Down Expand Up @@ -1529,6 +1530,7 @@ bool ConstructPrimTreeRec(const size_t primIdx,
}

for (const auto &cidx : node.children) {
DCOUT("parent: " << primIdx << ", child: " << cidx);
if (variantChildrenIndices.count(int64_t(cidx))) {
// Prim is processed
continue;
Expand Down

0 comments on commit 43f5d01

Please sign in to comment.