]> matita.cs.unibo.it Git - helm.git/blobdiff - helm/DEVEL/mathml_editor/test/editor.cc
Initial revision
[helm.git] / helm / DEVEL / mathml_editor / test / editor.cc
diff --git a/helm/DEVEL/mathml_editor/test/editor.cc b/helm/DEVEL/mathml_editor/test/editor.cc
new file mode 100644 (file)
index 0000000..265d35e
--- /dev/null
@@ -0,0 +1,214 @@
+
+#include "TNode.hh"
+#include "TToken.hh"
+#include "TDocument.hh"
+#include "TPushParser.hh"
+#include "TPushLexer.hh"
+#include "TDictionary.hh"
+#include "TListener.hh"
+#include <GdomeSmartDOMXSLT.hh>
+
+#include "guiGTK.h"
+
+class MyResultListener : public DOM::EventListener
+{
+public:
+  MyResultListener(const std::string& s) : msg(s) { };
+
+  virtual void handleEvent(const DOM::Event&);
+
+private:
+  const std::string msg;
+};
+
+void
+MyResultListener::handleEvent(const DOM::Event& ev)
+{
+  cout << "RECEIVED EVENT: " << ev.get_type() << " " << msg << " ";
+  const DOM::MutationEvent& me(ev);
+  assert(me);
+  const DOM::Node target(me.get_target());
+  assert(target);
+  cout << "target = " << target.get_nodeName() << " " << target.get_nodeType() << endl;
+}
+
+MyResultListener l1("?");
+
+TDictionary dictionary;
+DOM::Document result;
+
+extern void *parseMathMLFile(char *);
+
+bool
+subst(const DOM::Element& e1, const DOM::GdomeString& id, const DOM::Element& e2)
+{
+  assert(e1);
+  assert(e2);
+  if (e1.getAttribute("xref") == id)
+    {
+      DOM::Node parent = e1.get_parentNode();
+      assert(parent);
+      DOM::Node next = e1.get_nextSibling();
+      parent.removeChild(e1);
+      parent.insertBefore(e2, next);
+      //parent.replaceChild(e2, e1);
+      return true;
+    }
+  else
+    {
+      DOM::Node p = e1.get_firstChild();
+      while (p)
+       {
+         while (p && p.get_nodeType() != DOM::Node::ELEMENT_NODE) p = p.get_nextSibling();
+         if (p)
+           if (subst(p, id, e2)) return true;
+           else p = p.get_nextSibling();
+       }
+      return false;
+    }
+}
+
+class MyListener : public TListener
+{
+public:
+  MyListener(const DOM::XSLTStylesheet& s) : style(s) { };
+
+  void callback(TDocument& doc)
+  {
+    cout << "listener callback " << static_cast<GdomeNode*>(doc.document()) << endl;
+    TNode dirty = doc.dirtyNode();
+    if (dirty) 
+      {
+       cout << "recreating subtree with id " << std::string(dirty["id"]) << endl;
+       std::vector< std::pair<DOM::GdomeString, DOM::GdomeString> > dirtyId;
+       if (result)
+         dirtyId.push_back(std::make_pair(DOM::GdomeString("id"),
+                                          DOM::GdomeString("'" + std::string(dirty["id"]) + "'")));
+       DOM::Document res = style.apply(doc.document(), dirtyId);
+       assert(res);
+       style.save(doc.document(), stdout);
+       style.save(res, stdout);
+       if (result)
+         {
+           cout << "REPLACING A FRAGMENT OF THE DOCUMENT" << endl;
+           DOM::Element root = res.get_documentElement();
+           assert(root);
+           assert(root.hasAttribute("xref"));
+
+           if (result.get_documentElement().getAttribute("xref") == root.getAttribute("xref"))
+             {
+               cout << "REPLACING ROOT" << endl;
+               // the following remove should not be necessary
+               // according to the spec replaceChild should work just fine
+               result.removeChild(result.get_documentElement());
+               result.appendChild(result.importNode(root, true));
+             }
+           else
+             try
+               {
+                 cout << "before" << endl;
+                 bool ok = subst(result.get_documentElement(), root.getAttribute("xref"), result.importNode(root, true));
+                 assert(ok);
+                 cout << "after" << endl;
+               }
+             catch (DOM::DOMException e)
+               {
+                 cout << "!!!!!!!!!!!!!!!! EXCEPTION " << e.code << " " << e.msg << endl;
+                 assert(0);
+               }
+         }
+       else
+         {
+           cout << "SETTING THE DOCUMENT FOR THE FIRST TIME" << endl;
+           result = res;
+
+           DOM::EventTarget et(result);
+           assert(et);
+           cout << "SETTING EVENT LISTENER (EDITOR) ON " << static_cast<GdomeNode*>(result) << endl;
+           et.addEventListener("DOMSubtreeModified", l1, true);
+
+            if (GUI_load_document(gdome_cast_doc(static_cast<GdomeNode*>(result))) < 0)
+             cerr << "c'e' stato un errore" << endl;
+         }
+
+       doc.clearDirty();
+      }
+  }
+
+private:
+  const DOM::XSLTStylesheet& style;
+};
+
+struct Context
+{
+  Context(const std::string& s, TPushLexer& l) : buffer(s), i(0), lexer(l) { };
+
+  void send(void)
+  {
+    if (i < buffer.length())
+      {
+       cout << "document is " << static_cast<GdomeNode*>(result) << endl;
+       lexer.push(buffer[i++]);
+      }
+    else lexer.push('\n');
+  }
+
+  std::string buffer;
+  unsigned i;
+  TPushLexer& lexer;
+};
+
+extern "C" int
+edit_timeout(Context* data)
+{
+  assert(data);
+  GUI_freeze();
+  data->send();
+  GUI_thaw();
+  return 1;
+}
+
+extern "C" void
+push_char(Context* context, gchar ch)
+{
+  GUI_freeze();
+  cout << "*** SENDING " << ch << endl;
+  context->lexer.push(ch);
+  GUI_thaw();
+}
+
+main(int argc, char* argv[])
+{
+  cout << "loading the dictionary..." << endl;
+  dictionary.load("dictionary.xml");
+
+  cout << "loading the stylesheet..." << endl;
+  DOM::DOMImplementation di;
+  DOM::Document docStyle = di.createDocumentFromURI("./xsl/tml-mmlp.xsl");
+  DOM::XSLTStylesheet style(docStyle);
+  
+  MyListener listener(style);
+  TPushParser parser(dictionary, listener);
+  TPushLexer lexer(parser);
+
+#if 0
+  lexer.push('$');
+  lexer.push(' ');
+  assert(result);
+#endif
+
+#if 0
+  DOM::Document doc = parser.document().document();
+  std::vector< std::pair<DOM::GdomeString, DOM::GdomeString> > np;
+  result = style.apply(doc, np);
+  style.save(result, stdout);
+#endif
+
+  Context context("", lexer);
+
+  cout << "passing context " << &context << endl;
+  GUI_init(&argc, &argv, "mathmleditor", 500, 600, &context);
+  GUI_run();
+  GUI_uninit();
+  GUI_unload_document();
+}