def check(mk, time=False, report=False): frames_to_check = False if not time: today = datetime.datetime.now() time = today.strftime("%Y-%m-%dT%H:%M:%S") frame_dict = gen_frame_dict(mk, report=report) spiceypy.furnsh(mk) et = spiceypy.utc2et(time) for key in frame_dict.keys(): if frame_dict[key]['class'] == 4: fname = frame_dict[key]['name'] try: spiceypy.pxform(fname, 'J2000', et) except SpiceyError: frames_to_check = True print( f'Frame {fname} not properly defined at {time}\n' + f' NAME: {frame_dict[key]["name"]}\n' + f' CLASS: {frame_dict[key]["class"]}\n' + f' ID: {frame_dict[key]["id"]}\n' + f' CENTER: {frame_dict[key]["center"]}\n' + f' RELATIVE: {frame_dict[key]["relative"]}\n' ) pass spiceypy.kclear() if not frames_to_check: print(f'All {len(frame_dict)} frames are correct @ {time}') return
def test_spicepy_state_transformation(self): spice.furnsh(self.cass.metakernel) T = spice.sxform('IAU_EARTH', 'IAU_SATURN', self.etOne) R = spice.pxform('IAU_EARTH', 'IAU_SATURN', self.etOne) (Rout, wout) = spice.xf2rav(T) np.testing.assert_array_almost_equal(Rout, R) spice.kclear()
def clear_kernals(self): """ A function to clear out the loaded spice kernals. :return: """ spice.kclear() return
def __init__(self, meta_kernel_path): """Create an instance loading the spice kernel in the given meta kernel file. Parameters ---------- meta_kernel_path : `str` or `pathlib.Path` Path to the meta kernel """ self.meta_kernel_path = Path(meta_kernel_path) if not self.meta_kernel_path.exists(): raise ValueError(f'Meta kernel not found: {self.meta_kernel_path}') curdir = os.getcwd() try: # change to the 'kernels' dir os.chdir(self.meta_kernel_path.parent) # unload all old kernels spiceypy.kclear() # load the meta kernel spiceypy.furnsh(str(self.meta_kernel_path)) # spiceypy.unload(str(self.mod_meta_kernel_path)) finally: # change back to the old working directory os.chdir(curdir)
def Furnisher(k): ''' This function is used to load all kernels needed in an operation. Comment out kernels not in use and add the ones in use. Arguments: NA Returns: NA ''' spice.kclear() spice.furnsh('naif0008.tls.txt') if k == '310+341+435': spice.furnsh('jup310.bsp') spice.furnsh('jup341.bsp') spice.furnsh('de435.bsp') elif k == '310+341': spice.furnsh('jup310.bsp') spice.furnsh('jup341.bsp') elif k == '310+435': spice.furnsh('de435.bsp') spice.furnsh('jup310.bsp') elif k == '341+435': spice.furnsh('jup341.bsp') spice.furnsh('de435.bsp') elif k == '310': spice.furnsh('jup310.bsp') elif k == '341': spice.furnsh('jup341.bsp') elif k == '435': spice.furnsh('de435.bsp') pass
def test_near_landing_coverage(self): spice.furnsh(self.near.metakernel) utc = ['Feb 12, 2001 12:00:00 UTC', 'Feb 12, 2001 20:05:00 UTC'] etone = 35251264.18507089 ettwo = 35280364.18507829 np.testing.assert_almost_equal(spice.str2et(utc[0]), etone) np.testing.assert_almost_equal(spice.str2et(utc[1]), ettwo) spice.kclear()
def reload(self) -> None: logger = logging.getLogger(__name__) # clear all kernels spiceypy.kclear() for kernel in self.kernel_list: kernel.load()
def test_earth_spk_coverage(self): spice.furnsh(self.near.metakernel) spkids = spice.spkobj(self.near.SpkPlanet) cover = spice.stypes.SPICEDOUBLE_CELL(1000) spice.spkcov(self.near.SpkPlanet, 399, cover) result = [x for x in cover] expected_result = [-633873600.0, 347630400.0] np.testing.assert_array_almost_equal(result, expected_result) spice.kclear()
def test_eros_spk1_coverage(self): spice.furnsh(self.near.metakernel) code = spice.bodn2c('EROS') cover = spice.stypes.SPICEDOUBLE_CELL(1000) spice.spkcov(self.near.SpkEros, code, cover) result = [x for x in cover] expected_result = [-126273600.0, 37886400.0] np.testing.assert_array_almost_equal(result, expected_result) spice.kclear()
def test_msi_frame_transpose(self): spice.kclear() spice.furnsh(self.near.metakernel) utc = 'Feb 2, 2001 14:20:10 UTC' et = spice.str2et(utc) Rb2c = spice.pxform(self.near.near_body_frame, self.near.near_msi_frame, et) Rc2b = spice.pxform(self.near.near_msi_frame, self.near.near_body_frame, et) np.testing.assert_array_almost_equal_nulp(Rb2c, Rc2b.T) spice.kclear()
def test_msi_boresight_vector(self): spice.kclear() spice.furnsh(self.near.metakernel) bs_near_body = np.array([.9999988429, -.0004838414, .0014422523]) bs_msi_frame = np.array([1, 0, 0]) et = spice.str2et('Feb 12, 2001 UTC') Rc2b = spice.pxform(self.near.near_msi_frame, self.near.near_body_frame, et) np.testing.assert_array_almost_equal(Rc2b.dot(bs_msi_frame), bs_near_body) spice.kclear()
def main(): f_KERNELS = 'D:\\naif\\icy\\kernels\\gen\\' spice.furnsh(f_KERNELS + 'spk\\de421.bsp') spice.furnsh(f_KERNELS + 'lsk\\naif0011.tls') spice.furnsh(f_KERNELS + 'pck\\moon_pa_de421_1900-2050.bpc') spice.furnsh(f_KERNELS + 'pck\\earth_latest_high_prec.bpc') spice.furnsh(f_KERNELS + 'pck\\pck00010.tpc') spice.furnsh(f_KERNELS + 'fk\\moon_080317.tf') spice.furnsh(f_KERNELS + 'fk\\moon_assoc_pa.tf') spice.furnsh(f_KERNELS + 'fk\\moon_assoc_me.tf') spice.furnsh(f_KERNELS + 'lsk\\naif0011.tls.pc') #####无人机 brdf_file = 'H:\\BRDF\\dunhuang\\2019年试验\\0824-16.43定点不同高度-场外\\16.43定点不同高度-场外.csv' df = pd.read_csv(brdf_file, encoding='utf-8-sig') wave_num = 800 point_wave = df.loc[wave_num + 5].astype("float") wave = pd.array(df['高度'][5:].astype("float")) time_ymd = df.loc[1][2:-1] time_hms = df.loc[2][2:-1] #print(time_ymd,time_hms) lat = df.loc[3][2:-1].astype("float") # 纬度 lon = df.loc[4][2:-1].astype("float") # 经度 #print('UAV_wavelength:',wave[wave_num]) ref = np.array(point_wave[2:-1]) print('ref:', len(ref)) #height = [10, 10, 20, 20, 30, 30, 50, 50, 100, 100, 150, 150, 200, 200, 250, 250, 250, 250, 200, 200, 150, 150, 100, # 100, 50, 50, 30, 30, 20, 20, 10, 10] height = [ '10', '20', '30', '50', '100', '150', '200', '250', '降250', '降200', '降150', '降100', '降50', '降30', '降20', '降10' ] ref = np.array(df.loc[wave_num + 5].astype("float")[2:-1]) print(wave[wave_num], ref) h_ref = [] for i in range(round(len(ref) / 2)): #time_ymd = df.loc[0][i*2] mean_ref = (ref[i * 2] + ref[i * 2 + 1]) / 2 h_ref.append(mean_ref) print(i, height[i], mean_ref) fig, ax = plt.subplots() #print(len(local_point_num), len(ref)) #line1, = ax.plot(local_point_num, local_ref, 'o', ls='-',label=u'跑场, 其归一化std为:'+str(local_std)) #line1.set_dashes([2, 2, 10, 2]) # 2pt line, 2pt break, 10pt line, 2pt break line2, = ax.plot(height, h_ref, 'o', ls='-', dashes=[6, 2], label=u'外场') ax.set_xlabel("离地高度(m)") ax.set_title("场地均一性,波长:" + str(wave[wave_num]) + 'nm') ax.set_ylabel("反射率(%)") ax.legend() plt.show() spice.kclear() print('##FINISH###')
def test_msi_frame_transformation_fixed(self): spice.kclear() spice.furnsh(self.near.metakernel) etone = spice.str2et('Jan 1, 2001 10:04:02.2 UTC') ettwo = spice.str2et('Feb 12, 2001 18:03:02.6 UTC') Rone = spice.pxform(self.near.near_body_frame, self.near.near_msi_frame, etone) Rtwo = spice.pxform(self.near.near_body_frame, self.near.near_msi_frame, ettwo) np.testing.assert_array_almost_equal(Rone, Rtwo) spice.kclear()
def test_disable_found_catch(): spice.kclear() with spice.no_found_check(): name, found = spice.bodc2n(-9991) assert not found with pytest.raises(spice.stypes.SpiceyError): spice.bodc2n(-9991) # try more hands on method spice.found_check_off() name, found = spice.bodc2n(-9991) assert not found spice.found_check_on() spice.kclear()
def test_toBoolVector(): madeFromList = stypes.toBoolVector([False, True, False]) assert len(madeFromList) == 3 madeFromTuple = stypes.toBoolVector((False, True, False)) assert len(madeFromTuple) == 3 madeFromNumpyArray = stypes.toBoolVector(np.ones((3, 1), dtype=bool)) assert len(madeFromNumpyArray) == 3 TestArray3 = ctypes.c_bool * 3 madeFromCtypesArray = stypes.toBoolVector(TestArray3(False, True, False)) assert len(madeFromCtypesArray) == 3 with pytest.raises(TypeError): stypes.toBoolVector("ABCD") spice.kclear()
def __init__(self, json_file: str = None) -> None: logger = logging.getLogger(__name__) # clear all kernels spiceypy.kclear() self.kernel_list = [] self.group_list = [] base_path = os.path.join(os.path.dirname(heliosat.__file__), "spacecraft") self.data_path = os.getenv( 'HELIOSAT_DATAPATH', os.path.join(os.path.expanduser("~"), ".heliosat")) logger.debug("using data path \"%s\"", self.data_path) if json_file is None: json_file = os.path.join(base_path, "manager.json") json_mang = load_json(json_file) if json_mang["default_kernel_path"]: self.all_grps = load_json( os.path.join(base_path, json_mang["default_kernel_path"])) else: self.all_grps = {} if json_mang["default_spacecraft_path"]: self.all_spcs = load_json( os.path.join(base_path, json_mang["default_spacecraft_path"])) else: self.all_spcs = {} # update all groups and spacecraft for sub_folder in json_mang["sub_folders"]: if os.path.isfile( os.path.join(base_path, sub_folder, "kernels.json")): self.update_groups( os.path.join(base_path, sub_folder, "kernels.json")) if os.path.isfile( os.path.join(base_path, sub_folder, "{}.json".format(sub_folder))): self.update_spacecraft( os.path.join(base_path, sub_folder, "{}.json".format(sub_folder))) self.load_spacecraft()
def test_SpiceEllipse(): spice.kclear() spice.reset() viewpt = [2.0, 0.0, 0.0] limb = spice.edlimb(np.sqrt(2), 2.0 * np.sqrt(2), np.sqrt(2), viewpt) expected_s_minor = [0.0, 0.0, -1.0] expected_s_major = [0.0, 2.0, 0.0] expectedCenter = [1.0, 0.0, 0.0] npt.assert_array_almost_equal(limb.center, expectedCenter) npt.assert_array_almost_equal(limb.semi_major, expected_s_major) npt.assert_array_almost_equal(limb.semi_minor, expected_s_minor) assert str(limb).startswith("<SpiceEllipse") spice.reset() spice.kclear()
def test_SpiceEllipse(): spice.kclear() spice.reset() viewpt = [2.0, 0.0, 0.0] limb = spice.edlimb(np.sqrt(2), 2.0 * np.sqrt(2), np.sqrt(2), viewpt) expectedSMinor = [0.0, 0.0, -1.0] expectedSMajor = [0.0, 2.0, 0.0] expectedCenter = [1.0, 0.0, 0.0] npt.assert_array_almost_equal(limb.center, expectedCenter) npt.assert_array_almost_equal(limb.semi_major, expectedSMajor) npt.assert_array_almost_equal(limb.semi_minor, expectedSMinor) assert str(limb).startswith("<SpiceEllipse") spice.reset() spice.kclear()
def info(self): """Read and Output info about the loaded kernels """ spice.kclear() spice.furnsh(self.metakernel) self.spkList = [ self.SpkPlanet, self.SpkEros, self.SpkEros2, self.SpkMath, self.SpkNearLanded, self.SpkNearOrbit, self.SpkStations ] self.ckList = [self.Ck] self.pckList = [self.PckEros1, self.PckEros2] # check SPK coverage self.bodies = {} self.bodies_coverage = {} for spk in self.spkList: idcell = spice.spkobj(spk) for code in idcell: cover = spice.stypes.SPICEDOUBLE_CELL(1000) spice.spkcov(spk, code, cover) self.bodies[str(code)] = spice.bodc2n(code) self.bodies[spice.bodc2n(code)] = code self.bodies_coverage[str(code)] = [x for x in cover] self.bodies_coverage[spice.bodc2n(code)] = [x for x in cover] # check CK coverage self.ckframes = {} self.ckframes_coverage = {} for ck in self.ckList: idcell = spice.ckobj(ck) for code in idcell: cover = spice.ckcov(ck, code, True, 'SEGMENT', 0.0, 'TDB') self.ckframes[str(code)] = spice.frmnam(code) self.ckframes[spice.frmnam(code)] = code self.ckframes_coverage[str(code)] = [x for x in cover] self.ckframes_coverage[spice.frmnam(code)] = [x for x in cover] # check pck coverage self.pckframes = {} for pck in self.pckList: ids = spice.stypes.SPICEINT_CELL(1000) spice.pckfrm(pck, ids) for code in ids: self.pckframes[str(code)] = spice.frmnam(code) self.pckframes[spice.frmnam(code)] = code spice.kclear()
def exitNicely(sig, frame): """ aether-rest-server.py -- exitNicely: This function is called when the program receives a SIGINT signal. It simply clears the furnished kernels within the SPICE subsystem and exits. Params: sig, frame. Both are unused, but are required by the signal package since the function is a callback. Returns: None. """ spice.kclear() print("\nCleared loaded kernels.\nExiting...") exit(0)
def f_manage_kernels(kernel_meta): #Unload all kernels spiceypy.unload( kernel_meta ) #Load the necessary kernels from meta file spiceypy.kclear() spiceypy.furnsh(kernel_meta) spiceypy.furnsh(r'E:\Data Science Projects\Space Science\SpaceScience-P2-SSBandSunWobbling\data\external\_kernels\lsk\naif0012.tls') #List loaded kernels count = spiceypy.ktotal( 'ALL' ) for i in range(0, count): [ file, type, source, handle] = spiceypy.kdata(i, 'ALL'); print( 'File {0}'.format(file) ) print( 'Type {0}'.format(type) ) print( 'Source {0}\n'.format(source) )
class TestSpiceyPyFunctions(): cass = kernels.CassiniKernels() spice.furnsh(cass.metakernel) utc = ['Jun 20, 2004', 'Dec 1, 2005'] etOne = spice.str2et(utc[0]) etTwo = spice.str2et(utc[1]) step = 4000 times = np.linspace(etOne, etTwo, step) spice.kclear() def test_spiceypy_cassini(self): spice.furnsh(self.cass.metakernel) true_initial_pos = [-5461446.61080924 ,-4434793.40785864 ,-1200385.93315424] positions, lightTimes = spice.spkpos('Cassini', self.times, 'J2000', 'None', 'SATURN BARYCENTER') np.testing.assert_array_almost_equal(positions[0], true_initial_pos) spice.kclear() def test_spicepy_rotation_matrix_identity(self): spice.furnsh(self.cass.metakernel) R_E2E = spice.pxform('IAU_EARTH', 'IAU_EARTH', self.etOne) np.testing.assert_array_almost_equal(R_E2E, np.eye(3)) spice.kclear() # @pytest.mark.skip('failing') def test_spicepy_state_transformation(self): spice.furnsh(self.cass.metakernel) T = spice.sxform('IAU_EARTH', 'IAU_SATURN', self.etOne) R = spice.pxform('IAU_EARTH', 'IAU_SATURN', self.etOne) (Rout, wout) = spice.xf2rav(T) np.testing.assert_array_almost_equal(Rout, R) spice.kclear()
def test_msi_frame_transformation(self): """Check the frame at a specific time """ spice.kclear() spice.furnsh(self.near.metakernel) utc = ['Feb 10, 2001 12:00:00 UTC'] et = spice.str2et(utc) R_b2c = spice.pxform(self.near.near_body_frame, self.near.near_msi_frame, et) R_b2c_actual = np.array([ [.9999988429, -.0004838414, .0014422523], [.0004838419, .9999998829, .0000000000], [-.0014422522, .0000006978, .9999989600]]) spice.kclear() np.testing.assert_array_almost_equal(R_b2c, R_b2c_actual)
def test_near_body_frames(self): """Transformation from Body fixed frame to prime frame There is a constant rotation of 135 deg about the Z/Third axis """ spice.furnsh(self.near.metakernel) ckid = spice.ckobj(self.near.Ck)[0] cover = spice.ckcov(self.near.Ck, ckid, False, 'INTERVAL', 0.0, 'SCLK') R, av, clkout = spice.ckgpav(ckid, cover[0], 0, 'NEAR_SC_BUS') ang = 135*np.pi/180 R_act = np.array([[np.cos(ang), -np.sin(ang), 0], [np.sin(ang), np.cos(ang), 0], [0, 0, 1]]) np.testing.assert_array_almost_equal(R, R_act) np.testing.assert_array_almost_equal(av, np.zeros(3)) np.testing.assert_almost_equal(clkout, cover[0]) spice.kclear()
def unload_kernels(): """Unload kernels""" # global last_spice_time_window try: spiceypy.kclear() # But, we always want the LSK loaded. This should be safe provided # a) celsius was loaded first (safe assertion, this code won't work # without it), meaning that the latest.tls was updated if needs be # b) uptime for this instance is less than the lifetime of a tls kernel # (years?) spiceypy.furnsh( os.getenv("SC_DATA_DIR", default=expanduser('~/data/')) + \ 'latest.tls' ) spiceypy.last_spice_time_window = 'MVN:NONE_UNLOADED' except RuntimeError as e: spiceypy.last_spice_time_window = 'MVN:NONE_ERROR' raise e
def get_state(self, julianTime): # utc is an array of julian dates spice.furnsh(self.dataDir + "/raDec2PixKernels.txt") if np.isscalar(julianTime): julianTime = ru.make_col(np.array([julianTime])) if julianTime.ndim == 2: julianTime = julianTime.reshape((julianTime.size, )) julianTimes = Time(julianTime, format='jd', scale='utc') times = spice.str2et(julianTimes.iso) # in case the input is just a float with no len if not hasattr(times, "__len__"): times = [times] state = np.zeros((len(times), 6)) for i in range(len(times)): state[i, :], lightTimes = spice.spkezr('Kepler', times[i], 'J2000', 'NONE', 'SUN') spice.kclear() return state
def clear_uploaded_kernels(): """ aether-rest-server.py -- spk_clear This function allows users to clear all the uploaded kernels. Params: None Returns: a Flask response object with a list of strings. Each string in the list is the name of a body which was removed. """ # this function modifies the aether_bodies object so it must be declared global. global aether_bodies removed_bod_names = aether_bodies.removeUploadedKernels() spice.kclear() mkw.write() spice.furnsh("./SPICE/kernels/cumulative_metakernel.tm") return returnResponse(removed_bod_names, 200)
def test_found_check(): spice.kclear() spice.found_check_off() name, found = spice.bodc2n(-9991) assert not found spice.kclear() with spice.found_check(): with pytest.raises(spice.stypes.SpiceyError): name = spice.bodc2n(-9991) assert not spice.get_found_catch_state() spice.found_check_on() assert spice.get_found_catch_state() spice.kclear()
def test_recursive_disable_found_catch(): spice.kclear() assert spice.config.catch_false_founds def _recursive_call(i): if i <= 0: return else: with spice.no_found_check(): name, found = spice.bodc2n(-9991) assert not found _recursive_call(i-1) assert spice.config.catch_false_founds _recursive_call(100) spice.kclear() spice.found_check_off() _recursive_call(100) spice.kclear() spice.found_check_on() _recursive_call(100) spice.kclear()
def load_kernels(time=None, force=False, verbose=False, load_all=False, keep_previous=False): """Load spice kernels, with a stateful thing to prevent multiple calls""" last_spice_time_window = getattr(spiceypy, 'last_spice_time_window', 'MVN:NONE') if load_all: # Launch to now + 10 yrs start = celsius.spiceet("2013-11-19T00:00") finish = celsius.spiceet(celsius.now() + 10.*86400.*365.) if time is None: start = None finish = None start_str = 'NO_TIME_SET' finish_str = '' start_int=-999999 finish_int=-999999 else: if hasattr(time, '__len__'): start = time[0] finish = time[-1] else: start = time finish = time start_str = celsius.utcstr(start, 'ISOC') finish_str = celsius.utcstr(finish, 'ISOC') start_int = int(start_str[2:4] + start_str[5:7] + '01') finish_int = int(finish_str[2:4] + finish_str[5:7] + '01') start_str = '%06d' % start_int finish_str = '%06d' % finish_int this_spice_time_window = start_str + finish_str if not 'NONE' in last_spice_time_window: if last_spice_time_window == this_spice_time_window: if verbose: print('LOAD_KERNELS [MVN]: Interval unchanged') return if keep_previous: if verbose: print('LOAD_KERNELS [MVN]: Keeping loaded kernels') return spiceypy.last_spice_time_window = 'MVN:' + this_spice_time_window spiceypy.kclear() try: kernel_directory = os.getenv('MAVEN_KERNEL_DIR') if verbose: print('LOAD_KERNELS [MVN]: Registering kernels:') for k in REQUIRED_KERNELS: if '*' in k: files = glob(kernel_directory + k) m = -1 file_to_load = '' for f in files: t = os.path.getmtime(f) if t > m: m = t file_to_load = f if verbose: print(file_to_load) if file_to_load: spiceypy.furnsh(file_to_load) else: raise IOError("No match for %s" % k) else: spiceypy.furnsh(kernel_directory + k) if verbose: print(kernel_directory + k) # time sensitive kernels load_count = 0 # used to determine whether or not to load the most recent, unnumbered # rolling update kernel max_encountered = -99999 if start_int > -999999: # Load time-sensitive kenrels for f in iglob(kernel_directory + 'spk/maven_orb_rec_*.bsp'): this_start = int(f.split('_')[3]) this_finish = int(f.split('_')[4]) if this_finish < start_int: continue if this_start > finish_int: continue spiceypy.furnsh(f) load_count += 1 if verbose: print(f) if this_start > max_encountered: max_encountered = this_start if this_finish > max_encountered: max_encountered = this_finish if max_encountered < finish_int: # load the rolling-update kernel too f = kernel_directory + 'spk/maven_orb_rec.bsp' # spiceypy.furnsh(f) load_count += 1 if verbose: print(f) if load_count == 0: raise IOError("No kernels matched for time period") except Exception as e: spiceypy.kclear() spiceypy.last_spice_time_window = 'MVN:NONE_ERROR' raise print('LOAD_KERNELS [MVN]: Loaded %s' % spiceypy.last_spice_time_window)
def unloadSpiceFiles(self): # unload spice files for spiceFile in self.loadedSpiceFiles: spice.unload(spiceFile) spice.kclear()
# Jupiter has a mean radius of 69,911 kilometers # Voyager 1's closest approach to Jupiter occurred March 5, 1979 # Distance 349,000 km # Voyager 2's closest approach to Jupiter occurred on July 9, 1979. # It came within 570,000 km of the planet's cloud tops. for i, distance in enumerate(distances): print "%s %.0f" % (et2str(etTimes[i]), distance) # 1979-03-04T10:04:48 1720452 # 1979-03-04T14:24:00 1482460 # 1979-03-04T18:43:12 1238139 # 1979-03-04T23:02:24 987003 # 1979-03-05T03:21:36 730901 # 1979-03-05T07:40:48 485618 # 1979-03-05T12:00:00 348461 # 1979-03-05T16:19:12 477570 # 1979-03-05T20:38:24 721531 # 1979-03-06T00:57:36 977694 # 1979-03-06T05:16:48 1229137 # 1979-03-06T09:36:00 1473770 # 1979-03-06T13:55:12 1712063 # Clean up the kernels spice.kclear()
def vgPlot(): "create plot for each system flyby" loadSpice() #. loop through these, save each file to stepxx_maps/map-Jupiter-Voyager1.jpg etc #. crop each file when done to a square #. vg titles could use these for titlepage for each system flyby #. might as well draw info on maps here - Voyager 1 at Jupiter, date, etc - futura font # note: azimuthElevation values were determined with the plot viewer class Flyby: bodies = None date = None ndays = None axisMax = 1e6 # km axisCenter = (0,0,0) azimuthElevation = None flybys = [] flyby = Flyby() flyby.bodies = ['Jupiter', 'Voyager 1', 'Io', 'Europa', 'Ganymede', 'Callisto'] flyby.date = "1979-03-05" flyby.ndays = 4 flyby.axisMax = 1e6 # km flyby.axisCenter = (0.6e6,-0.2e6,0) flyby.azimuthElevation = (-100,48) flybys.append(flyby) flyby = Flyby() flyby.bodies = ['Saturn', 'Voyager 1','Titan','Enceladus','Rhea','Mimas','Tethys','Dione'] flyby.date = "1980-11-12" flyby.ndays = 3 flyby.axisMax = 0.6e6 # km flyby.axisCenter = (-0.4e6,-0.4e6,0) flyby.azimuthElevation = (80,97) flybys.append(flyby) flyby = Flyby() flyby.bodies = ['Jupiter', 'Voyager 2', 'Io', 'Europa', 'Ganymede', 'Callisto'] flyby.date = "1979-07-09" flyby.ndays = 5 flyby.axisMax = 1e6 # km flyby.axisCenter = (-0.2e6,0,0) flyby.azimuthElevation = (102,107) flybys.append(flyby) flyby = Flyby() flyby.bodies = ['Saturn','Voyager 2','Titan','Enceladus','Rhea','Mimas','Tethys','Dione'] flyby.date = "1981-08-26" flyby.ndays = 2 flyby.axisMax = 0.6e6 # km flyby.axisCenter = (-0.2e6,0.1e6,0) flyby.azimuthElevation = (172,82) flybys.append(flyby) flyby = Flyby() flyby.bodies = ['Uranus','Voyager 2','Ariel','Miranda','Oberon','Titania','Umbriel'] flyby.date = "1986-01-25" flyby.ndays = 2 flyby.axisMax = 0.4e6 # km flyby.azimuthElevation = (-82,-7) flybys.append(flyby) flyby = Flyby() flyby.bodies = ['Neptune','Voyager 2','Triton'] # proteus not in kernels flyby.date = "1989-08-25" flyby.ndays = 2 flyby.axisMax = 1e6 # km flyby.azimuthElevation = (-62,40) flybys.append(flyby) for flyby in flybys: planet = flyby.bodies[0] observer = flyby.bodies[1] print 'Generating plot for %s at %s' % (observer, planet) nsteps = 100 # plot density # get ephemeris time around closest approach (seconds since J2000) etClosest = int(spice.str2et(flyby.date)) etStart = int(etClosest - flyby.ndays * 24*60*60 / 2) etEnd = int(etClosest + flyby.ndays * 24*60*60 / 2) etStep = int((etEnd - etStart) / nsteps) # initialize data structs ets = [] positions = [] minDist = {} minPos = {} for body in flyby.bodies: minDist[body] = 9e15 # loop over time range, get positions for et in xrange(etStart, etEnd, etStep): row = [] for body in flyby.bodies: # get position of body (voyager or moon) relative to planet (eg Jupiter). # position is an (x,y,z) coordinate in the given frame of reference. frame = 'J2000' abberationCorrection = 'NONE' position, lightTime = spice.spkpos(planet, et, frame, abberationCorrection, body) # save time and position to arrays ets.append(et) row.append(position) # find closest approach of voyager to each body if body==observer: # voyager posVoyager = position # save for other bodies # distance = int(libspice.getDistance(position)) # if distance < minDist[body]: # minDist[body] = distance # minPos[body] = position elif body==planet: pass else: # get distance to voyager, km posToVoyager = position-posVoyager distance = int(libspice.getDistance(posToVoyager)) if distance < minDist[body]: minDist[body] = distance minPos[body] = position positions.append(row) # make the map plotMap(flyby, positions, minPos) # all done - clean up the kernels spice.kclear()
'''This script is a port of the contents of erwan_spice.m (in the same directory) to from MICE to spiceypy. ''' import netCDF4 import numpy as np import os import spiceypy as spice clktol = '10:000' spice.kclear() spice.furnsh('simple.furnsh') # Define time window utc0 = '2011 MAR 01 00:00:00.00' utc1 = '2012 MAR 01 00:00:00.00' stepet = 3600 et0 = spice.str2et(utc0) et1 = spice.str2et(utc1) nbet = int(np.ceil((et1 - et0) / stepet)) et = np.linspace(et0, et1, nbet) # Sun positions over time period possun = spice.spkpos('SUN', et, 'MOON_ME', 'LT+S', 'MOON')[0] lonsun = np.arctan2(possun[:, 1], possun[:, 0]) lonsun = np.mod(180 * lonsun / np.pi, 360)
def getFGMData(self,fgm_folder): #Mag data for each cooresponding crossing is found self.file_dict = {} p = re.compile(r'\d{7}') for parent,child,files in os.walk(fgm_folder): for file_name in files: if file_name.endswith('.csv'): file_path = os.path.join(fgm_folder,file_name) date = p.search(file_name).group() date_iso = datetime.datetime.strptime(date,'%Y%j').strftime('%Y-%m-%d') match = self.crossingdf.loc[self.crossingdf['DATE'] == date_iso] self.cdfdf = self.cdfdf.append(match,ignore_index = True) if date_iso not in self.file_dict.keys(): self.file_dict[date_iso] = file_path #The mag data is sorted through and two hours on either side of the crossing is pulled for row in self.cdfdf.itertuples(): date = row[1] time = row[2] type = row[3] crossing_stamp = datetime.datetime.strptime(f'{date}T{time}','%Y-%m-%dT%H:%M:%S') if date in self.file_dict.keys(): fgm_data = pd.read_csv(self.file_dict[date]) time_list = [datetime.datetime.fromisoformat(i) for i in fgm_data['SAMPLE UTC']] #crossing_index = min(time_list,key=lambda x: abs(x-crossing_stamp)) crossing_index_plus = time_list.index(min(time_list,key=lambda x: abs(x-(crossing_stamp+datetime.timedelta(hours=2))))) crossing_index_minus = time_list.index(min(time_list,key=lambda x: abs(x-(crossing_stamp-datetime.timedelta(hours=2))))) save_time_list = [i.isoformat() for i in time_list[crossing_index_minus:crossing_index_plus+1]] spice.furnsh('juno_2019_v03.tm') spice_time_list = [spice.utc2et(i) for i in save_time_list] position_list = [] latitude_list = [] x,y,z=[],[],[] for spice_time in spice_time_list: pos,lt = spice.spkpos('JUNO',spice_time,'IAU_JUPITER','NONE','JUPITER') pos_vec = spice.vpack(pos[0],pos[1],pos[2]) rad_pos,long,lat = spice.reclat(pos_vec) lat *= spice.dpr() rad_pos /= 69911 pos,lt = spice.spkpos('JUNO',spice_time,'IAU_SUN','NONE','JUPITER') x.append(pos[0]) y.append(pos[1]) z.append(pos[2]) position_list.append(rad_pos) latitude_list.append(lat) spice.kclear() file_save_date = crossing_stamp.strftime('%Y%jT%H%M%S') + f'_{type}' cdf_file = pycdf.CDF(f'..\crossings\cdf\jno_mag_{file_save_date}.cdf','') cdf_file.attrs['Author'] = 'Andrew Schok' cdf_file['TIME'] = save_time_list cdf_file['BX DATA'] = fgm_data['BX PLANETOCENTRIC'][crossing_index_minus:crossing_index_plus+1] cdf_file['BX DATA'].attrs['units'] = 'nT' cdf_file['BY DATA'] = fgm_data['BY PLANETOCENTRIC'][crossing_index_minus:crossing_index_plus+1] cdf_file['BY DATA'].attrs['units'] = 'nT' cdf_file['BZ DATA'] = fgm_data['BZ PLANETOCENTRIC'][crossing_index_minus:crossing_index_plus+1] cdf_file['BZ DATA'].attrs['units'] = 'nT' cdf_file['X POSITION'] = x cdf_file['X POSITION'].attrs['units'] = 'km' cdf_file['Y POSITION'] = y cdf_file['Y POSITION'].attrs['units'] = 'km' cdf_file['Z POSITION'] = z cdf_file['Z POSITION'].attrs['units'] = 'km' cdf_file['RADIAL DISTANCE'] = position_list cdf_file['RADIAL DISTANCE'].attrs['units'] = 'Rj' cdf_file['LATITUDE'] = latitude_list cdf_file['LATITUDE'].attrs['units'] = 'deg' cdf_file.close() print(f'Created CDF for {type} crossing {crossing_stamp.strftime("%Y-%m-%dT%H:%M:%S")}')
def load_kernels(time=None, force=False, verbose=False, load_all=False, keep_previous=False): """Load spice kernels, with a stateful thing to prevent multiple calls""" # global last_spice_time_window last_spice_time_window = getattr(spiceypy, 'last_spice_time_window', 'MEX:NONE') if load_all: # Launch to now + 10 yrs start = celsius.spiceet("2003-06-01T00:00") finish = celsius.spiceet(mex.now() + 10.*86400.*365.) if time is None: start = None finish = None start_str = 'NO_TIME_SET' finish_str = '' start_int=-999999 finish_int=-999999 else: if hasattr(time, '__len__'): start = time[0] finish = time[-1] else: start = time finish = time start_str = celsius.utcstr(start, 'ISOC') finish_str = celsius.utcstr(finish, 'ISOC') start_int = int(start_str[2:4] + start_str[5:7] + '01') finish_int = int(finish_str[2:4] + finish_str[5:7] + '01') start_str = '%06d' % start_int finish_str = '%06d' % finish_int this_spice_time_window = start_str + finish_str if not 'NONE' in last_spice_time_window: if last_spice_time_window == this_spice_time_window: if verbose: print('LOAD_KERNELS: Interval unchanged') return if keep_previous: if verbose: print('LOAD_KERNELS: Keeping loaded kernels') return spiceypy.last_spice_time_window = 'MEX:'+this_spice_time_window spiceypy.kclear() try: kernel_directory = mex.data_directory + 'spice' if verbose: print('LOAD_KERNELS: Registering kernels:') for k in REQUIRED_KERNELS: if '*' in k: files = glob.glob(kernel_directory + k) m = -1 file_to_load = '' for f in files: t = os.path.getmtime(f) if t > m: m = t file_to_load = f if verbose: print(file_to_load) if not file_to_load: raise IOError("No matches found for %s" % k) spiceypy.furnsh(file_to_load) else: spiceypy.furnsh(kernel_directory + k) if verbose: print(kernel_directory + k) if start_int > -999999: # Load time-sensitive kenrels for f in glob.iglob(kernel_directory + '/spk/ORMM_T19_*.BSP'): this_int = int(f.split('_T19_')[1][:6]) if this_int < start_int: continue if this_int > finish_int: continue spiceypy.furnsh(f) if verbose: print(f) except Exception as e: spiceypy.kclear() spiceypy.last_spice_time_window = 'MEX:NONE_ERROR' raise