使用JSON和过滤器管理的JavaScript过滤

分享于 

6分钟阅读

Web开发

  繁體 雙語
xFilter.jpg

介绍

本文将解释一个简单的客户端过滤框架,它可以在任何页面中实现以获得easy-to-use过滤器。

Background

我寻找一些可以帮助我创建应用程序的控件。 最适合我的控件是 jqGrid - 一个 jQuery插件。 jqGrid以表格格式显示JSON数据源,以及过滤和排序。 为此,我们必须使用JSON格式定义一个列模型( 请参阅示例) - 当然:

colModel:[
 {name:'id',index:'id', width:60, sorttype:"int"},
 {name:'name',index:'name', width:100, editable:true},
 {name:'note',index:'note', width:150, sortable:false} 
 ]

使用代码

不幸的是,jqGrid的过滤能力并不像我所需要的那样复杂。 过滤器是具有以下格式类型的JSON对象:

{ "groupOp": "and",
 "rules": [
 { "field": "name", "op": "eq", "data": "Romania" }, 
 { "field": "id", "op": "le", "data": "1"}
 ]
}

它基本上是一组使用逻辑运算符组合在一起的规则: " OR"或者或或者" AND"。对于简单的搜索,这个过滤器可以能是足够的,但任何更复杂的都需要。 让我们向这个结构添加一个 array 组。 现在我们有了我们需要的树结构,并且仍然维持对普通jqGrid过滤器的支持。 假设我们需要一个这样的过滤器:

(name == "John" AND age> 30) OR (name == "Doe" AND age <30) OR name == "Joe"

请注意,在组和组之间,我们必须具有相同的逻辑运算符,否则必须将它们隔离。 上面 公式将映射到:

{ "groupOp": "or",
 "groups": [
 { "groupOp": "AND", 
 "rules": [
 { "field": "name", "op": "eq", "data": "John" },
 { "field": "age", "op": "gt", "data": "30" }
 ]
 },
 { "groupOp": "AND", 
 "rules": [
 { "field": "name", "op": "eq", "data": "Doe" },
 { "field": "age", "op": "lt", "data": "30" }
 ]
 }
 ]
 "rules": [{ "field": "name", "op": "eq", "data": "Joe" }]
}

就像我所说,我们有两种类型的运算符: 组运算符和规则运算符。 唯一的组运算符是" OR"和" AND"。 作为规则运算符,我们有: eq ( 等于),( 不同于),( 低于),等等 以及字符串运算符: 通过使用函数,可以轻松地将 上面 ( 包含),( 开头),等等 转换为接近JavaScript的语法:

(eq(item.name, "John") && gt(item.age, "30")) || 
 (eq(item.name, "Doe") && lt(item.age, "30")) || eq(item.name, "Joe")

请注意,所有实体字段都带有" item."前缀。 让我们定义必要的JavaScript函数:

function eq(d1, d2) { return d1 == d2; }function lt(d1, d2) { return d1 <d2; }function gt(d1, d2) { return d1> d2; }

现在我们可以循环遍历JSON对象并评估 上面 公式。

var jsonItems = [
 {"name": "John", "age": "18"},
 {"name": "Amanda", "age": "21"},
 {"name": "Dave", "age": "31"}
];var expression = '(eq(item.name,"John") && gt(item.age,"30")) || 
 (eq(item.name,"Doe") && lt(item.age,"30")) || eq(item.name,"Joe")';var newJsonItems = [];for(var index = 0; index <jsonItems.length; index++){
 var item = jsonItems[index]; // define the item that will be evaluatedif(eval(expression) == true){
 newJsonItems.push(item);
 }
}

目前我们有逻辑,但是我们需要一个网络用户界面来过滤过滤器。 幸运的是,我编写了一个JS类: 使用 xFilter ( 查看附件),你只需要提供DOM父元素和列的模型。

var colModel = [
 { "name": "id"},// we only need this field, jqGrid requires the rest { "name": "name"},
 { "name": "note"}
];var items = [
 { "name": "Romania", "id": "1", "note": "ro" },
 { "name": "Franta", "id": "2", "note": "fr"},
 { "name": "Anglia", "id": "3", "note": "uk"},
 { "name": "Italia", "id": "4", "note": "it" },
 { "name": "Germania", "id": "5", "note": "ge" }
];var f = new xFilter(document.getElementById("fil"),
{
 columns: colModel,
 onchange: function() {
 document.getElementById("message").innerHTML = 
 this.toUserFriendlyString();
 var resItems = f.Apply(items);
 var s = "";
 for (var i = 0; i <resItems.length; i++) {
 s += "," + resItems[i].name;
 }
 document.getElementById("message").innerHTML = s;
 }
});

可以看到,只要发生对过滤器的更改,类就会触发" onchange"事件。 当然,可以使用" Apply"- 它的逻辑上的方法来过滤JSON对象。

结束语

希望你喜欢这个。下一篇文章将在服务器端( C# ) 上使用这个模型,我们创建的过滤器将成为LINQ实现。

链接

第 2部分在创建动态过滤机制


JAVA  Javascript  MAN  
相关文章