Обернуть тегами выделенный фрагмент текста
Есть такой блок:
<div class="editor-content" id="editor-content" contenteditable="true"> as dd sad as </div> кусок плагина в котором проверяю выделение: getSel = function(element) { var start = 0, end = 0; var sel, range, priorRange; if (typeof window.getSelection != "undefined") { range = window.getSelection().getRangeAt(0); priorRange = range.cloneRange(); priorRange.selectNodeContents(element); priorRange.setEnd(range.startContainer, range.startOffset); start = priorRange.toString().length; end = start + range.toString().length; } else if (typeof document.selection != "undefined" && (sel = document.selection).type != "Control") { range = sel.createRange(); priorRange = document.body.createTextRange(); priorRange.moveToElementText(element); priorRange.setEndPoint("EndToStart", range); start = priorRange.text.length; end = start + range.text.length; } return { start: start, end: end }; }, alertSelection = function() { var mainDiv = document.getElementById(sett.id); var sel = getSel(mainDiv); var val = editor.html(); var text = val.substr(0,sel.start) + "[abcd]" + val.substr(sel.start,sel.end) + "[/abcd]" + val.substr(sel.end,val.length); alert(text); } при выделении символов "dd", alert выводит следующее: "as [abcd]dd sad as[/abcd] sad as" хотя по логике должно вывести это: "as [abcd]dd[/abcd] sad as" проверял что возвращает функция getSel(), все правильно работает... непойму почему так... помогите разобраться. и желательно пример где подобная задача решается, именно такая... много перегуглил уже зараннее спасибо) p.s. просьба не троллить по поводу BB, т.к. [b] - здесь исключительно для примера |
Sanu0074,
потому что Цитата:
http://javascript.ru/String/substr var text = val.substr(0,sel.start) + "[abcd]" + val.substr(sel.start,sel.end-sel.start) + "[/abcd]" + val.substr(sel.end); |
рони, спасибо)
тупанул жестко с синтаксисом( я вот сделал щас так, работает, выделяет как надо: var editor = this, getSel = function(element) { var start = 0, end = 0; var sel, range, priorRange; if (typeof window.getSelection != "undefined") { range = window.getSelection().getRangeAt(0); priorRange = range.cloneRange(); priorRange.selectNodeContents(element); priorRange.setEnd(range.startContainer, range.startOffset); start = priorRange.toString().length; end = start + range.toString().length; } else if (typeof document.selection != "undefined" && (sel = document.selection).type != "Control") { range = sel.createRange(); priorRange = document.body.createTextRange(); priorRange.moveToElementText(element); priorRange.setEndPoint("EndToStart", range); start = priorRange.text.length; end = start + range.text.length; } return { start: start, end: end }; }, stripTags = function(text){ if(text.length<3){return;} var regex = /(<([^>]+)>)/ig; return text.replace(regex, ""); }, setTag = function(tag) { var mainDiv = document.getElementById(sett.id), sel = getSel(mainDiv), val = editor.html(), fragment = stripTags(val.substr(sel.start, (sel.end-sel.start))); text = val.substr(0, sel.start) + "<"+tag+">" + fragment + "</"+tag+">" + val.substr(sel.end); editor.html(text); } editor.bind('keydown','ctrl+b',function(){ setTag("strong"); return false; }); Теперь как правильно сделать, чтоб когда уже обрамленный текст (в данном случае жирный) выделяеш, нажимаеш ctrl+b, и он теряет выделение (в данном случае теги strong по краям должны пропасть).... Как правильно сделать? В этом примере при обратном выделении вставляется такое: "as dd g>sad as" |
Sanu0074,
так выделяется и считается видимый текст а вы редактируите строка 37 весь текст с тегами - стирайте теги сразу val = editor.html(); val = stripTags(val); fragment = val.substr(sel.start, (sel.end-sel.start)); |
рони,
Да, так работает, но всё что заранее было выделено теряется и обарачивается только текущий фрагмент. это не хорошо, как правильно обернуть фрагммент тегами сохранив существующие? |
Цитата:
sel.start и sel.end- -- нод может быть несколько оборачивать каждую |
рони,
подкиньте примерчик как это делать) Хорошо былобы как-то знать с какого участка текста было выделении или др вариант - цикл и регулярки которые будут удалять самые крайние соседние теги... перед этим сравнив их на сходство... пока непойму как все же правильно подойти к решению задачи |
Цитата:
|
рони,
я еще не пробовал, но думаю регулярками попробовать, при этом циклом искать теги в строке.... звучит это жестко, но пока еще не пробовал |
Sanu0074,
а вложенные теги? |
рони,
ну думаю будет так: проверяется строка, сначала находятся самые крайние теги к выделенному фрагменту проверяется наличие вложенных, если нет таких же тегов совпадающих с переданными - фрагмент обрамляется переданными тегами, если есть такиеже теги (вложенные или крайние) как переданные - то они обрезаются...... как то так... но все же я думаю это неоч хорошее решение, верится что есть другой более разумный подход, только не знаю какой( |
Вот сделал, но очень криво работает:
setTag = function(tag) { var mainDiv = document.getElementById(sett.id), sel = getSel(mainDiv), val = editor.html(); for(var i=sel.start; i>0; i--){ if(val[i]==' ' || val[i]=='<'){ sel.start=i; break; } } for(var i=sel.end; i<val.length; i++){ if(val[i]==' ' || val[i]=='<'){ sel.end=i; break; } } var fragment = val.substr(sel.start, (sel.end-sel.start)); if(fragment.search("<"+tag+">")==0){ fragment=fragment.replace("<"+tag+">",""); fragment=fragment.replace("</"+tag+">",""); } var text = val.substr(0, sel.start) + "<"+tag+">" + fragment + "</"+tag+">" + val.substr(sel.end); editor.html(text); $(".html").val(text); } надо что-то другое думать( если бы получить родительский элемент исходя из положения курсора (sel.start).... |
Sanu0074,
на всякий случай http://learn.javascript.ru/vydelenie...ge-i-selection |
Часовой пояс GMT +3, время: 17:29. |