@@ -4,6 +4,7 @@ var Lib = require('../../../src/lib');
44var Geo = require ( '../../../src/plots/geo' ) ;
55var GeoAssets = require ( '../../../src/assets/geo_assets' ) ;
66var constants = require ( '../../../src/plots/geo/constants' ) ;
7+ var getFitboundsLonRange = require ( '../../../src/plots/geo/get_fitbounds_lon_range' ) ;
78var geoLocationUtils = require ( '../../../src/lib/geo_location_utils' ) ;
89var topojsonUtils = require ( '../../../src/lib/topojson_utils' ) ;
910
@@ -36,6 +37,82 @@ function move(fromX, fromY, toX, toY, delay) {
3637 } ) ;
3738}
3839
40+ describe ( 'Test geo fitbounds longitude range' , function ( ) {
41+ it ( 'returns the compact crossing range when point data straddles the antimeridian' , function ( ) {
42+ expect ( getFitboundsLonRange ( [ 131.8855 , - 179 ] ) ) . toEqual ( [ 131.8855 , 181 ] ) ;
43+ expect ( getFitboundsLonRange ( [ 170 , 175 , - 170 ] ) ) . toEqual ( [ 170 , 190 ] ) ;
44+ } ) ;
45+
46+ it ( 'keeps the naive range (null) when the data does not straddle the antimeridian' , function ( ) {
47+ expect ( getFitboundsLonRange ( [ 131.8855 , 179 ] ) ) . toBe ( null ) ;
48+ expect ( getFitboundsLonRange ( [ - 10 , 0 , 20 ] ) ) . toBe ( null ) ;
49+ } ) ;
50+
51+ it ( 'keeps the naive range (null) when the data spans the whole globe' , function ( ) {
52+ var lons = [ ] ;
53+ for ( var lon = 0 ; lon <= 360 ; lon += 2.5 ) lons . push ( lon ) ;
54+ expect ( getFitboundsLonRange ( lons ) ) . toBe ( null ) ;
55+ } ) ;
56+
57+ it ( 'returns null when fewer than two finite longitudes are available' , function ( ) {
58+ expect ( getFitboundsLonRange ( [ 10 ] ) ) . toBe ( null ) ;
59+ expect ( getFitboundsLonRange ( [ NaN , 5 ] ) ) . toBe ( null ) ;
60+ expect ( getFitboundsLonRange ( [ ] ) ) . toBe ( null ) ;
61+ } ) ;
62+ } ) ;
63+
64+ describe ( 'Test geo fitbounds with antimeridian-straddling points' , function ( ) {
65+ var gd ;
66+
67+ beforeEach ( function ( ) { gd = createGraphDiv ( ) ; } ) ;
68+
69+ afterEach ( destroyGraphDiv ) ;
70+
71+ function _plot ( lons ) {
72+ return Plotly . newPlot ( gd , [ {
73+ type : 'scattergeo' ,
74+ mode : 'markers' ,
75+ lat : [ 43.1155 , 32.7157 ] ,
76+ lon : lons
77+ } ] , {
78+ geo : { fitbounds : 'locations' , projection : { type : 'equirectangular' } } ,
79+ width : 700 ,
80+ height : 500
81+ } ) ;
82+ }
83+
84+ it ( 'centers on the compact crossing view when points straddle the antimeridian' , function ( done ) {
85+ // lon = [131.8855, -179] spans ~311deg the naive way; the compact view
86+ // crosses the antimeridian, giving a range around [131.8855, 181] (padded
87+ // for markers like any fitbounds map) and a projection rotated to its
88+ // mid-longitude (~156.4deg), not to the naive mid (~-24deg).
89+ _plot ( [ 131.8855 , - 179 ] ) . then ( function ( ) {
90+ var geoLayout = gd . _fullLayout . geo ;
91+ var lonRange = geoLayout . lonaxis . _ax . range ;
92+ // crosses the antimeridian (upper bound past 180) and stays compact
93+ // (~49deg plus a little padding), nowhere near the naive ~311deg.
94+ expect ( lonRange [ 0 ] ) . toBeLessThan ( 131.8855 ) ;
95+ expect ( lonRange [ 1 ] ) . toBeGreaterThan ( 181 ) ;
96+ expect ( lonRange [ 1 ] - lonRange [ 0 ] ) . toBeGreaterThan ( 49 ) ;
97+ expect ( lonRange [ 1 ] - lonRange [ 0 ] ) . toBeLessThan ( 70 ) ;
98+ expect ( geoLayout . _subplot . projection . rotate ( ) [ 0 ] ) . toBeCloseTo ( - 156.44 , 1 ) ;
99+ } )
100+ . then ( done , done . fail ) ;
101+ } ) ;
102+
103+ it ( 'keeps the naive centering when points do not straddle the antimeridian' , function ( done ) {
104+ _plot ( [ 131.8855 , 179 ] ) . then ( function ( ) {
105+ var geoLayout = gd . _fullLayout . geo ;
106+ // projection rotated to the naive mid-longitude (~155.4deg); the range is
107+ // not wrapped across the antimeridian (which would rotate near -24deg or +156deg)
108+ var rotateLon = geoLayout . _subplot . projection . rotate ( ) [ 0 ] ;
109+ expect ( rotateLon ) . toBeLessThan ( - 150 ) ;
110+ expect ( rotateLon ) . toBeGreaterThan ( - 160 ) ;
111+ } )
112+ . then ( done , done . fail ) ;
113+ } ) ;
114+ } ) ;
115+
39116describe ( 'Test Geo layout defaults' , function ( ) {
40117 var layoutAttributes = Geo . layoutAttributes ;
41118 var supplyLayoutDefaults = Geo . supplyLayoutDefaults ;
0 commit comments