2014-02-01 5 views
2

Мне нужно создать веб-страницу с двумя списками, которые можно поменять местами. В списках есть элементы, которые также могут быть заменены или перемещены из одного списка в другой.Knockout вложенные сортируемые списки

Я использовал knockoutjs и knockoutjs-sortable для реализации этого.

HTML

<ul class="Tasks" data-bind="sortable: TaskLists"> 
    <li class="taskList"> 
     <span data-bind="text: Title" style='background: lightgray;'></span> 
     <ul data-bind="sortable: Tasks"> 
      <li class="item"> 
       <span class="taskName" href="#" data-bind="text: name"></span> 
      </li> 
     </ul> 
    </li> 
</ul> 

JS

var Task = function (name) { 
    this.name = ko.observable(name); 
} 

var ViewModel = function() { 
    var self = this; 
    self.tasks1 = ko.observableArray([]); 
    self.tasks2 = ko.observableArray([]); 
    for (var i = 0; i < 5; i++) { 
     self.tasks1.push(new Task("This task belongs to list one")); 
     self.tasks2.push(new Task("This task belongs to list two")); 
    } 
    self.TaskList1 = { 
     Tasks: self.tasks1, 
     Title: 'List One' 
    }; 
    self.TaskList2 = { 
     Tasks: self.tasks2, 
     Title: 'List Two' 
    }; 
    self.TaskLists = ko.observableArray([]); 
    self.TaskLists.push(self.TaskList1); 
    self.TaskLists.push(self.TaskList2); 
}; 

ko.bindingHandlers.sortable.options = { 
    placeholder: 'ui-state-highlight', 
    start: function (e, ui) { 
     var dragElements = $('.ui-state-highlight'); 
     dragElements.css("height", ui.helper.outerHeight()); 
    } 
}; 
ko.applyBindings(new ViewModel()); 

CSS

.frame { 
    padding: 10px; 
    overflow:auto; 
} 
.item { 
    border: black 1px solid; 
    width: 100px; 
    background-color: #DDD; 
    cursor: move; 
    text-align: center; 
    margin-top: 2px; 
    margin-bottom: 2px; 
} 
.taskList { 
    width: 110px; 
    float:left; 
    background: lightgreen; 
} 
.Tasks { 
    width:400px; 
    border: 1px #eee solid; 
    height: 100%; 
} 
.taskName { 
    word-wrap: break-word; 
} 
.ui-state-highlight { 
    background: grey; 
    border:1px dashed grey; 
} 

Вот что я до сих пор (fiddle).

Все работает как ожидалось, за исключением перемещения списков. При перемещении списка вокруг, я ожидаю, что перетащить фронтон заполнителем выглядеть следующим образом:

enter image description here

но я получаю:

enter image description here

Что я делаю неправильно? Как я могу достичь этих ожидаемых результатов?

ответ

1

Я нашел проблему после хорошего ночного сна. Был несколько подводных камней в моей конструкции выше:

  • Вложенные списки не имеют connectClass, что поможет Нокауту-сортировке выяснить, где элемент может быть втянут. Оставляя это неуказанным, один из списков принимает либо элемент, либо полный список, который нужно перетащить в него.
  • Держатель перетаскиваемого места отличается тем, что сами списки. Вот почему draggable placeholder был неправильно отображен (см. Приведенный скриншот в моем вопросе выше)
  • Был установлен только один держатель места, который применяется как к перетаскиваемому элементу, так и к перетаскиваемому списку, который не является хорошим.

fiddle показать все результаты поиска.

HTML

<div class="frame"> 
    <ul class="Tasks" data-bind="sortable: {data: TaskLists, connectClass: 'columns', options: { placeholder: 'list-highlight'}}"> 
     <li class="taskList"> 
     <span data-bind="text: Title" style='background: lightgray;'></span> 
     <ul data-bind="sortable: {data: Tasks, connectClass: 'columnItems', options : { placeholder: 'ui-state-highlight'}}"> 
      <li class="item"> 
       <span class="taskName" href="#" data-bind="text: name"></span> 
      </li> 
     </ul> 
     </li> 
    </ul> 
</div> 

JS

var Task = function(name) { 
    this.name = ko.observable(name); 
} 

var ViewModel = function() { 
    var self = this; 
    self.tasks1 = ko.observableArray([]); 
    self.tasks2 = ko.observableArray([]); 
    for (var i=0;i<5;i++){ 
     self.tasks1.push(new Task("This task belongs to list one")); 
     self.tasks2.push(new Task("This task belongs to list two")); 
    } 
    self.TaskList1 = {Tasks: self.tasks1, Title:'List One'}; 
    self.TaskList2 = {Tasks: self.tasks2, Title:'List Two'}; 
    self.TaskLists = ko.observableArray([]); 
    self.TaskLists.push(self.TaskList1); 
    self.TaskLists.push(self.TaskList2); 
}; 

ko.bindingHandlers.sortable.options = { 
     //placeholder: 'ui-state-highlight', 
     start: function (e, ui) { 
      var dragItems = $('.ui-state-highlight'); 
      var dragLists = $('.list-highlight'); 
      var elementClass = ui.helper[0].className; 
      if(elementClass === "item") 
        dragItems.css("height",ui.helper.outerHeight()); 
      if(elementClass === "taskList") 
        dragLists.css("height",ui.helper.outerHeight()); 
     } 
    }; 
ko.applyBindings(new ViewModel()); 

CSS

.frame{ 
     padding: 10px; 
     overflow:auto; 
    } 

    .item { 
     border: black 1px solid; 
     width: 100px; 
     background-color: #DDD; 
     cursor: move; 
     text-align: center; 
     margin-top: 2px; 
     margin-bottom: 2px; 
    } 

    .list-highlight{ 
     width: 100px; 
     float:left; 
     background: gray; 
    } 

    .taskList{ 
     width: 110px; 
     float:left; 
     background: lightgreen; 
    } 

    .Tasks{ 
     width:400px; 
     border: 1px #eee solid; 
     height: 100%; 
    } 

    .taskName{ 
     word-wrap: break-word; 
    } 

    .ui-state-highlight{ 
     background: grey; 
     border:1px dashed grey; 
} 
+0

Что отношения (если таковые имеются) между названиями connectClass/с значений» olumns 'и' columnItems ', а также ваш ViewModel или CSS? У меня есть (довольно) аналогичный пример скрипки http://jsfiddle.net/patware/3VS6s/ и не могу заставить его работать как ваша скрипка. –

+0

ConnectClass - это класс, который будет искать плагин перетаскивания при перетаскивании элементов html в документ. Я также использую те же классы для форматирования моих объектов. – GETah

+0

Я не могу найти «столбцы» или «columnItems» в вашем html или css. Я ожидал ваш html для класса = «столбцы» или что-то в этом роде. –

Смежные вопросы