如何将地图上显示的文本添加到传单中的geojson对象

时间:2012-08-16 02:00:46

标签: javascript leaflet

所以我在传单中有一个geojson图层,我可以在这个图层中添加geojson对象,以便在生成的地图上显示。

现在我想在对象附近添加一个文本标签。

此示例显示使用自定义L.control()对象在地图上显示其他信息。这似乎接近我想做的事情。

鉴于这个例子,我想添加位于每个状态上的State初始文本标签(即“TX”,“FL”)。 L.control()可以用来做这件事吗,还是有其他办法?

http://leaflet.cloudmade.com/examples/choropleth.html

var info = L.control();

info.onAdd = function (map) {
    this._div = L.DomUtil.create('div', 'info'); // create a div with a class "info"
    this.update();
    return this._div;
};

// method that we will use to update the control based on feature properties passed
info.update = function (props) {
    this._div.innerHTML = '<h4>US Population Density</h4>' +  (props ?
        '<b>' + props.name + '</b><br />' + props.density + ' people / mi<sup>2</sup>'
        : 'Hover over a state');
};

info.addTo(map);

3 个答案:

答案 0 :(得分:18)

使用标记类和带有“html”属性的DivIcon类

的传单中的标签叠加

就个人而言,我使用此方法在地图上实现文本标签。这样我就可以毫不费力地使用所有现有的Marker Class方法和事件。我想这有点像只用文字标签代替图标。

        var textLatLng = [35.1436, -111.5632];  
        var myTextLabel = L.marker(textLatLng, {
            icon: L.divIcon({
                className: 'text-labels',   // Set class for CSS styling
                html: 'A Text Label'
            }),
            draggable: true,       // Allow label dragging...?
            zIndexOffset: 1000     // Make appear above other map features
        });

我的CSS看起来像:

        .text-labels {
            font-size: 2em;
            font-weight: 700;
            /* Use color, background, set margins for offset, etc */
        }

另外,我还没有探讨过这个问题,但也许你可以在CSS中添加一个png然后偏移文本,这样你就可以使用Leaflet DivIcon类在同一个Marker对象中包装一个图标和标签?这对于div形状(例如方框,圆形)来说很容易,但我不确定是否为CSS标记对象添加了一个png - 因为我无论如何都不是CSS大师。

答案 1 :(得分:14)

我最近在寻找同样的问题,并且昨天根据谷歌小组的帖子实施了它。 https://groups.google.com/forum/#!topic/leaflet-js/sA2HnU5W9Fw

感谢Adrian提供原始代码示例。

以下是解决方案:

扩展以下类:

<script>

    L.LabelOverlay = L.Class.extend({
        initialize: function(/*LatLng*/ latLng, /*String*/ label, options) {
            this._latlng = latLng;
            this._label = label;
            L.Util.setOptions(this, options);
        },
        options: {
            offset: new L.Point(0, 2)
        },
        onAdd: function(map) {
            this._map = map;
            if (!this._container) {
                this._initLayout();
            }
            map.getPanes().overlayPane.appendChild(this._container);
            this._container.innerHTML = this._label;
            map.on('viewreset', this._reset, this);
            this._reset();
        },
        onRemove: function(map) {
            map.getPanes().overlayPane.removeChild(this._container);
            map.off('viewreset', this._reset, this);
        },
        _reset: function() {
            var pos = this._map.latLngToLayerPoint(this._latlng);
            var op = new L.Point(pos.x + this.options.offset.x, pos.y - this.options.offset.y);
            L.DomUtil.setPosition(this._container, op);
        },
        _initLayout: function() {
            this._container = L.DomUtil.create('div', 'leaflet-label-overlay');
        }
    });   

</script>

再加上这个css:

<style>
    .leaflet-popup-close-button {
        display:none;
    }

    .leaflet-label-overlay {
        line-height:0px;
        margin-top: 9px;
        position:absolute;
    }
</style>

然后显示文本标签如下:

<script>
    var map = L.map('map').setView([51.898712, 6.7307100000001], 4);

    // add markers
    // ...

    // add text labels:
    var labelLocation = new L.LatLng(51.329219337279405, 10.454119349999928);
    var labelTitle = new L.LabelOverlay(labelLocation, '<b>GERMANY</b>');
    map.addLayer(labelTitle);


    var labelLocation2 = new L.LatLng(47.71329162782909, 13.34573480000006);
    var labelTitle2 = new L.LabelOverlay(labelLocation2, '<b>AUSTRIA</b>');
    map.addLayer(labelTitle2);

    // In order to prevent the text labels to "jump" when zooming in and out,
    // in Google Chrome, I added this event handler:

    map.on('movestart', function () {
        map.removeLayer(labelTitle);
        map.removeLayer(labelTitle2);
    });
    map.on('moveend', function () {
        map.addLayer(labelTitle);
        map.addLayer(labelTitle2);
    });
</script>

结果:

enter image description here

答案 2 :(得分:1)

我将当前版本采用此代码。

    <style>
        .leaflet-popup-close-button {
            display:none;
        }

        .leaflet-label-overlay {
            line-height:0px;
            margin-top: 9px;
            position:absolute;
        }
    </style>    

    <script>
        L.LabelOverlay = L.Layer.extend({
            initialize: function(/*LatLng*/ latLng, /*String*/ label, options) {
                this._latlng = latLng;
                this._label = label;
                L.Util.setOptions(this, options);
            },
            options: {
                offset: new L.Point(0, 2)
            },
            onAdd: function(map) {
                this._map = map;
                if (!this._container) {
                    this._initLayout();
                }
                map.getPanes().popupPane.appendChild(this._container);
                this._container.innerHTML = this._label;
                map.on('movestart', this._update_start, this);
                map.on('moveend', this._update_end, this);
                this._update_end();
            },
            onRemove: function(map) {
                map.getPanes().popupPane.removeChild(this._container);
                map.off('movestart', this._update_start, this);
                map.off('moveend', this._update_end, this);
            },
            _update_start: function(){
                L.DomUtil.setPosition(this._container, 0);
            },
            _update_end: function() {
                var pos = this._map.latLngToLayerPoint(this._latlng);
                var op = new L.Point(pos.x + this.options.offset.x, pos.y - this.options.offset.y);
                L.DomUtil.setPosition(this._container, op);
            },
            _initLayout: function() {
                this._container = L.DomUtil.create('div', 'leaflet-label-overlay');
            }
        });   
    </script>