summaryrefslogtreecommitdiffstats
path: root/divelist.c
diff options
context:
space:
mode:
Diffstat (limited to 'divelist.c')
-rw-r--r--divelist.c103
1 files changed, 103 insertions, 0 deletions
diff --git a/divelist.c b/divelist.c
index f8e9f1682..a426d67c3 100644
--- a/divelist.c
+++ b/divelist.c
@@ -17,6 +17,12 @@
#include <math.h>
#include <glib/gi18n.h>
#include <assert.h>
+#ifdef LIBZIP
+#include <zip.h>
+#endif
+#ifdef XSLT
+#include <libxslt/transform.h>
+#endif
#include "divelist.h"
#include "dive.h"
@@ -1965,6 +1971,94 @@ static void delete_dive_cb(GtkWidget *menuitem, GtkTreePath *path)
mark_divelist_changed(TRUE);
}
+#if defined(LIBZIP) && defined(XSLT)
+static void export_selected_dives_cb(GtkWidget *menuitem, GtkTreePath *path)
+{
+ int i;
+ struct dive *dive;
+ FILE *f;
+ char filename[PATH_MAX], *tempfile, *template;
+ size_t streamsize;
+ char *membuf;
+ xmlDoc *doc;
+ xsltStylesheetPtr xslt = NULL;
+ xmlDoc *transformed;
+ struct zip_source *s[dive_table.nr];
+ struct zip *zip;
+
+ /*
+ * Creating a temporary .DLD file to be eventually uploaded to
+ * divelogs.de. I wonder if this could be done in-memory.
+ */
+
+ template = strdup("/tmp/export.DLD-XXXXXX");
+ tempfile = mktemp(template);
+ zip = zip_open(tempfile, ZIP_CREATE, NULL);
+
+ if (!zip)
+ return;
+
+ if (!amount_selected)
+ return;
+
+ /* walk the dive list in chronological order */
+ for (i = 0; i < dive_table.nr; i++) {
+
+ dive = get_dive(i);
+ if (!dive)
+ continue;
+ if (!dive->selected)
+ continue;
+
+ /*
+ * Saving the dive is done into a memory buffer
+ */
+
+ f = open_memstream(&membuf, &streamsize);
+ if (!f)
+ return;
+ save_dive(f, dive);
+ fclose(f);
+
+ /*
+ * Parse the memory buffer into XML document and
+ * transform it to divelogs.de format, finally dumping
+ * the XML into a character buffer.
+ */
+
+ doc = xmlReadMemory(membuf, strlen(membuf), "divelog", NULL, 0);
+ if (!doc)
+ continue;
+
+ xslt = get_stylesheet("divelogs-export.xslt");
+ transformed = xsltApplyStylesheet(xslt, doc, NULL);
+ xsltFreeStylesheet(xslt);
+ xmlDocDumpMemory(transformed, (xmlChar **) &membuf, (int *)&streamsize);
+ xmlFreeDoc(doc);
+ xmlFreeDoc(transformed);
+
+ /*
+ * Save the XML document into a zip file.
+ */
+
+ snprintf(filename, PATH_MAX, "%d.xml", i + 1);
+ if ((s[i]=zip_source_buffer(zip, membuf, streamsize, 0)) == NULL || zip_add(zip, filename, s[i]) == -1)
+ fprintf(stderr, "failed to include dive %d\n", i);
+
+ }
+ zip_close(zip);
+
+ /*
+ * divelogs.de upload functionality should get rid of this
+ * message and use proper dialog to inform user of the success
+ * or failure of the upload
+ */
+
+ fprintf(stderr, "Created .DLD file %s\n", tempfile);
+ free(template);
+}
+#endif
+
static void merge_dive_index(int i, struct dive *a)
{
struct dive *b = get_dive(i+1);
@@ -2034,6 +2128,9 @@ static void popup_divelist_menu(GtkTreeView *tree_view, GtkTreeModel *model, int
char deleteplurallabel[] = N_("Delete dives");
char deletesinglelabel[] = N_("Delete dive");
char *deletelabel;
+#if defined(LIBZIP) && defined(XSLT)
+ char exportlabel[] = N_("Export dive(s)");
+#endif
GtkTreePath *path, *prevpath, *nextpath;
GtkTreeIter iter, previter, nextiter;
int idx, previdx, nextidx;
@@ -2101,6 +2198,12 @@ static void popup_divelist_menu(GtkTreeView *tree_view, GtkTreeModel *model, int
g_signal_connect(menuitem, "activate", G_CALLBACK(delete_selected_dives_cb), path);
gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem);
+#if defined(LIBZIP) && defined(XSLT)
+ menuitem = gtk_menu_item_new_with_label(exportlabel);
+ g_signal_connect(menuitem, "activate", G_CALLBACK(export_selected_dives_cb), path);
+ gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem);
+#endif
+
menuitem = gtk_menu_item_new_with_label(editlabel);
g_signal_connect(menuitem, "activate", G_CALLBACK(edit_selected_dives_cb), NULL);
gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem);