2009-08-23 14 views
2

Ich habe eine Liste von ziehbaren Geräten mit einer Liste von sortierbaren verbunden. Das Ziehen/Ablegen funktioniert genauso gut wie das Sortieren. Die Sache ist, dass, bevor die Liste sortiert wird, ich einen Datensatz in der DB erstellen muss (mit Schienen). Also verwende ich $ .post, was gut funktioniert, aber ich muss die ID des eingefügten Elements ändern. Dazu ändere ich die ID des eingefügten Elements mit dem $ .post-Callback. Funktioniert gut, aber es passiert nach der Sorte. Und wenn Sie sich wundern, warum ich den dragbaren Stop-Callback nicht verwendet habe, ist es, weil es dasselbe tut. Hier ist der abgekürzte Code (entfernt irrelevant db Material):JQuery ziehbare Rückruf nach Sortierung von sortierbaren

$("#operations_container").sortable({items:'.process_small', axis:'y', update: function(ev,ui) { 
    if (ui.item.attr('id').match("workcenter")) 
    { 
     $.post('/operations', 'fancyrailspoststuffignore', function(data) { 
        $("#operations_container > #workcenter_" + workcenterid).attr("id", "operation_" + data.operation.id); 
        }, "json"); 
    } 
    $.post('/jobs/sort/<%= @job.id %>', 'morefancyschamncyrailsjunk); 
}}); 

Der sortierbar Behälter ist einfach:

<div id="operations_container" class="in_grid"> 
</div> 

So scheint es mir, dass alle Rückrufe nach die Art genannt werden. Ist das wahr? Wie kommst du dazu, wenn du das DOM vor der Sortierung aktualisieren musst?

UPDATE: Falls sie in den Kommentaren verpasst werden, hier sind die Bild- und Beispieldateien, die das Problem veranschaulichen.

Image: http://dl.getdropbox.com/u/1826667/sortable.png Beispieldateien: http://dl.getdropbox.com/u/1826667/jquery_callback_order.zip

So scheint es, dass die Rückrufe immer am Ende von irgendwelchen anderen Ereignissen am Ende unabhängig davon, wo sie genannt werden (@ .post Rückruf vor sortierbar Update noch zuletzt genannt wird , etc). Ich denke nicht, dass es ein Fehler in JQuery ist (obwohl ich es seltsam finde); Ich versuche, eine Reihe von Posts (die erforderlich sind, da sie co-abhängig sind; erstellen Sie einen Datensatz, dann sortieren) in dem einen gehen, was vielleicht nicht der Weg ist, es zu tun. Ich werde versuchen, es im Backend zu umgehen (ich habe etwas fast funktioniert), also werde ich dies geschlossen betrachten. Danke an alle, die mit dem Problem geholfen haben. SO Regeln.

MEGAIMPORTANTUPDATE: Es funktioniert! Shawn hat es (siehe Antwort) und ich bin immer noch ein bisschen schwindlig. Es waren ein paar Tage auf diesem Ding. Danke nochmal an alle und besonders an Shawn. Du schaukelst.

+0

Ich habe Probleme, das Problem zu sehen. Möchten Sie beispielsweise # workcenter_43 zu # operation_64 ändern, bevor die Sortierreihenfolge geändert wird? –

+0

Das stimmt. Aber der Callback zum Ändern der ID wird nach der sortierbaren Änderung aufgerufen. –

+0

Ich glaube nicht, dass es einen Weg gibt, genau das zu tun; Vielleicht können wir einen Workaround finden. Warum musst du das vor der Sortierung anrufen? –

Antwort

2

Aha! Ich habs. Dieses Bild war genau das, was ich brauchte. Hier ist, was zu tun ist:

$("#operations_container").sortable({items:'.process_small', axis:'y', update: function(ev,ui) { 
    var sortDbTable = function(){ 
     $.post('/jobs/sort/<%= @job.id %>', 'morefancyschamncyrailsjunk); 
    } 
    if (ui.item.attr('id').match("workcenter")) 
    { 
      $.post('/operations', 'fancyrailspoststuffignore', function(data) { 
            $("#operations_container > #workcenter_" + workcenterid).attr("id", "operation_" + data.operation.id); //is there any reason you're not using the ui.item.attr("id",...) here? 
            sortDbTable(); //this will make sure id is changed before DB sort 
            }, "json"); 
    } else { //else not absolutely needed, but will make sure it's not unnecessarily sorted again 
     sortDbTable(); 
    } 
}}); 
+0

Heilige Affen! Das ist hervorragend! Setzen Sie es ein und funktioniert perfekt. Es ist immer noch seltsam, es zu sehen (ich habe Warnungen, die die Reihenfolge zeigen), aber es funktioniert PERFEKT! Ich danke dir sehr. Du bist ein Genie. –

+1

Es gab tatsächlich ein größeres Problem als nur die Reihenfolge der Rückrufe; Es ist der "asynchrone" Teil von AJAX. Diese Server-Aufrufe haben keine Garantie, wann sie zurückkommen; Sie starten einen und Ihr Code wird fortgesetzt. Wenn Sie etwas haben, das nach einer Antwort vom Server (zum Beispiel Ihre Sortierung) passieren muss, muss es vom Rückruf aufgerufen werden. –

0

Vor dem Update-Ereignis wird das Startereignis aufgerufen, das Sie verwenden können.

+0

Ja, ich habe mir das angesehen (eigentlich so ziemlich jeder Callback). Aber ich kann den Datensatz nicht erstellen, wenn der Benutzer das Element nicht auf dem Sortierbar löscht.:) Ich habe Spielzeug mit der Idee, es unabhängig zu erstellen und dann löschen, wenn nicht verwendet, aber das schien nur soooo falsch. –

+0

Haben Sie versucht, es stattdessen an das stop() -Ereignis des ziehbaren Objekts anzuhängen? –

+0

Ja, das ist eigentlich der erste Rückruf, den ich benutzt habe (weil es mehr Sinn gemacht hat). Aber das wird auch nach der Sortierung aufgerufen, also habe ich versucht, die Funktionen in den sortierbaren Callback zu injizieren, um die Reihenfolge der Callbacks zu erzwingen. Immer noch versuchen ... –