def _compute_missing_lonlat(self, missed_utcs): """compute lon lat values using pyorbital""" tic = datetime.datetime.now() scan_rate = datetime.timedelta(milliseconds=1/self.scan_freq).total_seconds() sgeom = avhrr_gac(missed_utcs.astype(datetime.datetime), self.scan_points, frequency=scan_rate) t0 = missed_utcs[0].astype(datetime.datetime) s_times = sgeom.times(t0) tle1, tle2 = self.get_tle_lines() rpy = self.get_attitude_coeffs() pixels_pos = compute_pixels((tle1, tle2), sgeom, s_times, rpy) pos_time = get_lonlatalt(pixels_pos, s_times) missed_lons, missed_lats = pos_time[:2] pixels_per_line = self.lats.shape[1] missed_lons = missed_lons.reshape(-1, pixels_per_line) missed_lats = missed_lats.reshape(-1, pixels_per_line) toc = datetime.datetime.now() LOG.warning("Computation of geolocation: %s", str(toc - tic)) return missed_lons, missed_lats
def get_lonlats(self): """Get the lonlats.""" if self.lons is not None and self.lats is not None: return self.lons, self.lats from pyorbital.orbital import Orbital from pyorbital.geoloc import compute_pixels, get_lonlatalt from pyorbital.geoloc_instrument_definitions import avhrr if self.times is None: self.times = time_seconds(self._data["timecode"], self.year) scanline_nb = len(self.times) scan_points = np.arange(0, 2048, 32) # scan_points = np.arange(2048) sgeom = avhrr(scanline_nb, scan_points, apply_offset=False) # no attitude error rpy = [0, 0, 0] s_times = sgeom.times(self.times[:, np.newaxis]).ravel() # s_times = (np.tile(sgeom._times[0, :], (scanline_nb, 1)).astype( # 'timedelta64[s]') + self.times[:, np.newaxis]).ravel() orb = Orbital(self.platform_name) pixels_pos = compute_pixels(orb, sgeom, s_times, rpy) lons, lats, alts = get_lonlatalt(pixels_pos, s_times) self.lons, self.lats = geo_interpolate(lons.reshape((scanline_nb, -1)), lats.reshape((scanline_nb, -1))) return self.lons, self.lats
def navigate(timecodes, satellite): orb = Orbital(satellite) first_time = timecode(timecodes[0]) first_time = datetime(first_time.year, first_time.month, first_time.day) hrpttimes = [timecode(x) - first_time for x in timecodes] hrpttimes = np.array([x.seconds + x.microseconds / 1000000.0 for x in hrpttimes]) scan_points = np.arange(2048) if satellite == "noaa 16": scan_angle = 55.25 else: scan_angle = 55.37 scans_nb = len(hrpttimes) avhrr_inst = np.vstack(((scan_points / 1023.5 - 1) * np.deg2rad(-scan_angle), np.zeros((len(scan_points),)))).T avhrr_inst = np.tile(avhrr_inst, [scans_nb, 1]) offset = hrpttimes times = (np.tile(scan_points * 0.000025, [scans_nb, 1]) + np.expand_dims(offset, 1)) sgeom = ScanGeometry(avhrr_inst, times.ravel()) s_times = sgeom.times(first_time) rpy = (0, 0, 0) pixels_pos = compute_pixels((orb.tle._line1, orb.tle._line2), sgeom, s_times, rpy) pos_time = get_lonlatalt(pixels_pos, s_times) return pos_time
def get_lonlats(self): if self.lons is not None and self.lats is not None: return self.lons, self.lats from pyorbital.orbital import Orbital from pyorbital.geoloc import compute_pixels, get_lonlatalt from pyorbital.geoloc_instrument_definitions import avhrr if self.times is None: self.times = time_seconds(self._data["timecode"], self.year) scanline_nb = len(self.times) scan_points = np.arange(0, 2048, 32) # scan_points = np.arange(2048) sgeom = avhrr(scanline_nb, scan_points, apply_offset=False) # no attitude error rpy = [0, 0, 0] s_times = sgeom.times( self.times[:, np.newaxis]).ravel() # s_times = (np.tile(sgeom._times[0, :], (scanline_nb, 1)).astype( # 'timedelta64[s]') + self.times[:, np.newaxis]).ravel() orb = Orbital(self.platform_name) pixels_pos = compute_pixels(orb, sgeom, s_times, rpy) lons, lats, alts = get_lonlatalt(pixels_pos, s_times) self.lons, self.lats = geo_interpolate( lons.reshape((scanline_nb, -1)), lats.reshape((scanline_nb, -1))) return self.lons, self.lats
def navigate(timecodes, satellite): orb = Orbital(satellite) first_time = timecode(timecodes[0]) first_time = datetime(first_time.year, first_time.month, first_time.day) hrpttimes = [timecode(x) - first_time for x in timecodes] hrpttimes = np.array( [x.seconds + x.microseconds / 1000000.0 for x in hrpttimes]) scan_points = np.arange(2048) if satellite == "noaa 16": scan_angle = 55.25 else: scan_angle = 55.37 scans_nb = len(hrpttimes) avhrr_inst = np.vstack( ((scan_points / 1023.5 - 1) * np.deg2rad(-scan_angle), np.zeros((len(scan_points), )))).T avhrr_inst = np.tile(avhrr_inst, [scans_nb, 1]) offset = hrpttimes times = (np.tile(scan_points * 0.000025, [scans_nb, 1]) + np.expand_dims(offset, 1)) sgeom = ScanGeometry(avhrr_inst, times.ravel()) s_times = sgeom.times(first_time) rpy = (0, 0, 0) pixels_pos = compute_pixels((orb.tle._line1, orb.tle._line2), sgeom, s_times, rpy) pos_time = get_lonlatalt(pixels_pos, s_times) return pos_time
def compute_lonlat(self, width, utcs=None, clock_drift_adjust=True): """Compute lat/lon coordinates. Args: width: Number of coordinates per scanlines utcs: Scanline timestamps clock_drift_adjust: If True, adjust clock drift. """ tle1, tle2 = self.get_tle_lines() scan_points = np.arange(3.5, 2048, 5) if utcs is None: utcs = self.get_times() # adjusting clock for drift tic = datetime.datetime.now() if clock_drift_adjust: from pygac.clock_offsets_converter import get_offsets try: offset_times, clock_error = get_offsets(self.spacecraft_name) except KeyError: LOG.info("No clock drift info available for %s", self.spacecraft_name) else: offset_times = np.array(offset_times, dtype='datetime64[ms]') offsets = np.interp(utcs.astype(np.uint64), offset_times.astype(np.uint64), clock_error) utcs -= (offsets * 1000).astype('timedelta64[ms]') t = utcs[0].astype(datetime.datetime) if "constant_yaw_attitude_error" in self.head.dtype.fields: rpy = np.deg2rad([ self.head["constant_roll_attitude_error"] / 1e3, self.head["constant_pitch_attitude_error"] / 1e3, self.head["constant_yaw_attitude_error"] / 1e3 ]) else: rpy = [0, 0, 0] LOG.info("Using rpy: %s", str(rpy)) from pyorbital.geoloc_instrument_definitions import avhrr_gac from pyorbital.geoloc import compute_pixels, get_lonlatalt sgeom = avhrr_gac(utcs.astype(datetime.datetime), scan_points, 55.385) s_times = sgeom.times(t) pixels_pos = compute_pixels((tle1, tle2), sgeom, s_times, rpy) pos_time = get_lonlatalt(pixels_pos, s_times) toc = datetime.datetime.now() LOG.warning("Computation of geolocation: %s", str(toc - tic)) lons, lats = pos_time[:2] return lons.reshape(-1, width), lats.reshape(-1, width)
def _get_avhrr_tiepoints(self, scan_points, scanline_nb): sgeom = avhrr(scanline_nb, scan_points, apply_offset=False) # no attitude error rpy = [0, 0, 0] s_times = sgeom.times(self.times[:, np.newaxis]) orb = Orbital(self.platform_name) pixels_pos = compute_pixels(orb, sgeom, s_times, rpy) lons, lats, alts = get_lonlatalt(pixels_pos, s_times) return lons, lats
def scan_line_lonlats(self, t): """ Returns a single instrument scan line starting at datetime t """ s_times = self.scan_geom.times(t) pixels_pos = compute_pixels((self.orbital.tle.line1, self.orbital.tle.line2), self.scan_geom, s_times) pos_time = get_lonlatalt(pixels_pos, s_times) return np.array((pos_time[0],pos_time[1]))
def scan_line_lonlats(self, t): """ Returns a single instrument scan line starting at datetime t """ s_times = self.scan_geom.times(t) pixels_pos = compute_pixels( (self.orbital.tle.line1, self.orbital.tle.line2), self.scan_geom, s_times) pos_time = get_lonlatalt(pixels_pos, s_times) return np.array((pos_time[0], pos_time[1]))
def get_instrument_points(self, overpass, utctime, scans_nb, scanpoints, scan_step=1): """Get the boundary points for a given overpass. """ instrument = overpass.instrument # logger.debug("Instrument: %s", str(instrument)) # cheating at the moment. # scan_angle = 55.37 if instrument == "modis": scan_angle = 55.0 instrument = "avhrr" elif instrument == "viirs": scan_angle = 55.84 instrument = "viirs" elif instrument == "iasi": scan_angle = 48.3 instrument = "avhrr" elif overpass.satellite == "noaa 16": scan_angle = 55.25 instrument = "avhrr" elif instrument == "mersi2": scan_angle = 55.4 instrument = "avhrr" else: scan_angle = 55.25 instrument_fun = getattr(geoloc_instrument_definitions, INSTRUMENT.get(instrument, instrument)) if instrument.startswith("avhrr"): sgeom = instrument_fun(scans_nb, scanpoints, scan_angle=scan_angle, frequency=100) elif instrument in ["ascat", ]: sgeom = instrument_fun(scans_nb, scanpoints) elif instrument in ["olci", ]: sgeom = instrument_fun(scans_nb, scanpoints) elif instrument == 'viirs': sgeom = instrument_fun(scans_nb, scanpoints, scan_step=scan_step) else: logger.warning("Instrument not tested: %s", instrument) sgeom = instrument_fun(scans_nb) times = sgeom.times(utctime) pixel_pos = geoloc.compute_pixels((self.orb.tle._line1, self.orb.tle._line2), sgeom, times) lons, lats, alts = geoloc.get_lonlatalt(pixel_pos, times) del alts return (lons.reshape(-1, len(scanpoints)), lats.reshape(-1, len(scanpoints)))
def get_instrument_points(self, overpass, utctime, scans_nb, scanpoints, frequency=1): """Get the boundary points for a given overpass. """ instrument = overpass.instrument # cheating at the moment. scan_angle = 55.37 if instrument == "modis": scan_angle = 55.0 elif instrument == "viirs": scan_angle = 55.84 elif overpass.satellite == "noaa 16": scan_angle = 55.25 instrument = "avhrr" instrument_fun = getattr(geoloc_instrument_definitions, instrument) sgeom = instrument_fun(scans_nb, scanpoints, scan_angle=scan_angle, frequency=frequency) times = sgeom.times(utctime) pixel_pos = geoloc.compute_pixels((self.orb.tle._line1, self.orb.tle._line2), sgeom, times) lons, lats, alts = geoloc.get_lonlatalt(pixel_pos, times) del alts return (lons.reshape(-1, len(scanpoints)), lats.reshape(-1, len(scanpoints)))
# build the scan geometry object return ScanGeometry(samples, times.ravel()) # build the scan geometry object sgeom = amsua(scanline_nb, edges_only=False) #sgeom = ScanGeometry(amsua, amsua_times.ravel()) # roll, pitch, yaw in radians rpy = (0, 0, 0) # print the lonlats for the pixel positions s_times = sgeom.times(t) pixels_pos = compute_pixels((tle1, tle2), sgeom, s_times, rpy) pos_time = get_lonlatalt(pixels_pos, s_times) m = Basemap(projection='stere', llcrnrlat=24, urcrnrlat=70, llcrnrlon=-25, urcrnrlon=120, lat_ts=58, lat_0=58, lon_0=14, resolution='l') #m = Basemap(projection='ortho',lat_0=45,lon_0=20,resolution='l') # convert and plot the predicted pixels in red x, y = m(pos_time[0], pos_time[1]) p1 = m.plot(x,y, marker='+', color='red', markerfacecolor='red', markeredgecolor='red', markersize=1, markevery=1, zorder=4, linewidth=0.0) m.fillcontinents(color='0.85', lake_color=None, zorder=3) m.drawparallels(np.arange(-90.,90.,5.), labels=[1,0,1,0],fontsize=10, dashes=[1, 0], color=[0.8,0.8,0.8], zorder=1) m.drawmeridians(np.arange(-180.,180.,5.), labels=[0,1,0,1],fontsize=10, dashes=[1, 0], color=[0.8,0.8,0.8], zorder=2) plt.show()
def get_instrument_points(self, overpass, utctime, scans_nb, scanpoints, scan_step=1): """Get the boundary points for a given overpass. """ instrument = overpass.instrument # logger.debug("Instrument: %s", str(instrument)) # cheating at the moment. # scan_angle = 55.37 if instrument == "modis": scan_angle = 55.0 instrument = "avhrr" elif instrument == "viirs": scan_angle = 55.84 instrument = "viirs" elif instrument == "iasi": scan_angle = 48.3 instrument = "avhrr" elif overpass.satellite == "noaa 16": scan_angle = 55.25 instrument = "avhrr" elif instrument == "mersi": scan_angle = 55.4 instrument = "avhrr" elif instrument == "mersi2": scan_angle = 55.4 instrument = "avhrr" else: scan_angle = 55.25 instrument_fun = getattr(geoloc_instrument_definitions, INSTRUMENT.get(instrument, instrument)) if instrument.startswith("avhrr"): sgeom = instrument_fun(scans_nb, scanpoints, scan_angle=scan_angle, frequency=100) elif instrument in [ "ascat", ]: sgeom = instrument_fun(scans_nb, scanpoints) elif instrument in [ "olci", ]: sgeom = instrument_fun(scans_nb, scanpoints) elif instrument == 'viirs': sgeom = instrument_fun(scans_nb, scanpoints, scan_step=scan_step) elif instrument in ['mhs', 'atms', 'mwhs-2']: sgeom = instrument_fun(scans_nb, scanpoints) else: logger.warning("Instrument not tested: %s", instrument) sgeom = instrument_fun(scans_nb) times = sgeom.times(utctime) pixel_pos = geoloc.compute_pixels( (self.orb.tle._line1, self.orb.tle._line2), sgeom, times) lons, lats, alts = geoloc.get_lonlatalt(pixel_pos, times) del alts return (lons.reshape(-1, len(scanpoints)), lats.reshape(-1, len(scanpoints)))
def compute_lonlat(self, width, utcs=None, clock_drift_adjust=True): """Compute lat/lon coordinates. Args: width: Number of coordinates per scanlines utcs: Scanline timestamps clock_drift_adjust: If True, adjust clock drift. """ if utcs is None: utcs = self.get_times() # adjusting clock for drift tic = datetime.datetime.now() if clock_drift_adjust: from pygac.clock_offsets_converter import get_offsets try: offset_times, clock_error = get_offsets(self.spacecraft_name) except KeyError: LOG.info("No clock drift info available for %s", self.spacecraft_name) else: offset_times = np.array(offset_times, dtype='datetime64[ms]') offsets = np.interp(utcs.astype(np.uint64), offset_times.astype(np.uint64), clock_error) utcs = utcs - (offsets * 1000).astype('timedelta64[ms]') t = utcs[0].astype(datetime.datetime) if "constant_yaw_attitude_error" in self.head.dtype.fields: rpy = np.deg2rad([ self.head["constant_roll_attitude_error"] / 1e3, self.head["constant_pitch_attitude_error"] / 1e3, self.head["constant_yaw_attitude_error"] / 1e3 ]) else: try: # This needs to be checked thoroughly first # rpy_spacecraft = rpy_coeffs[self.spacecraft_name] # rpy = [rpy_spacecraft['roll'], # rpy_spacecraft['pitch'], # rpy_spacecraft['yaw']] # LOG.debug("Using static attitude correction") raise KeyError except KeyError: LOG.debug("Not applying attitude correction") rpy = [0, 0, 0] LOG.info("Using rpy: %s", str(rpy)) from pyorbital.geoloc_instrument_definitions import avhrr_gac from pyorbital.geoloc import compute_pixels, get_lonlatalt # TODO: Are we sure all satellites have this scan width in degrees ? sgeom = avhrr_gac(utcs.astype(datetime.datetime), self.scan_points, 55.385) s_times = sgeom.times(t) tle1, tle2 = self.get_tle_lines() pixels_pos = compute_pixels((tle1, tle2), sgeom, s_times, rpy) pos_time = get_lonlatalt(pixels_pos, s_times) toc = datetime.datetime.now() LOG.warning("Computation of geolocation: %s", str(toc - tic)) lons, lats = pos_time[:2] return lons.reshape(-1, width), lats.reshape(-1, width)
# building the corresponding times array offset = np.arange(scanline_nb) * 0.1666667 times = (np.tile(scan_points * 0.000025 + 0.0025415, [scanline_nb, 1]) + np.expand_dims(offset, 1)) # build the scan geometry object sgeom = ScanGeometry(avhrr, times.ravel()) # roll, pitch, yaw in radians rpy = (0, 0, 0) # print the lonlats for the pixel positions s_times = sgeom.times(t) pixels_pos = compute_pixels((tle1, tle2), sgeom, s_times, rpy) pos_time = get_lonlatalt(pixels_pos, s_times) print pos_time # Plot the result from mpl_toolkits.basemap import Basemap import matplotlib.pyplot as plt m = Basemap(projection='stere', llcrnrlat=24, urcrnrlat=70, llcrnrlon=-25, urcrnrlon=120, lat_ts=58, lat_0=58, lon_0=14, resolution='l') # convert and plot the predicted pixels in red x, y = m(pos_time[0], pos_time[1]) p1 = m.plot(x,y, marker='+', color='red', markerfacecolor='red', markeredgecolor='red', markersize=1, markevery=1, zorder=4, linewidth=0.0) m.fillcontinents(color='0.85', lake_color=None, zorder=3)