【问题标题】:Edit, save, self-modifying HTML document; format generated HTML, JavaScript编辑、保存、自修改HTML文档;格式生成的 HTML、JavaScript
【发布时间】:2015-08-14 07:15:09
【问题描述】:

动机:https://stackoverflow.com/questions/28120689/create-self-modifying-html-page-on-box

Bug:字符串转义,格式化htmljs由初始编辑生成,保存htmljs

例如,

a) 如果在本地浏览器打开“saveFile.html”;

b) 在textarea 中输入“abc”;

c) 点击save file 按钮;

d) 在Save File 对话框中单击Save

e) file-*[date according to universal time].html 保存到磁盘;

f) 在浏览器中打开file-*[date according to universal time].html

g) 在textarea 中输入“def”;

h) 重复 d) , e) , f) ;

i) 错误:第二个file-*[date according to universal time].html 的结果确实显示包含“abc def”文本内容的textareabutton显示在html:

// at rendered `html` from second `file-*[date according to universal time].html`
// `textarea` containing "abc def" displayed here , 
// `button` _not_ displayed ; following string displayed following `textarea`:
');"console.log(clone);var file = new Blob([clone], {'type':'text/html'});a.href = URL.createObjectURL(file);a.download = 'file-' + new Date().getTime() + '.html';a.click();};

26 行生成,“saveFile.html”

+ "var clone = '<!doctype html>'+ document.documentElement.outerHTML.replace(/<textarea>.*<.+textarea>/, '<textarea>'+document.getElementsByTagName('textarea')[0].value+'<\/textarea>');"

“saveFile.html”v 1.0.0

html,js

<!doctype html>
<html>
<!-- saveFile.html 1.0.0 2015 guest271314 edit, save `html` document -->
<head>
</head>
<body>
<textarea>
</textarea>
<button>save file</button>
<script type="text/javascript">
var saveFile = document.getElementsByTagName("button")[0];
var input = document.getElementsByTagName("textarea")[0];
var a = document.createElement("a");

saveFile.onclick = function(e) {

  var clone = ["<!doctype html><head></head><body><textarea>"
              + input.value
              + "</textarea>"
              + "<button>save file</button>"
              + "<script type='text/javascript'>"
              + "var saveFile = document.getElementsByTagName('button')[0];"
              + "var input = document.getElementsByTagName('textarea')[0];"
              + "var a = document.createElement('a');"
              + "saveFile.onclick = function(e) {"
              + "var clone = '<!doctype html>'+ document.documentElement.outerHTML.replace(/<textarea>.*<.+textarea>/, '<textarea>'+document.getElementsByTagName('textarea')[0].value+'<\/textarea>');"
              + "console.log(clone);"
              + "var file = new Blob([clone], {'type':'text/html'});"
              + "a.href = URL.createObjectURL(file);"
              + "a.download = 'file-' + new Date().getTime() + '.html';"
              + "a.click();"
              + "};"
              + "</scr"+"ipt>"
              + "</body>"
              + "</html>"];

  var file = new Blob([clone], {"type":"text/html"});  
  a.href = URL.createObjectURL(file);
  a.download = "file-" + new Date().getTime() + ".html";
  a.click();  

};
</script>
</body>
</html>

【问题讨论】:

  • 您能否更清楚、更简单地解释应该发生什么与实际发生什么?或许也可以为整体概念提供一些更好的背景信息?
  • @Anthony 预期的结果是在“保存文件”button 上的 click 之后保存的文件,打开时,应将文本输入呈现到上一个 html 文档中的 textarea 元素中,包括兄弟@ 987654344@ 元素。上下文试图创建自修改、伪多态 html 文档,其中在 textarea 所做的更改,保存在一个版本,在下一个保存的版本呈现。

标签: javascript html self-modifying


【解决方案1】:

您的替换函数将替换到您的clone 变量中的/textarea&gt;。它不会从第一个文件中执行此操作,因为 html 中的 textarea 之后有一个换行符。解决它的一种方法是在生成的 html 中添加一个 newline 字符。像这样:

var clone = ["<!doctype html><head></head><body><textarea>"
          + input.value
         // add newline here
          + "</textarea>\n"
          + "<button>save file</button>"
          + "<script type='text/javascript'>"
          + "var saveFile = document.getElementsByTagName('button')[0];"
          + "var input = document.getElementsByTagName('textarea')[0];"
          + "var a = document.createElement('a');"
          + "saveFile.onclick = function(e) {"
          + "var clone = '<!doctype html>'+ document.documentElement.outerHTML.replace(/<textarea>.*<.+textarea>/, '<textarea>'+document.getElementsByTagName('textarea')[0].value+'<\/textarea>');"
          + "console.log(clone);"
          + "var file = new Blob([clone], {'type':'text/html'});"
          + "a.href = URL.createObjectURL(file);"
          + "a.download = 'file-' + new Date().getTime() + '.html';"
          + "a.click();"
          + "};"
          + "</scr"+"ipt>"
          + "</body>"
          + "</html>"];

【讨论】:

  • 试过 + '&lt;/textarea&gt;\n');"button 显示,虽然似乎在 js 呈现新行;以');console.log(clone) 开头的下一行呈现为文本字符串,而不是源代码中的js
  • 查看编辑,您需要在第一个“”之后添加\n
【解决方案2】:

我不确定是什么破坏了第三代克隆,从而导致将 js 信息输出到页面,但使用实际的文档对象来克隆/操作原始文件和输出可能会更好其内容为Blob 对象的字符串。例如,我使用您的基本 saveFile.html 进行了测试,并进行了以下更改:

//remove original clone var and replace with:
var clone = document.cloneNode(true);

// grab textarea elements from both original document and clone:
var doc_input = document.getElementsByTagName("textarea")[0];
var clone_input = clone.getElementsByTagName("textarea")[0];

// set clone textarea's innerHTML to current textarea value:
clone_input.innerHTML = doc_input.value;

// use outerHTML of clone.documentElement to get string for Blob
var clone_string = [clone.documentElement.outerHTML];
var file = new Blob([clone_string], {"type":"text/html"});

我看到的唯一缺点是:

  1. 这可能很难扩展为一个更通用的框架来生成加载 HTML 页面当前状态的“实时 HTML 文件”(尽管它不应该比您的示例方法更复杂)。

  2. clone.documentElement.outerHTML 返回的字符串似乎将文档类型声明放到一个简单元素中,这样:

不在输出字符串中。你可能会使用类似的东西:

var clone_string = ["<!doctype html>" + clone.documentElement.outerHTML];

作为一种解决方法。或者,对于更强大的东西:

var doc_doctype = new XMLSerializer().serializeToString(document.doctype);

var clone_string = [doc_doctype + clone.documentElement.outerHTML];

【讨论】:

  • 已更新。还添加了仅使用serializeToString 而不是outerHTML 的html v2。确保针对您希望它使用的任何浏览器进行测试。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-04-20
  • 1970-01-01
  • 2014-07-15
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-11-06
相关资源
最近更新 更多