2015-10-20 50 views
0

我有一个产品和服务列表,这些列表在knockout中被输入到observables中。目前,它在用户从流派列表中选择并且敲除返回在逗号分隔字段中包含该流派的产品列表。如何从筛选值中选择类型逗号分隔值仅包含选择的内容

每个产品得到送入淘汰赛,因为这:

+-------------------+------------------------------------+ 
|  name  |    genre    | 
+-------------------+------------------------------------+ 
| Star Wars   | Sci-Fi, Action, Adventure, Blueray | 
| Lord of the Rings | Fantasy, Fiction, Adventure, DVD | 
| Matrix   | Sci-Fi, Fantasy, Blueray   | 
+-------------------+------------------------------------+ 

和我的复选框列表是因为这在视图:

<div class="col-md-3 filterlist" > 
<form name="specialties" action="" method="POST"> 
    <strong>Specialties</strong> 
    <ul class="categorySearchList"> 


      <li><label><input type="checkbox" name="" value="Sci-Fi" data- bind="checked:filterValues" /> Sci-Fi</label></li> 
      <li><label><input type="checkbox" name="" value="Action" data-bind="checked:filterValues" /> Action</label></li> 
      <li><label><input type="checkbox" name="" value="Adventure" data-bind="checked:filterValues" /> Adventure</label></li> 
      <li><label><input type="checkbox" name="" value="Fantasy" data-bind="checked:filterValues" /> Fantasy</label></li> 
      <li><label><input type="checkbox" name="" value="Fiction" data-bind="checked:filterValues" /> Fiction</label></li> 

    </ul> 
    <hr /> 
    <strong>Type</strong> 
    <ul class="categorySearchList"> 

      <li><label><input type="checkbox" name="" value="DVD" data-bind="checked:filterValues " /> DVD</label></li> 
      <li><label><input type="checkbox" name="" value="Bluray" data-bind="checked:filterValues " /> Bluray</label></li> 

    </ul> 
</form> 
</div> 
<div></div> 
<div class="span8" style="float: left;"> 

<div data-bind="foreach: filterProducts"> 

    <div class="wrapp2 span2" style="margin: 12px 5px;"> 
     <p> 
      <img src="~/Content/images/image.jpg" style="width: 100%;" alt="Product Name"/> 
      <strong data-bind="text: genre"></strong>&nbsp;strong data-bind="text: name"></strong> 
     </p> 
    </div> 
</div> 

...

和所以在哪个输出端上:

☐科幻

☐行动

☐冒险

☐幻想

☐小说


☐DVD

☐蓝光

我淘汰赛的脚本是这样的:

function Program(course) { 
this.name = course.Value; 
this.genre = course.Text; 
} 


function ProgramModel() { 

var self = this; 
self.isLoading = ko.observable(true); 
self.products = ko.observableArray(); 
self.filterValues = ko.observableArray(); 

$.getJSON("/extra/api/api/GetProductProgramList", function (data) { 
    ko.utils.arrayForEach(data, function (course) { 
     self.products.push(new Program(course)); 

    }); 
    self.isLoading(false); 
}); 

self.filterProducts = ko.computed(function() { 
    return ko.utils.arrayFilter(self.products(), 
    function (product) { 
      var genreValues = product.genre.split(","); 
      var match = ko.utils.arrayFirst(genreValues, 
       function (genre) { 
        return self.filterValues.indexOf(genre.trim()) > -1; 
       }); 
     if (match) { 
      return match; 
     } 
    }); 
}); 

self.filter = function (genre) { 
    self.currentFilter(genre); 
}; 


} 

ko.applyBindings(new ProgramModel()); 

所以它的工作原理当用户从列表中选择一个流派,它显示。例如,用户选择科幻和星球大战和矩阵显示,但是当用户选择科幻和DVD时,所有三个出现。当真的什么都不应该出现时,因为那里没有科幻电影。

所以我想让它分裂流派,只选择被选中的ANDS。就像我选择Adventure AND Blueray一样;只有星球大战应该出现。

任何帮助,将不胜感激!

+0

你能提供完整的HTML绑定标记吗? –

+0

您需要一个'selectedProducts'的observableArray,您可以使用它来代替计算中的'products'。 –

回答

1
self.filterProducts = ko.computed(function() { 
    return ko.utils.arrayFilter(self.products(), 
    function (product) { 
      var genreValues = product.genre.split(","); 
      var matches = ko.utils.arrayFilter(genreValues, function (genre) { 
       return self.filterValues.indexOf(genre.trim()) >= 0; 
      }); 
      return matches.length == self.filterValues().length; 
    }); 
}); 

想通了。它就像使用filterValues返回匹配长度一样简单!

这里是工作fiddle

0
function (product) { 
    var genres = ko.utils.arrayForEach(product.genre.split(","), 
     function(genre) { return genre.trim();}); 
    var filters = self.filterValues(); 
    for (var i = 0; i < filters.length; ++i) { 
     if (genres.indexOf(filters[i].trim()) < 0) { 
      return false; 
     } 
    } 
    return true; 
} 

如果我明白发生了什么,可能会工作正常。基本上,您需要检查每个过滤器是否存在于产品的流派列表中,而不是仅仅检查是否存在。