当我们遇到问题的时候改如何解决

作者: 牛老师讲GIS | 来源:发表于2017-10-26 10:54 被阅读111次

本文不讲技术,不撸代码,只讲思路。

一、问题

在Openlayers中展示风速风向图,共分为以下两个阶段:

加载PNG图片→加载SVG图片

二、解决

1、加载PNG图片

问题
在Openlayer3中直接加载PNG图片,在API中提供了ImageStatic可以将图片展示出来,但是如何设置图片的imageExtent让图片能够在地图的正确位置展示成了问题的关键。

解决
首先,看到官方的demo里面有个加载ImageStatic的例子,于是就看了一下,官方的例子是通过proj定义了图片的坐标,这样通过坐标转换的方式将静态图片叠加到了地图上。(此过程,我的理解遥感里面做影像的纠正的原理类似。)

有了上面代码的思路,我就想如果我的输出的图片是按照地图的坐标输出的话是不是就可以直接叠加上去而不用做图片的投影了。接下来,就在Arcmap里面打开了一个tif数据,将其直接通过Export Data导出为PNG,并查看其属性获取到图象的四至。

导出图片 设置输出格式为PNG 获取图片四至信息

再在代码里面根据输出的PNG和四至信息做测试,哎,思路是对的,能够完美的叠加到地图上。

完美与地图叠加

实现代码

var bounds = [63.9796331669,14.7451916725, 140.181255914,55.4673388687];
var projection = new ol.proj.Projection({
    code: 'EPSG:4326',
    units: 'degrees'
});
var image = new ol.layer.Image({
  source: new ol.source.ImageStatic({
    url: "img/china.png",
    imageExtent: bounds
  })
});

有了上面的测试,终于明白了OL3中StaticImage的加载逻辑。

2、加载SVG图片

由于是PNG图片,在地图放大后会有马赛克现象,特别影像视觉效果,所以为了让展示的效果更加美观,所以就考虑将PNG图片换乘SVG图片。换完之后,首先是在Leaflet中做的测试,比PNG的效果好很多。可当我将SVGyizhi到Openlayers中的时候傻眼了,效果如下:

加载PNG 加载SVG

这个不是臣妾想要的,我想要高清,不要模糊!!!

所以,就开始了研究如何展示SVG。百度、谷歌、必应了一圈后,发现Openlayers的开发者给大家的回复是OL3的版本没法加载SVG!WHAT???没法加载,这不是逗我呢??不过呢,我想这个问题我一定可以解决的!!

后来一直在思考这个问题,有一天突然灵光一现:我可以在地图上面那直接叠加一层SVG的,类似于曾经做过的OL3和echat的结合的逻辑,再绑定地图的事件刷新不就OK了,没错,就是这个思路,哦,此时觉的我就是个天才!

大笑

可是当我写好代码,运行代码的时候,发现地图动不了了?怎么办???怎么办???可不能这样啊!!!还好我机智,瞄了一眼OL4的源码,发现地图的时间是在Map这个div上面触发的,所以我就想到了把这个img放到map div里面,代码如下:

self.image = new Image();
self.image.src = self._url;
self._map.getViewport().appendChild(self.image);

再测试,哈哈,妥了,再加点地图事件,就搞定了!此刻深深的被我的聪明才智折服。

机智

但是,我就是这样一个perfect的人,为了更加好用所以我将此扩展成了一个类,源码如下:

/**
 * @author lzugis
 * 2017-10-20
 * @param option, 默认参数如下
   {
        map:null,
        extent:[],
        url:"",
        opacity:1,
        visible:true
    }
 */
ol.layer.SvgImageLayer = function(option){
    this._option = {
        map:null,
        extent:[],
        url:"",
        opacity:1,
        visible:true
    };
    this._init(option);
};
ol.layer.SvgImageLayer.prototype = {
    image:null,
    _init:function(option){
        //将option合并
        for(var opt in option){
            this._option[opt] = option[opt];
        }
        this._map = this._option.map;
        this._extent = this._option.extent;
        this._url = this._option.url;
        this._opacity = this._option.opacity;
        this._visible = this._option.visible;
    },
    addToMap:function(){
        if(this._map) {
            var self = this;
            self.image = new Image();
            self.image.src = self._url;
            self._map.getViewport().appendChild(self.image);
            self._updateImgStyle();
            self._addMapEvent();
        }
        else{
            alert("map参数定义不正确!");
        }
    },
    updateImage: function(option){
        this._init(option);
        if(option.url)this.image.src = this._url;
        this._updateImgStyle();
    },
    hide: function(){
        this.image.style.display = "none";
    },
    show: function(){
        this.image.style.display = "";
    },
    destroy: function(){
        this.image.remove();
    },
    _updateImgStyle: function(){
        var self = this;
        var _min = [self._extent[0], self._extent[1]],
            _max = [self._extent[2], self._extent[3]],
            _topLeft = [self._extent[0], self._extent[3]];
        var _scrMin = self._toScreenPoint(_min),
            _scrMax = self._toScreenPoint(_max),
            _scrTopLeft = self._toScreenPoint(_topLeft);
        var _w = Math.round(_scrMax[0] - _scrMin[0]),
            _h = Math.round(_scrMin[1] - _scrMax[1]),
            _left = _scrTopLeft[0],
            _top = _scrTopLeft[1];
        var cssText = "";
        var styles = {
            "opacity": self._opacity,
            "z-index": 0,
            "position":"absolute",
            "width":_w+"px",
            "height":_h+"px",
            "top":_top+"px",
            "left":_left+"px"
        };
        for(var style in styles){
            cssText+=style+":"+styles[style]+";"
        }
        self.image.style.cssText = cssText;
        self._visible?self.show():self.hide();
    },
    _addMapEvent:function(){
        var self = this;
        self._map.on("precompose",function(evt){
            evt.stopPropagation();
            self._updateImgStyle();
        });
    },
    _toScreenPoint: function(mapPoint){
        var srcPoint = this._map.getPixelFromCoordinate(mapPoint);
        return srcPoint;
    }
};

ol.inherits(ol.layer.SvgImageLayer, ol.layer.base);

实现后,效果如下,心理满满的成就感。。。

实现后

正当我沉溺在满满的成就感的时候,有一天,突然发现,我的WMS图层怎么被盖住了???Oh, NO!!!!Kill me!!OL4中map所有的图层都是绘制在一个canvas画布里面的,我叠上去一个图层势必会挡住的,肿么办?what can I do for you??不行,我不能坐以待毙,要是让客户发现这个问题就惨了,客户是我们的衣食父母,这个时候就必须体现我们的专业性和我的钻研性了。

被挡的妥妥的

于是乎,上git,扒源码,看了好一阵,都没找到头绪,怎么办,我可不是就此放手的人。恩,先看看API再说,突然,看到了imageSize,凭我的直觉,他应该就是我要找的,这个时候就又不得不发挥我的主观能动性了,计算了一个大小就贴上去,wonderful!!!

完美解决

附上源码如下:

var bounds = [12836027.844390793, 4745190.4650304755, 13098185.245208949, 5069741.1276835548];
var source = new ol.source.ImageStatic({
    url: "bjoutput/wind.svg",
    imageExtent: bounds,
        imageSize:getImageSize(bounds)
});
image.setSource(source);
//获取图片大小
function getImageSize(bounds){
    var _min = [bounds[0], bounds[1]],
            _max = [bounds[2], bounds[3]],
            _topLeft = [bounds[0], bounds[3]];
    var _scrMin = map.getPixelFromCoordinate(_min),
            _scrMax = map.getPixelFromCoordinate(_max);
    var _w = Math.round(_scrMax[0] - _scrMin[0]),
            _h = Math.round(_scrMin[1] - _scrMax[1]);
    return [_w, _h];
}

三、总结

写此篇的目的是为了告诉大家姿势的正确解锁方式,要善于思考,勤于动手,问题才会解决。


山重水复疑无路,柳暗花明又一村
LZUGIS

相关文章

  • 当我们遇到问题的时候改如何解决

    本文不讲技术,不撸代码,只讲思路。 一、问题 在Openlayers中展示风速风向图,共分为以下两个阶段: 加载P...

  • 正面管教第12天

    关注于解决问题 我们往往发现,当我们遇到问题再去解决问题的时候,我们给出的方案更像是做出一些惩罚。 那我们如何真正...

  • 你真的知道该怎么解决问题吗?——《你的灯还亮着吗?》书评

    当你遇到问题的时候你真的想解决吗?问题又该如何解决?《你的灯还亮着吗?》通过一些小故事启发我们找到问题,解决问题。...

  • 问题就是用来解决的,你需要不断迭代

    遇到问题如何解决?解决问题的一些方法 一、问题是什么 当现在的我们回过头看学生时代,发现那时的问题已经不算是问题,...

  • 如何更好的提出问题

    遇到问题时,如何全面正确的分析问题,找到关键因素当我们遇到问题的时候,要尝试着自己解决问题,通过问题出现的情况去判...

  • 教无定法

    当遇到问题的时候,我们总是会急需一种解决办法,让问题马上解决,殊不知错过了成长的机会。有时候为了平复孩子的...

  • 自己之外的思维

    当遇到问题的时候,每个人都会习惯性的按自己的思维思考如何解决…… 在开始的时候会经常怀疑自己,给自己造成很大的压力...

  • iOS问题-解决方法总结

    遇到问题不紧要,关键是得懂得如何解决问题。 遇到问题需Google时更新:) 问题: 1.当运行时,App崩溃,并...

  • 激发孩子的潜力

    当孩子遇到问题的时候,很容易需求我们的帮助,如果事事帮他解决,那么孩子永远也学不会自己解决问题,所以要激发孩子的潜...

  • 5why 分析法 -- 直击问题的本质(5/365)

    遇到问题--分析问题--解决问题,这是人人都知晓的思路,但是,你真的会分析问题么? 当问题出现的时候,如何从一连串...

网友评论

    本文标题:当我们遇到问题的时候改如何解决

    本文链接:https://www.haomeiwen.com/subject/lhkcpxtx.html