const {ipcRenderer} = require('electron');
const marked = require('marked');
const renderer = new marked.Renderer();
const hljs = require('highlight.js');
const fs = require('fs');
const path = require('path');
const Viz = require("viz.js");

marked.setOptions({
  renderer: renderer,
  gfm: true,
  breaks: false
});

// escape HTML special characters
// from: http://qiita.com/noriaki/items/4bfef8d7cf85dc1035b3
function escapeHtml(content) {
  var TABLE_FOR_ESCAPE_HTML = {
    "&": "&amp;",
    "\"": "&quot;",
    "<": "&lt;",
    ">": "&gt;"
  };
  return content.replace(/[&"<>]/g, function(match) {
    return TABLE_FOR_ESCAPE_HTML[match];
  });
}

// redering code
renderer.code = function (code, language) {
  const CONV_ERR_HEAD = "\n******************* Convert Error *******************\n";
  const CONV_ERR_TAIL = "*****************************************************\n";
  if (language == "graphviz") {
    let result;
    try {
      result = Viz(code);
      return result;
    } catch (error) {
      return '<pre><code>' + hljs.highlightAuto(code).value + CONV_ERR_HEAD + error + CONV_ERR_TAIL +'</code></pre>';
    }
  } else {
    return '<pre><code>' + hljs.highlightAuto(code).value + '</code></pre>';
  }
}

// rendering list
renderer.listitem = function (text) {
  if (text.startsWith("[x]")) {
    return '<li class="task-list-item"><input type="checkbox" checked="true" disabled="true">' + text.slice(3) + '</li>';
  } else if (text.startsWith("[ ]")) {
    return '<li class="task-list-item"><input type="checkbox" disabled="true">' + text.slice(3) + '</li>';
  } else {
    return '<li>' + text + '</li>';
  }
}

// rendering html (sanitize script)
renderer.html = function (html) {
  if (html.match(/<[^>]*script[^>]*>/g) !== null) {
    return '<pre><code>' + html.replace(/\</g, "&lt;").replace(/\>/g, "&gt;").trim() + '</code></pre>';
  } else if (html.match(/<[^>]* on[^=>]*=/) !== null) {
    return '<pre><code>' + html.replace(/\</g, "&lt;").replace(/\>/g, "&gt;").trim() + '</code></pre>';
  } else {
    return html;
  }
}

// request preview
ipcRenderer.on('preview', function(event, data, baseURI) {
  let base = document.getElementsByTagName("base")[0];
  if (baseURI != "") {
    base.setAttribute("href", baseURI);
  }
  base.setAttribute("target", "_blank");
  document.getElementById('body').innerHTML = marked(data, { renderer: renderer });
  document.title = document.getElementsByTagName("h1")[0].innerHTML;
});

// request export HTML
ipcRenderer.on('export-HTML', function(event, filename) {
  let base = document.getElementsByTagName("base")[0];
  base.removeAttribute("href");
  base.removeAttribute("target");

  // http://blog.mudatobunka.org/entry/2015/12/23/211425#postscript
  fs.writeFile (filename, new XMLSerializer().serializeToString(document), function (error) {
    if (error != null) {
      alert ('error: ' + error + '\n' + filename);
      return;
    }
    let src_css = path.join(__dirname, '../templates/github.css');
    let dest_css = path.join(path.dirname(filename), "github.css");
    fs.createReadStream(src_css).pipe(fs.createWriteStream(dest_css));
  });

  base.setAttribute("target", "_blank");
});


@@ -234,16 +234,50 @@
 iz.js%22);
+%0Aconst uiflow = require(%22uiflow%22);
 %0A%0Amarked
@@ -1164,16 +1164,288 @@
 ;%0A    %7D%0A
+  %7D else if(language == %22uiflow%22) %7B%0A    try %7B%0A      let dot = uiflow.compile(code);%0A      return Viz(dot);%0A    %7D catch (error) %7B%0A      console.log(error);%0A      return '%3Cpre%3E%3Ccode%3E' + escapeHtml(code) + CONV_ERR_HEAD + error + '%5Cn' + CONV_ERR_TAIL +'%3C/code%3E%3C/pre%3E';%0A    %7D%0A
   %7D else

add uiflow support