2014-01-17 66 views
2

我有這樣的自定義綁定,更新可觀察到的與被應用到該元素的聚焦子元素的數據:雙向焦點knockout.js結合

ko.bindingHandlers.selected = 
    init: (element, valueAccessor) -> 
    receiver = valueAccessor() 
    $(element).focusin((event) -> 
     data = ko.dataFor(event.target) 
     receiver(data) 
    ) 

這工作比標準hasFocus更好

<ul data-bind="foreach: items, selected: selectedItem"> 
    <li><a href="#" data-bind="text: name"></a></li> 
</ul> 
<p data-bind="with: selectedItem"> 
    Selected: <span data-bind="text: name"></span> 
</p> 

現在我想使這是一個雙向綁定,這樣我可以從我的腳本改變selectedItem:對於使用情況,我想在頁面的其他部分,顯示關於關注項目的信息結合代碼,並使th e以$.focus()爲重點的正確列表元素。任何想法如何擴展綁定工作在兩個方面?

我意識到我可能需要使用「控制後代綁定」方法,並且不能將綁定應用於與綁定相同的元素,但這很好。我遇到的問題是,當調用更新函數時,子元素似乎沒有被綁定(dataFor返回未定義)。

+0

你可以發表你的意見嗎?你可以發表你想要達到的目標嗎? –

+0

試試這個:http://jsfiddle.net/ptWxF/2/它在普通的瀏覽器中不能很好地工作,但是這是一個帶有空間導航的平臺,其中重點非常重要。 – Ropez

+0

另一個更新,一些樣式http://jsfiddle.net/ptWxF/3/ – Ropez

回答

1

您可以在update功能通過後代元素走路,使用ko.dataFor檢查要集中哪個元素:

update: (element, valueAccessor) -> 
    receiver = valueAccessor() 
    item = receiver() 
    $(element).find("*").each((index, elem) ->  
     if (item == ko.dataFor(elem)) 
     $(elem).focus() 
    ) 

演示JSFiddle

+0

存在潛在的問題,例如找到與項目相對應的元素,但不是可聚焦,隱藏等,但總體思路是有效的。我希望淘汰賽有一些與dataFor相反的東西,但我認爲這是不可能的。 – Ropez

0

我不知道你決定創建一個自定義綁定,以找出集合中的選定項目並將其存儲在可觀察對象中?

你可以簡單地捕捉事件,並找出所選擇的項目:

var data = [ 
    { "Id" : 0, "Name" : "Item0" }, 
    { "Id" : 1, "Name" : "Item1" }, 
    { "Id" : 2, "Name" : "Item2" }, 
    { "Id" : 3, "Name" : "Item3" }, 
    { "Id" : 4, "Name" : "Item4" }, 
    { "Id" : 5, "Name" : "Item5" }, 
    { "Id" : 6, "Name" : "Item6" }, 
    { "Id" : 7, "Name" : "Item7" } 
] 

function vm(){ 
    var self = this; 
    self.items = ko.observableArray(data); 
    self.selectedItem = ko.observable(); 
    self.selectItem = function(item){ 
     self.selectedItem(item); 
    } 
    self.select3rd = function(){ 
     self.selectedItem(self.items()[2]); 
    } 
} 

ko.applyBindings(new vm()); 

HTML:

<ul data-bind="foreach: items"> 
    <li><a href="#" data-bind="text: Name, event: { focus : $parent.selectItem }, attr: { 'tabindex' : $index }"></a></li> 
</ul> 

<p>Selected item: <span data-bind="text: ko.toJSON(selectedItem)"></span></p> 

<button data-bind="click: select3rd">Select 3rd item</button> 

And the fiddle is here

+0

整個問題的關鍵在於控制和監視瀏覽器的焦點指示器,不處理鼠標事件。 – Ropez

+0

更新爲不使用鼠標事件。所有非webkit瀏覽器在單擊錨時觸發焦點,但webkit需要tabindex來激活它(我認爲這是一個已知的bug) – XGreen

+0

如果您願意,還可以將tabindex更改爲$ index + 1,以便第一個tabindex不爲零 – XGreen