วิธีใช้ Leaflet เพื่อแสดงบางส่วนของชุดข้อมูลขนาดใหญ่ได้อย่างมีประสิทธิภาพ


13

ฉันเห็นผู้พัฒนาเว็บที่ไม่ใช่ GIS ยังคงพบปัญหานี้อยู่และฉันไม่แน่ใจว่าโซลูชันนี้เป็นอย่างไร

  1. มีชุดข้อมูลหลายพันรายการ
  2. เราต้องการแสดงแผนที่ให้กับผู้ใช้ด้วยชุดย่อยที่มองเห็นได้ของพวกเขาแสดงเป็นองค์ประกอบแบบโต้ตอบและคลิกได้

มีวิธีการอะไรในการทำสิ่งนี้?

ฉันสามารถคิดถึงสิ่งเหล่านี้ได้ แต่พวกเขาไม่พอใจอย่างมากดังนั้นฉันจึงสงสัยว่ามีอะไรอีกบ้าง:

  1. เก็บข้อมูลทั้งหมดในไฟล์ GeoJSON โอนไปยังเบราว์เซอร์และให้ Leaflet แสดงข้อมูล ปัญหา: ไม่ได้ทำงานกับชุดข้อมูลขนาดใหญ่ TopoJSON เพิ่มขีด จำกัด เล็กน้อย นอกจากนี้ยังทำให้เกิดความล่าช้ามากในการโหลดหน้า

  2. ใช้ Mapbox จัดเก็บข้อมูลทั้งหมดในเลเยอร์แบบโต้ตอบบน Mapbox และใช้ Mapbox.js เพื่อแสดง ใช้งานได้ดี แต่มีค่าใช้จ่ายและคุณไม่สามารถโฮสต์ด้วยตัวเองได้

  3. ใช้ GeoServer เพื่อเข้าถึงฐานข้อมูล PostGIS ใช้ปลั๊กอินใบปลิว WFS-geojson เพื่อเข้าถึงข้อมูลจากที่นั่น อาจใช้งานได้ แต่ปลั๊กอิน WFS-geojson Leafletดูเหมือนจะไม่ได้รับการดูแลรักษาอีกต่อไป

  4. ใช้ CartoDB จัดเก็บข้อมูลทั้งหมดในตาราง CartoDB และใช้CartoDB.jsเพื่อแสดง ใช้งานได้ดี แต่อาจมีราคาแพงมาก เป็นไปได้ที่จะโฮสต์ด้วยตัวคุณเอง แต่การติดตั้ง CartoDB นั้นไม่สำคัญ

ทั้งหมดนี้ทำให้ฉันคิดว่าต้องมีวิธีที่ดีกว่าและอิสระมากกว่าที่ฉันคิดถึง มันคืออะไร?

แก้ไข

บางทีฉันอาจเขียนปลั๊กอิน WFS-geojson ง่ายเกินไป มีทางแยกที่ยังคงเห็นกิจกรรมบางอย่าง (4 เดือนที่ผ่านมา): https://github.com/johanlahti/azgs-leaflet


1
แค่ถาม geoserver wfs สำหรับ json?
Ian Turton

ถ้าฉันเข้าใจถูกต้องถ้าคุณ hardcode คำขอสำหรับ JSON คุณก็แค่บอกให้ถ่ายโอนชุดข้อมูลทั้งหมดเป็น JSON หยดเดียว - เหมือนกับวิธีแก้ปัญหา 1 คุณต้องใช้ WFS จริงเพื่อรับคำขอที่ถูกผูกไว้ ไปที่วิวพอร์ตปัจจุบันใช่ไหม
Steve Bennett

WFS กรองร้องขอโดยขอบเขตของแผนที่ (ไม่ใบปลิวทำอย่างนั้นโดยอัตโนมัติ?)
เอียนตั๋น

ในการทำเช่นนั้นจะต้องพูด WFS ใช่ไหม? และ afaik ที่มีเฉพาะในปลั๊กอิน WFS-geojson (ไม่ได้รับการบำรุงรักษา) หรือไม่
Steve Bennett

1
WFS นั้นไม่ยาก - ใบปลิวอาจเป็นปัญหา>
Ian Turton

คำตอบ:


4

โอเคสมมติฐานของฉันใน 2 ไม่ถูกต้อง คุณสามารถใช้ mapbox.js ผลลัพธ์ที่ได้จะแตกต่างออกไปเล็กน้อยฉันเชื่อว่าตัวทำเครื่องหมายจะเป็นเลเยอร์แรสเตอร์แบบคงที่ แต่จะสามารถคลิกได้

ข้อมูลจำเพาะที่ทำให้การโต้ตอบขนาดใหญ่ทำงานได้ที่https://github.com/mapbox/utfgrid-spec

มันใช้งานไคลเอนต์ใน https://github.com/danzel/Leaflet.utfgrid (ปลั๊กอินใบปลิว) และ mapbox.js

เซิร์ฟเวอร์ถูกติดตั้งใน https://github.com/mapbox/tilelive.jsและด้วยเหตุนี้ TileMill เช่น: http://tilemill-server/tile/projectname/7/115/78.grid.json

มันยังนำมาใช้ใน TileStache แต่ไม่ใช่ tilestream หรือ mbtiles-server ดูเหมือนว่าข้อมูล UTFgrid จะถูกเก็บไว้ในไฟล์ mbtiles โดย TileMill แต่จะถูกละเว้นไปด้วย

ดังนั้นไม่เพียง แต่คุณไม่ต้องการ mapbox.com คุณไม่จำเป็นต้องใช้ mapbox.js เช่นกัน Mapbox.js ส่วนใหญ่ดูเหมือนจะยึดสิ่งต่าง ๆ เข้าด้วยกันเพื่อความสะดวก: การโทรเพียงครั้งเดียวที่สร้างแผนที่ขึ้นมาดึงกระเบื้องและเพิ่มการโต้ตอบ

แต่ถ้าคุณใช้ mapbox.js มันมีจิ๊กซอว์หนึ่งส่วนที่ฉันขาดไปและนั่นก็คือ tilejson คุณให้ mapbox.json ไฟล์ tilejson ที่สอดคล้องกับแผนที่ของคุณ


1

นอกจากนี้ยังมีปลั๊กอิน leaflet-vector-layer ที่รองรับบริการ postGIS http://jasonsanford.github.io/leaflet-vector-layers/demos/postgis-restful-web-service-framework/

โดยลักษณะของมันคุณสามารถกรองบริการ

ฉันใช้ปลั๊กอินนี้สำหรับบริการ ArcGIS และมันก็ดีมาก


0

หากคุณไม่สามารถหาวิธีแก้ปัญหาได้ที่นี่ก็เป็นวิธีหนึ่ง: http://gis.xyz/leaflet.html#

 var owsrootUrl = 'http://217.8.255.188:8080/geoserver/opengeo/ows';

 var defaultParameters = {
     service : 'WFS',
     version : '2.0',
     request : 'GetFeature',
     typeName : 'opengeo:evernote_geom',
     outputFormat : 'text/javascript',
     format_options : 'callback:getJson',
     SrsName : 'EPSG:4326'
};

var parameters = L.Util.extend(defaultParameters);
var URL = owsrootUrl + L.Util.getParamString(parameters);

var WFSLayer = null;
var ajax = $.ajax({
    url : URL,
    dataType : 'jsonp',
    jsonpCallback : 'getJson',
    success : function (response) {
       WFSLayer = L.geoJson(response, {
            style: function (feature) {
                return {
                    stroke: false,
                    fillColor: 'FFFFFF',
                    fillOpacity: 0
                };
            },
            onEachFeature: function (feature, layer) {
                popupOptions = {maxWidth: 600};
                layer.bindPopup('<h4>'+feature.properties.url+'</h4><br>'+feature.properties.title
                    ,popupOptions);
            }
        }).addTo(map);
    }
});

ฉันไม่เห็นว่าสิ่งนี้ จำกัด การร้องขอไปยังวิวพอร์ตปัจจุบันหรือไม่
alphabetasoup
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.