自学内容网 自学内容网

OpenLayers基础教程——WebGLPoints设置不同图标样式的方法

1、前言

OpenLayers中,WebGLPointsVectorLayer设置不同图标样式的方法有所不同。本文就来介绍一下如何在WebGLPoints图层中根据要素类型设置不同的图标样式。

2、ol.layer.Vector的实现方法

ol.layer.Vector设置不同图标的样式很简单,直接上代码:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <style>
        html,
        body,
        #map {
            width: 100%;
            height: 100%;
            margin: 0;
            padding: 0;
        }
    </style>
    <link rel="stylesheet" href="libs/ol/ol.css" />
    <script src="libs/ol/ol.js"></script>
</head>
<body>
    <div id="map"></div>

    <script>
        var vectorLayer = new ol.layer.Vector({
            source: new ol.source.Vector({
                features: [
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.00, 30.00], "EPSG:4326", "EPSG:3857")),
                        type: 1
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.02, 30.02], "EPSG:4326", "EPSG:3857")),
                        type: 2
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.04, 30.04], "EPSG:4326", "EPSG:3857")),
                        type: 3
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.06, 30.06], "EPSG:4326", "EPSG:3857")),
                        type: 4
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.08, 30.08], "EPSG:4326", "EPSG:3857")),
                        type: 5
                    })
                ]
            }),
            style: function (feature, resolution) {
                var type = feature.get("type");
                var src = "";
                if (type == 1) {
                    src = "img/1.png";
                } else if (type == 2) {
                    src = "img/2.png";
                } else if (type == 3) {
                    src = "img/3.png";
                } else if (type == 4) {
                    src = "img/4.png";
                } else {
                    src = "img/5.png";
                }
                return new ol.style.Style({
                    image: new ol.style.Icon({
                        src: src
                    })
                });
            }
        })

        // 创建地图
        var map = new ol.Map({
            target: "map",
            layers: [vectorLayer],
            view: new ol.View({
                projection: "EPSG:3857",
                center: ol.proj.transform([120, 30], "EPSG:4326", "EPSG:3857"),
                zoom: 10,
                minZoom: 7,
                maxZoom: 18
            })
        });
    </script>
</body>
</html>

运行结果如下图所示:

在这里插入图片描述

3、ol.layer.WebGLPoints的实现方法

WebGLPoints采用样式表达式的方法来渲染要素,所以很多同志都会想到:用match表达式来做不就行了吗?所以有如下错误代码:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <style>
        html,
        body,
        #map {
            width: 100%;
            height: 100%;
            margin: 0;
            padding: 0;
        }
    </style>
    <link rel="stylesheet" href="libs/ol/ol.css" />
    <script src="libs/ol/ol.js"></script>
</head>
<body>
    <div id="map"></div>

    <script>
        var vectorLayer = new ol.layer.WebGLPoints({
            source: new ol.source.Vector({
                features: [
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.00, 30.00], "EPSG:4326", "EPSG:3857")),
                        type: 1
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.02, 30.02], "EPSG:4326", "EPSG:3857")),
                        type: 2
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.04, 30.04], "EPSG:4326", "EPSG:3857")),
                        type: 3
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.06, 30.06], "EPSG:4326", "EPSG:3857")),
                        type: 4
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.08, 30.08], "EPSG:4326", "EPSG:3857")),
                        type: 5
                    })
                ]
            }),
            style: {
                symbol: {
                    symbolType: "image",
                    src: [
                        "match", 
                        ["get", "type"],
                        1, "img/1.png",
                        2, "img/2.png",
                        3, "img/3.png",
                        4, "img/4.png",
                        5, "img/5.png",
                        "img/1.png",
                    ],
                    size: [32, 32]
                }
            }
        })

        // 创建地图
        var map = new ol.Map({
            target: "map",
            layers: [vectorLayer],
            view: new ol.View({
                projection: "EPSG:3857",
                center: ol.proj.transform([120, 30], "EPSG:4326", "EPSG:3857"),
                zoom: 10,
                minZoom: 7,
                maxZoom: 18
            })
        });
    </script>
</body>
</html>

运行结果如下图所示:

在这里插入图片描述
很明显,通过match表达式无法得到我们想要的结果,此时就需要使用textureCoord属性了。之前的代码使用532x32图片来分别表示不同的要素类型,如下图所示:

在这里插入图片描述
现在将这5张图片拼接成1张大图,这张大图的尺寸就是160x32,如下图所示:

在这里插入图片描述
1个图标占据的位置可表示为:[0/160, 0/32, 32/160, 32/32],也就是[0.0, 0.0, 0.2, 1.0],以此类推,这5个图标占据的位置如下所示:

第1个图标:[0.0, 0.0, 0.2, 1.0]
第2个图标:[0.2, 0.0, 0.4, 1.0]
第3个图标:[0.4, 0.0, 0.6, 1.0]
第4个图标:[0.6, 0.0, 0.8, 1.0]
第5个图标:[0.8, 0.0, 1.0, 1.0]

然后使用textureCoord属性,代码如下:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <style>
        html,
        body,
        #map {
            width: 100%;
            height: 100%;
            margin: 0;
            padding: 0;
        }
    </style>
    <link rel="stylesheet" href="libs/ol/ol.css" />
    <script src="libs/ol/ol.js"></script>
</head>
<body>
    <div id="map"></div>

    <script>
        var vectorLayer = new ol.layer.WebGLPoints({
            source: new ol.source.Vector({
                features: [
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.00, 30.00], "EPSG:4326", "EPSG:3857")),
                        type: 1
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.02, 30.02], "EPSG:4326", "EPSG:3857")),
                        type: 2
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.04, 30.04], "EPSG:4326", "EPSG:3857")),
                        type: 3
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.06, 30.06], "EPSG:4326", "EPSG:3857")),
                        type: 4
                    }),
                    new ol.Feature({
                        geometry: new ol.geom.Point(ol.proj.transform([120.08, 30.08], "EPSG:4326", "EPSG:3857")),
                        type: 5
                    })
                ]
            }),
            style: {
                symbol: {
                    symbolType: "image",
                    src: "img/big.png",
                    size: [32, 32],
                    textureCoord: [
                        "match",
                        ["get", "type"],
                        1, [0.0, 0.0, 0.2, 1.0],
                        2, [0.2, 0.0, 0.4, 1.0],
                        3, [0.4, 0.0, 0.6, 1.0],
                        4, [0.6, 0.0, 0.8, 1.0],
                        5, [0.8, 0.0, 1.0, 1.0],
                        [0.0, 0.0, 0.2, 1.0]
                    ],
                }
            }
        })

        // 创建地图
        var map = new ol.Map({
            target: "map",
            layers: [vectorLayer],
            view: new ol.View({
                projection: "EPSG:3857",
                center: ol.proj.transform([120, 30], "EPSG:4326", "EPSG:3857"),
                zoom: 10,
                minZoom: 7,
                maxZoom: 18
            })
        });
    </script>
</body>
</html>

运行结果如下图所示:

在这里插入图片描述

4、结语

本文主要介绍了WebGLPoints图层中设置不同图标样式的方法。本质上就是把小图标合成一张大图,最后按照纹理位置读取即可。


原文地址:https://blog.csdn.net/HerryDong/article/details/144403637

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!