def run_test(a, scale, shear=0, translation=(0, 0), tol=1e-8): A = mkA(a, scale=scale, shear=shear, translation=translation) R, W, S = decompose_rws(A) assert get_diff(A, R * W * S) < tol assert get_diff(S, mkA(0, scale)) < tol assert get_diff(R, mkA(a, translation=translation)) < tol
def test_geobox(): points_list = [ [(148.2697, -35.20111), (149.31254, -35.20111), (149.31254, -36.331431), (148.2697, -36.331431)], [(148.2697, 35.20111), (149.31254, 35.20111), (149.31254, 36.331431), (148.2697, 36.331431)], [(-148.2697, 35.20111), (-149.31254, 35.20111), (-149.31254, 36.331431), (-148.2697, 36.331431)], [(-148.2697, -35.20111), (-149.31254, -35.20111), (-149.31254, -36.331431), (-148.2697, -36.331431), (148.2697, -35.20111)], ] for points in points_list: polygon = geometry.polygon(points, crs=epsg3577) resolution = (-25, 25) geobox = geometry.GeoBox.from_geopolygon(polygon, resolution) assert abs(resolution[0]) > abs(geobox.extent.boundingbox.left - polygon.boundingbox.left) assert abs(resolution[0]) > abs(geobox.extent.boundingbox.right - polygon.boundingbox.right) assert abs(resolution[1]) > abs(geobox.extent.boundingbox.top - polygon.boundingbox.top) assert abs(resolution[1]) > abs(geobox.extent.boundingbox.bottom - polygon.boundingbox.bottom) A = mkA(0, scale=(10, -10), translation=(-48800, -2983006)) w, h = 512, 256 gbox = geometry.GeoBox(w, h, A, epsg3577) assert gbox.shape == (h, w) assert gbox.transform == A assert gbox.extent.crs == gbox.crs assert gbox.geographic_extent.crs == epsg4326 assert gbox.extent.boundingbox.height == h*10.0 assert gbox.extent.boundingbox.width == w*10.0 assert isinstance(str(gbox), str) assert 'EPSG:3577' in repr(gbox) assert geometry.GeoBox(1, 1, mkA(0), epsg4326).geographic_extent.crs == epsg4326 g2 = gbox[:-10, :-20] assert g2.shape == (gbox.height - 10, gbox.width - 20) # step of 1 is ok g2 = gbox[::1, ::1] assert g2.shape == gbox.shape assert gbox[0].shape == (1, gbox.width) assert gbox[:3].shape == (3, gbox.width) with pytest.raises(NotImplementedError): gbox[::2, :] # too many slices with pytest.raises(ValueError): gbox[:1, :1, :] assert gbox.buffered(10, 0).shape == (gbox.height + 2*1, gbox.width) assert gbox.buffered(30, 20).shape == (gbox.height + 2*3, gbox.width + 2*2) assert (gbox | gbox) == gbox assert (gbox & gbox) == gbox
def mk_transform(sx, sy): A = mkA(37, scale=(sx, sy), translation=(2127, 93891)) def transofrom(pts): return [A * x for x in pts] return transofrom
def test_fit(): from random import uniform def run_test(A, n, tol=1e-5): X = [(uniform(0, 1), uniform(0, 1)) for _ in range(n)] Y = [A * x for x in X] A_ = affine_from_pts(X, Y) assert get_diff(A, A_) < tol A = mkA(13, scale=(3, 4), shear=3, translation=(100, -3000)) run_test(A, 3) run_test(A, 10) run_test(mkA(), 3) run_test(mkA(), 10)
def test_geobox_xr_coords(): A = mkA(0, scale=(10, -10), translation=(-48800, -2983006)) w, h = 512, 256 gbox = GeoBox(w, h, A, epsg3577) cc = gbox.xr_coords() assert list(cc) == ['y', 'x'] assert cc['y'].shape == (gbox.shape[0],) assert cc['x'].shape == (gbox.shape[1],) assert 'crs' in cc['y'].attrs assert 'crs' in cc['x'].attrs cc = gbox.xr_coords(with_crs=True) assert list(cc) == ['y', 'x', 'spatial_ref'] assert cc['spatial_ref'].shape == () assert cc['spatial_ref'].attrs['spatial_ref'] == gbox.crs.wkt assert isinstance(cc['spatial_ref'].attrs['grid_mapping_name'], str) cc = gbox.xr_coords(with_crs='Albers') assert list(cc) == ['y', 'x', 'Albers'] # geographic CRS A = mkA(0, scale=(0.1, -0.1), translation=(10, 30)) gbox = GeoBox(w, h, A, 'epsg:4326') cc = gbox.xr_coords(with_crs=True) assert list(cc) == ['latitude', 'longitude', 'spatial_ref'] assert cc['spatial_ref'].shape == () assert cc['spatial_ref'].attrs['spatial_ref'] == gbox.crs.wkt assert isinstance(cc['spatial_ref'].attrs['grid_mapping_name'], str) # missing CRS for GeoBox gbox = GeoBox(w, h, A, None) cc = gbox.xr_coords(with_crs=True) assert list(cc) == ['y', 'x'] # check CRS without name crs = MagicMock() crs.projected = True crs.wkt = epsg3577.wkt crs.epsg = epsg3577.epsg crs._crs = MagicMock() crs._crs.to_cf.return_value = {} assert _mk_crs_coord(crs).attrs['grid_mapping_name'] == '??'
def test_apply_affine(): A = mkA(rot=10, scale=(3, 1.3), translation=(-100, +2.3)) xx, yy = np.meshgrid(np.arange(13), np.arange(11)) xx_, yy_ = apply_affine(A, xx, yy) assert xx_.shape == xx.shape assert yy_.shape == xx.shape xy_expect = [A * (x, y) for x, y in zip(xx.ravel(), yy.ravel())] xy_got = [(x, y) for x, y in zip(xx_.ravel(), yy_.ravel())] np.testing.assert_array_almost_equal(xy_expect, xy_got)
def test_pix_transform(): pt = tuple([ int(x / 10) * 10 for x in geometry.point(145, -35, epsg4326).to_crs(epsg3577).coords[0] ]) A = mkA(scale=(20, -20), translation=pt) src = geometry.GeoBox(1024, 512, A, epsg3577) dst = geometry.GeoBox.from_geopolygon(src.geographic_extent, (0.0001, -0.0001)) tr = native_pix_transform(src, dst) pts_src = [(0, 0), (10, 20), (300, 200)] pts_dst = tr(pts_src) pts_src_ = tr.back(pts_dst) np.testing.assert_almost_equal(pts_src, pts_src_) assert tr.linear is None # check identity transform tr = native_pix_transform(src, src) pts_src = [(0, 0), (10, 20), (300, 200)] pts_dst = tr(pts_src) pts_src_ = tr.back(pts_dst) np.testing.assert_almost_equal(pts_src, pts_src_) np.testing.assert_almost_equal(pts_src, pts_dst) assert tr.linear is not None assert tr.back.linear is not None assert tr.back.back is tr # check scale only change tr = native_pix_transform(src, scaled_down_geobox(src, 2)) pts_dst = tr(pts_src) pts_src_ = tr.back(pts_dst) assert tr.linear is not None assert tr.back.linear is not None assert tr.back.back is tr np.testing.assert_almost_equal(pts_dst, [(x / 2, y / 2) for (x, y) in pts_src]) np.testing.assert_almost_equal(pts_src, pts_src_)
def test_geobox_scale_down(): from datacube.utils.geometry import GeoBox, CRS crs = CRS('EPSG:3857') A = mkA(0, (111.2, 111.2), translation=(125671, 251465)) for s in [2, 3, 4, 8, 13, 16]: gbox = GeoBox(233 * s, 755 * s, A, crs) gbox_ = scaled_down_geobox(gbox, s) assert gbox_.width == 233 assert gbox_.height == 755 assert gbox_.crs is crs assert gbox_.extent.contains(gbox.extent) assert gbox.extent.difference(gbox.extent).area == 0.0 gbox = GeoBox(1, 1, A, crs) for s in [2, 3, 5]: gbox_ = scaled_down_geobox(gbox, 3) assert gbox_.shape == (1, 1) assert gbox_.crs is crs assert gbox_.extent.contains(gbox.extent)
def test_geobox(): points_list = [ [(148.2697, -35.20111), (149.31254, -35.20111), (149.31254, -36.331431), (148.2697, -36.331431)], [(148.2697, 35.20111), (149.31254, 35.20111), (149.31254, 36.331431), (148.2697, 36.331431)], [(-148.2697, 35.20111), (-149.31254, 35.20111), (-149.31254, 36.331431), (-148.2697, 36.331431)], [(-148.2697, -35.20111), (-149.31254, -35.20111), (-149.31254, -36.331431), (-148.2697, -36.331431), (148.2697, -35.20111)], ] for points in points_list: polygon = geometry.polygon(points, crs=epsg3577) resolution = (-25, 25) geobox = geometry.GeoBox.from_geopolygon(polygon, resolution) assert abs(resolution[0]) > abs(geobox.extent.boundingbox.left - polygon.boundingbox.left) assert abs(resolution[0]) > abs(geobox.extent.boundingbox.right - polygon.boundingbox.right) assert abs(resolution[1]) > abs(geobox.extent.boundingbox.top - polygon.boundingbox.top) assert abs(resolution[1]) > abs(geobox.extent.boundingbox.bottom - polygon.boundingbox.bottom) A = mkA(0, scale=(10, -10), translation=(-48800, -2983006)) w, h = 512, 256 gbox = GeoBox(w, h, A, epsg3577) assert gbox.shape == (h, w) assert gbox.transform == A assert gbox.extent.crs == gbox.crs assert gbox.geographic_extent.crs == epsg4326 assert gbox.extent.boundingbox.height == h * 10.0 assert gbox.extent.boundingbox.width == w * 10.0 assert isinstance(str(gbox), str) assert 'EPSG:3577' in repr(gbox) assert GeoBox(1, 1, mkA(0), epsg4326).geographic_extent.crs == epsg4326 assert GeoBox(1, 1, mkA(0), None).dimensions == ('y', 'x') g2 = gbox[:-10, :-20] assert g2.shape == (gbox.height - 10, gbox.width - 20) # step of 1 is ok g2 = gbox[::1, ::1] assert g2.shape == gbox.shape assert gbox[0].shape == (1, gbox.width) assert gbox[:3].shape == (3, gbox.width) with pytest.raises(NotImplementedError): gbox[::2, :] # too many slices with pytest.raises(ValueError): gbox[:1, :1, :] assert gbox.buffered(10, 0).shape == (gbox.height + 2 * 1, gbox.width) assert gbox.buffered(30, 20).shape == (gbox.height + 2 * 3, gbox.width + 2 * 2) assert (gbox | gbox) == gbox assert (gbox & gbox) == gbox assert gbox.is_empty() is False assert bool(gbox) is True assert (gbox[:3, :4] & gbox[3:, 4:]).is_empty() assert (gbox[:3, :4] & gbox[30:, 40:]).is_empty() with pytest.raises(ValueError): geobox_intersection_conservative([]) with pytest.raises(ValueError): geobox_union_conservative([]) # can not combine across CRSs with pytest.raises(ValueError): bounding_box_in_pixel_domain(GeoBox(1, 1, mkA(0), epsg4326), GeoBox(2, 3, mkA(0), epsg3577))
def test_affine_checks(): assert is_affine_st(mkA(scale=(1, 2), translation=(3, -10))) is True assert is_affine_st(mkA(scale=(1, -2), translation=(-3, -10))) is True assert is_affine_st(mkA(rot=0.1)) is False assert is_affine_st(mkA(shear=0.4)) is False