summaryrefslogtreecommitdiff
path: root/src/core/model/Document.cpp
diff options
context:
space:
mode:
authorBenjamin Paassen <bpaassen@techfak.uni-bielefeld.de>2015-02-12 11:33:01 +0100
committerBenjamin Paassen <bpaassen@techfak.uni-bielefeld.de>2015-02-12 11:33:01 +0100
commitebac41111fa33790acce7be45e599f8de37e7f43 (patch)
treef23a5875d30d28c35e5a8e352856f5f9a9ef7cf2 /src/core/model/Document.cpp
parentdbf2eebdd88118dca79045ad0524061f8078e668 (diff)
Anchors do not have a name anymore and have a unique mapping to their AnnotationEntities. This also makes serialization much easier.
Diffstat (limited to 'src/core/model/Document.cpp')
-rw-r--r--src/core/model/Document.cpp112
1 files changed, 99 insertions, 13 deletions
diff --git a/src/core/model/Document.cpp b/src/core/model/Document.cpp
index 8b31f14..b38f2c0 100644
--- a/src/core/model/Document.cpp
+++ b/src/core/model/Document.cpp
@@ -275,9 +275,9 @@ static int enforceGetFieldDescriptorIndex(Handle<Descriptor> desc,
{
ssize_t idx = desc->getFieldDescriptorIndex(fieldName);
if (idx == -1) {
- throw OusiaException(
- std::string("Descriptor \"") + desc->getName() +
- "\" has no field with the name \"" + fieldName + "\"");
+ throw OusiaException(std::string("Descriptor \"") + desc->getName() +
+ "\" has no field with the name \"" + fieldName +
+ "\"");
}
return idx;
}
@@ -287,8 +287,7 @@ static int enforceGetFieldDescriptorIndex(
{
ssize_t idx = desc->getFieldDescriptorIndex(fieldDescriptor);
if (idx == -1) {
- throw OusiaException(std::string("Descriptor \"") +
- desc->getName() +
+ throw OusiaException(std::string("Descriptor \"") + desc->getName() +
"\" does not reference the given field \"" +
fieldDescriptor->getName() + "\"");
}
@@ -419,11 +418,10 @@ Rooted<DocumentPrimitive> DocumentEntity::createChildDocumentPrimitive(
subInst->getManager(), subInst, std::move(content), fieldName)};
}
-Rooted<Anchor> DocumentEntity::createChildAnchor(std::string name,
- const std::string &fieldName)
+Rooted<Anchor> DocumentEntity::createChildAnchor(const std::string &fieldName)
{
return Rooted<Anchor>{
- new Anchor(subInst->getManager(), std::move(name), subInst, fieldName)};
+ new Anchor(subInst->getManager(), subInst, fieldName)};
}
/* Class StructureNode */
@@ -494,13 +492,61 @@ bool Anchor::doValidate(Logger &logger) const
{
bool valid = true;
// check name
- if (getName().empty()) {
- logger.error("An Anchor needs a name!", *this);
+ if (!getName().empty()) {
+ logger.error(
+ "This anchor has a name! Anchors should only be referred to by "
+ "reference, not by name!",
+ *this);
valid = false;
}
+ if (annotation == nullptr) {
+ // this is valid but should throw a warning.
+ logger.warning("This anchor is disconnected.", *this);
+ }
return valid & StructureNode::doValidate(logger);
}
+void Anchor::setAnnotation(Handle<AnnotationEntity> anno, bool start)
+{
+ if (annotation == anno) {
+ return;
+ }
+ invalidate();
+ // unset the old reference.
+ if (annotation != nullptr) {
+ if (isStart()) {
+ annotation->setStart(nullptr);
+ } else {
+ annotation->setEnd(nullptr);
+ }
+ }
+ annotation = acquire(anno);
+ // set the new reference.
+ if (anno != nullptr) {
+ if (start) {
+ anno->setStart(this);
+ } else {
+ anno->setEnd(this);
+ }
+ }
+}
+
+bool Anchor::isStart() const
+{
+ if (annotation == nullptr) {
+ return false;
+ }
+ return annotation->getStart() == this;
+}
+
+bool Anchor::isEnd() const
+{
+ if (annotation == nullptr) {
+ return false;
+ }
+ return annotation->getEnd() == this;
+}
+
/* Class AnnotationEntity */
AnnotationEntity::AnnotationEntity(Manager &mgr, Handle<Document> parent,
@@ -508,13 +554,13 @@ AnnotationEntity::AnnotationEntity(Manager &mgr, Handle<Document> parent,
Handle<Anchor> start, Handle<Anchor> end,
Variant attributes, std::string name)
: Node(mgr, std::move(name), parent),
- DocumentEntity(this, descriptor, attributes),
- start(acquire(start)),
- end(acquire(end))
+ DocumentEntity(this, descriptor, attributes)
{
if (parent != nullptr) {
parent->addAnnotation(this);
}
+ setStart(start);
+ setEnd(end);
}
bool AnnotationEntity::doValidate(Logger &logger) const
@@ -567,10 +613,50 @@ bool AnnotationEntity::doValidate(Logger &logger) const
valid = false;
}
}
+ // check if the Anchors reference this AnnotationEntity correctly.
+ if (start != nullptr) {
+ if (start->getAnnotation() != this) {
+ logger.error(
+ "This annotations start anchor does not have the correct "
+ "annotation as parent!",
+ *this);
+ valid = false;
+ }
+ }
+ if (end != nullptr) {
+ if (end->getAnnotation() != this) {
+ logger.error(
+ "This annotations end anchor does not have the correct "
+ "annotation as parent!",
+ *this);
+ valid = false;
+ }
+ }
+
// check the validity as a DocumentEntity.
return valid & DocumentEntity::doValidate(logger);
}
+void AnnotationEntity::setStart(Handle<Anchor> s)
+{
+ if (start == s) {
+ return;
+ }
+ invalidate();
+ start = acquire(s);
+ s->setAnnotation(this, true);
+}
+
+void AnnotationEntity::setEnd(Handle<Anchor> e)
+{
+ if (end == e) {
+ return;
+ }
+ invalidate();
+ end = acquire(e);
+ e->setAnnotation(this, false);
+}
+
/* Class Document */
void Document::doResolve(ResolutionState &state)