0
Fork 0
mirror of https://github.com/fastmail/Squire.git synced 2025-01-03 13:16:31 -05:00

Fix range construction in addFormat method.

This commit is contained in:
Neil Jenkins 2014-10-02 16:00:35 +07:00
parent 6080cbf819
commit a408fcaca6
3 changed files with 64 additions and 56 deletions

View file

@ -1745,7 +1745,7 @@ proto._addFormat = function ( tag, attributes, range ) {
// If the range is collapsed we simply insert the node by wrapping // If the range is collapsed we simply insert the node by wrapping
// it round the range and focus it. // it round the range and focus it.
var el, walker, startContainer, endContainer, startOffset, endOffset, var el, walker, startContainer, endContainer, startOffset, endOffset,
textnode, needsFormat; textNode, needsFormat;
if ( range.collapsed ) { if ( range.collapsed ) {
el = fixCursor( this.createElement( tag, attributes ) ); el = fixCursor( this.createElement( tag, attributes ) );
@ -1773,39 +1773,43 @@ proto._addFormat = function ( tag, attributes, range ) {
// Start at the beginning node of the range and iterate through // Start at the beginning node of the range and iterate through
// all the nodes in the range that need formatting. // all the nodes in the range that need formatting.
startOffset = 0; startContainer = range.startContainer;
endOffset = 0; startOffset = range.startOffset;
textnode = walker.currentNode = range.startContainer; endContainer = range.endContainer;
endOffset = range.endOffset;
if ( textnode.nodeType !== TEXT_NODE ) { // Make sure we start inside a text node.
textnode = walker.nextNode(); walker.currentNode = startContainer;
if ( startContainer.nodeType !== TEXT_NODE ) {
startContainer = walker.nextNode();
startOffset = 0;
} }
do { do {
needsFormat = !getNearest( textnode, tag, attributes ); textNode = walker.currentNode;
if ( textnode === range.endContainer ) { needsFormat = !getNearest( textNode, tag, attributes );
if ( needsFormat && textnode.length > range.endOffset ) {
textnode.splitText( range.endOffset );
} else {
endOffset = range.endOffset;
}
}
if ( textnode === range.startContainer ) {
if ( needsFormat && range.startOffset ) {
textnode = textnode.splitText( range.startOffset );
} else {
startOffset = range.startOffset;
}
}
if ( needsFormat ) { if ( needsFormat ) {
el = this.createElement( tag, attributes ); if ( textNode === endContainer &&
replaceWith( textnode, el ); textNode.length > endOffset ) {
el.appendChild( textnode ); textNode.splitText( endOffset );
endOffset = textnode.length; }
if ( textNode === startContainer && startOffset ) {
textNode = textNode.splitText( startOffset );
startContainer = textNode;
startOffset = 0;
}
el = this.createElement( tag, attributes );
replaceWith( textNode, el );
el.appendChild( textNode );
}
} while ( walker.nextNode() );
// Make sure we finish inside a text node. Otherwise offset may have
// changed.
if ( endContainer.nodeType !== TEXT_NODE ) {
endContainer = textNode;
endOffset = textNode.length;
} }
endContainer = textnode;
if ( !startContainer ) { startContainer = endContainer; }
} while ( textnode = walker.nextNode() );
// Now set the selection to as it was before // Now set the selection to as it was before
range = this._createRange( range = this._createRange(

File diff suppressed because one or more lines are too long

View file

@ -628,7 +628,7 @@ proto._addFormat = function ( tag, attributes, range ) {
// If the range is collapsed we simply insert the node by wrapping // If the range is collapsed we simply insert the node by wrapping
// it round the range and focus it. // it round the range and focus it.
var el, walker, startContainer, endContainer, startOffset, endOffset, var el, walker, startContainer, endContainer, startOffset, endOffset,
textnode, needsFormat; textNode, needsFormat;
if ( range.collapsed ) { if ( range.collapsed ) {
el = fixCursor( this.createElement( tag, attributes ) ); el = fixCursor( this.createElement( tag, attributes ) );
@ -656,39 +656,43 @@ proto._addFormat = function ( tag, attributes, range ) {
// Start at the beginning node of the range and iterate through // Start at the beginning node of the range and iterate through
// all the nodes in the range that need formatting. // all the nodes in the range that need formatting.
startOffset = 0; startContainer = range.startContainer;
endOffset = 0; startOffset = range.startOffset;
textnode = walker.currentNode = range.startContainer; endContainer = range.endContainer;
endOffset = range.endOffset;
if ( textnode.nodeType !== TEXT_NODE ) { // Make sure we start inside a text node.
textnode = walker.nextNode(); walker.currentNode = startContainer;
if ( startContainer.nodeType !== TEXT_NODE ) {
startContainer = walker.nextNode();
startOffset = 0;
} }
do { do {
needsFormat = !getNearest( textnode, tag, attributes ); textNode = walker.currentNode;
if ( textnode === range.endContainer ) { needsFormat = !getNearest( textNode, tag, attributes );
if ( needsFormat && textnode.length > range.endOffset ) {
textnode.splitText( range.endOffset );
} else {
endOffset = range.endOffset;
}
}
if ( textnode === range.startContainer ) {
if ( needsFormat && range.startOffset ) {
textnode = textnode.splitText( range.startOffset );
} else {
startOffset = range.startOffset;
}
}
if ( needsFormat ) { if ( needsFormat ) {
el = this.createElement( tag, attributes ); if ( textNode === endContainer &&
replaceWith( textnode, el ); textNode.length > endOffset ) {
el.appendChild( textnode ); textNode.splitText( endOffset );
endOffset = textnode.length; }
if ( textNode === startContainer && startOffset ) {
textNode = textNode.splitText( startOffset );
startContainer = textNode;
startOffset = 0;
}
el = this.createElement( tag, attributes );
replaceWith( textNode, el );
el.appendChild( textNode );
}
} while ( walker.nextNode() );
// Make sure we finish inside a text node. Otherwise offset may have
// changed.
if ( endContainer.nodeType !== TEXT_NODE ) {
endContainer = textNode;
endOffset = textNode.length;
} }
endContainer = textnode;
if ( !startContainer ) { startContainer = endContainer; }
} while ( textnode = walker.nextNode() );
// Now set the selection to as it was before // Now set the selection to as it was before
range = this._createRange( range = this._createRange(