From 3ed124aeed2cb65b05f61224115366601ee3b05f Mon Sep 17 00:00:00 2001 From: Benjamin Paassen Date: Thu, 12 Feb 2015 22:36:38 +0100 Subject: added Descriptor::getPermittedChildren. --- src/core/model/Domain.cpp | 13 +++++++++++++ src/core/model/Domain.hpp | 12 ++++++++++++ test/core/model/DomainTest.cpp | 37 +++++++++++++++++++++++++++++++++++++ 3 files changed, 62 insertions(+) diff --git a/src/core/model/Domain.cpp b/src/core/model/Domain.cpp index 6f33ebd..3cc9755 100644 --- a/src/core/model/Domain.cpp +++ b/src/core/model/Domain.cpp @@ -471,6 +471,19 @@ NodeVector Descriptor::getDefaultFields() const return res; } +NodeVector Descriptor::getPermittedChildren() const +{ + // TODO: In principle a cast would be nicer here, but for now we copy. + NodeVector nodes = collect(this, [](Handle n) { + return n->isa(&RttiTypes::StructuredClass); + }); + NodeVector res; + for (auto n : nodes) { + res.push_back(n.cast()); + } + return res; +} + static ssize_t getFieldDescriptorIndex(const NodeVector &fds, const std::string &name) { diff --git a/src/core/model/Domain.hpp b/src/core/model/Domain.hpp index c277812..6bc2fba 100644 --- a/src/core/model/Domain.hpp +++ b/src/core/model/Domain.hpp @@ -624,6 +624,18 @@ public: * children of an instance of this Descriptor. */ NodeVector getDefaultFields() const; + + /** + * Returns a vector of all StructuredClasses that are allowed as children + * of an instance of this Descriptor in the structure tree. This also makes + * use of transparency. + * The list is sorted by the number of transparent elements that have to be + * constructed to arrive at the respective FieldDescriptor. + * + * @return a vector of all StructuredClasses that are allowed as children + * of an instance of this Descriptor in the structure tree. + */ + NodeVector getPermittedChildren() const; }; /* * TODO: We should discuss Cardinalities one more time. Is it smart to define diff --git a/test/core/model/DomainTest.cpp b/test/core/model/DomainTest.cpp index 83f290f..8fcbdf2 100644 --- a/test/core/model/DomainTest.cpp +++ b/test/core/model/DomainTest.cpp @@ -301,6 +301,43 @@ TEST(Descriptor, getDefaultFields) ASSERT_EQ(F_field, fields[1]); } +TEST(Descriptor, getPermittedChildren) +{ + // analyze the book domain. + TerminalLogger logger{std::cout}; + Manager mgr{1}; + Rooted sys{new SystemTypesystem(mgr)}; + // Get the domain. + Rooted domain = constructBookDomain(mgr, sys, logger); + // get the relevant classes. + Rooted book = getClass("book", domain); + Rooted section = getClass("section", domain); + Rooted paragraph = getClass("paragraph", domain); + Rooted text = getClass("text", domain); + /* + * as permitted children we expect section, paragraph and text in exactly + * that order. section should be before paragraph because of declaration + * order and text should be last because it needs a transparent paragraph + * in between. + */ + NodeVector children = book->getPermittedChildren(); + ASSERT_EQ(3, children.size()); + ASSERT_EQ(section, children[0]); + ASSERT_EQ(paragraph, children[1]); + ASSERT_EQ(text, children[2]); + + // Now we add a subclass to text. + Rooted sub{new StructuredClass( + mgr, "Subclass", domain, Cardinality::any(), text, true, false)}; + // And that should be in the result list as well now. + children = book->getPermittedChildren(); + ASSERT_EQ(4, children.size()); + ASSERT_EQ(section, children[0]); + ASSERT_EQ(paragraph, children[1]); + ASSERT_EQ(text, children[2]); + ASSERT_EQ(sub, children[3]); +} + TEST(StructuredClass, isSubclassOf) { // create an inheritance hierarchy. -- cgit v1.2.3