Merge pull request #1144

Preserve format tags and entities in bibliography editor

Closes #1144
This commit is contained in:
Dan Stillman 2017-01-04 23:40:25 -05:00
commit 231a276b06
2 changed files with 51 additions and 23 deletions

View File

@ -51,19 +51,26 @@
this._onInitCallbacks = []; this._onInitCallbacks = [];
this._iframe = document.getAnonymousElementByAttribute(this, "anonid", "rt-view"); this._iframe = document.getAnonymousElementByAttribute(this, "anonid", "rt-view");
// Atomic units, HTML -> RTF (cleanup)
//[/<\/p>(?!\s*$)/g, "\\par{}"],
//[/ /g, "&nbsp;"],
//[/\u00A0/g, " "],
this._htmlRTFmap = [ this._htmlRTFmap = [
// Atomic units, HTML -> RTF (cleanup)
[/<br \/>/g, "\x0B"], [/<br \/>/g, "\x0B"],
[/<span class=\"tab\">&nbsp;<\/span>/g, "\\tab{}"],
[/&lsquo;/g, ""],
[/&rsquo;/g, ""],
[/&ldquo;/g, "“"],
[/&rdquo;/g, "”"],
[/&nbsp;/g, "\u00A0"],
[/"(\w)/g, "“$1"], [/"(\w)/g, "“$1"],
[/([\w,.?!])"/g, "$1”"], [/([\w,.?!])"/g, "$1”"],
[/<p>/g, ""], [/<p>/g, ""],
//[/<\/p>(?!\s*$)/g, "\\par{}"], [/<\/?div[^>]*>/g, ""]
[/<\/?div[^>]*>/g, ""],
[/[\x7F-\uFFFF]/g, function(aChar) { return "\\uc0\\u"+aChar.charCodeAt(0).toString()+"{}"}]
]; ];
// Atomic units, RTF -> HTML (cleanup)
this._rtfHTMLmap = [ this._rtfHTMLmap = [
// Atomic units, RTF -> HTML (cleanup)
[/\\uc0\{?\\u([0-9]+)\}?(?:{}| )?/g, function(wholeStr, aCode) { return String.fromCharCode(aCode) }], [/\\uc0\{?\\u([0-9]+)\}?(?:{}| )?/g, function(wholeStr, aCode) { return String.fromCharCode(aCode) }],
[/\\tab(?:\{\}| )/g, '<span class="tab">&nbsp;</span>'], [/\\tab(?:\{\}| )/g, '<span class="tab">&nbsp;</span>'],
[/(?:\\par{}|\\\r?\n)/g, "</p><p>"] [/(?:\\par{}|\\\r?\n)/g, "</p><p>"]
@ -77,7 +84,7 @@
var _rexData = [ var _rexData = [
[ [
[ [
["<span style=\"font-variant:small-caps;\">"], ["<span +style=\"font-variant: *small-caps;\">"],
["{\\scaps ", "{\\scaps{}"] ["{\\scaps ", "{\\scaps{}"]
], ],
[ [
@ -87,7 +94,7 @@
], ],
[ [
[ [
["<span style=\"text-decoration:underline;\">"], ["<span +style=\"text-decoration: *underline;\">"],
["{\\ul{}", "{\\ul "] ["{\\ul{}", "{\\ul "]
], ],
[ [
@ -157,7 +164,7 @@
], ],
[ [
[ [
["<span style=\"font-variant:normal;\">"], ["<span +style=\"font-variant: *normal;\">"],
["{\\scaps0{}", "{\\scaps0 "] ["{\\scaps0{}", "{\\scaps0 "]
], ],
[ [
@ -167,7 +174,7 @@
], ],
[ [
[ [
["<span style=\"font-style:normal;\">"], ["<span +style=\"font-style: *normal;\">"],
["{\\i0{}", "{\\i0 "] ["{\\i0{}", "{\\i0 "]
], ],
[ [
@ -177,7 +184,7 @@
], ],
[ [
[ [
["<span style=\"font-weight:normal;\">"], ["<span +style=\"font-weight: *normal;\">"],
["{\\b0{}", "{\\b0 "] ["{\\b0{}", "{\\b0 "]
], ],
[ [
@ -197,6 +204,16 @@
} }
} }
function normalizeRegExpString(str) {
if (!str) return str;
return str.replace(/\s+/g, " ")
.replace(/(?:[\+]|\s[\*])/g, "")
.replace(/[\']/g, '\"')
.replace(/:\s/g, ":");
}
this.normalizeRegExpString = normalizeRegExpString;
function composeRex(rexes, noGlobal) { function composeRex(rexes, noGlobal) {
var lst = []; var lst = [];
for (var rex in rexes) { for (var rex in rexes) {
@ -240,13 +257,15 @@
function openTagRemapMaker(segment) { function openTagRemapMaker(segment) {
var ret = {}; var ret = {};
for (var i=0,ilen=_rexData.length; i < ilen; i++) { for (var i=0,ilen=_rexData.length; i < ilen; i++) {
var master = _rexData[i][0][segment][0]; var primaryVal = normalizeRegExpString(_rexData[i][0][segment][0]);
for (var j=0,jlen=_rexData[i][0][segment].length; j < jlen; j++) { for (var j=0,jlen=_rexData[i][0][segment].length; j < jlen; j++) {
ret[_rexData[i][0][segment][j]] = master; var key = normalizeRegExpString(_rexData[i][0][segment][j]);
ret[key] = primaryVal;
} }
} }
return ret; return ret;
} }
this.rtfHTMLopenTagRemap = openTagRemapMaker(1); this.rtfHTMLopenTagRemap = openTagRemapMaker(1);
this.htmlRTFopenTagRemap = openTagRemapMaker(0); this.htmlRTFopenTagRemap = openTagRemapMaker(0);
@ -255,11 +274,11 @@
var ret = {}; var ret = {};
var rexes = {}; var rexes = {};
for (var i=0,ilen=_rexData.length; i < ilen; i++) { for (var i=0,ilen=_rexData.length; i < ilen; i++) {
var master = _rexData[i][0][segment][0]; var primaryVal = _rexData[i][0][segment][0];
for (var j=0,jlen=_rexData[i][1][segment].length; j < jlen; j++) { for (var j=0,jlen=_rexData[i][1][segment].length; j < jlen; j++) {
rexes[_rexData[i][1][segment][j]] = true; rexes[_rexData[i][1][segment][j]] = true;
} }
ret[master] = composeRex(rexes); ret[primaryVal] = composeRex(rexes);
} }
return ret; return ret;
} }
@ -274,14 +293,15 @@
} }
var ret = {}; var ret = {};
for (var i=0,ilen=_rexData.length; i < ilen; i++) { for (var i=0,ilen=_rexData.length; i < ilen; i++) {
var master = _rexData[i][0][segment][0]; var primaryVal = normalizeRegExpString(_rexData[i][0][segment][0]);
ret[master] = { ret[primaryVal] = {
open: _rexData[i][0][antisegment][0], open: normalizeRegExpString(_rexData[i][0][antisegment][0]),
close: _rexData[i][1][antisegment][0] close: _rexData[i][1][antisegment][0]
} }
} }
return ret; return ret;
} }
this.rtfHTMLtagRegistry = tagRegistryMaker(1); this.rtfHTMLtagRegistry = tagRegistryMaker(1);
this.htmlRTFtagRegistry = tagRegistryMaker(0); this.htmlRTFtagRegistry = tagRegistryMaker(0);
@ -304,7 +324,7 @@
this.getOpenTag = function(mode, str) { this.getOpenTag = function(mode, str) {
var m = str.match(this[mode + "openSniffRex"]); var m = str.match(this[mode + "openSniffRex"]);
if (m) { if (m) {
m = this[mode + "openTagRemap"][m[0]]; m = this[mode + "openTagRemap"][this.normalizeRegExpString(m[0])];
} }
return m; return m;
} }
@ -339,14 +359,13 @@
} }
this.htmlToRTF = function(txt) { this.htmlToRTF = function(txt) {
// Catch this one before &nbsp; is clobbered by unescape txt = this.convert("htmlRTF", txt);
txt = txt.replace(/<span class=\"tab\">&nbsp;<\/span>/g, "\\tab{}");
txt = Zotero.Utilities.unescapeHTML(txt);
for (var i=0,ilen=this._htmlRTFmap.length; i < ilen; i++) { for (var i=0,ilen=this._htmlRTFmap.length; i < ilen; i++) {
var entry = this._htmlRTFmap[i]; var entry = this._htmlRTFmap[i];
txt = txt.replace(entry[0], entry[1]); txt = txt.replace(entry[0], entry[1]);
} }
txt = this.convert("htmlRTF", txt); txt = Zotero.Utilities.unescapeHTML(txt);
txt = txt.replace(/[\x7F-\uFFFF]/g, function(aChar) { return "\\uc0\\u"+aChar.charCodeAt(0).toString()+"{}"});
return txt.trim(); return txt.trim();
} }

View File

@ -41,6 +41,7 @@ var Zotero_Citation_Dialog = new function () {
var _previewShown = false; var _previewShown = false;
var _suppressNextTreeSelect = false; var _suppressNextTreeSelect = false;
var _suppressNextListSelect = false; var _suppressNextListSelect = false;
var _customHTML = false;
var _locatorIndexArray = {}; var _locatorIndexArray = {};
var _locatorNameArray = {}; var _locatorNameArray = {};
var _autoRegeneratePref; var _autoRegeneratePref;
@ -556,6 +557,9 @@ var Zotero_Citation_Dialog = new function () {
if(_previewShown) { if(_previewShown) {
document.documentElement.getButton("extra2").label = Zotero.getString("citation.hideEditor"); document.documentElement.getButton("extra2").label = Zotero.getString("citation.hideEditor");
if (!text && _customHTML) {
text = _customHTML;
}
if(text) { if(text) {
io.preview().then(function(preview) { io.preview().then(function(preview) {
_originalHTML = preview; _originalHTML = preview;
@ -565,6 +569,11 @@ var Zotero_Citation_Dialog = new function () {
_updatePreview(); _updatePreview();
} }
} else { } else {
if (editor.initialized) {
if (editor.value) {
_customHTML = editor.value;
}
}
document.documentElement.getButton("extra2").label = Zotero.getString("citation.showEditor"); document.documentElement.getButton("extra2").label = Zotero.getString("citation.showEditor");
} }
} }
@ -795,4 +804,4 @@ var Zotero_Citation_Dialog = new function () {
function _clearCitationList() { function _clearCitationList() {
while(_citationList.firstChild) _citationList.removeChild(_citationList.firstChild); while(_citationList.firstChild) _citationList.removeChild(_citationList.firstChild);
} }
} }