1

У меня есть два элемента формы, оба с двухсторонней привязкой по ссылке через backbone.stickit. Второй элемент формы (# input) - это просто косметика - там для показа фактически работает.(Re) рендеринг Магистральный вид в обработчике события изменения не работает

Идея состоит в том, что мой просмотр получает (повторно) визуализируется каждый раз, когда изменяется опция внутри выпадающего меню (#select).

Я пытаюсь добиться этого, поймав «измененное» событие #select и вызывая this.render() для (re) визуализации представления.

Видимо, что не работает. Выбранная опция не возвращается обратно в модель, и я не понимаю, почему.

Я не ищу решения, а не объяснения, почему следующий код не работает. Решение (как в: работает для меня) является частью скрипки - прокомментировано.

HTML:

<script type="text/template" id="tpl"> 
    <h1>Hello <%= select %></h1> 
    <select id="select"> 
    </select> 
    <p>Select: 
    <%= select %> 
    </p> 
    <hr> 
    <input type="text" id="input"> 
    <p>Input: 
    <%= input %> 
    </p> 
</script> 

<div id="ctr"></div> 

JavaScript:

Foo = Backbone.Model.extend({ 
    defaults: { 
    select: "", 
    input: "", 
    } 
}); 
FooView = Backbone.View.extend({ 
    el: '#ctr', 
    template: _.template($('#tpl').html()), 
    initialize() { 
    this.model.bind('change', function() { 
     console.log("model change:"); 
     console.log(this.model.get('select')); 
     console.log(this.model.get('input')); 
    }, this); 
    //this.model.bind('change:select', function() { this.render(); }, this); // <--------------------- WORKS 
    }, 
    render: function() { 
    this.$el.html(this.template(this.model.toJSON())); 
    this.stickit(); 
    return this; 
    }, 
    events: { 
    'change #select': function(ev) { 
     console.log('change event triggered:'); 
     console.log(this.model.get('select')); 
     console.log(this.model.get('input')); 
     this.render(); // <--------------------- DOES NOT WORK - WHY? 
    }, 
    /* 'click #render': function(ev) { 
     console.log('render event triggered:'); 
     console.log(this.model.get('select')); 
     console.log(this.model.get('input')); 
     this.render(); 
    } */ 
    }, 
    bindings: { 
    '#input': 'input', 
    '#select': { 
     observe: 'select', 
     selectOptions: { 
     collection: function() { 
      return [{ 
      value: '1', 
      label: 'Foo' 
      }, { 
      value: '2', 
      label: 'Bar' 
      }, { 
      value: '3', 
      label: 'Blub' 
      }] 
     } 
     } 
    }, 
    }, 
}); 
new FooView({ 
    model: new Foo() 
}).render(); 

https://jsfiddle.net/r7vL9u07/9/

ответ

1

Причина, по которой не работает, чтобы позвонить this.render() из вашего обработчика событий change #select потому, что вы срыве двух- которое связывает Backbone.stickit. Поток выглядит примерно так:

  • Пользователь меняет значение '#select'.
  • Ваш change #select обработчик и звонки this.render().
  • render repopulate #ctr с новым меню выбора без выбора option.
  • Backbone.stickit отвечает на изменение на #select.
  • Backbone.stickit пытается получить значение #select, но так как в нем не выбрано option значение равно undefined.
  • Атрибут Backbone.sticket устанавливает атрибут modelselect на undefined.

Причина это работает, если вы перемещаете this.render() вызов в change:select обработчика model «s потому, что Backbone.stickit способен правильно обновить модель без DOM меняющегося, прежде чем он получает шанс.

+0

Большое спасибо за объяснение. Выполнение этого с помощью model.bind ('change: select') - это правильный способ сделать это? – daten

+0

Если вы хотите повторно выполнить рендеринг при изменении выбора, тогда да. – 76484

+0

Спасибо большое! – daten

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

  • Нет связанных вопросов^_^