2013-03-26 3 views
1

간단히 말하자면, 이것은 체크 박스를 불확정 상태로두기위한 제 녹아웃 커스텀 바인딩입니다.불확정 체크 박스에 대한 넉 아웃 커스텀 바인딩이 작동하지 않습니다.

ko.bindingHandlers.nullableChecked = { 
    update: function (element, valueAccessor) { 
     var value = ko.utils.unwrapObservable(valueAccessor()); 
     if (value == null) element.indeterminate = true; 
     ko.bindingHandlers.checked.update(element, function() { return value; }); 
    } 
}; 

모든 것이 잘 작동하고 체크 박스가 불확정 상태로 전환되어 있지만이 확인란을 클릭하면 그에 따라 참/거짓에 대한 바운드 프로퍼티의 값을 업데이트하지 않는 것 null 초기 값 인 경우. 내가 놓친 게 있니?

+0

jsFiddle을 함께 사용하여 게임 할 수있는 기회가 있습니까? –

답변

4

초기화를 호출하지 않았습니다.

nullableChecked init 함수에서 확인한 init 함수를 업데이트 할 때처럼 프록시하십시오. 초기화없이

ko.bindingHandlers.nullableChecked = { 
    init: function(element, valueAccessor) { 
      ko.bindingHandlers.checked.init(element, valueAccessor); 
    }, 
    update: function (element, valueAccessor) { 
     var value = ko.utils.unwrapObservable(valueAccessor()); 
     if (value == null) element.indeterminate = true; 
     ko.bindingHandlers.checked.update(element, valueAccessor); 
    } 
}; 

, 그것은 결코 실제로 "클릭"체크 박스에 바인딩 뭔가 녹아웃 얘기가 변경된 설정하지입니다. 디버그 코드 ( http://knockoutjs.com/downloads/knockout-2.2.1.debug.js)를 보면, init이 jQuery를 사용하여 체크 박스에 '클릭'이벤트를 설정하여 값이 변경 될 때 관찰 가능 객체를 업데이트한다는 것을 알 수 있습니다.

ko.bindingHandlers['checked'] = { 
'init': function (element, valueAccessor, allBindingsAccessor) { 
    var updateHandler = function() { 
     var valueToWrite; 
     if (element.type == "checkbox") { 
      valueToWrite = element.checked; 
     } else if ((element.type == "radio") && (element.checked)) { 
      valueToWrite = element.value; 
     } else { 
      return; // "checked" binding only responds to checkboxes and selected radio buttons 
     } 

     var modelValue = valueAccessor(), unwrappedValue = ko.utils.unwrapObservable(modelValue); 
     if ((element.type == "checkbox") && (unwrappedValue instanceof Array)) { 
      // For checkboxes bound to an array, we add/remove the checkbox value to that array 
      // This works for both observable and non-observable arrays 
      var existingEntryIndex = ko.utils.arrayIndexOf(unwrappedValue, element.value); 
      if (element.checked && (existingEntryIndex < 0)) 
       modelValue.push(element.value); 
      else if ((!element.checked) && (existingEntryIndex >= 0)) 
       modelValue.splice(existingEntryIndex, 1); 
     } else { 
      ko.expressionRewriting.writeValueToProperty(modelValue, allBindingsAccessor, 'checked', valueToWrite, true); 
     } 
    }; 
    ko.utils.registerEventHandler(element, "click", updateHandler); 

    // IE 6 won't allow radio buttons to be selected unless they have a name 
    if ((element.type == "radio") && !element.name) 
     ko.bindingHandlers['uniqueName']['init'](element, function() { return true }); 
}, 

편집 :는 여기에 바이올린입니다 : http://jsfiddle.net/cclose/NFfVn/

+0

실제로 코드에서 업데이트를 가능하게하려면 핸들러의 업데이트 콜백은! = null 값인 경우 indeterminate 속성을 false로 설정해야합니다. – MarkO

+1

이것은 Knockout <= 2.3.0에서는 작동하지만 Knockout> = 3.0에서는 작동하지 않습니다 .0. 어떤 아이디어? Knockout 3.0.0에서 작동하는 솔루션이 있습니까? –

1

checked 처리기는 값을 보유하고있는 관측 가능 값이 아니라 저장된 값에 대한 접근자를 수신합니다. 따라서 관측 가능 객체는 핸들러로 인해 값을 변경하지 않습니다. 나는 당신이 값 접근자를 그대로 전달할 수 있어야한다고 생각한다.

ko.bindingHandlers.nullableChecked = { 
    update: function (element, valueAccessor) { 
     var value = ko.utils.unwrapObservable(valueAccessor()); 
     if (value == null) element.indeterminate = true; 
     ko.bindingHandlers.checked.update(element, valueAccessor); 
    } 
}; 
4

@Fodagus에 의한 대답은 넉 아웃 < = 2.3.0와 함께 작동하지만, 녹아웃에>는 = 3.0.0, ko.bindingHandlers.checked.update는 정의되지 않습니다.

ko.bindingHandlers.nullableChecked = { 
     init: function (element, valueAccessor) { 
      ko.bindingHandlers.checked.init(element, valueAccessor); 
     }, 
     update: function (element, valueAccessor) { 
      var value = ko.utils.unwrapObservable(valueAccessor()); 
      if (value == null) { 
       element.indeterminate = true; 
      } 
      else { 
       element.indeterminate = false; 
      } 
     } 
    }; 

우리가 무엇을 누락 :

우리는이 녹아웃 3.1.0에서 우리를 위해 작동하는 것을 발견?

2

knockout 3.0.0 이상의 새 버전이 있음. checkbox 바인딩 처리기의 업데이트 메서드가 제거되었습니다. 따라서 함수에 click event을 작성하여 checkbox을 클릭 할 때마다 업데이트 메소드를 트리거해야합니다. 다음은 jquery checkboxuniform checkbox으로 변환하는 바인딩 처리기의 예입니다. 누군가가 여기에 모든 하위 항목이 선택하는 경우 중간으로 선택 모든 유형의 확인란 쇼를 가지고 찾고 있다면

ko.bindingHandlers.checkedUniform = 
{ 
    init: function (element, valueAccessor) { 
     ko.bindingHandlers.checked.init(element, valueAccessor); 
     $(element).uniform().on('click', ko.bindingHandlers.checkedUniform.update); 
    }, 
    update: function (element, valueAccessor) 
    { 
     ko.bindingHandlers.checked.update(element, valueAccessor); 
     $.uniform.update($(element)); 
    } 
}; 
+0

유니폼이란 무엇을 의미 할 수 있습니까? –

0

, 당신은 당신이 할 수있는 다음이

ko.bindingHandlers.indeterminateValue = { 
    update: function (element, valueAccessor) { 
     var value = ko.utils.unwrapObservable(valueAccessor()); 
     element.indeterminate = value; 
    } 
}; 

같은 바인딩 간단한을 사용할 수 있습니다 모든 예를 선택한 다음,이

<input type="checkbox" data-bind="checked: selectedAllProduce, indeterminateValue: selectedProduce().length > 0 && selectedProduce().length < produce.length" title="Select all/none"/> 

것처럼 바이올린 그것을 계산 된 관찰 작업을 보여주는 사용 https://jsfiddle.net/deannorth/crqwac12/

관련 문제