2012-03-03 31 views
28

Khi thêm sự kiện thay đổi ràng buộc vào hộp nhập bằng cách sử dụng knockout.js, giá trị cũ được chuyển đến hàm thay đổi khi sự kiện được kích hoạt. Tôi có thể giải quyết vấn đề này bằng cách sử dụng làm mờ. Đây có phải là hành vi dự định không? Ý tưởng có sử dụng sự kiện thay đổi để có giá trị cũ và sau đó sử dụng bộ chọn thông thường để lấy giá trị từ dom? Có vẻ như truy cập trực quan.thay đổi sự kiện hộp đầu vào knockout.js - chuyển giá trị cũ

jsFiddle Example

JavaScript 
---------- 
var data = { 
    saved_value:"1", 
    value_changed: function(data){ 
     alert(data.saved_value()); 
    } 
}; 
var viewModel = ko.mapping.fromJS(data); 
ko.applyBindings(viewModel); 

HTML 
---- 
Current Value:<span data-bind="text:saved_value"></span><br/> 
<input data-bind="event:{change:value_changed},value:saved_value"></input> 

Trả lời

6

Hãy thử sử dụng văn bản và giá trị ràng buộc:

Current Value:<span data-bind="text: saved_value"></span><br/> 
<input data-bind="value: saved_value"></input> 

Và thay đổi JavaScri pt này:

var data = { 
    saved_value: "1"  
}; 

var viewModel = ko.mapping.fromJS(data); 
ko.applyBindings(viewModel);​ 

Dưới đây là một jsFiddle liên quan: http://jsfiddle.net/6zmJs/

Nếu bạn muốn alert() giá trị của saved_value khi nó được cập nhật, bạn có thể sử dụng ko.computed hoặc viewModel.saved_value.subscribe(function(value) { alert(value); }); - mặc dù những không phải là cách duy nhất để làm điều này.

+0

saved_value phải là ko.observable ("1") –

68

Không, đây không phải là cách đúng đắn để làm điều này.

Bạn nhận được giá trị cũ vì saved_value không được cập nhật cho đến khi hộp văn bản bị mất tiêu điểm.

Nếu bạn muốn đẩy giá trị mới trong khi người dùng, sử dụng tùy chọn valueUpdate của đầu vào ràng buộc:

<input data-bind="event: { change: value_changed }, value: saved_value, valueUpdate: 'afterkeydown'" /> 

Tùy chọn valueUpdate mất một tên sự kiện (ví dụ 'KeyUp'). Khi sự kiện đó kích hoạt, giá trị saved_value của bạn sẽ được cập nhật.


Bây giờ, hãy để tôi đề xuất giải pháp thay thế.

Tuy nhiên làm valueUpdate ràng buộc như tôi đã giới thiệu ở trên, nhưng thay vì lắng nghe các sự kiện thay đổi, chỉ cần đăng ký vào quan sát:

<input data-bind="textInput: saved_value" /> 

Sau đó, trong JS:

var viewModel = { 
    saved_value: ko.observable("1"), 
}; 
viewModel.saved_value.subscribe(function (newValue) { 
    alert(data.saved_value()); 
}); 
ko.applyBindings(viewModel); 
+2

tôi phải sử dụng 'afterkeydown', nếu không tôi là một nhân vật muộn. –

+0

Điểm tốt, tôi sẽ cập nhật câu trả lời. –

+0

Có lý do tại sao không sử dụng 'textInput binding'? Tài liệu của KO đề xuất sử dụng 'textInput binding' thay vì' value binding': http://knockoutjs.com/documentation/textinput-binding.html "Mặc dù ràng buộc giá trị cũng có thể thực hiện hai chiều ràng buộc giữa các hộp văn bản và thuộc tính viewmodel, bạn nên sử dụng textInput bất cứ khi nào bạn muốn cập nhật trực tiếp ngay lập tức. " –

10

Nếu bạn đặt tùy chọn 'sự kiện' ở cuối, bạn không cần tùy chọn 'valueUpdate'. Như thế này:

<input data-bind="value: saved_value, event: { change: value_changed }" />

Cũng lưu ý rằng khi bạn sử dụng đăng ký với một quan sát được, nó được kích hoạt mỗi khi thay đổi giá trị của bạn. (theo tương tác của người dùng hoặc theo lập trình).

+1

Vậy thứ tự các mục trong "ràng buộc dữ liệu" có liên quan? Có tài liệu ở đâu đó giải thích những quy tắc nào nên được theo sau để tôi có thể tránh được các gotchas trong tương lai không? – Ominus

+1

Có, thứ tự quan trọng, chúng xảy ra theo thứ tự từ trái sang phải (tùy thuộc vào chức năng của chúng) – pilavdzice

+0

Chỉ cần ném cái này ra ngoài, nhưng nếu bạn đang sử dụng liên kết "đã kiểm tra", sử dụng sự kiện ở cuối * không * làm cho nó đợi cho đến khi dữ liệu thay đổi. Nó vẫn sẽ sử dụng giá trị cũ. – Andrew

3

Hãy thử điều này trong các dữ liệu ràng buộc xử lý ghi sự kiện, sau khi xử lý giá trị và không trước:

<input data-bind="value: property, event:{ change: doSomething}" /> 
+0

Đây chính là vấn đề của tôi. Cảm ơn bạn! –

Các vấn đề liên quan