mirror of
https://github.com/fastmail/Squire.git
synced 2024-12-22 23:40:35 -05:00
Update to latest release
This commit is contained in:
parent
5d0731836c
commit
75c524720b
2 changed files with 140 additions and 81 deletions
|
@ -47,6 +47,7 @@ var cantFocusEmptyTextNodes = isIElt11 || isWebKit;
|
||||||
var losesSelectionOnBlur = isIElt11;
|
var losesSelectionOnBlur = isIElt11;
|
||||||
|
|
||||||
var canObserveMutations = typeof MutationObserver !== 'undefined';
|
var canObserveMutations = typeof MutationObserver !== 'undefined';
|
||||||
|
var canWeakMap = typeof WeakMap !== 'undefined';
|
||||||
|
|
||||||
// Use [^ \t\r\n] instead of \S so that nbsp does not count as white-space
|
// Use [^ \t\r\n] instead of \S so that nbsp does not count as white-space
|
||||||
var notWS = /[^ \t\r\n]/;
|
var notWS = /[^ \t\r\n]/;
|
||||||
|
@ -201,25 +202,53 @@ function every ( nodeList, fn ) {
|
||||||
|
|
||||||
// ---
|
// ---
|
||||||
|
|
||||||
|
var UNKNOWN = 0;
|
||||||
|
var INLINE = 1;
|
||||||
|
var BLOCK = 2;
|
||||||
|
var CONTAINER = 3;
|
||||||
|
|
||||||
|
var nodeCategoryCache = canWeakMap ? new WeakMap() : null;
|
||||||
|
|
||||||
function isLeaf ( node ) {
|
function isLeaf ( node ) {
|
||||||
return node.nodeType === ELEMENT_NODE &&
|
return node.nodeType === ELEMENT_NODE && !!leafNodeNames[ node.nodeName ];
|
||||||
!!leafNodeNames[ node.nodeName ];
|
|
||||||
}
|
}
|
||||||
function isInline ( node ) {
|
function getNodeCategory ( node ) {
|
||||||
return inlineNodeNames.test( node.nodeName ) &&
|
switch ( node.nodeType ) {
|
||||||
|
case TEXT_NODE:
|
||||||
|
return INLINE;
|
||||||
|
case ELEMENT_NODE:
|
||||||
|
case DOCUMENT_FRAGMENT_NODE:
|
||||||
|
if ( canWeakMap && nodeCategoryCache.has( node ) ) {
|
||||||
|
return nodeCategoryCache.get( node );
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
return UNKNOWN;
|
||||||
|
}
|
||||||
|
|
||||||
|
var nodeCategory;
|
||||||
|
if ( !every( node.childNodes, isInline ) ) {
|
||||||
// Malformed HTML can have block tags inside inline tags. Need to treat
|
// Malformed HTML can have block tags inside inline tags. Need to treat
|
||||||
// these as containers rather than inline. See #239.
|
// these as containers rather than inline. See #239.
|
||||||
( node.nodeType === TEXT_NODE || every( node.childNodes, isInline ) );
|
nodeCategory = CONTAINER;
|
||||||
|
} else if ( inlineNodeNames.test( node.nodeName ) ) {
|
||||||
|
nodeCategory = INLINE;
|
||||||
|
} else {
|
||||||
|
nodeCategory = BLOCK;
|
||||||
|
}
|
||||||
|
if ( canWeakMap ) {
|
||||||
|
nodeCategoryCache.set( node, nodeCategory );
|
||||||
|
}
|
||||||
|
return nodeCategory;
|
||||||
|
}
|
||||||
|
function isInline ( node ) {
|
||||||
|
return getNodeCategory( node ) === INLINE;
|
||||||
}
|
}
|
||||||
function isBlock ( node ) {
|
function isBlock ( node ) {
|
||||||
var type = node.nodeType;
|
return getNodeCategory( node ) === BLOCK;
|
||||||
return ( type === ELEMENT_NODE || type === DOCUMENT_FRAGMENT_NODE ) &&
|
|
||||||
!isInline( node ) && every( node.childNodes, isInline );
|
|
||||||
}
|
}
|
||||||
function isContainer ( node ) {
|
function isContainer ( node ) {
|
||||||
var type = node.nodeType;
|
return getNodeCategory( node ) === CONTAINER;
|
||||||
return ( type === ELEMENT_NODE || type === DOCUMENT_FRAGMENT_NODE ) &&
|
|
||||||
!isInline( node ) && !isBlock( node );
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function getBlockWalker ( node, root ) {
|
function getBlockWalker ( node, root ) {
|
||||||
|
@ -374,13 +403,14 @@ function fixCursor ( node, root ) {
|
||||||
// unfocussable if they have no content. To remedy this, a <BR> must be
|
// unfocussable if they have no content. To remedy this, a <BR> must be
|
||||||
// inserted. In Opera and IE, we just need a textnode in order for the
|
// inserted. In Opera and IE, we just need a textnode in order for the
|
||||||
// cursor to appear.
|
// cursor to appear.
|
||||||
var doc = node.ownerDocument,
|
var self = root.__squire__;
|
||||||
originalNode = node,
|
var doc = node.ownerDocument;
|
||||||
fixer, child;
|
var originalNode = node;
|
||||||
|
var fixer, child;
|
||||||
|
|
||||||
if ( node === root ) {
|
if ( node === root ) {
|
||||||
if ( !( child = node.firstChild ) || child.nodeName === 'BR' ) {
|
if ( !( child = node.firstChild ) || child.nodeName === 'BR' ) {
|
||||||
fixer = getSquireInstance( doc ).createDefaultBlock();
|
fixer = self.createDefaultBlock();
|
||||||
if ( child ) {
|
if ( child ) {
|
||||||
node.replaceChild( fixer, child );
|
node.replaceChild( fixer, child );
|
||||||
}
|
}
|
||||||
|
@ -406,7 +436,7 @@ function fixCursor ( node, root ) {
|
||||||
if ( !child ) {
|
if ( !child ) {
|
||||||
if ( cantFocusEmptyTextNodes ) {
|
if ( cantFocusEmptyTextNodes ) {
|
||||||
fixer = doc.createTextNode( ZWS );
|
fixer = doc.createTextNode( ZWS );
|
||||||
getSquireInstance( doc )._didAddZWS();
|
self._didAddZWS();
|
||||||
} else {
|
} else {
|
||||||
fixer = doc.createTextNode( '' );
|
fixer = doc.createTextNode( '' );
|
||||||
}
|
}
|
||||||
|
@ -442,7 +472,7 @@ function fixCursor ( node, root ) {
|
||||||
try {
|
try {
|
||||||
node.appendChild( fixer );
|
node.appendChild( fixer );
|
||||||
} catch ( error ) {
|
} catch ( error ) {
|
||||||
getSquireInstance( doc ).didError({
|
self.didError({
|
||||||
name: 'Squire: fixCursor – ' + error,
|
name: 'Squire: fixCursor – ' + error,
|
||||||
message: 'Parent: ' + node.nodeName + '/' + node.innerHTML +
|
message: 'Parent: ' + node.nodeName + '/' + node.innerHTML +
|
||||||
' appendChild: ' + fixer.nodeName
|
' appendChild: ' + fixer.nodeName
|
||||||
|
@ -455,11 +485,11 @@ function fixCursor ( node, root ) {
|
||||||
|
|
||||||
// Recursively examine container nodes and wrap any inline children.
|
// Recursively examine container nodes and wrap any inline children.
|
||||||
function fixContainer ( container, root ) {
|
function fixContainer ( container, root ) {
|
||||||
var children = container.childNodes,
|
var children = container.childNodes;
|
||||||
doc = container.ownerDocument,
|
var doc = container.ownerDocument;
|
||||||
wrapper = null,
|
var wrapper = null;
|
||||||
i, l, child, isBR,
|
var i, l, child, isBR;
|
||||||
config = getSquireInstance( doc )._config;
|
var config = root.__squire__._config;
|
||||||
|
|
||||||
for ( i = 0, l = children.length; i < l; i += 1 ) {
|
for ( i = 0, l = children.length; i < l; i += 1 ) {
|
||||||
child = children[i];
|
child = children[i];
|
||||||
|
@ -867,7 +897,7 @@ var deleteContentsOfRange = function ( range, root ) {
|
||||||
fixCursor( root, root );
|
fixCursor( root, root );
|
||||||
range.selectNodeContents( root.firstChild );
|
range.selectNodeContents( root.firstChild );
|
||||||
} else {
|
} else {
|
||||||
range.collapse( false );
|
range.collapse( range.endContainer === root ? true : false );
|
||||||
}
|
}
|
||||||
return frag;
|
return frag;
|
||||||
};
|
};
|
||||||
|
@ -1865,7 +1895,7 @@ var stylesRewriters = {
|
||||||
newTreeBottom, newTreeTop;
|
newTreeBottom, newTreeTop;
|
||||||
if ( face ) {
|
if ( face ) {
|
||||||
fontSpan = createElement( doc, 'SPAN', {
|
fontSpan = createElement( doc, 'SPAN', {
|
||||||
'class': 'font',
|
'class': FONT_FAMILY_CLASS,
|
||||||
style: 'font-family:' + face
|
style: 'font-family:' + face
|
||||||
});
|
});
|
||||||
newTreeTop = fontSpan;
|
newTreeTop = fontSpan;
|
||||||
|
@ -1873,7 +1903,7 @@ var stylesRewriters = {
|
||||||
}
|
}
|
||||||
if ( size ) {
|
if ( size ) {
|
||||||
sizeSpan = createElement( doc, 'SPAN', {
|
sizeSpan = createElement( doc, 'SPAN', {
|
||||||
'class': 'size',
|
'class': FONT_SIZE_CLASS,
|
||||||
style: 'font-size:' + fontSizes[ size ] + 'px'
|
style: 'font-size:' + fontSizes[ size ] + 'px'
|
||||||
});
|
});
|
||||||
if ( !newTreeTop ) {
|
if ( !newTreeTop ) {
|
||||||
|
@ -1889,7 +1919,7 @@ var stylesRewriters = {
|
||||||
colour = '#' + colour;
|
colour = '#' + colour;
|
||||||
}
|
}
|
||||||
colourSpan = createElement( doc, 'SPAN', {
|
colourSpan = createElement( doc, 'SPAN', {
|
||||||
'class': 'colour',
|
'class': COLOUR_CLASS,
|
||||||
style: 'color:' + colour
|
style: 'color:' + colour
|
||||||
});
|
});
|
||||||
if ( !newTreeTop ) {
|
if ( !newTreeTop ) {
|
||||||
|
@ -1909,7 +1939,7 @@ var stylesRewriters = {
|
||||||
},
|
},
|
||||||
TT: function ( node, parent ) {
|
TT: function ( node, parent ) {
|
||||||
var el = createElement( node.ownerDocument, 'SPAN', {
|
var el = createElement( node.ownerDocument, 'SPAN', {
|
||||||
'class': 'font',
|
'class': FONT_FAMILY_CLASS,
|
||||||
style: 'font-family:menlo,consolas,"courier new",monospace'
|
style: 'font-family:menlo,consolas,"courier new",monospace'
|
||||||
});
|
});
|
||||||
parent.replaceChild( el, node );
|
parent.replaceChild( el, node );
|
||||||
|
@ -2155,7 +2185,7 @@ var onCopy = function ( event ) {
|
||||||
range = range.cloneRange();
|
range = range.cloneRange();
|
||||||
startBlock = getStartBlockOfRange( range, root );
|
startBlock = getStartBlockOfRange( range, root );
|
||||||
endBlock = getEndBlockOfRange( range, root );
|
endBlock = getEndBlockOfRange( range, root );
|
||||||
copyRoot = ( startBlock === endBlock ) ? startBlock : root;
|
copyRoot = ( ( startBlock === endBlock ) && startBlock ) || root;
|
||||||
moveRangeBoundariesDownTree( range );
|
moveRangeBoundariesDownTree( range );
|
||||||
moveRangeBoundariesUpTree( range, copyRoot );
|
moveRangeBoundariesUpTree( range, copyRoot );
|
||||||
contents = range.cloneContents();
|
contents = range.cloneContents();
|
||||||
|
@ -2234,7 +2264,7 @@ var onPaste = function ( event ) {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
} else if ( plainItem ) {
|
} else if ( plainItem ) {
|
||||||
item.getAsString( function ( text ) {
|
plainItem.getAsString( function ( text ) {
|
||||||
self.insertPlainText( text, true );
|
self.insertPlainText( text, true );
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -2364,20 +2394,6 @@ var onDrop = function ( event ) {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
var instances = [];
|
|
||||||
|
|
||||||
function getSquireInstance ( doc ) {
|
|
||||||
var l = instances.length,
|
|
||||||
instance;
|
|
||||||
while ( l-- ) {
|
|
||||||
instance = instances[l];
|
|
||||||
if ( instance._doc === doc ) {
|
|
||||||
return instance;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
function mergeObjects ( base, extras, mayOverride ) {
|
function mergeObjects ( base, extras, mayOverride ) {
|
||||||
var prop, value;
|
var prop, value;
|
||||||
if ( !base ) {
|
if ( !base ) {
|
||||||
|
@ -2518,7 +2534,7 @@ function Squire ( root, config ) {
|
||||||
doc.execCommand( 'enableInlineTableEditing', false, 'false' );
|
doc.execCommand( 'enableInlineTableEditing', false, 'false' );
|
||||||
} catch ( error ) {}
|
} catch ( error ) {}
|
||||||
|
|
||||||
instances.push( this );
|
root.__squire__ = this;
|
||||||
|
|
||||||
// Need to register instance before calling setHTML, so that the fixCursor
|
// Need to register instance before calling setHTML, so that the fixCursor
|
||||||
// function can lookup any default block tag options set.
|
// function can lookup any default block tag options set.
|
||||||
|
@ -2527,6 +2543,15 @@ function Squire ( root, config ) {
|
||||||
|
|
||||||
var proto = Squire.prototype;
|
var proto = Squire.prototype;
|
||||||
|
|
||||||
|
var sanitizeToDOMFragment = function ( html/*, isPaste*/ ) {
|
||||||
|
var frag = DOMPurify.sanitize( html, {
|
||||||
|
WHOLE_DOCUMENT: false,
|
||||||
|
RETURN_DOM: true,
|
||||||
|
RETURN_DOM_FRAGMENT: true
|
||||||
|
});
|
||||||
|
return doc.importNode( frag, true );
|
||||||
|
};
|
||||||
|
|
||||||
proto.setConfig = function ( config ) {
|
proto.setConfig = function ( config ) {
|
||||||
config = mergeObjects({
|
config = mergeObjects({
|
||||||
blockTag: 'DIV',
|
blockTag: 'DIV',
|
||||||
|
@ -2542,7 +2567,13 @@ proto.setConfig = function ( config ) {
|
||||||
undo: {
|
undo: {
|
||||||
documentSizeThreshold: -1, // -1 means no threshold
|
documentSizeThreshold: -1, // -1 means no threshold
|
||||||
undoLimit: -1 // -1 means no limit
|
undoLimit: -1 // -1 means no limit
|
||||||
}
|
},
|
||||||
|
isInsertedHTMLSanitized: true,
|
||||||
|
isSetHTMLSanitized: true,
|
||||||
|
sanitizeToDOMFragment:
|
||||||
|
typeof DOMPurify !== 'undefined' && DOMPurify.isSupported ?
|
||||||
|
sanitizeToDOMFragment : null
|
||||||
|
|
||||||
}, config, true );
|
}, config, true );
|
||||||
|
|
||||||
// Users may specify block tag in lower case
|
// Users may specify block tag in lower case
|
||||||
|
@ -2592,6 +2623,7 @@ proto.modifyDocument = function ( modificationCallback ) {
|
||||||
characterData: true,
|
characterData: true,
|
||||||
subtree: true
|
subtree: true
|
||||||
});
|
});
|
||||||
|
this._ignoreChange = false;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -2653,7 +2685,6 @@ proto.fireEvent = function ( type, event ) {
|
||||||
};
|
};
|
||||||
|
|
||||||
proto.destroy = function () {
|
proto.destroy = function () {
|
||||||
var l = instances.length;
|
|
||||||
var events = this._events;
|
var events = this._events;
|
||||||
var type;
|
var type;
|
||||||
|
|
||||||
|
@ -2663,11 +2694,7 @@ proto.destroy = function () {
|
||||||
if ( this._mutation ) {
|
if ( this._mutation ) {
|
||||||
this._mutation.disconnect();
|
this._mutation.disconnect();
|
||||||
}
|
}
|
||||||
while ( l-- ) {
|
delete this._root.__squire__;
|
||||||
if ( instances[l] === this ) {
|
|
||||||
instances.splice( l, 1 );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Destroy undo stack
|
// Destroy undo stack
|
||||||
this._undoIndex = -1;
|
this._undoIndex = -1;
|
||||||
|
@ -3109,6 +3136,9 @@ proto._keyUpDetectChange = function ( event ) {
|
||||||
};
|
};
|
||||||
|
|
||||||
proto._docWasChanged = function () {
|
proto._docWasChanged = function () {
|
||||||
|
if ( canWeakMap ) {
|
||||||
|
nodeCategoryCache = new WeakMap();
|
||||||
|
}
|
||||||
if ( this._ignoreAllChanges ) {
|
if ( this._ignoreAllChanges ) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -3934,14 +3964,21 @@ proto.getHTML = function ( withBookMark ) {
|
||||||
};
|
};
|
||||||
|
|
||||||
proto.setHTML = function ( html ) {
|
proto.setHTML = function ( html ) {
|
||||||
var frag = this._doc.createDocumentFragment();
|
var config = this._config;
|
||||||
var div = this.createElement( 'DIV' );
|
var sanitizeToDOMFragment = config.isSetHTMLSanitized ?
|
||||||
|
config.sanitizeToDOMFragment : null;
|
||||||
var root = this._root;
|
var root = this._root;
|
||||||
var child;
|
var div, frag, child;
|
||||||
|
|
||||||
// Parse HTML into DOM tree
|
// Parse HTML into DOM tree
|
||||||
|
if ( typeof sanitizeToDOMFragment === 'function' ) {
|
||||||
|
frag = sanitizeToDOMFragment( html, false );
|
||||||
|
} else {
|
||||||
|
div = this.createElement( 'DIV' );
|
||||||
div.innerHTML = html;
|
div.innerHTML = html;
|
||||||
|
frag = this._doc.createDocumentFragment();
|
||||||
frag.appendChild( empty( div ) );
|
frag.appendChild( empty( div ) );
|
||||||
|
}
|
||||||
|
|
||||||
cleanTree( frag );
|
cleanTree( frag );
|
||||||
cleanupBRs( frag, root );
|
cleanupBRs( frag, root );
|
||||||
|
@ -4076,6 +4113,9 @@ var addLinks = function ( frag, root, self ) {
|
||||||
// insertTreeFragmentIntoRange will delete the selection so that it is replaced
|
// insertTreeFragmentIntoRange will delete the selection so that it is replaced
|
||||||
// by the html being inserted.
|
// by the html being inserted.
|
||||||
proto.insertHTML = function ( html, isPaste ) {
|
proto.insertHTML = function ( html, isPaste ) {
|
||||||
|
var config = this._config;
|
||||||
|
var sanitizeToDOMFragment = config.isInsertedHTMLSanitized ?
|
||||||
|
config.sanitizeToDOMFragment : null;
|
||||||
var range = this.getSelection();
|
var range = this.getSelection();
|
||||||
var doc = this._doc;
|
var doc = this._doc;
|
||||||
var startFragmentIndex, endFragmentIndex;
|
var startFragmentIndex, endFragmentIndex;
|
||||||
|
@ -4084,13 +4124,8 @@ proto.insertHTML = function ( html, isPaste ) {
|
||||||
// Edge doesn't just copy the fragment, but includes the surrounding guff
|
// Edge doesn't just copy the fragment, but includes the surrounding guff
|
||||||
// including the full <head> of the page. Need to strip this out. If
|
// including the full <head> of the page. Need to strip this out. If
|
||||||
// available use DOMPurify to parse and sanitise.
|
// available use DOMPurify to parse and sanitise.
|
||||||
if ( typeof DOMPurify !== 'undefined' && DOMPurify.isSupported ) {
|
if ( typeof sanitizeToDOMFragment === 'function' ) {
|
||||||
frag = DOMPurify.sanitize( html, {
|
frag = sanitizeToDOMFragment( html, isPaste );
|
||||||
WHOLE_DOCUMENT: false,
|
|
||||||
RETURN_DOM: true,
|
|
||||||
RETURN_DOM_FRAGMENT: true
|
|
||||||
});
|
|
||||||
frag = doc.importNode( frag, true );
|
|
||||||
} else {
|
} else {
|
||||||
if ( isPaste ) {
|
if ( isPaste ) {
|
||||||
startFragmentIndex = html.indexOf( '<!--StartFragment-->' );
|
startFragmentIndex = html.indexOf( '<!--StartFragment-->' );
|
||||||
|
@ -4122,12 +4157,12 @@ proto.insertHTML = function ( html, isPaste ) {
|
||||||
|
|
||||||
addLinks( frag, frag, this );
|
addLinks( frag, frag, this );
|
||||||
cleanTree( frag );
|
cleanTree( frag );
|
||||||
cleanupBRs( frag, null );
|
cleanupBRs( frag, root );
|
||||||
removeEmptyInlines( frag );
|
removeEmptyInlines( frag );
|
||||||
frag.normalize();
|
frag.normalize();
|
||||||
|
|
||||||
while ( node = getNextBlock( node, frag ) ) {
|
while ( node = getNextBlock( node, frag ) ) {
|
||||||
fixCursor( node, null );
|
fixCursor( node, root );
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( isPaste ) {
|
if ( isPaste ) {
|
||||||
|
@ -4264,12 +4299,12 @@ proto.setFontFace = function ( name ) {
|
||||||
this.changeFormat( name ? {
|
this.changeFormat( name ? {
|
||||||
tag: 'SPAN',
|
tag: 'SPAN',
|
||||||
attributes: {
|
attributes: {
|
||||||
'class': 'font',
|
'class': FONT_FAMILY_CLASS,
|
||||||
style: 'font-family: ' + name + ', sans-serif;'
|
style: 'font-family: ' + name + ', sans-serif;'
|
||||||
}
|
}
|
||||||
} : null, {
|
} : null, {
|
||||||
tag: 'SPAN',
|
tag: 'SPAN',
|
||||||
attributes: { 'class': 'font' }
|
attributes: { 'class': FONT_FAMILY_CLASS }
|
||||||
});
|
});
|
||||||
return this.focus();
|
return this.focus();
|
||||||
};
|
};
|
||||||
|
@ -4277,13 +4312,13 @@ proto.setFontSize = function ( size ) {
|
||||||
this.changeFormat( size ? {
|
this.changeFormat( size ? {
|
||||||
tag: 'SPAN',
|
tag: 'SPAN',
|
||||||
attributes: {
|
attributes: {
|
||||||
'class': 'size',
|
'class': FONT_SIZE_CLASS,
|
||||||
style: 'font-size: ' +
|
style: 'font-size: ' +
|
||||||
( typeof size === 'number' ? size + 'px' : size )
|
( typeof size === 'number' ? size + 'px' : size )
|
||||||
}
|
}
|
||||||
} : null, {
|
} : null, {
|
||||||
tag: 'SPAN',
|
tag: 'SPAN',
|
||||||
attributes: { 'class': 'size' }
|
attributes: { 'class': FONT_SIZE_CLASS }
|
||||||
});
|
});
|
||||||
return this.focus();
|
return this.focus();
|
||||||
};
|
};
|
||||||
|
@ -4292,12 +4327,12 @@ proto.setTextColour = function ( colour ) {
|
||||||
this.changeFormat( colour ? {
|
this.changeFormat( colour ? {
|
||||||
tag: 'SPAN',
|
tag: 'SPAN',
|
||||||
attributes: {
|
attributes: {
|
||||||
'class': 'colour',
|
'class': COLOUR_CLASS,
|
||||||
style: 'color:' + colour
|
style: 'color:' + colour
|
||||||
}
|
}
|
||||||
} : null, {
|
} : null, {
|
||||||
tag: 'SPAN',
|
tag: 'SPAN',
|
||||||
attributes: { 'class': 'colour' }
|
attributes: { 'class': COLOUR_CLASS }
|
||||||
});
|
});
|
||||||
return this.focus();
|
return this.focus();
|
||||||
};
|
};
|
||||||
|
@ -4306,33 +4341,42 @@ proto.setHighlightColour = function ( colour ) {
|
||||||
this.changeFormat( colour ? {
|
this.changeFormat( colour ? {
|
||||||
tag: 'SPAN',
|
tag: 'SPAN',
|
||||||
attributes: {
|
attributes: {
|
||||||
'class': 'highlight',
|
'class': HIGHLIGHT_CLASS,
|
||||||
style: 'background-color:' + colour
|
style: 'background-color:' + colour
|
||||||
}
|
}
|
||||||
} : colour, {
|
} : colour, {
|
||||||
tag: 'SPAN',
|
tag: 'SPAN',
|
||||||
attributes: { 'class': 'highlight' }
|
attributes: { 'class': HIGHLIGHT_CLASS }
|
||||||
});
|
});
|
||||||
return this.focus();
|
return this.focus();
|
||||||
};
|
};
|
||||||
|
|
||||||
proto.setTextAlignment = function ( alignment ) {
|
proto.setTextAlignment = function ( alignment ) {
|
||||||
this.forEachBlock( function ( block ) {
|
this.forEachBlock( function ( block ) {
|
||||||
block.className = ( block.className
|
var className = block.className
|
||||||
.split( /\s+/ )
|
.split( /\s+/ )
|
||||||
.filter( function ( klass ) {
|
.filter( function ( klass ) {
|
||||||
return !( /align/.test( klass ) );
|
return !!klass && !/^align/.test( klass );
|
||||||
})
|
})
|
||||||
.join( ' ' ) +
|
.join( ' ' );
|
||||||
' align-' + alignment ).trim();
|
if ( alignment ) {
|
||||||
|
block.className = className + ' align-' + alignment;
|
||||||
block.style.textAlign = alignment;
|
block.style.textAlign = alignment;
|
||||||
|
} else {
|
||||||
|
block.className = className;
|
||||||
|
block.style.textAlign = '';
|
||||||
|
}
|
||||||
}, true );
|
}, true );
|
||||||
return this.focus();
|
return this.focus();
|
||||||
};
|
};
|
||||||
|
|
||||||
proto.setTextDirection = function ( direction ) {
|
proto.setTextDirection = function ( direction ) {
|
||||||
this.forEachBlock( function ( block ) {
|
this.forEachBlock( function ( block ) {
|
||||||
|
if ( direction ) {
|
||||||
block.dir = direction;
|
block.dir = direction;
|
||||||
|
} else {
|
||||||
|
block.removeAttribute( 'dir' );
|
||||||
|
}
|
||||||
}, true );
|
}, true );
|
||||||
return this.focus();
|
return this.focus();
|
||||||
};
|
};
|
||||||
|
@ -4446,6 +4490,21 @@ proto.removeList = command( 'modifyBlocks', removeList );
|
||||||
proto.increaseListLevel = command( 'modifyBlocks', increaseListLevel );
|
proto.increaseListLevel = command( 'modifyBlocks', increaseListLevel );
|
||||||
proto.decreaseListLevel = command( 'modifyBlocks', decreaseListLevel );
|
proto.decreaseListLevel = command( 'modifyBlocks', decreaseListLevel );
|
||||||
|
|
||||||
|
// Node.js exports
|
||||||
|
Squire.isInline = isInline;
|
||||||
|
Squire.isBlock = isBlock;
|
||||||
|
Squire.isContainer = isContainer;
|
||||||
|
Squire.getBlockWalker = getBlockWalker;
|
||||||
|
Squire.getPreviousBlock = getPreviousBlock;
|
||||||
|
Squire.getNextBlock = getNextBlock;
|
||||||
|
Squire.areAlike = areAlike;
|
||||||
|
Squire.hasTagAttributes = hasTagAttributes;
|
||||||
|
Squire.getNearest = getNearest;
|
||||||
|
Squire.isOrContains = isOrContains;
|
||||||
|
Squire.detach = detach;
|
||||||
|
Squire.replaceWith = replaceWith;
|
||||||
|
Squire.empty = empty;
|
||||||
|
|
||||||
// Range.js exports
|
// Range.js exports
|
||||||
Squire.getNodeBefore = getNodeBefore;
|
Squire.getNodeBefore = getNodeBefore;
|
||||||
Squire.getNodeAfter = getNodeAfter;
|
Squire.getNodeAfter = getNodeAfter;
|
||||||
|
|
File diff suppressed because one or more lines are too long
Loading…
Reference in a new issue