2016-05-15 82 views
3

input控件的value傳遞給視圖模型函數的語法是什麼(假設有一個)?在我的場景中,我不想將輸入的值綁定到viewmodel上的屬性。我只需要對輸入控件中輸入的值進行操作(基本上,我正在遍歷項目集合並過濾掉那些不包含輸入文本的項目)。將輸入元素的值作爲參數傳遞給視圖模型函數

<input data-bind="text: filterText($data), valueUpdate: 'afterkeydown'"> 

我試過filterText($data, value)但淘汰賽試圖尋找在視圖模型value財產。我實際上需要輸入控件的當前值。

這可能嗎?

回答

4

處理此用例的典型方法是使用textInput與調用filterText的綁定值上的訂閱進行綁定。

<input data-bind="textInput: filter"> 

在你的腳本:

filter.subscribe(function(newValue) { 
    filterText(newValue) 
}); 

,您可以簡化爲:

filter.subscribe(filterText); 

但你可能仍然想着這個錯誤。您的過濾列表應該是一個計算引用textInput綁定的filter值來計算過濾列表。

filteredList = ko.pureComputed(function() { 
    // return the list filtered by the bound filter() value 
}, self); 

那麼無論你需要數據的過濾列表,你可以使用filteredList()

0

如果你沒有將屬性綁定到視圖模型,那麼你可以使用jquery/javascript直接在你的視圖模型函數中獲取輸入控件的值。

self.Filter= function() {   
    var filter = $('#textBoxID').val(); 
    //  
} 

這樣,您不需要將值傳遞給您的視圖模型函數參數。

+0

爲什麼投票沒有理由? – pso

+0

這不適用於OP的視圖代碼,它具有「文本」綁定。另外,假設有一個'value'綁定,這個解決方案在技術上是可行的,但它不是慣用的KnockoutJS,完全依賴於KO在內部工作的副作用,並且導致我的經驗中出現問題。 – Jeroen

+0

但是這個人已經聲明「在我的場景中,我不想將輸入的值綁定到視圖模型上的屬性。」我的解決方案適用於他相信的場景。 – pso

1

第一件事是第一件事。您的示例代碼在input節點上使用a text binding,這並不是那麼有用(這意味着從視圖模型到DOM的單向單向綁定,該input的「文本」內容是無意義的)。鑑於目前的valueUpdate綁定你可能意味着the value binding?請注意,the textInput binding是在現代版本的KnockoutJS中結合這兩者的方式。

至於你的實際問題,重要的背景缺失:爲什麼你(想你)想要做到這一點?根據具體情況,解決方案會有所不同,或者甚至可能會有XY-problem

無論如何,要答案。

選項1
嘗試仍然回答具體問題,我第二@JohnnyHK's answer您觀察到的是一個可能的解決方案編寫.subscribe的。

選項2
另一種可能的解決方案十分相似的那一個,而是試圖滿足「我不感興趣輸入的值」的一部分,我建議使用只讀計算觀察到:

function Root() { 
 
    var self = this; 
 
    
 
    self.filter = ko.computed({ 
 
    read: function() { return ""; }, // <-- not recommended, read context! 
 
    write: function(newValue) { 
 
     // You're free to discard the newValue <-- not recommended, read context! 
 
     alert("Input has been changed."); 
 
    } 
 
    }); 
 
} 
 

 
ko.applyBindings(new Root());
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.4.0/knockout-min.js"></script> 
 
<input data-bind="textInput: filter">

現在,這明確地丟棄在寫入位newValue(根據您的要求),因此也公頃看起來很奇怪read功能。 我不建議這個,而是建議使用一個私有變量,支持可觀察的讀取和寫入。實際上,這會使該選項等同於其他答案中的第一個選項。

一個有趣的注意,雖然,你的問題的關於「聚集」和過濾輸入比特:如果你看一下the docs from writeable computeds你會發現,接受用戶輸入或沒有,如果滿足一定條件其實用例爲了這。

選項3
我建議什麼,雖然,如果我改一下你的要求一點:

你怎麼到inputvalue變化與慣用KnockoutJS反應過來的時候你的行動不會關心實際的value

要編寫與DOM的自定義交互,有custom binding handlers。你可以有一個根本不使用ViewModel,或者有一個可觀察的。

選項3.A

ko.bindingHandlers["opacitor"] = { 
 
    init: function(element, valueAccessor, allBindings, viewModel, bindingContext) { 
 
    $(element).on("keydown", function() { 
 
     $(this).animate({ opacity: 0.05 }, 1000, function() { $(this).animate({ opacity: 1.0 }, 1000); }); 
 
    }); 
 
    } 
 
} 
 

 
ko.applyBindings({});
input { background-color: gold; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> 
 
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.4.0/knockout-min.js"></script> 
 

 
<input data-bind="opacitor">

選項3.B
或者說確實使用視圖模型的第二個選項:

ko.bindingHandlers["opacitor"] = { 
 
    init: function(element, valueAccessor, allBindings, viewModel, bindingContext) { 
 
    $(element).on("keydown", function() { 
 
     var speed = ko.utils.unwrapObservable(valueAccessor)(); 
 
     $(this).animate({ opacity: 0.05 }, speed, function() { $(this).animate({ opacity: 1.0 }, speed); }); 
 
    }); 
 
    } 
 
} 
 

 
// speed1 and speed2 could also be observables 
 
ko.applyBindings({ speed1: 500, speed2: 2000 });
input { background-color: gold; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> 
 
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.4.0/knockout-min.js"></script> 
 

 
<input data-bind="opacitor: speed1"> 
 
<input data-bind="opacitor: speed2">

選項3A和3B的缺點是您需要編寫自定義事件處理邏輯。如果你有一個在the textInput source from KO偷看你會發現它是不平凡正確處理這些東西跨瀏覽器。所以使用選項1或2可能仍然更好(即使「你不感興趣」,即使你有一些視圖模型交互)。

選項4
使用the event binding。這與選項3具有相同的缺點,但可能是一個直接的解決方案。這裏有一個例子:

function Root(){ 
 
    var self = this; 
 
    self.myFn = function(data, element) { 
 
    console.log(element.target.value); 
 
    return true; 
 
    }; 
 
} 
 

 
ko.applyBindings(new Root());
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.4.0/knockout-min.js"></script> 
 
<input data-bind="event: { keyup: myFn }">

一個微妙的變化,你會在這最後一個看到的,我想結束一個問題:你其實沒有this issue,你確實需要新的價值,因此不應該看afterkeydown,但對於不同的事件?

1

使用$ element.value來訪問輸入的值。

相關問題