whole_func_string: function getRange() {
  			var ieRange = selection.getRng(), domRange = dom.createRng(), element, collapsed, tmpRange, element2, bookmark, fail;
  
  			// If selection is outside the current document just return an empty range
  			element = ieRange.item ? ieRange.item(0) : ieRange.parentElement();
  			if (element.ownerDocument != dom.doc)
  				return domRange;
  
  			collapsed = selection.isCollapsed();
  
  			// Handle control selection
  			if (ieRange.item) {
  				domRange.setStart(element.parentNode, dom.nodeIndex(element));
  				domRange.setEnd(domRange.startContainer, domRange.startOffset + 1);
  
  				return domRange;
  			}
  
  			function findEndPoint(start) {
  				var endPoint = getPosition(ieRange, start), container, offset, textNodeOffset = 0, sibling, undef, nodeValue;
  
  				container = endPoint.node;
  				offset = endPoint.offset;
  
  				if (endPoint.inside && !container.hasChildNodes()) {
  					domRange[start ? 'setStart' : 'setEnd'](container, 0);
  					return;
  				}
  
  				if (offset === undef) {
  					domRange[start ? 'setStartBefore' : 'setEndAfter'](container);
  					return;
  				}
  
  				if (endPoint.position < 0) {
  					sibling = endPoint.inside ? container.firstChild : container.nextSibling;
  
  					if (!sibling) {
  						domRange[start ? 'setStartAfter' : 'setEndAfter'](container);
  						return;
  					}
  
  					if (!offset) {
  						if (sibling.nodeType == 3)
  							domRange[start ? 'setStart' : 'setEnd'](sibling, 0);
  						else
  							domRange[start ? 'setStartBefore' : 'setEndBefore'](sibling);
  
  						return;
  					}
  
  					// Find the text node and offset
  					while (sibling) {
  						nodeValue = sibling.nodeValue;
  						textNodeOffset += nodeValue.length;
  
  						// We are at or passed the position we where looking for
  						if (textNodeOffset >= offset) {
  							container = sibling;
  							textNodeOffset -= offset;
  							textNodeOffset = nodeValue.length - textNodeOffset;
  							break;
  						}
  
  						sibling = sibling.nextSibling;
  					}
  				} else {
  					// Find the text node and offset
  					sibling = container.previousSibling;
  
  					if (!sibling)
  						return domRange[start ? 'setStartBefore' : 'setEndBefore'](container);
  
  					// If there isn't any text to loop then use the first position
  					if (!offset) {
  						if (container.nodeType == 3)
  							domRange[start ? 'setStart' : 'setEnd'](sibling, container.nodeValue.length);
  						else
  							domRange[start ? 'setStartAfter' : 'setEndAfter'](sibling);
  
  						return;
  					}
  
  					while (sibling) {
  						textNodeOffset += sibling.nodeValue.length;
  
  						// We are at or passed the position we where looking for
  						if (textNodeOffset >= offset) {
  							container = sibling;
  							textNodeOffset -= offset;
  							break;
  						}
  
  						sibling = sibling.previousSibling;
  					}
  				}
  
  				domRange[start ? 'setStart' : 'setEnd'](container, textNodeOffset);
  			};
  
  			try {
  				// Find start point
  				findEndPoint(true);
  
  				// Find end point if needed
  				if (!collapsed)
  					findEndPoint();
  			} catch (ex) {
  				// IE has a nasty bug where text nodes might throw "invalid argument" when you
  				// access the nodeValue or other properties of text nodes. This seems to happend when
  				// text nodes are split into two nodes by a delete/backspace call. So lets detect it and try to fix it.
  				if (ex.number == -2147024809) {
  					// Get the current selection
  					bookmark = self.getBookmark(2);
  
  					// Get start element
  					tmpRange = ieRange.duplicate();
  					tmpRange.collapse(true);
  					element = tmpRange.parentElement();
  
  					// Get end element
  					if (!collapsed) {
  						tmpRange = ieRange.duplicate();
  						tmpRange.collapse(false);
  						element2 = tmpRange.parentElement();
  						element2.innerHTML = element2.innerHTML;
  					}
  
  					// Remove the broken elements
  					element.innerHTML = element.innerHTML;
  
  					// Restore the selection
  					self.moveToBookmark(bookmark);
  
  					// Since the range has moved we need to re-get it
  					ieRange = selection.getRng();
  
  					// Find start point
  					findEndPoint(true);
  
  					// Find end point if needed
  					if (!collapsed)
  						findEndPoint();
  				} else
  					throw ex; // Throw other errors
  			}
  
  			return domRange;
  		}
func_code_string: function getRange() {
  			var ieRange = selection.getRng(), domRange = dom.createRng(), element, collapsed, tmpRange, element2, bookmark, fail;
  
  			// If selection is outside the current document just return an empty range
  			element = ieRange.item ? ieRange.item(0) : ieRange.parentElement();
  			if (element.ownerDocument != dom.doc)
  				return domRange;
  
  			collapsed = selection.isCollapsed();
  
  			// Handle control selection
  			if (ieRange.item) {
  				domRange.setStart(element.parentNode, dom.nodeIndex(element));
  				domRange.setEnd(domRange.startContainer, domRange.startOffset + 1);
  
  				return domRange;
  			}
  
  			function findEndPoint(start) {
  				var endPoint = getPosition(ieRange, start), container, offset, textNodeOffset = 0, sibling, undef, nodeValue;
  
  				container = endPoint.node;
  				offset = endPoint.offset;
  
  				if (endPoint.inside && !container.hasChildNodes()) {
  					domRange[start ? 'setStart' : 'setEnd'](container, 0);
  					return;
  				}
  
  				if (offset === undef) {
  					domRange[start ? 'setStartBefore' : 'setEndAfter'](container);
  					return;
  				}
  
  				if (endPoint.position < 0) {
  					sibling = endPoint.inside ? container.firstChild : container.nextSibling;
  
  					if (!sibling) {
  						domRange[start ? 'setStartAfter' : 'setEndAfter'](container);
  						return;
  					}
  
  					if (!offset) {
  						if (sibling.nodeType == 3)
  							domRange[start ? 'setStart' : 'setEnd'](sibling, 0);
  						else
  							domRange[start ? 'setStartBefore' : 'setEndBefore'](sibling);
  
  						return;
  					}
  
  					// Find the text node and offset
  					while (sibling) {
  						nodeValue = sibling.nodeValue;
  						textNodeOffset += nodeValue.length;
  
  						// We are at or passed the position we where looking for
  						if (textNodeOffset >= offset) {
  							container = sibling;
  							textNodeOffset -= offset;
  							textNodeOffset = nodeValue.length - textNodeOffset;
  							break;
  						}
  
  						sibling = sibling.nextSibling;
  					}
  				} else {
  					// Find the text node and offset
  					sibling = container.previousSibling;
  
  					if (!sibling)
  						return domRange[start ? 'setStartBefore' : 'setEndBefore'](container);
  
  					// If there isn't any text to loop then use the first position
  					if (!offset) {
  						if (container.nodeType == 3)
  							domRange[start ? 'setStart' : 'setEnd'](sibling, container.nodeValue.length);
  						else
  							domRange[start ? 'setStartAfter' : 'setEndAfter'](sibling);
  
  						return;
  					}
  
  					while (sibling) {
  						textNodeOffset += sibling.nodeValue.length;
  
  						// We are at or passed the position we where looking for
  						if (textNodeOffset >= offset) {
  							container = sibling;
  							textNodeOffset -= offset;
  							break;
  						}
  
  						sibling = sibling.previousSibling;
  					}
  				}
  
  				domRange[start ? 'setStart' : 'setEnd'](container, textNodeOffset);
  			};
  
  			try {
  				// Find start point
  				findEndPoint(true);
  
  				// Find end point if needed
  				if (!collapsed)
  					findEndPoint();
  			} catch (ex) {
  				// IE has a nasty bug where text nodes might throw "invalid argument" when you
  				// access the nodeValue or other properties of text nodes. This seems to happend when
  				// text nodes are split into two nodes by a delete/backspace call. So lets detect it and try to fix it.
  				if (ex.number == -2147024809) {
  					// Get the current selection
  					bookmark = self.getBookmark(2);
  
  					// Get start element
  					tmpRange = ieRange.duplicate();
  					tmpRange.collapse(true);
  					element = tmpRange.parentElement();
  
  					// Get end element
  					if (!collapsed) {
  						tmpRange = ieRange.duplicate();
  						tmpRange.collapse(false);
  						element2 = tmpRange.parentElement();
  						element2.innerHTML = element2.innerHTML;
  					}
  
  					// Remove the broken elements
  					element.innerHTML = element.innerHTML;
  
  					// Restore the selection
  					self.moveToBookmark(bookmark);
  
  					// Since the range has moved we need to re-get it
  					ieRange = selection.getRng();
  
  					// Find start point
  					findEndPoint(true);
  
  					// Find end point if needed
  					if (!collapsed)
  						findEndPoint();
  				} else
  					throw ex; // Throw other errors
  			}
  
  			return domRange;
  		}
func_documentation_string: Returns a W3C DOM compatible range object by using the IE Range API