@@ -25,7 +25,7 @@ if(!Array.isArray) {
2525 return Object . prototype . toString . call ( arg ) === '[object Array]' ;
2626 } ;
2727} ; /**
28- * @license wysihtml5x v0.4.8
28+ * @license wysihtml5x v0.4.9
2929 * https://github.com/Edicy/wysihtml5
3030 *
3131 * Author: Christopher Blum (https://github.com/tiff)
@@ -36,7 +36,7 @@ if(!Array.isArray) {
3636 *
3737 */
3838var wysihtml5 = {
39- version : "0.4.8 " ,
39+ version : "0.4.9 " ,
4040
4141 // namespaces
4242 commands : { } ,
@@ -5813,10 +5813,15 @@ wysihtml5.dom.parse = (function() {
58135813 var context = config . context || elementOrHtml . ownerDocument || document ,
58145814 fragment = context . createDocumentFragment ( ) ,
58155815 isString = typeof ( elementOrHtml ) === "string" ,
5816+ clearInternals = false ,
58165817 element ,
58175818 newNode ,
58185819 firstChild ;
58195820
5821+ if ( config . clearInternals === true ) {
5822+ clearInternals = true ;
5823+ }
5824+
58205825 if ( config . uneditableClass ) {
58215826 uneditableClass = config . uneditableClass ;
58225827 }
@@ -5829,11 +5834,13 @@ wysihtml5.dom.parse = (function() {
58295834
58305835 while ( element . firstChild ) {
58315836 firstChild = element . firstChild ;
5832- newNode = _convert ( firstChild , config . cleanUp ) ;
5833- element . removeChild ( firstChild ) ;
5837+ newNode = _convert ( firstChild , config . cleanUp , clearInternals ) ;
58345838 if ( newNode ) {
58355839 fragment . appendChild ( newNode ) ;
58365840 }
5841+ if ( firstChild !== newNode ) {
5842+ element . removeChild ( firstChild ) ;
5843+ }
58375844 }
58385845
58395846 // Clear element contents
@@ -5845,7 +5852,7 @@ wysihtml5.dom.parse = (function() {
58455852 return isString ? wysihtml5 . quirks . getCorrectInnerHTML ( element ) : element ;
58465853 }
58475854
5848- function _convert ( oldNode , cleanUp ) {
5855+ function _convert ( oldNode , cleanUp , clearInternals ) {
58495856 var oldNodeType = oldNode . nodeType ,
58505857 oldChilds = oldNode . childNodes ,
58515858 oldChildsLength = oldChilds . length ,
@@ -5855,21 +5862,28 @@ wysihtml5.dom.parse = (function() {
58555862 newNode ,
58565863 newChild ;
58575864
5865+ // Passes directly elemets with uneditable class
58585866 if ( uneditableClass && oldNodeType === 1 && wysihtml5 . dom . hasClass ( oldNode , uneditableClass ) ) {
58595867 return oldNode ;
58605868 }
58615869
5862- newNode = method && method ( oldNode ) ;
5870+ newNode = method && method ( oldNode , clearInternals ) ;
58635871
5872+ // Remove or unwrap node in case of return value null or false
58645873 if ( ! newNode ) {
58655874 if ( newNode === false ) {
58665875 // false defines that tag should be removed but contents should remain (unwrap)
58675876 fragment = oldNode . ownerDocument . createDocumentFragment ( ) ;
58685877
58695878 for ( i = oldChildsLength ; i -- ; ) {
5870- newChild = _convert ( oldChilds [ i ] , cleanUp ) ;
5871- if ( newChild ) {
5872- fragment . insertBefore ( newChild , fragment . firstChild ) ;
5879+ if ( oldChilds [ i ] ) {
5880+ newChild = _convert ( oldChilds [ i ] , cleanUp , clearInternals ) ;
5881+ if ( newChild ) {
5882+ if ( oldChilds [ i ] === newChild ) {
5883+ i -- ;
5884+ }
5885+ fragment . insertBefore ( newChild , fragment . firstChild ) ;
5886+ }
58735887 }
58745888 }
58755889
@@ -5893,22 +5907,29 @@ wysihtml5.dom.parse = (function() {
58935907 }
58945908 return fragment ;
58955909 } else {
5896- return null ;
5910+ // Remove
5911+ return null ;
58975912 }
58985913 }
58995914
5915+ // Converts all childnodes
59005916 for ( i = 0 ; i < oldChildsLength ; i ++ ) {
5901- newChild = _convert ( oldChilds [ i ] , cleanUp ) ;
5902- if ( newChild ) {
5903- newNode . appendChild ( newChild ) ;
5917+ if ( oldChilds [ i ] ) {
5918+ newChild = _convert ( oldChilds [ i ] , cleanUp , clearInternals ) ;
5919+ if ( newChild ) {
5920+ if ( oldChilds [ i ] === newChild ) {
5921+ i -- ;
5922+ }
5923+ newNode . appendChild ( newChild ) ;
5924+ }
59045925 }
59055926 }
59065927
59075928 // Cleanup senseless <span> elements
59085929 if ( cleanUp &&
59095930 newNode . nodeName . toLowerCase ( ) === DEFAULT_NODE_NAME &&
59105931 ( ! newNode . childNodes . length ||
5911- ( ( / ^ \s * $ / gi) . test ( newNode . innerHTML ) && oldNode . className !== "_wysihtml5-temp-placeholder" && oldNode . className !== "rangySelectionBoundary" ) ||
5932+ ( ( / ^ \s * $ / gi) . test ( newNode . innerHTML ) && ( clearInternals || ( oldNode . className !== "_wysihtml5-temp-placeholder" && oldNode . className !== "rangySelectionBoundary" ) ) ) ||
59125933 ! newNode . attributes . length )
59135934 ) {
59145935 fragment = newNode . ownerDocument . createDocumentFragment ( ) ;
@@ -5927,7 +5948,7 @@ wysihtml5.dom.parse = (function() {
59275948 return newNode ;
59285949 }
59295950
5930- function _handleElement ( oldNode ) {
5951+ function _handleElement ( oldNode , clearInternals ) {
59315952 var rule ,
59325953 newNode ,
59335954 tagRules = currentRules . tags ,
@@ -5985,10 +6006,10 @@ wysihtml5.dom.parse = (function() {
59856006 }
59866007
59876008 newNode = oldNode . ownerDocument . createElement ( rule . rename_tag || nodeName ) ;
5988- _handleAttributes ( oldNode , newNode , rule ) ;
6009+ _handleAttributes ( oldNode , newNode , rule , clearInternals ) ;
59896010 _handleStyles ( oldNode , newNode , rule ) ;
59906011 // tests if type condition is met or node should be removed/unwrapped
5991- if ( rule . one_of_type && ! _testTypes ( oldNode , currentRules , rule . one_of_type ) ) {
6012+ if ( rule . one_of_type && ! _testTypes ( oldNode , currentRules , rule . one_of_type , clearInternals ) ) {
59926013 return ( rule . remove_action && rule . remove_action == "unwrap" ) ? false : null ;
59936014 }
59946015
@@ -5998,11 +6019,11 @@ wysihtml5.dom.parse = (function() {
59986019 return newNode ;
59996020 }
60006021
6001- function _testTypes ( oldNode , rules , types ) {
6022+ function _testTypes ( oldNode , rules , types , clearInternals ) {
60026023 var definition , type ;
60036024
60046025 // do not interfere with placeholder span or pasting caret position is not maintained
6005- if ( oldNode . nodeName === "SPAN" && ( oldNode . className === "_wysihtml5-temp-placeholder" || oldNode . className === "rangySelectionBoundary" ) ) {
6026+ if ( oldNode . nodeName === "SPAN" && ! clearInternals && ( oldNode . className === "_wysihtml5-temp-placeholder" || oldNode . className === "rangySelectionBoundary" ) ) {
60066027 return true ;
60076028 }
60086029
@@ -6112,7 +6133,8 @@ wysihtml5.dom.parse = (function() {
61126133 }
61136134 }
61146135
6115- function _handleAttributes ( oldNode , newNode , rule ) {
6136+ // TODO: refactor. Too long to read
6137+ function _handleAttributes ( oldNode , newNode , rule , clearInternals ) {
61166138 var attributes = { } , // fresh new set of attributes to set on newNode
61176139 setClass = rule . set_class , // classes to set
61186140 addClass = rule . add_class , // add classes based on existing attributes
@@ -6189,8 +6211,11 @@ wysihtml5.dom.parse = (function() {
61896211 attributes [ "class" ] = oldNode . getAttribute ( "class" ) ;
61906212 } else {
61916213 // make sure that wysihtml5 temp class doesn't get stripped out
6192- allowedClasses [ "_wysihtml5-temp-placeholder" ] = 1 ;
6193- allowedClasses [ "_rangySelectionBoundary" ] = 1 ;
6214+ if ( ! clearInternals ) {
6215+ allowedClasses [ "_wysihtml5-temp-placeholder" ] = 1 ;
6216+ allowedClasses [ "_rangySelectionBoundary" ] = 1 ;
6217+ allowedClasses [ "wysiwyg-tmp-selected-cell" ] = 1 ;
6218+ }
61946219
61956220 // add old classes last
61966221 oldClasses = oldNode . getAttribute ( "class" ) ;
@@ -6210,6 +6235,14 @@ wysihtml5.dom.parse = (function() {
62106235 }
62116236 }
62126237
6238+ // remove table selection class if present
6239+ if ( attributes [ "class" ] && clearInternals ) {
6240+ attributes [ "class" ] = attributes [ "class" ] . replace ( "wysiwyg-tmp-selected-cell" , "" ) ;
6241+ if ( ( / ^ \s * $ / g) . test ( attributes [ "class" ] ) ) {
6242+ delete attributes . class ;
6243+ }
6244+ }
6245+
62136246 if ( styles . length ) {
62146247 attributes [ "style" ] = wysihtml5 . lang . array ( styles ) . unique ( ) . join ( " " ) ;
62156248 }
@@ -10827,7 +10860,7 @@ wysihtml5.commands.formatCode = {
1082710860 return wysihtml5 . commands . insertList . state ( composer , command , "UL" ) ;
1082810861 }
1082910862} ;
10830- ; wysihtml5 . commands . insertList = ( function ( ) {
10863+ ; wysihtml5 . commands . insertList = ( function ( wysihtml5 ) {
1083110864
1083210865 var isNode = function ( node , name ) {
1083310866 if ( node && node . nodeName ) {
@@ -10985,7 +11018,7 @@ wysihtml5.commands.formatCode = {
1098511018 }
1098611019 } ;
1098711020
10988- } ) ( ) ; ; wysihtml5 . commands . italic = {
11021+ } ) ( wysihtml5 ) ; ; wysihtml5 . commands . italic = {
1098911022 exec : function ( composer , command ) {
1099011023 wysihtml5 . commands . formatInline . execWithToggle ( composer , command , "i" ) ;
1099111024 } ,
@@ -11451,7 +11484,7 @@ wysihtml5.commands.formatCode = {
1145111484
1145211485 transact : function ( ) {
1145311486 var previousHtml = this . historyStr [ this . position - 1 ] ,
11454- currentHtml = this . composer . getValue ( ) ;
11487+ currentHtml = this . composer . getValue ( false , false ) ;
1145511488
1145611489 if ( currentHtml === previousHtml ) {
1145711490 return ;
@@ -11654,11 +11687,10 @@ wysihtml5.views.View = Base.extend(
1165411687 this . element . innerHTML = browser . displaysCaretInEmptyContentEditableCorrectly ( ) ? "" : this . CARET_HACK ;
1165511688 } ,
1165611689
11657- getValue : function ( parse ) {
11690+ getValue : function ( parse , clearInternals ) {
1165811691 var value = this . isEmpty ( ) ? "" : wysihtml5 . quirks . getCorrectInnerHTML ( this . element ) ;
11659-
11660- if ( parse ) {
11661- value = this . parent . parse ( value ) ;
11692+ if ( parse !== false ) {
11693+ value = this . parent . parse ( value , ( clearInternals === false ) ? false : true ) ;
1166211694 }
1166311695
1166411696 return value ;
@@ -11795,7 +11827,7 @@ wysihtml5.views.View = Base.extend(
1179511827 this . element = ( this . config . contentEditableMode ) ? this . sandbox . getContentEditable ( ) : this . doc . body ;
1179611828 if ( ! this . config . noTextarea ) {
1179711829 this . textarea = this . parent . textarea ;
11798- this . element . innerHTML = this . textarea . getValue ( true ) ;
11830+ this . element . innerHTML = this . textarea . getValue ( true , false ) ;
1179911831 } else {
1180011832 this . cleanUp ( ) ; // cleans contenteditable on initiation as it may contain html
1180111833 }
@@ -12374,7 +12406,7 @@ wysihtml5.views.View = Base.extend(
1237412406
1237512407 wysihtml5 . views . Composer . prototype . observe = function ( ) {
1237612408 var that = this ,
12377- state = this . getValue ( ) ,
12409+ state = this . getValue ( false , false ) ,
1237812410 container = ( this . sandbox . getIframe ) ? this . sandbox . getIframe ( ) : this . sandbox . getContentEditable ( ) ,
1237912411 element = this . element ,
1238012412 focusBlurElement = ( browser . supportsEventsInIframeCorrectly ( ) || this . sandbox . getContentEditable ) ? element : this . sandbox . getWindow ( ) ,
@@ -12422,11 +12454,11 @@ wysihtml5.views.View = Base.extend(
1242212454
1242312455 // Delay storing of state until all focus handler are fired
1242412456 // especially the one which resets the placeholder
12425- setTimeout ( function ( ) { state = that . getValue ( ) ; } , 0 ) ;
12457+ setTimeout ( function ( ) { state = that . getValue ( false , false ) ; } , 0 ) ;
1242612458 } ) ;
1242712459
1242812460 dom . observe ( focusBlurElement , "blur" , function ( ) {
12429- if ( state !== that . getValue ( ) ) {
12461+ if ( state !== that . getValue ( false , false ) ) {
1243012462 that . parent . fire ( "change" ) . fire ( "change:composer" ) ;
1243112463 }
1243212464 that . parent . fire ( "blur" ) . fire ( "blur:composer" ) ;
@@ -12603,7 +12635,7 @@ wysihtml5.views.View = Base.extend(
1260312635 * @param {Boolean } shouldParseHtml Whether the html should be sanitized before inserting it into the textarea
1260412636 */
1260512637 fromComposerToTextarea : function ( shouldParseHtml ) {
12606- this . textarea . setValue ( wysihtml5 . lang . string ( this . composer . getValue ( ) ) . trim ( ) , shouldParseHtml ) ;
12638+ this . textarea . setValue ( wysihtml5 . lang . string ( this . composer . getValue ( false , false ) ) . trim ( ) , shouldParseHtml ) ;
1260712639 } ,
1260812640
1260912641 /**
@@ -12612,7 +12644,7 @@ wysihtml5.views.View = Base.extend(
1261212644 * @param {Boolean } shouldParseHtml Whether the html should be sanitized before inserting it into the composer
1261312645 */
1261412646 fromTextareaToComposer : function ( shouldParseHtml ) {
12615- var textareaValue = this . textarea . getValue ( ) ;
12647+ var textareaValue = this . textarea . getValue ( false , false ) ;
1261612648 if ( textareaValue ) {
1261712649 this . composer . setValue ( textareaValue , shouldParseHtml ) ;
1261812650 } else {
@@ -12693,7 +12725,7 @@ wysihtml5.views.View = Base.extend(
1269312725
1269412726 getValue : function ( parse ) {
1269512727 var value = this . isEmpty ( ) ? "" : this . element . value ;
12696- if ( parse ) {
12728+ if ( parse !== false ) {
1269712729 value = this . parent . parse ( value ) ;
1269812730 }
1269912731 return value ;
@@ -12878,8 +12910,8 @@ wysihtml5.views.View = Base.extend(
1287812910 return this ;
1287912911 } ,
1288012912
12881- getValue : function ( parse ) {
12882- return this . currentView . getValue ( parse ) ;
12913+ getValue : function ( parse , clearInternals ) {
12914+ return this . currentView . getValue ( parse , clearInternals ) ;
1288312915 } ,
1288412916
1288512917 setValue : function ( html , parse ) {
@@ -12926,13 +12958,14 @@ wysihtml5.views.View = Base.extend(
1292612958 return this . currentView . hasPlaceholderSet ( ) ;
1292712959 } ,
1292812960
12929- parse : function ( htmlOrElement ) {
12930- var parseContext = ( this . config . contentEditableMode ) ? document : this . composer . sandbox . getDocument ( ) ;
12961+ parse : function ( htmlOrElement , clearInternals ) {
12962+ var parseContext = ( this . config . contentEditableMode ) ? document : ( ( this . composer ) ? this . composer . sandbox . getDocument ( ) : null ) ;
1293112963 var returnValue = this . config . parser ( htmlOrElement , {
1293212964 "rules" : this . config . parserRules ,
1293312965 "cleanUp" : this . config . cleanUp ,
1293412966 "context" : parseContext ,
12935- "uneditableClass" : this . config . uneditableContainerClassname
12967+ "uneditableClass" : this . config . uneditableContainerClassname ,
12968+ "clearInternals" : clearInternals
1293612969 } ) ;
1293712970 if ( typeof ( htmlOrElement ) === "object" ) {
1293812971 wysihtml5 . quirks . redraw ( htmlOrElement ) ;
0 commit comments