summary | shortlog | log | commit | commitdiff | tree
raw | patch | inline | side by side (parent: cf035fa)
raw | patch | inline | side by side (parent: cf035fa)
author | Gert van Valkenhoef <g.h.m.van.valkenhoef@rug.nl> | |
Tue, 8 Nov 2011 22:18:05 +0000 (22:18 +0000) | ||
committer | Gert van Valkenhoef <g.h.m.van.valkenhoef@rug.nl> | |
Tue, 8 Nov 2011 22:18:05 +0000 (22:18 +0000) |
Makefile | patch | blob | history | |
alien.cc | patch | blob | history | |
alien.h | patch | blob | history | |
fold.cc | patch | blob | history | |
fold.h | patch | blob | history | |
odcread.cc | patch | blob | history | |
store.cc | patch | blob | history | |
store.h | patch | blob | history | |
textmodel.cc | patch | blob | history | |
textmodel.h | patch | blob | history | |
visitor.h | [new file with mode: 0644] | patch | blob |
diff --git a/Makefile b/Makefile
index e3f74e5ddf148a5018ffd21b9347676e16466af8..4ad7260b49abef09e303cfabd32437671153d4ff 100644 (file)
--- a/Makefile
+++ b/Makefile
-HEADERS=oberon.h store.h reader.h domain.h alien.h typeregister.h textmodel.h fold.h
+HEADERS=oberon.h store.h reader.h domain.h alien.h typeregister.h textmodel.h fold.h visitor.h
odcread: odcread.o reader.o store.o util.o alien.o typeregister.o textmodel.o fold.o
g++ -o $@ $^
diff --git a/alien.cc b/alien.cc
index fddd2024dbcb0dfd2ee200c52b3b93170f8c6a54..dc4f50920c7d61d30bec5744a7bba9e8ccacd018 100644 (file)
--- a/alien.cc
+++ b/alien.cc
return std::string("AlienPiece");
}
-std::string AlienPiece::toPlainText() {
- return std::string();
+void AlienPiece::accept(Visitor &visitor) const {
}
AlienPart::AlienPart(Store * const store): d_store(store) {}
return "NULL";
}
-std::string AlienPart::toPlainText() {
- if (d_store != 0)
- return d_store->toPlainText();
- else
- return std::string();
+void AlienPart::accept(Visitor &visitor) const {
+ if (d_store != 0) {
+ d_store->accept(visitor);
+ }
}
Alien::Alien(INTEGER id, const TypePath &path): Store(id), d_path(path), d_comps() {}
return sofar + "}";
}
-std::string Alien::toPlainText() {
- std::string sofar = std::string();
+void Alien::accept(Visitor &visitor) const {
for (int i = 0; i < d_comps.size(); ++i) {
- sofar += d_comps[i]->toPlainText();
+ d_comps[i]->accept(visitor);
}
- return sofar;
}
}
index 7447f953cc9ec3e4ee9b987853cb4b94f1629d9f..9f061dc412224be3e1236b94191afb3b54ee5faa 100644 (file)
--- a/alien.h
+++ b/alien.h
#include <oberon.h>
#include <store.h>
+#include <visitor.h>
#include <iostream>
#include <vector>
#include <string>
*/
struct AlienComponent {
virtual std::string toString() = 0;
- virtual std::string toPlainText() = 0;
+ virtual void accept(Visitor &visitor) const = 0;
};
/**
AlienPiece(const char * const data, const size_t len);
virtual std::string toString();
- virtual std::string toPlainText();
+ virtual void accept(Visitor &visitor) const;
};
/**
AlienPart(Store * const store);
virtual std::string toString();
- virtual std::string toPlainText();
+ virtual void accept(Visitor &visitor) const;
};
class Alien : public Store {
// comps-: AlienComp (** the constituent components of this alien store **)
virtual std::string toString();
- virtual std::string toPlainText();
+ virtual void accept(Visitor &visitor) const;
};
}
index ae4d016cfd3d602bfadc9c0318ea212dec6f88c7..37e0fd667756bff233d05d0a9f911d6257b373b8 100644 (file)
--- a/fold.cc
+++ b/fold.cc
// rd.ReadXInt(xint);fold.leftSide := xint = 0;
reader.readSInt();
// rd.ReadXInt(xint); fold.collapsed := xint = 0;
- reader.readSInt();
+ SHORTINT c = reader.readSInt();
+ d_collapsed = (c == 0);
// rd.ReadXString(fold.label);
d_label = new SHORTCHAR[32];
reader.readSString(d_label); // the label
return std::string("Fold(left) \"") + std::string(d_label) + std::string("\" { ") + d_hidden->toString() + std::string(" }");
}
-std::string Fold::toPlainText() {
- if (d_hidden == 0) {
- return std::string();
+void Fold::accept(Visitor &visitor) const {
+ if (d_hidden == 0) { // right part
+ visitor.foldRight();
+ } else { // left part
+ visitor.foldLeft(d_collapsed);
+ d_hidden->accept(visitor);
}
- return std::string(d_label) + std::string("\n") + d_hidden->toPlainText();
}
} // namespace odc
index e53e06d08ce1ee65d41128610b8101d6126f21cf..589b76b28783fa740cb718e700231fbb09a9d0d8 100644 (file)
--- a/fold.h
+++ b/fold.h
-#ifndef _TEXTMODEL_H_
-#define _TEXTMODEL_H_
+#ifndef _FOLD_H_
+#define _FOLD_H_
#include <oberon.h>
#include <typeregister.h>
Store *d_hidden;
SHORTCHAR *d_label;
+ bool d_collapsed;
public:
Fold(INTEGER id);
virtual void internalize(Reader &reader);
virtual std::string toString();
- virtual std::string toPlainText();
+ virtual void accept(Visitor &visitor) const;
};
}
-#endif
+#endif // _FOLD_H_
diff --git a/odcread.cc b/odcread.cc
index 151c86181db470156f3c31c3154bafc0255d8941..4ba36802c058412591472bd9fb6c4af470c6a41f 100644 (file)
--- a/odcread.cc
+++ b/odcread.cc
#include <oberon.h>
#include <reader.h>
#include <store.h>
+#include <textmodel.h>
+#include <visitor.h>
namespace odc {
+ class Context {
+ public:
+ virtual void addPiece(std::string &piece) = 0;
+ virtual std::string getPlainText() const = 0;
+ };
+ class PartContext : public Context {
+ private:
+ std::string d_text;
+ public:
+ virtual void addPiece(std::string &piece) {
+ d_text += piece;
+ }
+ virtual std::string getPlainText() const {
+ return d_text;
+ }
+ };
+ class FoldContext : public Context {
+ private:
+ bool d_collapsed;
+ bool d_haveFirst; // flag that first part has been set
+ std::string d_firstPart;
+ std::string d_remainder;
+ public:
+ FoldContext(bool collapsed) : d_collapsed(collapsed), d_haveFirst(false) {}
+ virtual void addPiece(std::string &piece) {
+ if (!d_haveFirst) {
+ d_haveFirst = true;
+ d_firstPart = piece;
+ } else {
+ d_remainder += piece;
+ }
+ }
+ virtual std::string getPlainText() const {
+ if (d_collapsed) {
+ return std::string("##=>") + d_remainder + "\n" + d_firstPart +"##<=";
+ } else {
+ return std::string("##=>") + d_firstPart + "\n" + d_remainder +"##<=";
+ }
+ }
+ };
+
+ class MyVisitor : public Visitor {
+ private:
+ std::vector<Context*> d_context;
+
+ void terminateContext() {
+ Context *c = *(d_context.end() - 1);
+ d_context.erase(d_context.end() - 1);
+ if (d_context.size() == 0) {
+ std::cout << c->getPlainText() << std::endl;
+ } else {
+ std::string text = c->getPlainText();
+ (*(d_context.end() - 1))->addPiece(text);
+ }
+ delete c;
+ }
+
+ public:
+ virtual void partStart() {
+ d_context.push_back(new PartContext());
+ }
+ virtual void partEnd() {
+ terminateContext();
+ }
+ virtual void foldLeft(bool collapsed) {
+ d_context.push_back(new FoldContext(collapsed));
+ }
+ virtual void foldRight() {
+ terminateContext();
+ }
+ virtual void textShortPiece(const ShortPiece *piece) {
+ std::string text = piece->getText();
+ (*(d_context.end() - 1))->addPiece(text);
+ }
+ virtual void textLongPiece(const LongPiece *piece) {
+ std::string text = piece->getText();
+ (*(d_context.end() - 1))->addPiece(text);
+ }
+ };
+
Store* importDocument(std::istream &is) {
const INTEGER docTag = 0x6F4F4443;
const INTEGER docVersion = 0;
// std::cout << s->toPlainText() << std::endl;
// std::cout << std::endl << std::endl;
- std::cout << s->toString() << std::endl;
+ odc::MyVisitor visitor;
+ s->accept(visitor);
+// std::cout << s->toString() << std::endl;
// std::cout << in.tellg() << " " << in.eof() << std::endl;
// odc::TypePath path;
diff --git a/store.cc b/store.cc
index d03467cf64df6a8736cdc81ba86d34462293aeb9..4bbabf83591858e3106d1a1fd5cd4767240d3362 100644 (file)
--- a/store.cc
+++ b/store.cc
#include <store.h>
#include <reader.h>
+#include <visitor.h>
#include <iostream>
return getTypeName();
}
-std::string Store::toPlainText() {
- return std::string();
-}
+void Store::accept(Visitor &visitor) const {}
const std::string Elem::TYPENAME("Stores.Elem^");
const TypeProxy<Elem> Elem::PROXY;
index 66e58b0cae59d4dd6d0d093c5cccbcf1d3d74b71..4e7360e782170315dafd917c53816b6ae5d141c4 100644 (file)
--- a/store.h
+++ b/store.h
#include <oberon.h>
#include <domain.h>
#include <typeregister.h>
+#include <visitor.h>
#include <string>
#include <vector>
// FIXME
virtual std::string toString();
- virtual std::string toPlainText();
+
+ /**
+ * Receiving end of the Visitor pattern.
+ */
+ virtual void accept(Visitor &visitor) const;
private:
void calcTypePath(TypePath * out, const std::string &name) const;
diff --git a/textmodel.cc b/textmodel.cc
index 977bd447e35ecca8efd0b71617597f709577771b..f9dbae242b007f39c8438e7dfae1708cae626a8c 100644 (file)
--- a/textmodel.cc
+++ b/textmodel.cc
return sofar + "}";
}
-std::string StdTextModel::toPlainText() {
- std::string sofar = "";
+void StdTextModel::accept(Visitor &visitor) const {
+ visitor.partStart();
for (int i = 0; i < d_pieces.size(); ++i) {
- sofar += d_pieces[i]->toPlainText();
+ d_pieces[i]->accept(visitor);
}
- return sofar;
+ visitor.partEnd();
}
TextPiece::TextPiece(size_t len): d_len(len) {}
reader.readLChar(d_buf, d_len);
}
-std::string LongPiece::toString() {
+std::string LongPiece::toString() const {
return std::string("LongPiece(FIXME)");// + std::wstring((wchar_t*)d_buf) + std::string(")");
}
-std::string LongPiece::toPlainText() {
+std::string LongPiece::getText() const {
return std::string("FIXME");// + std::wstring((wchar_t*)d_buf) + std::string(")");
}
+void LongPiece::accept(Visitor &visitor) const {
+ visitor.textLongPiece(this);
+}
+
ShortPiece::ShortPiece(size_t len): TextPiece(len) {}
ShortPiece::~ShortPiece() {
// delete buf;
}
-std::string ShortPiece::toString() {
+std::string ShortPiece::toString() const {
return std::string("ShortPiece(") + std::string(d_buf) + std::string(")");
}
-std::string ShortPiece::toPlainText() {
- return std::string(d_buf);
+std::string ShortPiece::getText() const {
+ std::string str(d_buf);
+ for (std::string::iterator it = str.begin(); it < str.end(); ++it) {
+ if (*it == '\r') *it = '\n';
+ }
+ return str;
+}
+
+void ShortPiece::accept(Visitor &visitor) const {
+ visitor.textShortPiece(this);
}
ViewPiece::ViewPiece(Store *view): TextPiece(0), d_view(view) {}
reader.readByte();
}
-std::string ViewPiece::toString() {
+std::string ViewPiece::toString() const {
return std::string("ViewPiece { ") + d_view->toString() + " }";
}
-std::string ViewPiece::toPlainText() {
- return d_view->toPlainText();
+void ViewPiece::accept(Visitor &visitor) const {
+ return d_view->accept(visitor);
}
} // namespace odc
diff --git a/textmodel.h b/textmodel.h
index 38eb7c55b73d0546c5884263a98e2ec01d53b474..92d387a61b5596595b4dd985c9f1c36692671755 100644 (file)
--- a/textmodel.h
+++ b/textmodel.h
const size_t d_len;
TextPiece(size_t len);
virtual void read(Reader &reader) = 0;
- virtual std::string toString() = 0;
- virtual std::string toPlainText() = 0;
+ virtual std::string toString() const = 0;
+ virtual void accept(Visitor &visitor) const = 0;
};
class LongPiece : public TextPiece {
LongPiece(size_t len);
~LongPiece();
virtual void read(Reader &reader);
- virtual std::string toString();
- virtual std::string toPlainText();
+ virtual std::string toString() const;
+ virtual std::string getText() const;
+ virtual void accept(Visitor &visitor) const;
};
class ShortPiece : public TextPiece {
ShortPiece(size_t len);
~ShortPiece();
virtual void read(Reader &reader);
- virtual std::string toString();
- virtual std::string toPlainText();
+ virtual std::string toString() const;
+ virtual std::string getText() const;
+ virtual void accept(Visitor &visitor) const;
};
class ViewPiece : public TextPiece {
public:
ViewPiece(Store *view);
virtual void read(Reader &reader);
- virtual std::string toString();
- virtual std::string toPlainText();
+ virtual std::string toString() const;
+ virtual void accept(Visitor &visitor) const;
};
class StdTextModel : public TextModel {
virtual void internalize(Reader &reader);
virtual std::string toString();
- virtual std::string toPlainText();
+ virtual void accept(Visitor &visitor) const;
};
} // namespace odc
diff --git a/visitor.h b/visitor.h
--- /dev/null
+++ b/visitor.h
@@ -0,0 +1,45 @@
+#ifndef _VISITOR_H_
+#define _VISITOR_H_
+
+namespace odc {
+
+ class ShortPiece;
+ class LongPiece;
+
+ /**
+ * Visitor role of the Visitor design pattern.
+ * Can be used to transform the document tree.
+ */
+ class Visitor {
+ public:
+ /**
+ * A "part" that can contain other elements starts here.
+ * This can be an StdTextModel or a ViewPiece or another container.
+ */
+ virtual void partStart() = 0;
+ /**
+ * A "part" ends here.
+ */
+ virtual void partEnd() = 0;
+ /**
+ * A left fold has been found.
+ * If the fold is collapsed, the first part that follows is the
+ * "hidden" part, otherwise the first part that follows is the
+ * "alternative" text. The rest is the vice versa.
+ * This is the main reason we even need a visitor.
+ * @param collapsed true if the fold is in collapsed form.
+ */
+ virtual void foldLeft(bool collapsed) = 0;
+ /**
+ * A right fold has been found.
+ */
+ virtual void foldRight() = 0;
+ /**
+ * A text piece has been found.
+ */
+ virtual void textShortPiece(const ShortPiece *piece) = 0;
+ virtual void textLongPiece(const LongPiece *piece) = 0;
+ };
+}
+
+#endif // _VISITOR_H_