Actualizado 5 de septiembre de 2010
Como parece que todos se dirigen aquí para este problema, estoy agregando mi respuesta a una pregunta similar, que contiene el mismo código que esta respuesta pero con antecedentes completos para aquellos que estén interesados:
El documento document.selection.createRange de IE no incluye líneas en blanco iniciales o finales
Tener en cuenta los saltos de línea finales es complicado en IE, y no he visto ninguna solución que lo haga correctamente, incluidas otras respuestas a esta pregunta. Sin embargo, es posible usar la siguiente función, que le devolverá el inicio y el final de la selección (que son los mismos en el caso de un cursor) dentro de un <textarea>
texto <input>
.
Tenga en cuenta que el área de texto debe tener foco para que esta función funcione correctamente en IE. En caso de duda, llame focus()
primero al método del área de texto.
function getInputSelection(el) {
var start = 0, end = 0, normalizedValue, range,
textInputRange, len, endRange;
if (typeof el.selectionStart == "number" && typeof el.selectionEnd == "number") {
start = el.selectionStart;
end = el.selectionEnd;
} else {
range = document.selection.createRange();
if (range && range.parentElement() == el) {
len = el.value.length;
normalizedValue = el.value.replace(/\r\n/g, "\n");
// Create a working TextRange that lives only in the input
textInputRange = el.createTextRange();
textInputRange.moveToBookmark(range.getBookmark());
// Check if the start and end of the selection are at the very end
// of the input, since moveStart/moveEnd doesn't return what we want
// in those cases
endRange = el.createTextRange();
endRange.collapse(false);
if (textInputRange.compareEndPoints("StartToEnd", endRange) > -1) {
start = end = len;
} else {
start = -textInputRange.moveStart("character", -len);
start += normalizedValue.slice(0, start).split("\n").length - 1;
if (textInputRange.compareEndPoints("EndToEnd", endRange) > -1) {
end = len;
} else {
end = -textInputRange.moveEnd("character", -len);
end += normalizedValue.slice(0, end).split("\n").length - 1;
}
}
}
}
return {
start: start,
end: end
};
}