Это довольно обсуждаемая проблема на форумах jQuery, но я не могу найти решение для моей ситуации.
У меня есть неупорядоченный список с некоторыми текстовыми элементами в них ... пользователь может создавать новые элементы списка через jQuery, которые сохраняются в базе данных SQL. Они также могут редактировать существующие элементы списка. Кроме того, поскольку текст в каждом элементе списка может быть довольно длинным, у них есть возможность «скрыть» каждый элемент списка, чтобы он отображал усеченную версию строки. Это обрабатывается пользовательским плагином jQuery, который усекает элементы списка более определенной длины ... вот как выглядит каждый элемент списка после его форматирования плагином усечения:
<li id="item_1">
<div class="note">
This is the text that shows when this element is truncated <span style="display: none;" class="truncate_ellipsis">...</span>
<span style="display: inline;" class="truncate_more">This is the text that will be hidden if the user clicks on the 'hide' button</span>
</div>
<div class="toggle_wrapper">
<div class="note_toggle">
<a href="#" class="truncate_more_link">Hide note</a>
</div>
<div style="display: block;" class="note_controls">
<span class="edit_note"><a href="#note_textfield" id="edit_note_1">Edit</a></span> | <span class="delete_note"><a href="#" id="delete_note_1">Delete</a></span>
</div>
</div>
</li>
Проблема, с которой я столкнулся, заключается в том, что пользователь нажимает «edit», и он берет содержимое div с классом «note» и назначает его текстовой области. Затем пользователь может отредактировать текст и сохранить его. Я использую следующий скрипт, чтобы получить содержимое div и присвоить его текстовой области:
$('.edit_note a').click(function(event){
// Get the parent li of the 'edit' link that was clicked
var parentLi = $(this).closest('li');
// fade out the li that's being edited
parentLi.fadeOut('fast');
// remove the '...' that shows when the note is truncated
parentLi.find('.truncate_ellipsis').remove();
// find the 'note' div within the li that's being edited
var currentNote = parentLi.find('.note');
// grab the id of this note... used when saving to the DB
var noteId = $(this).attr('id').substr(10);
// Set the current note id variable and editing status
currentNoteId = noteId;
currentNoteStatus = 'edit';
//add the note ID as a hidden field to the text editor form
$('input[name$="note_id"]').val(noteId);
// grab the text from this note and add it to the text area
// (textarea id is 'notes_content')
$('#notes_content').val($.trim(currentNote.text()); // this is the text area
// fade in the text area so the user can edit
$('div.notes_textarea').fadeIn();
});
Как только он сохранен, я использую функцию, которую я нашел в Интернете, чтобы преобразовать разрывы строк в БР, прежде чем присваивать содержимое текстовой области обратно div 'note' в соответствующем элементе списка:
function nl2br (str, is_xhtml) {
var breakTag = (is_xhtml || typeof is_xhtml === 'undefined') ? '<br />' : '<br>';
return (str + '').replace(/([^>\r\n]?)(\r\n|\n\r|\r|\n)/g, '$1'+ breakTag +'$2');
}
Все это прекрасно работает в firefox / chrome / opera / safari ... однако IE избавляется от разрывов строк, когда получает текст с помощью функции text () jQuery. Это обсуждается в комментариях этой страницы к документации jQuery:
http://api.jquery.com/text/
Некоторые люди добились успеха, клонировав исходный элемент, обернув его в теги pre, затем взяв его содержимое и поместив в текстовую область. Это работает для разрывов строк, но также приводит к появлению лишних пробелов, табуляции и т. Д., И выглядит немного беспорядочно. Лучшим решением, по-видимому, является использование функции html () jQuery для захвата текста, затем замена br на разрывы строк и удаление любого другого html-форматирования.
Я новичок в Javascript, однако, и я мусор на регулярных выражениях, поэтому я не имею понятия, как это сделать, и у меня заканчивается время! Мне нужно регулярное выражение или просто некоторая помощь с форматированием строки, чтобы сделать следующее:
удалить все теги span из строки БЕЗ удаления содержимого диапазона (моя функция truncate добавляет диапазон с классом "truncate_more" ... см. Выше HTML-код)
Удалите символы br и замените их символами новой строки, которые будут правильно отображаться в элементе textarea и будут согласованы во всех браузерах
ИЛИ ... если кто-нибудь знает о лучшем обходном пути к этой проблеме IE / textarea / linebreak, я бы очень признателен за руководство для идиотов:)
Немного информации о том, что, вероятно, является простым решением, но я подумал, что постараюсь объяснить ситуацию как можно лучше! Любая помощь будет принята с благодарностью ....
EDIT : 'Ответ TheJuice ниже работал для проблемы разрывов строк в br / IE (спасибо!), Но мне нужно выполнить аналогичное регулярное выражение, чтобы избавиться от промежутков, поскольку они только инкапсулируют некоторые текста. Я попробовал следующее, которое, кажется, работает нормально в Firefox, но в IE, диапазоны остаются:
var withBRs = currentNote.html();
var textWithBreaks = withBRs.replace(/\<br\>/gi,'\r');
textWithBreaks = textWithBreaks.replace(/\<.*span.*\>/g, '');
ДРУГОЕ РЕДАКТИРОВАНИЕ : «TheJuice» тоже решил эту проблему ... не обращайте внимания на мое ужасное регулярное выражение и просто делайте то, что он говорит, если вы попадаете в ту же ситуацию! Спасибо всем, кто предложил предложения ...