knockout.js
바인딩
수색…
통사론
-
<!-- ko if:myObservable --><!-- /ko -->
-
<i data-bind="if:myObservable"></i>
비고
바인딩이란 무엇입니까?
본질적으로 바인딩 또는 데이터 바인딩은 ViewModel을 뷰 (템플릿)에 링크하는 방법이며 그 반대의 경우도 마찬가지입니다. KnockoutJS는 양방향 데이터 바인딩을 사용합니다. 이는 ViewModel에 대한 변경 사항이 View에 영향을 미치고 View에 대한 변경 사항이 ViewModel에 영향을 줄 수 있음을 의미합니다.
후드 (간략한 개요)
바인딩은 특정 작업을 해결할 수있는 플러그인 (스크립트)입니다. 이 작업은 ViewModel에 따라 마크 업 (html)을 변경하는 것보다 더 자주 발생합니다.
예를 들어 text
바인딩을 사용하면 텍스트를 표시하고 ViewModel이 변경 될 때마다 텍스트를 동적으로 변경할 수 있습니다.
KnockoutJS에는 많은 강력한 바인딩이 있으며 사용자 정의 바인딩으로 확장 할 수 있습니다.
가장 중요한 바인딩은 마법 같은 것이 아니며, 일련의 규칙에 따라 작동하며 바인딩이 무엇인지, 어떤 매개 변수가 필요한지 또는 바인딩의 소스 코드를 참조 할 수있는 뷰를 업데이트 할시기를 알 수 없습니다.
사용자 정의 바인딩의 다음 예제를 고려하십시오.
ko.bindingHandlers.debug = {
init: function (element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {
ko.computed(function () {
var value = ko.unwrap(valueAccessor());
console.log({
value: value,
viewModel: viewModel,
bindingContext: bindingContext
});
}, null, { disposeWhenNodeIsRemoved: element });
}
};
- 바인딩에는 이름 -
debug
있으므로 다음과 같이 사용할 수 있습니다.
data-bind="debug: 'foo'"
-
init
메소드는 바인딩이 시작될 때 한 번 호출됩니다. 나머지 업데이트는element
가 제거 될 때 삭제되는 익명 계산에 의해 처리됩니다. - 바인딩은 여러 가지를 콘솔에 출력합니다.이 예제에서 전달 된 값은
foo
(이 값은ko.unwrap
메소드가 읽기 위해 사용되기 때문에 관찰 가능합니다), 현재 viewModel 및 bindingContext입니다. - 전달 된 값이 변경 될 때마다 바인딩은 업데이트 된 정보를 콘솔에 인쇄합니다.
- 이 바인딩은
ko.virtualElements.allowedBindings.debug
플래그가 true로 설정되지 않았ko.virtualElements.allowedBindings.debug
실제 요소에서만 가상 요소 (HTML 주석)와 함께 사용할 수 없습니다.
괄호 사용시기
추가 플러그인이 없으면, KnockoutJS는 ViewModel에서 관찰 할 수 있는 속성 (일반 observable
하지만 computed
, pureComputed
, observableArray
등)에 대한 실시간 View 업데이트 만 갖습니다. observable은 다음과 같이 생성됩니다 :
var vm = { name: ko.observable("John") };
이 경우, vm.name
은 두 개의 별도 "모드"가있는 함수 입니다.
- Getter :
vm.name()
은 인수없이 현재 값을 가져옵니다. - Setter :
vm.name("Johnnyboy")
은 인수를 사용하여 새 값을 설정합니다.
내장 된 데이터 바인딩에서는 항상 getter 양식을 사용할 수 있으며 실제로는 괄호를 생략 할 수 있으며 바인딩은 효과적으로이를 "추가"합니다. 그래서 이것들은 같습니다 :
<p data-bind="text: name"></p> ... will work
<p data-bind="text: name()"></p> ... works too
그러나 이것은 실패 할 것이다 :
<p data-bind="text: 'Hello, ' + name + '!'"></p> ... FAILS!
값 비교를 포함하여 값을 데이터 바인딩에 전달하기 전에 무언가를하고 싶다면 모든 관측 값에 대한 값을 적절하게 "얻어야"합니다. 예를 들면 다음과 같습니다.
<p data-bind="text: 'Hello, ' + name() + '!'"></p> ... works
자세한 내용은 Q & A 를 참조하십시오.
/ ifnot
if
바인딩을 사용하여 노드의 하위 요소를 만들어야하는지 여부를 결정할 수 있습니다.
<div class="product-info">
<h2> Product1 </h2>
<img src="../products/product1.jpg"/>
<span data-bind="if:featured">
<span class="featured"></span>
</span>
<span data-bind="ifnot:inStock">
<span class="out-of-stock"></span>
</span>
</div>
<script>
ko.applyBindings({
product: {
featured: ko.observable(true),
inStock: ko.observable(false)
}
});
</script>
if
바인딩의 ifnot
은 ifnot
이 ifnot
<div data-bind="ifnot: someProperty">...</div>
~에 해당합니다.
<div data-bind="if: !someProperty()">...</div>
때로는 컨테이너를 만들 필요없이 요소의 존재를 제어하지 않을 것입니다 (일반적으로 <li>
<select>
내부의 <select>
<ul>
또는 <option>
요소에있는 요소)
녹아웃은 다음과 같은 주석 태그를 기반으로 컨테이너없는 제어 흐름 구문을 사용하여이를 가능하게합니다.
<select>
<option value="0">fixed option</option>
<!-- ko if: featured-->
<option value="1">featured option</option>
<!-- /ko -->
</select>
각각
다른 언어에서 사용되는 리피터와 유사합니다. 이 바인딩을 사용하면 배열의 각 항목에 대해 html 블록을 복제 할 수 있습니다.
<div data-bind="foreach:contacts">
<div class="contact">
<h2 data-bind="text:name">
<p data-bind="text:info">
</div>
</div>
<script type="text/javascript">
var contactViewModel = function (data) {
this.name = ko.observable(data.name);
this.info = ko.observable(data.info);
};
ko.applyBindings({
contacts: [
new contactViewModel({name:'Erik', info:'[email protected]'}),
new contactViewModel({name:'Audrey', info:'[email protected]'})
]
});
</script>
우리가 컨텍스트를 순환 할 때 컨텍스트는 배열 내의 항목이되며,이 경우 contactViewModel
의 인스턴스가 contactViewModel
. foreach
내에서 우리는 또한
-
$parent
-이 바인딩을 작성한 뷰 모델 -
$root
- 루트 뷰 모델 (부모 일 수도 있음) -
$data
-이 배열의 인덱스에있는 데이터 -
$index
- 렌더링 된 항목의 (관찰 가능한) 0부터 시작하는 인덱스
와
with
바인딩은 바인딩 된 노드 내부의 HTML을 별도의 컨텍스트에 바인딩합니다.
<div data-bind="with: subViewModel">
<p data-bind="text: title"></p>
</div>
with
바인딩은 컨테이너 요소가 적합하지 않을 수도있는 컨테이너 요소없이 사용될 수도 있습니다.
<!-- ko with: subViewModel -->
<p data-bind="text: title"></p>
<!-- /ko -->
var vm = {
subViewModel: ko.observable()
};
// Doesn't throw an error on the `text: title`; the `<p>` element
// isn't bound to any context (and even removed from the DOM)
ko.applyBindings(vm);
// Includes the `<p>` element and binds it to our new object
vm.subViewModel({ title: "SubViewModel" });
with
바인딩은 template
이나 foreach
바인딩과 많은 공통점이 있습니다.
명백한
visible
바인딩은 style="display: none;"
을 적용하여 요소를 숨 깁니다 style="display: none;"
바인딩이 거짓으로 평가 될 때
<input type="text" data-bind="textInput: name"> <span class="error" data-bind="visible: isInvalid">Required!</span>
ko.applyBindings(new ViewModel());
function ViewModel(){
var vm = this;
vm.name = ko.observable("test");
vm.isInvalid = ko.computed(function() {
return vm.name().length == 0;
});
}