import { select as d3Select } from "d3-selection" ; import { tile as d3Tile } from "d3-tile" ; import { Layer } from "./Layer" ; const constScale = 1 << 12 ; import "../src/OpenStreet.css" ; export class OpenStreet extends Layer { static _copyrightText = "© OpenStreetMap contributors" ; _tile ; _openStreet ; _copyright ; _copyrightBBox ; _prevTileProvider ; _zoomLayerID : number = 0 ; _prevZoomLevel ; constructor ( ) { super ( ) ; this . autoScaleMode ( "none" ) ; } layerEnter ( base , svgElement , domElement ) { Layer . prototype . layerEnter . apply ( this , arguments ) ; base . zoomExtent ( [ 0.1 , constScale * 4 ] ) ; this . _openStreet = svgElement . append ( "g" ) ; this . _copyright = svgElement . append ( "text" ) . attr ( "x" , - 100 ) . attr ( "y" , - 100 ) . style ( "opacity" , 0.5 ) . text ( OpenStreet . _copyrightText ) ; this . _copyrightBBox = this . _copyright . node ( ) . getBBox ( ) ; } layerUpdate ( base ) { this . _tile = d3Tile ( ) . size ( [ base . width ( ) , base . height ( ) ] ) . wrap ( false ) ; if ( ! this . visible ( ) ) { this . _copyright . text ( "" ) ; } else { this . _copyright . attr ( "x" , base . width ( ) - this . _copyrightBBox . width - this . _copyrightBBox . height / 2 ) . attr ( "y" , base . height ( ) - this . _copyrightBBox . height / 2 ) . text ( OpenStreet . _copyrightText ) ; } this . layerZoomed ( base ) ; } layerZoomed ( base ) { const scale = base . zoomScale ( ) ; const transform = base . zoomTranslate ( ) ; const tiles = this . _tile . scale ( scale * constScale ) . translate ( transform ) ( ) ; const tilesScale = tiles . scale / scale ; const tilesTranslate = [ tiles . translate [ 0 ] / tiles . scale , tiles . translate [ 1 ] / tiles . scale ] ; const zoomLevel = Math . round ( tilesScale * 1000 ) ; if ( this . _prevZoomLevel !== zoomLevel ) { this . _prevZoomLevel = zoomLevel ; this . _zoomLayerID ++ ; } const scaleG = this . _openStreet . selectAll ( ".scaleG" ) . data ( [ this . _zoomLayerID ] , d => d ) ; const scaleGUpdate = scaleG . enter ( ) . append ( "g" ) . attr ( "class" , "scaleG" ) . attr ( "transform" , stringify ( tilesScale , tilesTranslate ) ) . each ( function ( d ) { console . log ( d ) ; } ) . merge ( scaleG ) ; scaleG . exit ( ) . style ( "opacity" , 1 ) . transition ( ) . duration ( 1000 ) . style ( "opacity" , 0 ) . on ( "end" , function ( d ) { d3Select ( this ) . selectAll ( ".image" ) . attr ( "xlink:href" , null ) ; } ) . remove ( ) ; const image = scaleGUpdate . selectAll ( ".image" ) . data ( tiles , function ( d ) { return "" + d . x + "," + d . y ; } ) ; image . enter ( ) . append ( "image" ) . attr ( "class" , "image" ) . style ( "opacity" , 0 ) . attr ( "x" , function ( d ) { return d . tx ; } ) . attr ( "y" , function ( d ) { return d . ty ; } ) . attr ( "width" , 256 ) . attr ( "height" , 256 ) . attr ( "xlink:href" , function ( d ) { return "http://" + "abc" [ d . y % 3 ] + ".tile.openstreetmap.org/" + d . z + "/" + d . x + "/" + d . y + ".png" ; } ) . each ( function ( d ) { console . log ( "http://" + "abc" [ d . y % 3 ] + ".tile.openstreetmap.org/" + d . z + "/" + d . x + "/" + d . y + ".png" ) ; } ) . transition ( ) . duration ( 500 ) . style ( "opacity" , 1 ) ; } tileProvider : { ( ) : string ; ( _ ) : OpenStreet ; } ; tileProvider_exists : ( ) => boolean ; } OpenStreet . prototype . _class += " map_OpenStreet" ; OpenStreet . prototype . publish ( "tileProvider" , "OpenStreetMap" , "set" , "Tile Provider" , [ "OpenStreetMap" , "OpenStreetMap Hot" , "MapQuest" , "MapQuest Sat" , "Stamen Watercolor" , "OpenCycleMap" ] , { tags : [ "Basic" , "Shared" ] } ) ; function stringify ( scale , translate ) { const k = scale / 256 ; return "translate(" + - constScale / 2 + "," + - constScale / 2 + ") scale(" + k + ")" ; }