      1 ﻿/*
      2 Copyright (c) 2003-2009, CKSource - Frederico Knabben. All rights reserved.
      3 For licensing, see LICENSE.html or http://ckeditor.com/license
      4 */
      5
      6 /**
      7  * @fileOverview Defines the {@link CKEDITOR.dom.text} class, which represents
      8  *		a DOM text node.
      9  */
     10
     11 /**
     12  * Represents a DOM text node.
     13  * @constructor
     14  * @augments CKEDITOR.dom.node
     15  * @param {Object|String} text A native DOM text node or a string containing
     16  *		the text to use to create a new text node.
     17  * @param {CKEDITOR.dom.document} [ownerDocument] The document that will contain
     18  *		the node in case of new node creation. Defaults to the current document.
     19  * @example
     20  * var nativeNode = document.createTextNode( 'Example' );
     21  * var text = CKEDITOR.dom.text( nativeNode );
     22  * @example
     23  * var text = CKEDITOR.dom.text( 'Example' );
     24  */
     25 CKEDITOR.dom.text = function( text, ownerDocument )
     26 {
     27 	if ( typeof text == 'string' )
     28 		text = ( ownerDocument ? ownerDocument.$ : document ).createTextNode( text );
     29
     30 	// Theoretically, we should call the base constructor here
     31 	// (not CKEDITOR.dom.node though). But, IE doesn't support expando
     32 	// properties on text node, so the features provided by domObject will not
     33 	// work for text nodes (which is not a big issue for us).
     34 	//
     35 	// CKEDITOR.dom.domObject.call( this, element );
     36
     37 	/**
     38 	 * The native DOM text node represented by this class instance.
     39 	 * @type Object
     40 	 * @example
     41 	 * var element = new CKEDITOR.dom.text( 'Example' );
     42 	 * alert( element.$.nodeType );  // "3"
     43 	 */
     44 	this.$ = text;
     45 };
     46
     47 CKEDITOR.dom.text.prototype = new CKEDITOR.dom.node();
     48
     49 CKEDITOR.tools.extend( CKEDITOR.dom.text.prototype,
     50 	/** @lends CKEDITOR.dom.text.prototype */
     51 	{
     52 		/**
     53 		 * The node type. This is a constant value set to
     54 		 * {@link CKEDITOR.NODE_TEXT}.
     55 		 * @type Number
     56 		 * @example
     57 		 */
     58 		type : CKEDITOR.NODE_TEXT,
     59
     60 		getLength : function()
     61 		{
     62 			return this.$.nodeValue.length;
     63 		},
     64
     65 		getText : function()
     66 		{
     67 			return this.$.nodeValue;
     68 		},
     69
     70 		/**
     71 		 * Breaks this text node into two nodes at the specified offset,
     72 		 * keeping both in the tree as siblings. This node then only contains
     73 		 * all the content up to the offset point. A new text node, which is
     74 		 * inserted as the next sibling of this node, contains all the content
     75 		 * at and after the offset point. When the offset is equal to the
     76 		 * length of this node, the new node has no data.
     77 		 * @param {Number} The position at which to split, starting from zero.
     78 		 * @returns {CKEDITOR.dom.text} The new text node.
     79 		 */
     80 		split : function( offset )
     81 		{
     82 			// If the offset is after the last char, IE creates the text node
     83 			// on split, but don't include it into the DOM. So, we have to do
     84 			// that manually here.
     85 			if ( CKEDITOR.env.ie && offset == this.getLength() )
     86 			{
     87 				var next = this.getDocument().createText( '' );
     88 				next.insertAfter( this );
     89 				return next;
     90 			}
     91
     92 			var doc = this.getDocument();
     93 			var retval = new CKEDITOR.dom.text( this.$.splitText( offset ), doc );
     94
     95 			// IE BUG: IE8 does not update the childNodes array in DOM after splitText(),
     96 			// we need to make some DOM changes to make it update. (#3436)
     97 			if ( CKEDITOR.env.ie8 )
     98 			{
     99 				var workaround = new CKEDITOR.dom.text( '', doc );
    100 				workaround.insertAfter( retval );
    101 				workaround.remove();
    102 			}
    103
    104 			return retval;
    105 		},
    106
    107 		/**
    108 		 * Extracts characters from indexA up to but not including indexB.
    109 		 * @param {Number} indexA An integer between 0 and one less than the
    110 		 *		length of the text.
    111 		 * @param {Number} [indexB] An integer between 0 and the length of the
    112 		 *		string. If omitted, extracts characters to the end of the text.
    113 		 */
    114 		substring : function( indexA, indexB )
    115 		{
    116 			// We need the following check due to a Firefox bug
    117 			// https://bugzilla.mozilla.org/show_bug.cgi?id=458886
    118 			if ( typeof indexB != 'number' )
    119 				return this.$.nodeValue.substr( indexA );
    120 			else
    121 				return this.$.nodeValue.substring( indexA, indexB );
    122 		}
    123 	});
    124