2014-06-11 1 views
2

knockout.js로 Select2를 사용합니다.Knockout.js inital 값이있는 Select2

그러나 컨트롤에 초기 값이 올바르게 표시되지 않습니다. select 함수가 발생하지 않는 것 같습니다.

내 문제를 설명하기 위해 기존 jsbin을 수정했습니다.

http://jsbin.com/xufovura/6/edit

바인딩 :합니다 (jsbin의 전체 코드를) 바인딩 정의의

<div data-bind="value: selectedState, select2: { data: states, placeholder: 'Select a State', formatResult: format ,initSelection: initSelect}" class="select2" style="width: 200px"></div> 

부분 :

ko.bindingHandlers.select2 = { 
    init: function(el, valueAccessor, allBindingsAccessor, viewModel) { 
     ko.utils.domNodeDisposal.addDisposeCallback(el, function() { 
    $(el).select2('destroy'); 
}); 

      var allBindings = allBindingsAccessor(), 
      select2 = ko.utils.unwrapObservable(allBindings.select2); 

     $(el).select2(select2); 

    } 
}; 

function initSelect(element, callback) { 
    console.log("initSelect"); 
      var selectedItems = $.grep(this.states, function (e) { return e.id == element.id; }); 

      console.log(element); 


      callback(selectedItems[0]); 
     } 
+0

는 이유는 당신의 initSelect 기능이없는이 방법은 또한 당신이 (즉, 단지 그것 ID가있어, 실제 "상태"개체를 저장하는) 대신 문자열 값의 객체에 백업 저장소를 변경해야해야합니다 select2가 자리 표시자를 선택했다고 생각한다는 것입니다. select2는 jQuery의 val 함수를 호출하여 요소의 현재 "값"을 읽으므로 div가 아닌 input 요소를 사용해야합니다. div 요소는 항상 ""을 반환합니다. –

답변

3

당신의 initSelect 함수가 호출되지 않습니다 이유는 것입니다 선택 2 귀하의 자리 표시자가 선택되었다고 생각합니다. Select2는 $(element).val()을 나타내고 그 결과가 false이면 자리 표시자가 선택 된 것으로 간주됩니다.

div 요소는 val() 결과에 대해 항상 ""을 반환합니다.

div 요소를 입력 요소로 전환해야하지만 jsBin에서이 작업을 수행하면 입력 값이 녹아웃으로 초기화되지 않은 것으로 나타났습니다. select2 바인딩의 init 함수가 호출 될 때 값 바인딩의 업데이트 함수가 아직 호출되지 않았으므로 값 바인딩에 타이밍 문제가 있습니다.

녹아웃은 모든 초기화 기능을 먼저 호출 한 다음 업데이트 기능을 호출합니다.

Select2를 사용하지 않을 때 Select2가 Knockout과 잘 맞지 않습니다 !!

빠르고 간단하게 해결하려면 select2 플러그인을 호출하기 전에 요소의 값이 설정되어 있는지 확인해야합니다.

init: function(el, valueAccessor, allBindingsAccessor, viewModel) { 
    ko.utils.domNodeDisposal.addDisposeCallback(el, function() { 
    $(el).select2('destroy'); 
    }); 

    var allBindings = allBindingsAccessor(), 
    select2 = ko.utils.unwrapObservable(allBindings.select2); 

    // Ensure the input's value is set before calling select2 
    $(el).val(allBindings.value()); 
    $(el).select2(select2);  
} 

당신은 또한 더 이상 initSelected 옵션이 필요하지 않으며, 사실에 의한 $.grep(this.states, ...)에 jsBin 실패 "이"그 시점에서 뷰 모델을 참조하지 않습니다.

은 또한 더 길고 더 완전한 대답은 다양한 선택 2 이벤트에 핸들러를 설정 포함 3.X에게


녹아웃 이동할 때 allBindingsAccessor이 변경 사실을 양지해야하고, 기가 값으로 수동 가입 바인딩의 업데이트 방법에서 필요할 경우 수동 호출을 $(el).select2('data', ...)으로 조정합니다.

+0

안녕하세요 정확히 무슨 뜻입니까? "녹아웃 3.x로 이동할 때 allBindingsAccessor가 변경됩니다."무엇을 변경해야합니까? –

+0

KO 3.x에서는 요소의 개별 바인딩이 해당 종속성이 변경된 경우에만 업데이트됩니다. KO 2.x에서 바인딩 종속성 중 ANY가 업데이트되면 요소의 모든 바인딩이 업데이트됩니다.이로 인해 allBindingAccessor 매개 변수에서 작은 API 변경이 발생했습니다. 'allBindingAccessor(). value'는 이제'allBindingsAccessor.get ('value')'입니다. –