An example about how Leaflet.js can be integrated with Vue.js.
Last active
July 28, 2018 15:12
-
-
Save fabiovalse/9e711f6d83f80e2f698cad58a5f75ba3 to your computer and use it in GitHub Desktop.
Vue.js + Leaflet.js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
{ | |
"annotations": [ | |
{ | |
"p1": { | |
"x": 10745, | |
"y": -23.25 | |
}, | |
"p2": { | |
"x": 11283.75, | |
"y": -387 | |
}, | |
"text": { | |
"full": "坤與 萬國 全圗", | |
"tokens": [ | |
{ | |
"text": "坤與", | |
"graphemes": [ | |
{ | |
"text": "坤", | |
"tone": "1", | |
"transliteration": { | |
"pinyin": "kun", | |
"zhuyin_fuhao": "ㄎㄨㄣ" | |
}, | |
"radical": "土", | |
"domain": "cosmologia", | |
"translation": { | |
"fr": "Globe terrestre; obéissance, soumission.", | |
"en": "The earth as contrasted with heaven." | |
} | |
}, | |
{ | |
"text": "與", | |
"tone": "2", | |
"transliteration": { | |
"pinyin": "yu", | |
"zhuyin_fuhao": "ㄩˊ" | |
}, | |
"radical": "車", | |
"domain": "cosmologia", | |
"translation": { | |
"fr": "La plate-forme ou plancher d'une voiture. Voiture, chaise à porteurs, bard, civièr. La terre. ", | |
"en": "The bottom of a carriage. A carriage or chariot; a sedan-chair." | |
} | |
} | |
] | |
}, | |
{ | |
"text": "萬國", | |
"graphemes": [ | |
{ | |
"text": "萬", | |
"tone": "4", | |
"transliteration": { | |
"pinyin": "wan", | |
"zhuyin_fuhao": "ㄨㄢˋ" | |
}, | |
"radical": "艸", | |
"domain": "", | |
"translation": { | |
"fr": "Dix mille; très nombreux; tout, entièrment.", | |
"en": "Ten thousand. Large numbers. All." | |
} | |
}, | |
{ | |
"text": "國", | |
"tone": "2", | |
"transliteration": { | |
"pinyin": "guo", | |
"zhuyin_fuhao": "ㄍㄨㄛˊ" | |
}, | |
"radical": "囗", | |
"domain": "", | |
"translation": { | |
"fr": "État, royaume, principauté.", | |
"en": "A kingdom; a nation." | |
} | |
} | |
] | |
}, | |
{ | |
"text": "全圗", | |
"graphemes": [ | |
{ | |
"text": "全", | |
"tone": "2", | |
"transliteration": { | |
"pinyin": "quan", | |
"zhuyin_fuhao": "ㄑㄩㄢˊ" | |
}, | |
"radical": "入", | |
"domain": "", | |
"translation": { | |
"fr": "Tout, entier, complet, parfait.", | |
"en": "Perfect, entire, the whole, all, complete." | |
} | |
}, | |
{ | |
"text": "圗", | |
"tone": "2", | |
"transliteration": { | |
"pinyin": "tu", | |
"zhuyin_fuhao": "ㄊㄨˊ" | |
}, | |
"radical": "囗", | |
"domain": "", | |
"translation": { | |
"fr": "Delibération, dessein, projet, plan, détermination.", | |
"en": "A map; a picture; a diagram; a portrait." | |
} | |
} | |
] | |
} | |
], | |
"translation": { | |
"it": "Carta geografica completa di tutti i regni" | |
} | |
} | |
}, | |
{ | |
"p1": { | |
"x": 10745, | |
"y": -387 | |
}, | |
"p2": { | |
"x": 11283.75, | |
"y": -5075.5 | |
}, | |
"text1": "", | |
"text2": "" | |
}, | |
{ | |
"p1": { | |
"x": 9591.5, | |
"y": -22.25 | |
}, | |
"p2": { | |
"x": 9936, | |
"y": -357.25 | |
}, | |
"text1": "", | |
"text2": "" | |
}, | |
{ | |
"p1": { | |
"x": 10448.4, | |
"y": -852 | |
}, | |
"p2": { | |
"x": 10745, | |
"y": -1365.8 | |
}, | |
"text1": "", | |
"text2": "" | |
}, | |
{ | |
"p1": { | |
"x": 29, | |
"y": -1214 | |
}, | |
"p2": { | |
"x": 534.8, | |
"y": -3881 | |
}, | |
"text1": "", | |
"text2": "" | |
}, | |
{ | |
"p1": { | |
"x": 5949.4, | |
"y": -1920.8 | |
}, | |
"p2": { | |
"x": 6997.9, | |
"y": -2511.3 | |
}, | |
"text1": "", | |
"text2": "" | |
}, | |
{ | |
"path": [ | |
{"x": 1418.1, "y": -1338.4}, | |
{"x": 3050.1, "y": -959.4}, | |
{"x": 3068.3, "y": -1041.9}, | |
{"x": 1425.6, "y": -1401.2} | |
], | |
"text1": "歐邏巴", | |
"text2": "Europa (Ou Luo Ba)" | |
}, | |
{ | |
"path": [ | |
{"x": 3854, "y": -794.2}, | |
{"x": 3932, "y": -785}, | |
{"x": 4109, "y": -2479.7}, | |
{"x": 4044, "y": -2492} | |
], | |
"text1": "亞細亞", | |
"text2": "Asia (Ya Xi Ya)" | |
}, | |
{ | |
"path": [ | |
{"x": 2095.4, "y": -1919.3}, | |
{"x": 2173.9, "y": -1920}, | |
{"x": 2116.3, "y": -3298.3}, | |
{"x": 2038.3, "y": -3297.3} | |
], | |
"text1": "利未亞", | |
"text2": "Africa (Libya) (Li Wei Ya)" | |
}, | |
{ | |
"path": [ | |
{"x": 8058.75, "y": -564.5}, | |
{"x": 8134.75, "y": -565}, | |
{"x": 8143.5, "y": -1763.75}, | |
{"x": 8066, "y": -1762.75} | |
], | |
"text1": "北亞墨利加", | |
"text2": "North America (Bei Ya Mo Li Jia)" | |
}, | |
{ | |
"path": [ | |
{"x": 9350.6, "y": -2286.5}, | |
{"x": 9415.1, "y": -2285}, | |
{"x": 9414.3, "y": -3735}, | |
{"x": 9328.8, "y": -3737.5} | |
], | |
"text1": "南亞墨利加", | |
"text2": "South America (Nan Ya Mo Li Jia)" | |
} | |
] | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
leaflet_conf = | |
width: 45177 | |
height: 20538 | |
tileLayer: 'http://wafi.iit.cnr.it/webvis/tiles/vips_zoomify_kunyu_wanguo_quantu/' | |
realMaxZoom: 6 | |
zoomControlPosition: 'bottomright' | |
map: { | |
minZoom: 1, | |
maxZoom: 8, | |
zoomControl: false, | |
crs: L.CRS.Simple | |
} | |
app = new Vue | |
el: '#app' | |
data: | |
annotations: [] | |
conf: leaflet_conf | |
components: | |
'leaflet': window.leafletComponent |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
body, html { | |
width: 100%; | |
height: 100%; | |
padding: 0; | |
margin: 0; | |
} | |
#app { | |
display: flex; | |
width: 100%; | |
height: 100%; | |
} | |
#map { | |
flex-grow: 1; | |
} | |
.image_portion rect, .image_portion path { | |
stroke: steelblue; | |
fill: rgba(176,196,222,0.8); | |
} | |
.infobox { | |
position: absolute; | |
top: 0; | |
left: 0; | |
width: 400px; | |
height: 100%; | |
background: #FFFFFF; | |
z-index: 1; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!doctype html> | |
<html lang="en"> | |
<head> | |
<meta charset="utf-8"> | |
<title>Vue.js + Leaflet.js</title> | |
<script src="https://d3js.org/d3.v4.min.js"></script> | |
<script src="https://d3js.org/d3-selection-multi.v0.4.min.js"></script> | |
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.0.3/vue.js"></script> | |
<script src="http://cdn.leafletjs.com/leaflet/v0.7.7/leaflet.js"></script> | |
<script src="L.D3SvgOverlay.js"></script> | |
<script src="L.TileLayer.Zoomify.js"></script> | |
<link rel="stylesheet" href="http://cdn.leafletjs.com/leaflet/v0.7.7/leaflet.css" /> | |
<link rel="stylesheet" href="index.css"> | |
</head> | |
<body> | |
<div id="app"> | |
<leaflet :conf="conf"></leaflet> | |
</div> | |
<script src="leaflet.js"></script> | |
<script src="index.js"></script> | |
</body> | |
</html> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Generated by CoffeeScript 1.10.0 | |
(function() { | |
var app, leaflet_conf; | |
leaflet_conf = { | |
width: 45177, | |
height: 20538, | |
tileLayer: 'http://wafi.iit.cnr.it/webvis/tiles/vips_zoomify_kunyu_wanguo_quantu/', | |
realMaxZoom: 6, | |
zoomControlPosition: 'bottomright', | |
map: { | |
minZoom: 1, | |
maxZoom: 8, | |
zoomControl: false, | |
crs: L.CRS.Simple | |
} | |
}; | |
app = new Vue({ | |
el: '#app', | |
data: { | |
annotations: [], | |
conf: leaflet_conf | |
}, | |
components: { | |
'leaflet': window.leafletComponent | |
} | |
}); | |
}).call(this); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** | |
* Copyright 2015 Teralytics AG | |
* | |
* @author Kirill Zhuravlev <kirill.zhuravlev@teralytics.ch> | |
* | |
*/ | |
(function (factory) { | |
if (typeof define === 'function' && define.amd) { | |
define(['leaflet', 'd3'], factory); | |
} else if (typeof module === 'object' && module.exports) { | |
module.exports = factory(require('leaflet', 'd3')); | |
} else { | |
factory(L, d3); | |
} | |
}(function (L, d3) { | |
// Check requirements | |
if (typeof d3 == "undefined") { | |
throw "D3 SVG Overlay for Leaflet requires D3 library loaded first"; | |
} | |
if (typeof L == "undefined") { | |
throw "D3 SVG Overlay for Leaflet requires Leaflet library loaded first"; | |
} | |
// Tiny stylesheet bundled here instead of a separate file | |
if (L.version >= "1.0") { | |
d3.select("head") | |
.append("style").attr("type", "text/css") | |
.text("g.d3-overlay *{pointer-events:visiblePainted;}"); | |
} | |
// Class definition | |
L.D3SvgOverlay = (L.version < "1.0" ? L.Class : L.Layer).extend({ | |
includes: (L.version < "1.0" ? L.Mixin.Events : []), | |
_undef: function(a){ return typeof a == "undefined"; }, | |
_options: function (options) { | |
if (this._undef(options)) { | |
return this.options; | |
} | |
options.zoomHide = this._undef(options.zoomHide) ? false : options.zoomHide; | |
options.zoomDraw = this._undef(options.zoomDraw) ? true : options.zoomDraw; | |
return this.options = options; | |
}, | |
_disableLeafletRounding: function(){ | |
this._leaflet_round = L.Point.prototype._round; | |
L.Point.prototype._round = function(){ return this; }; | |
}, | |
_enableLeafletRounding: function(){ | |
L.Point.prototype._round = this._leaflet_round; | |
}, | |
draw: function () { | |
this._disableLeafletRounding(); | |
this._drawCallback(this.selection, this.projection, this.map.getZoom()); | |
this._enableLeafletRounding(); | |
}, | |
initialize: function (drawCallback, options) { // (Function(selection, projection)), (Object)options | |
this._options(options || {}); | |
this._drawCallback = drawCallback; | |
}, | |
// Handler for "viewreset"-like events, updates scale and shift after the animation | |
_zoomChange: function (evt) { | |
this._disableLeafletRounding(); | |
var newZoom = this._undef(evt.zoom) ? this.map._zoom : evt.zoom; // "viewreset" event in Leaflet has not zoom/center parameters like zoomanim | |
this._zoomDiff = newZoom - this._zoom; | |
this._scale = Math.pow(2, this._zoomDiff); | |
this.projection.scale = this._scale; | |
this._shift = this.map.latLngToLayerPoint(this._wgsOrigin) | |
._subtract(this._wgsInitialShift.multiplyBy(this._scale)); | |
var shift = ["translate(", this._shift.x, ",", this._shift.y, ") "]; | |
var scale = ["scale(", this._scale, ",", this._scale,") "]; | |
this._rootGroup.attr("transform", shift.concat(scale).join("")); | |
if (this.options.zoomDraw) { this.draw() } | |
this._enableLeafletRounding(); | |
}, | |
onAdd: function (map) { | |
this.map = map; | |
var _layer = this; | |
// SVG element | |
if (L.version < "1.0") { | |
map._initPathRoot(); | |
this._svg = d3.select(map._panes.overlayPane) | |
.select("svg"); | |
this._rootGroup = this._svg.append("g"); | |
} else { | |
this._svg = L.svg(); | |
map.addLayer(this._svg); | |
this._rootGroup = d3.select(this._svg._rootGroup).classed("d3-overlay", true); | |
} | |
this._rootGroup.classed("leaflet-zoom-hide", this.options.zoomHide); | |
this.selection = this._rootGroup; | |
// Init shift/scale invariance helper values | |
this._pixelOrigin = map.getPixelOrigin(); | |
this._wgsOrigin = L.latLng([0, 0]); | |
this._wgsInitialShift = this.map.latLngToLayerPoint(this._wgsOrigin); | |
this._zoom = this.map.getZoom(); | |
this._shift = L.point(0, 0); | |
this._scale = 1; | |
// Create projection object | |
this.projection = { | |
latLngToLayerPoint: function (latLng, zoom) { | |
zoom = _layer._undef(zoom) ? _layer._zoom : zoom; | |
var projectedPoint = _layer.map.project(L.latLng(latLng), zoom)._round(); | |
return projectedPoint._subtract(_layer._pixelOrigin); | |
}, | |
layerPointToLatLng: function (point, zoom) { | |
zoom = _layer._undef(zoom) ? _layer._zoom : zoom; | |
var projectedPoint = L.point(point).add(_layer._pixelOrigin); | |
return _layer.map.unproject(projectedPoint, zoom); | |
}, | |
unitsPerMeter: 256 * Math.pow(2, _layer._zoom) / 40075017, | |
map: _layer.map, | |
layer: _layer, | |
scale: 1 | |
}; | |
this.projection._projectPoint = function(x, y) { | |
var point = _layer.projection.latLngToLayerPoint(new L.LatLng(y, x)); | |
this.stream.point(point.x, point.y); | |
}; | |
this.projection.pathFromGeojson = | |
d3.geoPath().projection(d3.geoTransform({point: this.projection._projectPoint})); | |
// Compatibility with v.1 | |
this.projection.latLngToLayerFloatPoint = this.projection.latLngToLayerPoint; | |
this.projection.getZoom = this.map.getZoom.bind(this.map); | |
this.projection.getBounds = this.map.getBounds.bind(this.map); | |
this.selection = this._rootGroup; | |
if (L.version < "1.0") map.on("viewreset", this._zoomChange, this); | |
// Initial draw | |
this.draw(); | |
}, | |
// Leaflet 1.0 | |
getEvents: function() { return {zoomend: this._zoomChange}; }, | |
onRemove: function (map) { | |
if (L.version < "1.0") { | |
map.off("viewreset", this._zoomChange, this); | |
this._rootGroup.remove(); | |
} else { | |
this._svg.remove(); | |
} | |
}, | |
addTo: function (map) { | |
map.addLayer(this); | |
return this; | |
} | |
}); | |
L.D3SvgOverlay.version = "2.2"; | |
// Factory method | |
L.d3SvgOverlay = function (drawCallback, options) { | |
return new L.D3SvgOverlay(drawCallback, options); | |
}; | |
})); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
* L.TileLayer.Zoomify display Zoomify tiles with Leaflet | |
*/ | |
L.TileLayer.Zoomify = L.TileLayer.extend({ | |
options: { | |
continuousWorld: true, | |
tolerance: 0.8 | |
}, | |
initialize: function (url, options) { | |
options = L.setOptions(this, options); | |
this._url = url; | |
var imageSize = L.point(options.width, options.height), | |
tileSize = options.tileSize; | |
this._imageSize = [imageSize]; | |
this._gridSize = [this._getGridSize(imageSize)]; | |
while (parseInt(imageSize.x) > tileSize || parseInt(imageSize.y) > tileSize) { | |
imageSize = imageSize.divideBy(2).floor(); | |
this._imageSize.push(imageSize); | |
this._gridSize.push(this._getGridSize(imageSize)); | |
} | |
this._imageSize.reverse(); | |
this._gridSize.reverse(); | |
this.options.maxZoom = this._gridSize.length - 1; | |
}, | |
onAdd: function (map) { | |
L.TileLayer.prototype.onAdd.call(this, map); | |
var mapSize = map.getSize(), | |
zoom = this._getBestFitZoom(mapSize), | |
imageSize = this._imageSize[zoom], | |
center = map.options.crs.pointToLatLng(L.point(imageSize.x / 2, imageSize.y / 2), zoom); | |
map.setView(center, zoom, true); | |
}, | |
_getGridSize: function (imageSize) { | |
var tileSize = this.options.tileSize; | |
return L.point(Math.ceil(imageSize.x / tileSize), Math.ceil(imageSize.y / tileSize)); | |
}, | |
_getBestFitZoom: function (mapSize) { | |
var tolerance = this.options.tolerance, | |
zoom = this._imageSize.length - 1, | |
imageSize, zoom; | |
while (zoom) { | |
imageSize = this._imageSize[zoom]; | |
if (imageSize.x * tolerance < mapSize.x && imageSize.y * tolerance < mapSize.y) { | |
return zoom; | |
} | |
zoom--; | |
} | |
return zoom; | |
}, | |
_tileShouldBeLoaded: function (tilePoint) { | |
var gridSize = this._gridSize[this._map.getZoom()]; | |
return (tilePoint.x >= 0 && tilePoint.x < gridSize.x && tilePoint.y >= 0 && tilePoint.y < gridSize.y); | |
}, | |
_addTile: function (tilePoint, container) { | |
var tilePos = this._getTilePos(tilePoint), | |
tile = this._getTile(), | |
zoom = this._map.getZoom(), | |
imageSize = this._imageSize[zoom], | |
gridSize = this._gridSize[zoom], | |
tileSize = this.options.tileSize; | |
if (tilePoint.x === gridSize.x - 1) { | |
tile.style.width = imageSize.x - (tileSize * (gridSize.x - 1)) + 'px'; | |
} | |
if (tilePoint.y === gridSize.y - 1) { | |
tile.style.height = imageSize.y - (tileSize * (gridSize.y - 1)) + 'px'; | |
} | |
L.DomUtil.setPosition(tile, tilePos, L.Browser.chrome || L.Browser.android23); | |
this._tiles[tilePoint.x + ':' + tilePoint.y] = tile; | |
this._loadTile(tile, tilePoint); | |
if (tile.parentNode !== this._tileContainer) { | |
container.appendChild(tile); | |
} | |
}, | |
getTileUrl: function (tilePoint) { | |
return this._url + 'TileGroup' + this._getTileGroup(tilePoint) + '/' + this._map.getZoom() + '-' + tilePoint.x + '-' + tilePoint.y + '.jpg'; | |
}, | |
_getTileGroup: function (tilePoint) { | |
var zoom = this._map.getZoom(), | |
num = 0, | |
gridSize; | |
for (z = 0; z < zoom; z++) { | |
gridSize = this._gridSize[z]; | |
num += gridSize.x * gridSize.y; | |
} | |
num += tilePoint.y * this._gridSize[zoom].x + tilePoint.x; | |
return Math.floor(num / 256);; | |
} | |
}); | |
L.tileLayer.zoomify = function (url, options) { | |
return new L.TileLayer.Zoomify(url, options); | |
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
window.leafletComponent = | |
props: | |
conf: | |
type: Object | |
required: true | |
data: () -> | |
map: null | |
point: (x,y) -> @map.unproject([x,-y], @conf.realMaxZoom) | |
to_path_description: (projection, points) -> | |
str = "" | |
starting_point = "#{projection.latLngToLayerPoint(@point(points[0].x, points[0].y)).x} #{projection.latLngToLayerPoint(@point(points[0].x, points[0].y)).y}" | |
for p,i in points | |
if i > 0 | |
str += "L #{projection.latLngToLayerPoint(@point(p.x, p.y)).x} #{projection.latLngToLayerPoint(@point(p.x, p.y)).y} " | |
return "M#{starting_point} #{str} L #{starting_point}" | |
loadOverlay: () -> | |
d3.json 'data.json', (data) => | |
_this = this | |
overlay = L.d3SvgOverlay (selection, projection) => | |
# Simple rectangles | |
rectangles = selection.selectAll '.rectangles' | |
.data data.annotations.filter (d) -> d.p1? and d.p2? | |
enter_rectangles = rectangles.enter().append 'g' | |
.attrs | |
class: 'rectangles image_portion' | |
.on 'click', (d) -> | |
console.log "#{d.text.full}" | |
enter_rectangles.append 'rect' | |
.attrs | |
width: (d) -> projection.latLngToLayerPoint(_this.point(d.p2.x, 0)).x - projection.latLngToLayerPoint(_this.point(d.p1.x, 0)).x | |
height: (d) -> projection.latLngToLayerPoint(_this.point(0, d.p2.y)).y - projection.latLngToLayerPoint(_this.point(0, d.p1.y)).y | |
x: (d) -> projection.latLngToLayerPoint(_this.point(d.p1.x, d.p1.y)).x | |
y: (d) -> projection.latLngToLayerPoint(_this.point(d.p1.x, d.p1.y)).y | |
'stroke-width': 5/_this.map.getZoom() | |
# Paths | |
paths = selection.selectAll '.path' | |
.data data.annotations.filter (d) -> d.path? | |
enter_paths = paths.enter().append 'g' | |
.attrs | |
class: 'path image_portion' | |
.on 'click', (d) -> | |
console.log "#{d.text.full}" | |
enter_paths.append 'path' | |
.attrs | |
d: (d) -> _this.to_path_description projection, d.path | |
'stroke-width': 5/_this.map.getZoom() | |
overlay.addTo(@map) | |
template: ''' | |
<div id="map"></div> | |
''' | |
mounted: () -> | |
@map = L.map('map', @conf.map) | |
center = @point(@conf.width/2, @conf.height/2) | |
@map.setView(center, 2, {animate:false}) | |
L.tileLayer.zoomify(@conf.tileLayer, { | |
width: @conf.width | |
height: @conf.height | |
}).addTo(@map) | |
L.control.zoom({ | |
position: @conf.zoomControlPosition | |
}).addTo(@map) | |
@loadOverlay() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Generated by CoffeeScript 1.10.0 | |
(function() { | |
window.leafletComponent = { | |
props: { | |
conf: { | |
type: Object, | |
required: true | |
} | |
}, | |
data: function() { | |
return { | |
map: null, | |
point: function(x, y) { | |
return this.map.unproject([x, -y], this.conf.realMaxZoom); | |
}, | |
to_path_description: function(projection, points) { | |
var i, j, len, p, starting_point, str; | |
str = ""; | |
starting_point = (projection.latLngToLayerPoint(this.point(points[0].x, points[0].y)).x) + " " + (projection.latLngToLayerPoint(this.point(points[0].x, points[0].y)).y); | |
for (i = j = 0, len = points.length; j < len; i = ++j) { | |
p = points[i]; | |
if (i > 0) { | |
str += "L " + (projection.latLngToLayerPoint(this.point(p.x, p.y)).x) + " " + (projection.latLngToLayerPoint(this.point(p.x, p.y)).y) + " "; | |
} | |
} | |
return "M" + starting_point + " " + str + " L " + starting_point; | |
}, | |
loadOverlay: function() { | |
return d3.json('data.json', (function(_this) { | |
return function(data) { | |
var overlay; | |
_this = _this; | |
overlay = L.d3SvgOverlay(function(selection, projection) { | |
var enter_paths, enter_rectangles, paths, rectangles; | |
rectangles = selection.selectAll('.rectangles').data(data.annotations.filter(function(d) { | |
return (d.p1 != null) && (d.p2 != null); | |
})); | |
enter_rectangles = rectangles.enter().append('g').attrs({ | |
"class": 'rectangles image_portion' | |
}).on('click', function(d) { | |
return console.log("" + d.text.full); | |
}); | |
enter_rectangles.append('rect').attrs({ | |
width: function(d) { | |
return projection.latLngToLayerPoint(_this.point(d.p2.x, 0)).x - projection.latLngToLayerPoint(_this.point(d.p1.x, 0)).x; | |
}, | |
height: function(d) { | |
return projection.latLngToLayerPoint(_this.point(0, d.p2.y)).y - projection.latLngToLayerPoint(_this.point(0, d.p1.y)).y; | |
}, | |
x: function(d) { | |
return projection.latLngToLayerPoint(_this.point(d.p1.x, d.p1.y)).x; | |
}, | |
y: function(d) { | |
return projection.latLngToLayerPoint(_this.point(d.p1.x, d.p1.y)).y; | |
}, | |
'stroke-width': 5 / _this.map.getZoom() | |
}); | |
paths = selection.selectAll('.path').data(data.annotations.filter(function(d) { | |
return d.path != null; | |
})); | |
enter_paths = paths.enter().append('g').attrs({ | |
"class": 'path image_portion' | |
}).on('click', function(d) { | |
return console.log("" + d.text.full); | |
}); | |
return enter_paths.append('path').attrs({ | |
d: function(d) { | |
return _this.to_path_description(projection, d.path); | |
}, | |
'stroke-width': 5 / _this.map.getZoom() | |
}); | |
}); | |
return overlay.addTo(_this.map); | |
}; | |
})(this)); | |
} | |
}; | |
}, | |
template: '<div id="map"></div>', | |
mounted: function() { | |
var center; | |
this.map = L.map('map', this.conf.map); | |
center = this.point(this.conf.width / 2, this.conf.height / 2); | |
this.map.setView(center, 2, { | |
animate: false | |
}); | |
L.tileLayer.zoomify(this.conf.tileLayer, { | |
width: this.conf.width, | |
height: this.conf.height | |
}).addTo(this.map); | |
L.control.zoom({ | |
position: this.conf.zoomControlPosition | |
}).addTo(this.map); | |
return this.loadOverlay(); | |
} | |
}; | |
}).call(this); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment