def test_default_observer_transform_hcc(): center = frames.HeliographicStonyhurst(0 * u.deg, 0 * u.deg, obstime="2017-07-11 15:00") hpc = center.transform_to(frames.Heliocentric(obstime="2017-07-11 15:00")) assert_quantity_allclose(hpc.y, -48471.1283979 * u.km)
def semi_circular_loop(length: u.m, theta0: u.deg = 0 * u.deg): """ Return a Heliographic Stonyhurst coordinate object with points of a semi circular loop in it. """ r_sun = const.R_sun def r_2_func(x): return np.arccos(0.5 * x / r_sun.to(u.cm).value) - np.pi + length.to( u.cm).value / 2. / x r_2 = scipy.optimize.bisect(r_2_func, length.to(u.cm).value / (2 * np.pi), length.to(u.cm).value / np.pi) * u.cm alpha = np.arccos(0.5 * (r_2 / r_sun).decompose()) phi = np.linspace(-np.pi * u.rad + alpha, np.pi * u.rad - alpha, 2000) # Quadratic formula to find r a = 1. b = -2 * (r_sun.to(u.cm) * np.cos(phi.to(u.radian))) c = r_sun.to(u.cm)**2 - r_2.to(u.cm)**2 r = (-b + np.sqrt(b**2 - 4 * a * c)) / 2 / a # Choose only points above the surface i_r = np.where(r > r_sun) r = r[i_r] phi = phi[i_r] hcc_frame = frames.Heliocentric( observer=SkyCoord(lon=0 * u.deg, lat=theta0, radius=r_sun, frame='heliographic_stonyhurst')) return SkyCoord(x=r.to(u.cm) * np.sin(phi.to(u.radian)), y=u.Quantity(r.shape[0] * [0 * u.cm]), z=r.to(u.cm) * np.cos(phi.to(u.radian)), frame=hcc_frame).transform_to('heliographic_stonyhurst')
def test_great_arc_calculable(start, end): c = SkyCoord(start[0]*u.degree, start[1]*u.degree, frame=frames.HeliographicStonyhurst, observer=frames.HeliographicStonyhurst(0*u.deg, 0*u.deg, 1*u.AU)) d = SkyCoord(end[0]*u.degree, end[1]*u.degree, frame=frames.HeliographicStonyhurst, observer=frames.HeliographicStonyhurst(0*u.deg, 0*u.deg, 1*u.AU)) gc = GreatArc(c, d) c_trans = c.transform_to(frames.Heliocentric) assert gc.start.x == c_trans.x assert gc.start.y == c_trans.y assert gc.start.z == c_trans.z assert gc.start.observer.lat == 0*u.deg assert gc.start.observer.lon == 0*u.deg assert gc.start.observer.radius == 1 * u.AU d_trans = d.transform_to(frames.Heliocentric(observer=c.observer)) assert gc.end.x == d_trans.x assert gc.end.y == d_trans.y assert gc.end.z == d_trans.z assert gc.end.observer.lat == 0*u.deg assert gc.end.observer.lon == 0*u.deg assert gc.end.observer.radius == 1 * u.AU np.testing.assert_almost_equal(gc.inner_angle.to('deg').value, 45.0) np.testing.assert_almost_equal(gc.radius.to('km').value, sun.constants.radius.to('km').value) np.testing.assert_almost_equal(gc.distance.to( 'km').value, sun.constants.radius.to('km').value * 2 * np.pi/8, decimal=1)
def rot_hcc(): return (f.Heliocentric, RotatedSunFrame(x=1 * u.AU, y=2 * u.AU, z=3 * u.AU, base=f.Heliocentric(observer='earth', obstime='2001-01-01'), duration=4 * u.day))
def test_hcc_observer_version(tmpdir): """ This test verifies that the heliocentric frame has an upto date list of the HGS schema versions by ensuring that a HPC frame with a instantiated HGS frame as the observer round trips correctly. """ time = "2021-10-13T11:08" obs = frames.HeliographicStonyhurst(0*u.deg, 0*u.deg, 1*u.AU, obstime=time) coord = frames.Heliocentric(1*u.Mm, 1*u.Mm, 1*u.Mm, obstime=time, observer=obs) assert_round_trip_frame(coord)
def semi_circular_loop(length: u.cm, latitude: u.deg = 0 * u.deg): """ Return HGS coordinates for a semi-circular loop """ angles = np.linspace(0, 1, 1000) * np.pi * u.rad z = length / np.pi * np.sin(angles) x = length / np.pi * np.cos(angles) hcc_frame = frames.Heliocentric(observer=frames.HeliographicStonyhurst( lon=0 * u.deg, lat=latitude, radius=constants.au)) return SkyCoord(x=x, y=np.zeros_like(x), z=z + constants.radius, frame=hcc_frame)
def test_great_arc_different_observer(aia171_test_map): a = SkyCoord(600 * u.arcsec, -600 * u.arcsec, frame=aia171_test_map.coordinate_frame) observer = SkyCoord(-10.0 * u.deg, 83 * u.deg, radius=0.9 * u.au, frame=frames.HeliographicStonyhurst, obstime=aia171_test_map.date) b = SkyCoord(400 * u.arcsec, 600 * u.arcsec, observer=observer, frame=frames.Helioprojective) # Test that the input observers are indeed different assert a.observer.lon != b.observer.lon assert a.observer.lat != b.observer.lat assert a.observer.radius != b.observer.radius # Create the great arc gc = GreatArc(a, b) # The start and end points stored internally are Heliocentric start = gc.start assert isinstance(start.frame, frames.Heliocentric) end = gc.end assert isinstance(end.frame, frames.Heliocentric) # The start and end points stored internally have the same observer assert start.observer.lon == end.observer.lon assert start.observer.lat == end.observer.lat assert start.observer.radius == end.observer.radius # The start point stored internally has the Heliocentric coordinates of the initial coordinate passed in. a2h = a.transform_to(frames.Heliocentric) assert start.x == a2h.x assert start.y == a2h.y assert start.z == a2h.z # The end point stored internally has the Heliocentric coordinates of the initial coordinate passed in. b2h = b.transform_to( frames.Heliocentric(observer=aia171_test_map.observer_coordinate)) # Missing an dp on b2h compared to end (TODO BUG?) np.testing.assert_almost_equal(end.x.value, b2h.x.value) np.testing.assert_almost_equal(end.y.value, b2h.y.value) np.testing.assert_almost_equal(end.z.value, b2h.z.value)
def test_obstime_hack(): """ Test that the obstime can be updated in place, this is used in the transform pipeline. """ h = frames.Heliocentric(observer="earth") obstime = "2011-01-01" h._obstime = obstime assert isinstance(h.observer, frames.HeliographicStonyhurst) earth = get_earth(obstime) obs = h._observer assert isinstance(obs, HeliographicStonyhurst) assert_quantity_allclose(obs.lon, earth.lon) assert_quantity_allclose(obs.lat, earth.lat) assert_quantity_allclose(obs.radius, earth.radius)
def semi_circular_loop(length: u.m, latitude: u.deg = 0 * u.deg): """ Return a Heliographic Stonyhurst coordinate object with points of a semi circular loop in it. """ r_sun = constants.radius def r_2_func(x): return np.arccos(0.5 * x / r_sun.to(u.cm).value) - np.pi + length.to( u.cm).value / 2. / x # Find the loop radius corresponding to the loop length r_2 = scipy.optimize.bisect(r_2_func, length.to(u.cm).value / (2 * np.pi), length.to(u.cm).value / np.pi) * u.cm alpha = np.arccos(0.5 * (r_2 / r_sun)) phi = np.linspace(-np.pi * u.rad + alpha, np.pi * u.rad - alpha, 2000) hcc_frame = frames.Heliocentric(observer=frames.HeliographicStonyhurst( lon=0 * u.deg, lat=latitude, radius=1 * u.AU)) return SkyCoord(x=r_2 * np.sin(phi), y=0 * u.cm, z=r_2 * np.cos(phi) + r_sun, frame=hcc_frame).transform_to('heliographic_stonyhurst')
def test_default_hcc_observer(): h = frames.Heliocentric() assert h.observer is None h = frames.Heliocentric(observer="mars") assert h.observer == "mars"
def behind_the_plane_of_the_sun(self): """ Returns True if the body is behind the plane of the Sun. """ return (self.body.transform_to(frames.Heliocentric(observer=self.observer))).z.value < 0
def test_great_arc_coordinates(points_requested, points_expected, first_point, last_point, last_inner_angle, last_distance, aia171_test_map): coordinate_frame = aia171_test_map.coordinate_frame a = SkyCoord(600 * u.arcsec, -600 * u.arcsec, frame=coordinate_frame) b = SkyCoord(-100 * u.arcsec, 800 * u.arcsec, frame=coordinate_frame) gc = GreatArc(a, b, points=points_requested) coordinates = gc.coordinates() inner_angles = gc.inner_angles() distances = gc.distances() # Ensure a GreatArc object is returned assert isinstance(gc, GreatArc) # Test the properties of the GreatArc object a_trans = a.transform_to(frames.Heliocentric) assert gc.start.x == a_trans.x assert gc.start.y == a_trans.y assert gc.start.z == a_trans.z b_trans = b.transform_to(frames.Heliocentric(observer=a.observer)) assert gc.end.x == b_trans.x assert gc.end.y == b_trans.y assert gc.end.z == b_trans.z assert gc.distance_unit == u.m assert gc.observer == a.observer assert gc.center.x == 0 * u.m assert gc.center.y == 0 * u.m assert gc.center.z == 0 * u.m assert u.allclose( gc.start_cartesian * u.m, np.asarray([428721.0913539, -428722.9051924, 341776.0910214]) * u.km) assert u.allclose( gc.end_cartesian * u.m, np.asarray([-71429.5229381, 571439.071248, 390859.5797815]) * u.km) assert u.allclose(gc.center_cartesian * u.m, np.asarray([0, 0, 0]) * u.km) assert u.allclose( gc.v1 * u.m, np.asarray([428721.0913539, -428722.9051924, 341776.0910214]) * u.km) assert u.allclose(gc._r, 696000000.0015007) assert u.allclose( gc.v2 * u.m, np.asarray([-71429.5229381, 571439.071248, 390859.5797815]) * u.km) assert u.allclose( gc.v3 * u.m, np.asarray([56761.6265851, 466230.7005856, 513637.0815867]) * u.km) # Inner angle assert gc.inner_angle.unit == u.rad np.testing.assert_almost_equal(gc.inner_angle.value, 1.8683580432741789) # Distance assert gc.distance.unit == u.m np.testing.assert_approx_equal(gc.distance.value, 1300377198.1299164) # Radius of the sphere assert gc.radius.unit == u.m assert u.isclose(gc.radius.value * u.m, 696000.000001501 * u.km) # Test the calculation of the SkyCoords # Coordinates method # Number of points assert len(coordinates) == points_expected # Start and end coordinates np.testing.assert_almost_equal(coordinates[0].Tx.value, first_point[0]) np.testing.assert_almost_equal(coordinates[0].Ty.value, first_point[1]) np.testing.assert_almost_equal(coordinates[-1].Tx.value, last_point[0]) np.testing.assert_almost_equal(coordinates[-1].Ty.value, last_point[1]) # Inner angles method # Inner angles assert len(inner_angles) == points_expected np.testing.assert_almost_equal(inner_angles[-1].value, last_inner_angle) # Distances method assert len(distances) == points_expected assert u.isclose(distances[-1].value * u.m, last_distance * u.km)