OpenLayers学习3-BaseTypes对基础类型对象的扩展

OpenLayers里从新封装了原生的基本对象, 比如String对象,
设计上, 解决了原生方法不够使的问题, 也没破坏基本对象的prototype, 不会和其他类库冲突

这些类就像Util工具, 没什么上下文的状态,
调用时候就直接调用: OpenLayers.String.startsWith(AAA,BBB) 通过处理拿到结果完事

OpenLayers这块的代码比较朴实, 没用那么多花招, 拣几个说说:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
//1.String
//其实这块用正则用的不多, 这儿用了个链式的正则处理
trim: function(str) {
return str.replace(/^\s\s*/, '').replace(/\s\s*$/, '');
},
//这个format就是把${token}U最终换成context["token"]的功能
//有种模版替换的思想, 将XXX模板化的成为==>YYY
tokenRegEx: /\$\{([\w.]+?)\}/g,
format: function(template, context, args) {
return template.replace(OpenLayers.String.tokenRegEx, replacer);
}
//2.Number
/*
num {Float}
dec {Integer} 数字的小数部分四舍五入到指定的位数. 默认为 0. 设置为null值时小数部分不变.
tsep {String} 千位分隔符. 默认值为 “,”.
dsep {String} 小数点分隔符. 默认值为 “.”.
*/
format: function(num, dec, tsep, dsep) {
//预防性处理
dec = (typeof dec != "undefined") ? dec : 0;
tsep = (typeof tsep != "undefined") ? tsep :
OpenLayers.Number.thousandsSeparator;
dsep = (typeof dsep != "undefined") ? dsep :
OpenLayers.Number.decimalSeparator;
//四舍五入,按dec去toFix
if (dec != null) {
num = parseFloat(num.toFixed(dec));
}
//按小数点切分(123.456).toString().split("."); ==> ["123", "456"]
var parts = num.toString().split(".");
if (parts.length == 1 && dec == null) {
// integer where we do not want to touch the decimals
dec = 0;
}
//切分后的int部分
var integer = parts[0];
if (tsep) {
var thousands = /(-?[0-9]+)([0-9]{3})/; //0-9三位
while(thousands.test(integer)) {
//循环写入千分位切分符
integer = integer.replace(thousands, "$1" + tsep + "$2");
}
}
var str;
if (dec == 0) {
str = integer;//就是整型
} else {
//rem是小数部分
var rem = parts.length > 1 ? parts[1] : "0";
if (dec != null) {
//用于产生末尾的补零
//new Array(指定长度 - 实际小数位长度+1)就是最后还差多少个0, 没初始化join("0"), 在最后补齐
rem = rem + new Array(dec - rem.length + 1).join("0");
}
//整型 + 小数点 + 小数部分
str = integer + dsep + rem;
}
return str;
},
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
//3.Function
//function就开始有意思了
OpenLayers.Function = {
/**
* APIFunction: bind
* 往一个对象上绑定一个function. 通过闭包改变this
*
* Parameters:
* func - {Function} 传入的 function.
* object - {Object} 要绑定function的object(this指向此对象).
*
* Returns:
* {Function} 'this'指向object的闭包
*/
bind: function(func, object) {
//将第二个参数往后的参数转成数组
//相当于调用(类数组) arguments.slice(2)
var args = Array.prototype.slice.apply(arguments, [2]);
return function() {
// 这个数组里前边是是第二个参数之后的参数
// 后边接全部传参的数组
var newArgs = args.concat(
Array.prototype.slice.apply(arguments, [0])
);
//闭包: object.func(参数是newArgs[])
return func.apply(object, newArgs);
};
},
/**
* APIFunction: bindAsEventListener
* 往一个对象上绑定一个function. 传给func的第一个参数将会是event对象
*
* Parameters:
* func - {Function} 接收event的函数.
* object - {Object} this所指的对象.
*
* Returns:
* {Function}
*/
bindAsEventListener: function(func, object) {
return function(event) {
//相当于调用 object.func(event || window.event)
return func.call(object, event || window.event);
};
},

3.json数据图层

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
map = new OpenLayers.Map({
div: "map",
maxExtent: new OpenLayers.Bounds(
1549471.9221, 6403610.94, 1550001.32545, 6404015.8
)
});
var vectors = new OpenLayers.Layer.Vector("Lines", {
strategies: [new OpenLayers.Strategy.Fixed()],
protocol: new OpenLayers.Protocol.HTTP({
url: "data/roads.json",//Ajax请求本地的json文件,chrome默认不允许 需要修改下
format: new OpenLayers.Format.GeoJSON()//格式是GeoJSON
}),
//styleMap: styles 可以单独制定线的样式等等,默认是黄的
});
map.addLayer(vectors);//json图层
map.zoomToMaxExtent();

4.多个图层及切换

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
//4.Array就一个函数, 补充原生的Array.prototype.filter
OpenLayers.Array = {
/**
* APIMethod: filter
* 检查原生Array对象里有没有filter方法, 没有的话自己实现一个
*
* Parameters:
* array - {Array} 被筛选的数据源数组, 此数组不变
* callback - {Function} 每个元素都会调用这个回调函数, 如果此回调返回true 则会将此元素加入结果集
* 此回调接受3个参数(array[idx],idx,array)
* 如果有caller参数, 则this对象指向caller后调用callback
* caller - {Object} 回调调用时, this指向此caller
*
* Returns:
* {Array} 回调新数组, 由返回true的元素组成
*/
filter: function(array, callback, caller) {
var selected = [];
if (Array.prototype.filter) {
selected = array.filter(callback, caller);//原生的
} else {
var len = array.length;
if (typeof callback != "function") {
throw new TypeError();//回调不是function 抛TypeError, 比我管用的判断不是function后 跳过不执行好...
}
for(var i=0; i<len; i++) {
if (i in array) {//这的in应该是针对类数组的筛选, 比如过滤"length"属性
var val = array[i];
//相当于caller.callback(val, i, array)
if (callback.call(caller, val, i, array)) {
selected.push(val);//筛选结果
}
}
}
}
return selected;
}
};