Edición en línea con AJAX: ¿cómo creo múltiples áreas editables en la misma página?

StackOverflow https://stackoverflow.com/questions/613670

  •  03-07-2019
  •  | 
  •  

Pregunta

Encontré un tutorial sobre cómo crear regiones editables en una página usando AJAX.

Esto es genial, excepto que fue escrito para un solo elemento con una ID única. Me gustaría poder hacer clic en varios elementos en la misma página y hacer que también sean editables (por ejemplo, me gustaría alterar el script a continuación para que no funcione con un solo elemento, sino con múltiples elementos de un determinado clase ).

Aquí está mi HTML:

<h2>Edit This</h2>
<p class="edit">This is some editable content</p>
<p class="edit">This is some more editable content</p>
<p class="edit">I could do this all day</p>

Aquí está el archivo JS con el que estoy trabajando (actualicé la secuencia de comandos según la respuesta de Rex a continuación): esta secuencia de comandos, por desgracia, no funciona. ¿Puede alguien indicarme la dirección correcta?

Event.observe(window, 'load', init, false);

function init() {
    makeEditable('edit');
}

function makeEditable(className) {
    var editElements = document.getElementsByClassName(className);
    for(var i=0;i<editElements.length;i++) {
        Event.observe(editElements[i], 'click', function(){edit($(className))}, false);
        Event.observe(editElements[i], 'mouseover', function(){showAsEditable($(className))}, false);
        Event.observe(editElements[i], 'mouseout', function(){showAsEditable($(className), true)}, false);
    }
}


function showAsEditable(obj, clear) {
    if (!clear) {
        Element.addClassName(obj, 'editable');
    } else {
        Element.removeClassName(obj, 'editable');
    }
}

function edit(obj) {
    Element.hide(obj);

    var textarea ='<div id="' + obj.id + '_editor"><textarea cols="60" rows="4" name="' + obj.id + '" id="' + obj.id + '_edit">' + obj.innerHTML + '</textarea>';

    var button = '<input type="button" value="SAVE" id="' + obj.id + '_save"/> OR <input type="button" value="CANCEL" id="' + obj.id + '_cancel"/></div>';

    new Insertion.After(obj, textarea+button);

    Event.observe(obj.id+'_save', 'click', function(){saveChanges(obj)}, false);
    Event.observe(obj.id+'_cancel', 'click', function(){cleanUp(obj)}, false);
}

function cleanUp(obj, keepEditable) {
    Element.remove(obj.id+'_editor');
    Element.show(obj);
    if (!keepEditable) showAsEditable(obj, true);
}

function saveChanges(obj) {
    var new_content = escape($F(obj.id+'_edit'));

    obj.preUpdate = obj.innerHTML // stow contents prior to saving in case of an error
    obj.innerHTML = "Saving…";
    cleanUp(obj, true);

    var success = function(t){editComplete(t, obj);}
    var failure = function(t){editFailed(t, obj);}

    var url = 'http://portal.3roadsmedia.com/scripts/edit.php';
    var pars = 'id=' + obj.id + '&content=' + new_content + '&pre=' + obj.preUpdate;
    var myAjax = new Ajax.Request(url, {method:'post',
    postBody:pars, onSuccess:success, onFailure:failure});
}

function editComplete(t, obj) {
    obj.innerHTML = t.responseText;
    showAsEditable(obj, true);
}

function editFailed(t, obj) {
    obj.innerHTML = 'Sorry, the update failed.';
    cleanUp(obj);
}
¿Fue útil?

Solución

El método Event.observe actualmente se adjunta a un único elemento con la ID especificada. Debe cambiar esto para iterar sobre una colección de elementos ubicados por nombre de clase y adjuntarlos a cada uno de ellos. De acuerdo con la documentación del prototipo, puede proporcionar un objeto elemento como primer parámetro, en lugar de una ID.

Actualmente, id es una cadena:

function makeEditable(id) {
    Event.observe(id, 'click', function(){edit($(id))}, false);
    //...

Lo que significa que Event.observe se adjunta al evento de clic del elemento con el ID proporcionado. Desea adjuntar a todos los elementos con una clase. Prueba:

function makeEditable(className) {
    var editElements = document.getElementsByClassName(className);
    for(var i=0;i<editElements.length;i++) {
        Event.observe(editElements[i], 'click', function()
        //...
    }
    //...
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top