diff options
Diffstat (limited to 'FileManager.cpp')
-rw-r--r-- | FileManager.cpp | 390 |
1 files changed, 390 insertions, 0 deletions
diff --git a/FileManager.cpp b/FileManager.cpp new file mode 100644 index 0000000..7650a2f --- /dev/null +++ b/FileManager.cpp @@ -0,0 +1,390 @@ +#include "FileManager.h" +#include "Window.h" + + +bool FileManager::writeTriangle(xmlTextWriterPtr writer, const Triangle &triangle, float height) { + // <triangle> + if(xmlTextWriterStartElement(writer, (xmlChar*)"triangle") < 0) + return false; + + //if(xmlTextWriterWriteAttribute(writer, (xmlChar*)"texture", (xmlChar*)"t0") < 0) + // return false; + + float y = 0.0f; + if(triangle.getDirection() == Triangle::CW) y = height; + + if(!writeVertex(writer, triangle.getVertexA().getX(), y, triangle.getVertexA().getY())) + return false; + //if(!writeTexCoords(writer, triangle.getVertexA().getX(), triangle.getVertexA().getY())) + // return false; + + if(!writeVertex(writer, triangle.getVertexB().getX(), y, triangle.getVertexB().getY())) + return false; + //if(!writeTexCoords(writer, triangle.getVertexB().getX(), triangle.getVertexB().getY())) + // return false; + + if(!writeVertex(writer, triangle.getVertexC().getX(), y, triangle.getVertexC().getY())) + return false; + //if(!writeTexCoords(writer, triangle.getVertexC().getX(), triangle.getVertexC().getY())) + // return false; + + // </triangle> + if(xmlTextWriterEndElement(writer) < 0) + return false; + + // <triangle> + if(xmlTextWriterStartElement(writer, (xmlChar*)"triangle") < 0) + return false; + + //if(xmlTextWriterWriteAttribute(writer, (xmlChar*)"texture", (xmlChar*)"t0") < 0) + // return false; + + y = height; + if(triangle.getDirection() == Triangle::CW) y = 0.0f; + + if(!writeVertex(writer, triangle.getVertexC().getX(), y, triangle.getVertexC().getY())) + return false; + //if(!writeTexCoords(writer, triangle.getVertexC().getX(), triangle.getVertexC().getY())) + // return false; + + if(!writeVertex(writer, triangle.getVertexB().getX(), y, triangle.getVertexB().getY())) + return false; + //if(!writeTexCoords(writer, triangle.getVertexB().getX(), triangle.getVertexB().getY())) + // return false; + + if(!writeVertex(writer, triangle.getVertexA().getX(), y, triangle.getVertexA().getY())) + return false; + //if(!writeTexCoords(writer, triangle.getVertexA().getX(), triangle.getVertexA().getY())) + // return false; + + // </triangle> + if(xmlTextWriterEndElement(writer) < 0) + return false; + + return true; +} + +bool FileManager::writeSide(xmlTextWriterPtr writer, const Vertex &v1, const Vertex &v2, float height) { + // <triangle> + if(xmlTextWriterStartElement(writer, (xmlChar*)"triangle") < 0) + return false; + + //if(xmlTextWriterWriteAttribute(writer, (xmlChar*)"texture", (xmlChar*)"t0") < 0) + // return false; + + if(!writeVertex(writer, v1.getX(), 0, v1.getY())) + return false; + if(!writeTexCoords(writer, v1.getX(), v1.getY())) + return false; + + if(!writeVertex(writer, v2.getX(), 0, v2.getY())) + return false; + if(!writeTexCoords(writer, v2.getX(), v2.getY())) + return false; + + if(!writeVertex(writer, v2.getX(), height, v2.getY())) + return false; + if(!writeTexCoords(writer, v2.getX(), v2.getY())) + return false; + + // </triangle> + if(xmlTextWriterEndElement(writer) < 0) + return false; + + // <triangle> + if(xmlTextWriterStartElement(writer, (xmlChar*)"triangle") < 0) + return false; + + //if(xmlTextWriterWriteAttribute(writer, (xmlChar*)"texture", (xmlChar*)"t0") < 0) + // return false; + + if(!writeVertex(writer, v2.getX(), height, v2.getY())) + return false; + if(!writeTexCoords(writer, v2.getX(), v2.getY())) + return false; + + if(!writeVertex(writer, v1.getX(), height, v1.getY())) + return false; + if(!writeTexCoords(writer, v1.getX(), v1.getY())) + return false; + + if(!writeVertex(writer, v1.getX(), 0, v1.getY())) + return false; + if(!writeTexCoords(writer, v1.getX(), v1.getY())) + return false; + + // </triangle> + if(xmlTextWriterEndElement(writer) < 0) + return false; + + return true; +} + +bool FileManager::writeVertex(xmlTextWriterPtr writer, float x, float y, float z) { + // <vertex> + if(xmlTextWriterStartElement(writer, (xmlChar*)"vertex") < 0) + return false; + + if(xmlTextWriterWriteFormatAttribute(writer, (xmlChar*)"x", "%f", x) < 0) + return false; + + if(xmlTextWriterWriteFormatAttribute(writer, (xmlChar*)"y", "%f", y) < 0) + return false; + + if(xmlTextWriterWriteFormatAttribute(writer, (xmlChar*)"z", "%f", z) < 0) + return false; + + // </vertex> + if(xmlTextWriterEndElement(writer) < 0) + return false; + + return true; +} + +bool FileManager::writeTexCoords(xmlTextWriterPtr writer, float s, float t) { + // <texcoords> + if(xmlTextWriterStartElement(writer, (xmlChar*)"texcoords") < 0) + return false; + + if(xmlTextWriterWriteFormatAttribute(writer, (xmlChar*)"s", "%f", s) < 0) + return false; + + if(xmlTextWriterWriteFormatAttribute(writer, (xmlChar*)"t", "%f", t) < 0) + return false; + + // </texcoords> + if(xmlTextWriterEndElement(writer) < 0) + return false; + + return true; +} + +FileManager::FileManager(Window *window) { + this->window = window; + + filename = NULL; + dirty = false; +} + +FileManager::~FileManager() { + if(filename) + g_free(filename); +} + +bool FileManager::save(GtkWindow *parent) { + if(filename == NULL) + return saveAs(parent); + + return write(); +} + +bool FileManager::saveAs(GtkWindow *parent) { + GtkWidget *dialog = gtk_file_chooser_dialog_new(NULL, parent, GTK_FILE_CHOOSER_ACTION_SAVE, + GTK_STOCK_OK, GTK_RESPONSE_ACCEPT, GTK_STOCK_CANCEL, GTK_RESPONSE_REJECT, NULL); + + if(filename) + gtk_file_chooser_set_filename(GTK_FILE_CHOOSER(dialog), filename); + else + gtk_file_chooser_set_current_name(GTK_FILE_CHOOSER(dialog), "level.lvl"); + + if(gtk_dialog_run(GTK_DIALOG(dialog)) != GTK_RESPONSE_ACCEPT) { + gtk_widget_destroy(dialog); + return false; + } + + if(filename) + g_free(filename); + + filename = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(dialog)); + + gtk_widget_destroy(dialog); + + if(!filename) + return false; + + return write(); +} + +bool FileManager::write() { + xmlTextWriterPtr writer; + + writer = xmlNewTextWriterFilename(filename, 9); + if(!writer) + return false; + + if(xmlTextWriterStartDocument(writer, NULL, "UTF-8", NULL) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterStartDTD(writer, (xmlChar*)"level", (xmlChar*)"-//libzoom//DTD level 0.1//EN", (xmlChar*)"level.dtd") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterSetIndent(writer, 1) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterSetIndentString(writer, (xmlChar*)" ") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterEndDTD(writer) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // <level> + if(xmlTextWriterStartElement(writer, (xmlChar*)"level") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // <info> + if(xmlTextWriterStartElement(writer, (xmlChar*)"info") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterWriteElement(writer, (xmlChar*)"name", (xmlChar*)"Level") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterWriteElement(writer, (xmlChar*)"desc", (xmlChar*)"Description") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // <start> + if(xmlTextWriterStartElement(writer, (xmlChar*)"start") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterWriteAttribute(writer, (xmlChar*)"x", (xmlChar*)"0.0") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterWriteAttribute(writer, (xmlChar*)"y", (xmlChar*)"2.0") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterWriteAttribute(writer, (xmlChar*)"z", (xmlChar*)"0.0") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // </start> + if(xmlTextWriterEndElement(writer) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // </info> + if(xmlTextWriterEndElement(writer) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // <rooms> + if(xmlTextWriterStartElement(writer, (xmlChar*)"rooms") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + for(Level::iterator room = window->getLevel().begin(); room != window->getLevel().end(); room++) { + // <room> + if(xmlTextWriterStartElement(writer, (xmlChar*)"room") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterWriteAttribute(writer, (xmlChar*)"id", (xmlChar*)room->getName().c_str()) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + std::vector<Triangle> triangles; + room->triangulate(triangles); + + for(std::vector<Triangle>::iterator triangle = triangles.begin(); triangle != triangles.end(); triangle++) { + if(!writeTriangle(writer, *triangle, room->getHeight())) { + xmlFreeTextWriter(writer); + return false; + } + } + + std::vector<Vertex> vertices = *room; + + if(room->getDirection() == Triangle::CCW) { + vertices = std::vector<Vertex>(vertices.rbegin(), vertices.rend()); + } + + for(std::vector<Vertex>::iterator v1 = vertices.begin(); v1 != vertices.end(); v1++) { + std::vector<Vertex>::iterator v2 = v1+1; + if(v2 == vertices.end()) v2 = vertices.begin(); + + if(!writeSide(writer, *v1, *v2, room->getHeight())) { + xmlFreeTextWriter(writer); + return false; + } + } + + // </room> + if(xmlTextWriterEndElement(writer) < 0) { + xmlFreeTextWriter(writer); + return false; + } + } + + // </rooms> + if(xmlTextWriterEndElement(writer) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // <gates> + if(xmlTextWriterStartElement(writer, (xmlChar*)"gates") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // </gates> + if(xmlTextWriterEndElement(writer) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // <textures> + if(xmlTextWriterStartElement(writer, (xmlChar*)"textures") < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // </textures> + if(xmlTextWriterEndElement(writer) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + // </level> + if(xmlTextWriterEndElement(writer) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + if(xmlTextWriterEndDocument(writer) < 0) { + xmlFreeTextWriter(writer); + return false; + } + + xmlFreeTextWriter(writer); + + return true; +} |