Содержимое HTML5 Редактируемый абзац после списка

Я использую Гугл Хром.

Мне нужен очень маленький HTML-редактор, и я нашел Simple Edit. Очень маленький редактор, как раз для моих нужд. Однако... У этого и многих других редакторов, использующих Content Editable, есть одна общая проблема.

Проблема

После создания списка (дважды нажмите Enter в последнем элементе списка) он создает новый div. Ожидается, что я создам новый тег абзаца.

Ссылки

Вопрос

Каков правильный способ предотвратить div и вместо этого добавить теги абзаца после списка?


person Jens Törnell    schedule 19.10.2012    source источник
comment
Это опубликует проблему, которую вы знаете. Если вы замените элемент контейнера тегами абзаца вместо div, последующие списки будут дочерними элементами абзацев, что является недопустимым html.   -  person Edward J Beckett    schedule 29.10.2012


Ответы (5)


Ответ, опубликованный Брайаном Алло, не учитывал, что вам нужно поместить курсор в конец div. В противном случае при каждом действии замены пользователю пришлось бы нажимать CTRL-End.

Это решение, которое я предлагаю, также можно увидеть в действии на http://jsfiddle.net/82dS6/. :

function setEndOfContenteditable(contentEditableElement){
    // Taken from http://stackoverflow.com/a/3866442/1601088
    var range,selection;
    if(document.createRange){//Firefox, Chrome, Opera, Safari, IE 9+
        range = document.createRange();
        range.selectNodeContents(contentEditableElement);
        range.collapse(false);
        selection = window.getSelection();
        selection.removeAllRanges();
        selection.addRange(range);
    }
    else if(document.selection){//IE 8 and lower
        range = document.body.createTextRange();
        range.moveToElementText(contentEditableElement);
        range.collapse(false);
        range.select();
    }
}

function replaceDivWithP(el){

    $(el).find('div').each(function(){
        $(this).replaceWith($('<p>' + $(this).html() + '</p>'));
    });
}

$(function(){
    $(".text").simpleEdit();
});

$('.textarea').bind('keyup', function(){
    replaceDivWithP(this);
    setEndOfContenteditable(this);
});


​
person maurits    schedule 27.10.2012
comment
Это решение является лучшим на данный момент. Голосуйте пока. Однако, когда я нажимаю значок списка, он добавляет список внутри абзаца. - person Jens Törnell; 29.10.2012
comment
Кажется, что нет простого способа обойти это, потому что библиотека, которую вы используете, использует ExecCommand для замены содержимого, к которому нелегко подключиться. - person maurits; 30.10.2012

Вместо обработки «на лету» каждого события keyup вы можете рассмотреть возможность постобработки:

$('.textarea').bind('blur', function(){
    $('.textarea div').contents().unwrap().wrap('<p/>');
});

Скрипт: http://jsfiddle.net/thNUS/4/

person user916011    schedule 29.10.2012

Быстрое решение — просто заменить любые DIV на Ps. Поместите это в редактируемый DIV вашего контента.

onkeyup="this.innerHTML=this.innerHTML.replace('div','p')"

Надеюсь, поможет. Удачи.

person Bryan Allo    schedule 19.10.2012
comment
вы можете заменить фактические теги, если хотите быть конкретными и избежать потенциальных конфликтов с действительным контентом. Только не забудьте заменить закрывающие теги. :-) - person Bryan Allo; 19.10.2012


В предыдущих ответах предлагалось решение на основе keyup или blur. Здесь используется событие click кнопки списка, чтобы минимизировать количество вызовов функций:

http://jsfiddle.net/9ZAL7/:

function replaceDivWithP(el){

    $(el).find('div').each(function(){
        $(this).replaceWith($('<p>' + $(this).html() + '</p>'));
    });
}

$(function(){
    $(".text").simpleEdit();
});

$('button.list').bind('click', function(){
    replaceDivWithP($('.textarea'));
});
​
person maurits    schedule 29.10.2012