2010-08-16 2 views
23

Dans le code ci-dessous, la fonction de mise à jour est appelée deux fois lorsqu'un élément est déplacé de la liste sortable1 vers sortable2. Bien que j'ai besoin d'appeler cette fonction qu'une seule fois:jquery Sortable connectWith appelle deux fois la méthode de mise à jour

$("#sortable1 tbody, #sortable2 tbody").sortable({ 
    connectWith: '.connectedSortable tbody', 
    helper: fixHelper, 
    handle : '.handle', 
    update : function() { 
     var order = $('#sortable1 tbody').sortable('serialize'); 
    }  
}).disableSelection(); 

Répondre

2

Je viens de courir dans cela. C'est un bug dans jQuery UI, voir http://bugs.jqueryui.com/ticket/4872#comment:2

J'ai commenté pour voir si je peux réveiller quelqu'un pour savoir quand il y aura une solution. Les joies du développement piloté par la communauté: P

+0

Ce n'est pas vraiment un bug, vous êtes juste lié au mauvais événement. –

52

Réponse de: http://forum.jquery.com/topic/sortables-update-callback-and-connectwith

update: function(e,ui) { 
    if (this === ui.item.parent()[0]) { 
     //your code here 
    } 
} 
+0

juste ce dont j'avais besoin. – Stephen

+5

Il vaut la peine de noter 'this' est la valeur intéressante ici. 'update' est lancé deux fois, à savoir la liste où l'élément est déplacé et la liste dans laquelle l'élément a été déplacé. 'ui.item.parent()' fait référence au parent de l'élément déplacé. Si vous vous demandez pourquoi cela fonctionne :) – yoshi

3

Essayez ceci:

update: function(e,ui) { 
    if (!ui.sender) { 
     //your code here 
    } 
} 
+0

cela ne fonctionnerait pas parce que vous ne voyez pas les mouvements dans le même conteneur. sauf si vous voulez les traiter séparément. – userfuser

7

Réponse de Stefan était bon, mais il ne mentionne pas une autre pièce du casse-tête, si elle est ici - en cas quelqu'un (comme moi) ne comprend pas tout de suite. Cela devrait permettre à vous de gérer tout cela dans la fonction update() et de ne pas avoir à jouer avec (qui se déclenchera que lorsque les mouvements inter-conteneurs se produisent):

update: function(e,ui) { 
    if (this === ui.item.parent()[0]) { 
     if (ui.sender !== null) { 
      // the movement was from one container to another - do something to process it 
      // ui.sender will be the reference to original container 
     } else { 
      // the move was performed within the same container - do your "same container" stuff 
     } 
    } 
} 
1

Comment l'utilisation de retirer , recevoir et mettre à jour pour capturer tous les changements et les envoyer au serveur en tant que tableau?

Démo: http://jsfiddle.net/r2d3/p3J8z/

$(function(){ 

    /* Here we will store all data */ 
    var myArguments = {}; 

    function assembleData(object,arguments) 
    {  
     var data = $(object).sortable('toArray'); // Get array data 
     var step_id = $(object).attr("id"); // Get step_id and we will use it as property name 
     var arrayLength = data.length; // no need to explain 

     /* Create step_id property if it does not exist */ 
     if(!arguments.hasOwnProperty(step_id)) 
     { 
      arguments[step_id] = new Array(); 
     } 

     /* Loop through all items */ 
     for (var i = 0; i < arrayLength; i++) 
     { 
      var image_id = data[i]; 
      /* push all image_id onto property step_id (which is an array) */ 
      arguments[step_id].push(image_id);   
     } 
     return arguments; 
    } 

    /* Sort images */ 
    $('.step').sortable({ 
     connectWith: '.step', 
     items : ':not(.title)', 
     /* That's fired first */  
     start : function(event, ui) { 
      myArguments = {}; /* Reset the array*/ 
     },  
     /* That's fired second */ 
     remove : function(event, ui) { 
      /* Get array of items in the list where we removed the item */   
      myArguments = assembleData(this,myArguments); 
     },  
     /* That's fired thrird */  
     receive : function(event, ui) { 
      /* Get array of items where we added a new item */ 
      myArguments = assembleData(this,myArguments);  
     }, 
     update: function(e,ui) { 
      if (this === ui.item.parent()[0]) { 
       /* In case the change occures in the same container */ 
       if (ui.sender == null) { 
        myArguments = assembleData(this,myArguments);  
       } 
      } 
     },  
     /* That's fired last */   
     stop : function(event, ui) {     
      /* Send JSON to the server */ 
      $("#result").html("Send JSON to the server:<pre>"+JSON.stringify(myArguments)+"</pre>");   
     }, 
    }); 
}); 

Voici l'explication complète de la solution: http://r2d2.cc/2014/07/22/jquery-sortable-connectwith-how-to-save-all-changes-to-the-database/

1

Pour appeler une fois l'événement, vous pouvez utiliser la méthode receive. Il est appelé une fois qu'un élément d'une liste est déposé dans une autre liste.

$(".selector").sortable({ 
    stop: function(event, ui) {} 
}); 

Source: http://api.jqueryui.com/sortable/#event-receive.

0
update: function(e, ui) { 
    var draggedOut = this !== ui.item.parent()[0] && !$.contains(this, ui.item.parent()[0]); 
    var draggedIn = ui.sender !== null; 
    var sameList = !draggedOut && !draggedIn; 

    if (sameList || draggedIn) { 
     // Do stuff 
    } 
} 
Questions connexes