Пример #1
0
    def get_observer_look(self, utc_time, lon, lat, alt):
        """Calculate observers look angle to a satellite.
        http://celestrak.com/columns/v02n02/

        utc_time: Observation time (datetime object)
        lon: Longitude of observer position on ground in degrees east
        lat: Latitude of observer position on ground in degrees north
        alt: Altitude above sea-level (geoid) of observer position on ground in km

        Return: (Azimuth, Elevation)
        """

        utc_time = dt2np(utc_time)
        (pos_x, pos_y, pos_z), (vel_x, vel_y,
                                vel_z) = self.get_position(utc_time,
                                                           normalize=False)
        (opos_x, opos_y, opos_z), (ovel_x, ovel_y, ovel_z) = \
            astronomy.observer_position(utc_time, lon, lat, alt)

        lon = np.deg2rad(lon)
        lat = np.deg2rad(lat)

        theta = (astronomy.gmst(utc_time) + lon) % (2 * np.pi)

        rx = pos_x - opos_x
        ry = pos_y - opos_y
        rz = pos_z - opos_z

        sin_lat = np.sin(lat)
        cos_lat = np.cos(lat)
        sin_theta = np.sin(theta)
        cos_theta = np.cos(theta)

        top_s = sin_lat * cos_theta * rx + \
            sin_lat * sin_theta * ry - cos_lat * rz
        top_e = -sin_theta * rx + cos_theta * ry
        top_z = cos_lat * cos_theta * rx + \
            cos_lat * sin_theta * ry + sin_lat * rz

        az_ = np.arctan(-top_e / top_s)

        az_ = np.where(top_s > 0, az_ + np.pi, az_)
        az_ = np.where(az_ < 0, az_ + 2 * np.pi, az_)

        rg_ = np.sqrt(rx * rx + ry * ry + rz * rz)
        el_ = np.arcsin(top_z / rg_)

        return np.rad2deg(az_), np.rad2deg(el_)
Пример #2
0
    def get_observer_look(self, utc_time, lon, lat, alt):
        """Calculate observers look angle to a satellite.
        http://celestrak.com/columns/v02n02/

        utc_time: Observation time (datetime object)
        lon: Longitude of observer position on ground in degrees east
        lat: Latitude of observer position on ground in degrees north
        alt: Altitude above sea-level (geoid) of observer position on ground in km

        Return: (Azimuth, Elevation)
        """

        utc_time = dt2np(utc_time)
        (pos_x, pos_y, pos_z), (vel_x, vel_y, vel_z) = self.get_position(
            utc_time, normalize=False)
        (opos_x, opos_y, opos_z), (ovel_x, ovel_y, ovel_z) = \
            astronomy.observer_position(utc_time, lon, lat, alt)

        lon = np.deg2rad(lon)
        lat = np.deg2rad(lat)

        theta = (astronomy.gmst(utc_time) + lon) % (2 * np.pi)

        rx = pos_x - opos_x
        ry = pos_y - opos_y
        rz = pos_z - opos_z

        sin_lat = np.sin(lat)
        cos_lat = np.cos(lat)
        sin_theta = np.sin(theta)
        cos_theta = np.cos(theta)

        top_s = sin_lat * cos_theta * rx + \
            sin_lat * sin_theta * ry - cos_lat * rz
        top_e = -sin_theta * rx + cos_theta * ry
        top_z = cos_lat * cos_theta * rx + \
            cos_lat * sin_theta * ry + sin_lat * rz

        az_ = np.arctan(-top_e / top_s)

        az_ = np.where(top_s > 0, az_ + np.pi, az_)
        az_ = np.where(az_ < 0, az_ + 2 * np.pi, az_)

        rg_ = np.sqrt(rx * rx + ry * ry + rz * rz)
        el_ = np.arcsin(top_z / rg_)

        return np.rad2deg(az_), np.rad2deg(el_)
Пример #3
0
    def propagate(self, utc_time):
        kep = {}

        # get the time delta in minutes
        # ts = astronomy._days(utc_time - self.t_0) * XMNPDA
        # print utc_time.shape
        # print self.t_0
        utc_time = dt2np(utc_time)
        ts = (utc_time - self.t_0) / np.timedelta64(1, 'm')

        em = self.eo
        xinc = self.xincl

        xmp = self.xmo + self.xmdot * ts
        xnode = self.xnodeo + ts * (self.xnodot + ts * self.xnodcf)
        omega = self.omegao + self.omgdot * ts

        if self.mode == SGDP4_ZERO_ECC:
            raise NotImplementedError('Mode SGDP4_ZERO_ECC not implemented')
        elif self.mode == SGDP4_NEAR_SIMP:
            raise NotImplementedError('Mode "Near-space, simplified equations"'
                                      ' not implemented')
        elif self.mode == SGDP4_NEAR_NORM:
            delm = self.xmcof * \
                ((1.0 + self.eta * np.cos(xmp))**3 - self.delmo)
            temp0 = ts * self.omgcof + delm
            xmp += temp0
            omega -= temp0
            tempa = 1.0 - \
                (ts *
                 (self.c1 + ts * (self.d2 + ts * (self.d3 + ts * self.d4))))
            tempe = self.bstar * \
                (self.c4 * ts + self.c5 * (np.sin(xmp) - self.sinXMO))
            templ = ts * ts * \
                (self.t2cof + ts *
                 (self.t3cof + ts * (self.t4cof + ts * self.t5cof)))
            a = self.aodp * tempa**2
            e = em - tempe
            xl = xmp + omega + xnode + self.xnodp * templ

        else:
            raise NotImplementedError('Deep space calculations not supported')

        if np.any(a < 1):
            raise Exception('Satellite crashed at time %s', utc_time)
        elif np.any(e < ECC_LIMIT_LOW):
            raise ValueError(
                'Satellite modified eccentricity too low: %s < %e' %
                (str(e[e < ECC_LIMIT_LOW]), ECC_LIMIT_LOW))

        e = np.where(e < ECC_EPS, ECC_EPS, e)
        e = np.where(e > ECC_LIMIT_HIGH, ECC_LIMIT_HIGH, e)

        beta2 = 1.0 - e**2

        # Long period periodics
        sinOMG = np.sin(omega)
        cosOMG = np.cos(omega)

        temp0 = 1.0 / (a * beta2)
        axn = e * cosOMG
        ayn = e * sinOMG + temp0 * self.aycof
        xlt = xl + temp0 * self.xlcof * axn

        elsq = axn**2 + ayn**2

        if np.any(elsq >= 1):
            raise Exception('e**2 >= 1 at %s', utc_time)

        kep['ecc'] = np.sqrt(elsq)

        epw = np.fmod(xlt - xnode, 2 * np.pi)
        # needs a copy in case of an array
        capu = np.array(epw)
        maxnr = kep['ecc']
        for i in range(10):
            sinEPW = np.sin(epw)
            cosEPW = np.cos(epw)

            ecosE = axn * cosEPW + ayn * sinEPW
            esinE = axn * sinEPW - ayn * cosEPW
            f = capu - epw + esinE
            if np.all(np.abs(f) < NR_EPS):
                break

            df = 1.0 - ecosE

            # 1st order Newton-Raphson correction.
            nr = f / df

            # 2nd order Newton-Raphson correction.
            nr = np.where(np.logical_and(i == 0,
                                         np.abs(nr) > 1.25 * maxnr),
                          np.sign(nr) * maxnr, f / (df + 0.5 * esinE * nr))
            epw += nr

        # Short period preliminary quantities
        temp0 = 1.0 - elsq
        betal = np.sqrt(temp0)
        pl = a * temp0
        r = a * (1.0 - ecosE)
        invR = 1.0 / r
        temp2 = a * invR
        temp3 = 1.0 / (1.0 + betal)
        cosu = temp2 * (cosEPW - axn + ayn * esinE * temp3)
        sinu = temp2 * (sinEPW - ayn - axn * esinE * temp3)
        u = np.arctan2(sinu, cosu)
        sin2u = 2.0 * sinu * cosu
        cos2u = 2.0 * cosu**2 - 1.0
        temp0 = 1.0 / pl
        temp1 = CK2 * temp0
        temp2 = temp1 * temp0

        # Update for short term periodics to position terms.

        rk = r * (1.0 - 1.5 * temp2 * betal * self.x3thm1) + \
            0.5 * temp1 * self.x1mth2 * cos2u
        uk = u - 0.25 * temp2 * self.x7thm1 * sin2u
        xnodek = xnode + 1.5 * temp2 * self.cosIO * sin2u
        xinck = xinc + 1.5 * temp2 * self.cosIO * self.sinIO * cos2u

        if np.any(rk < 1):
            raise Exception('Satellite crashed at time %s', utc_time)

        temp0 = np.sqrt(a)
        temp2 = XKE / (a * temp0)
        rdotk = ((XKE * temp0 * esinE * invR -
                  temp2 * temp1 * self.x1mth2 * sin2u) *
                 (XKMPER / AE * XMNPDA / 86400.0))
        rfdotk = ((XKE * np.sqrt(pl) * invR + temp2 * temp1 *
                   (self.x1mth2 * cos2u + 1.5 * self.x3thm1)) *
                  (XKMPER / AE * XMNPDA / 86400.0))

        kep['radius'] = rk * XKMPER / AE
        kep['theta'] = uk
        kep['eqinc'] = xinck
        kep['ascn'] = xnodek
        kep['argp'] = omega
        kep['smjaxs'] = a * XKMPER / AE
        kep['rdotk'] = rdotk
        kep['rfdotk'] = rfdotk

        return kep
Пример #4
0
def jdays2000(utc_time):
    """Get the days since year 2000.
    """
    return _days(dt2np(utc_time) - np.datetime64('2000-01-01T12:00'))
Пример #5
0
    def propagate(self, utc_time):
        kep = {}

        # get the time delta in minutes
        # ts = astronomy._days(utc_time - self.t_0) * XMNPDA
        # print utc_time.shape
        # print self.t_0
        utc_time = dt2np(utc_time)
        ts = (utc_time - self.t_0) / np.timedelta64(1, 'm')

        em = self.eo
        xinc = self.xincl

        xmp = self.xmo + self.xmdot * ts
        xnode = self.xnodeo + ts * (self.xnodot + ts * self.xnodcf)
        omega = self.omegao + self.omgdot * ts

        if self.mode == SGDP4_ZERO_ECC:
            raise NotImplementedError('Mode SGDP4_ZERO_ECC not implemented')
        elif self.mode == SGDP4_NEAR_SIMP:
            raise NotImplementedError('Mode "Near-space, simplified equations"'
                                      ' not implemented')
        elif self.mode == SGDP4_NEAR_NORM:
            delm = self.xmcof * \
                ((1.0 + self.eta * np.cos(xmp))**3 - self.delmo)
            temp0 = ts * self.omgcof + delm
            xmp += temp0
            omega -= temp0
            tempa = 1.0 - \
                (ts *
                 (self.c1 + ts * (self.d2 + ts * (self.d3 + ts * self.d4))))
            tempe = self.bstar * \
                (self.c4 * ts + self.c5 * (np.sin(xmp) - self.sinXMO))
            templ = ts * ts * \
                (self.t2cof + ts *
                 (self.t3cof + ts * (self.t4cof + ts * self.t5cof)))
            a = self.aodp * tempa**2
            e = em - tempe
            xl = xmp + omega + xnode + self.xnodp * templ

        else:
            raise NotImplementedError('Deep space calculations not supported')

        if np.any(a < 1):
            raise Exception('Satellite crased at time %s', utc_time)
        elif np.any(e < ECC_LIMIT_LOW):
            raise ValueError('Satellite modified eccentricity to low: %s < %e'
                             % (str(e[e < ECC_LIMIT_LOW]), ECC_LIMIT_LOW))

        e = np.where(e < ECC_EPS, ECC_EPS, e)
        e = np.where(e > ECC_LIMIT_HIGH, ECC_LIMIT_HIGH, e)

        beta2 = 1.0 - e**2

        # Long period periodics
        sinOMG = np.sin(omega)
        cosOMG = np.cos(omega)

        temp0 = 1.0 / (a * beta2)
        axn = e * cosOMG
        ayn = e * sinOMG + temp0 * self.aycof
        xlt = xl + temp0 * self.xlcof * axn

        elsq = axn**2 + ayn**2

        if np.any(elsq >= 1):
            raise Exception('e**2 >= 1 at %s', utc_time)

        kep['ecc'] = np.sqrt(elsq)

        epw = np.fmod(xlt - xnode, 2 * np.pi)
        # needs a copy in case of an array
        capu = np.array(epw)
        maxnr = kep['ecc']
        for i in range(10):
            sinEPW = np.sin(epw)
            cosEPW = np.cos(epw)

            ecosE = axn * cosEPW + ayn * sinEPW
            esinE = axn * sinEPW - ayn * cosEPW
            f = capu - epw + esinE
            if np.all(np.abs(f) < NR_EPS):
                break

            df = 1.0 - ecosE

            # 1st order Newton-Raphson correction.
            nr = f / df

            # 2nd order Newton-Raphson correction.
            nr = np.where(np.logical_and(i == 0, np.abs(nr) > 1.25 * maxnr),
                          np.sign(nr) * maxnr,
                          f / (df + 0.5 * esinE * nr))
            epw += nr

        # Short period preliminary quantities
        temp0 = 1.0 - elsq
        betal = np.sqrt(temp0)
        pl = a * temp0
        r = a * (1.0 - ecosE)
        invR = 1.0 / r
        temp2 = a * invR
        temp3 = 1.0 / (1.0 + betal)
        cosu = temp2 * (cosEPW - axn + ayn * esinE * temp3)
        sinu = temp2 * (sinEPW - ayn - axn * esinE * temp3)
        u = np.arctan2(sinu, cosu)
        sin2u = 2.0 * sinu * cosu
        cos2u = 2.0 * cosu**2 - 1.0
        temp0 = 1.0 / pl
        temp1 = CK2 * temp0
        temp2 = temp1 * temp0

        # Update for short term periodics to position terms.

        rk = r * (1.0 - 1.5 * temp2 * betal * self.x3thm1) + \
            0.5 * temp1 * self.x1mth2 * cos2u
        uk = u - 0.25 * temp2 * self.x7thm1 * sin2u
        xnodek = xnode + 1.5 * temp2 * self.cosIO * sin2u
        xinck = xinc + 1.5 * temp2 * self.cosIO * self.sinIO * cos2u

        if np.any(rk < 1):
            raise Exception('Satellite crashed at time %s', utc_time)

        temp0 = np.sqrt(a)
        temp2 = XKE / (a * temp0)
        rdotk = ((XKE * temp0 * esinE * invR - temp2 * temp1 * self.x1mth2 * sin2u) *
                 (XKMPER / AE * XMNPDA / 86400.0))
        rfdotk = ((XKE * np.sqrt(pl) * invR + temp2 * temp1 *
                   (self.x1mth2 * cos2u + 1.5 * self.x3thm1)) *
                  (XKMPER / AE * XMNPDA / 86400.0))

        kep['radius'] = rk * XKMPER / AE
        kep['theta'] = uk
        kep['eqinc'] = xinck
        kep['ascn'] = xnodek
        kep['argp'] = omega
        kep['smjaxs'] = a * XKMPER / AE
        kep['rdotk'] = rdotk
        kep['rfdotk'] = rfdotk

        return kep
Пример #6
0
def days_since_2000(utc_time):
    """Returns the days since year 2000.
    """
    return days_from_dt(dt2np(utc_time) - np.datetime64('2000-01-01T12:00')) 
Пример #7
0
def jdays2000(utc_time):
    """Get the days since year 2000.
    """
    return _days(dt2np(utc_time) - np.datetime64('2000-01-01T12:00'))
Пример #8
0
def findtask(norad_id, observation_time, LAT, LONG, ALT):

    id = norad_id
    id = id.rjust(5)

    counter = 0

    with open('3le.txt', 'r') as TLEs:
        for line in TLEs:
            if line[2:7] == id and counter == 0:
                # print(line)
                line1 = line
                counter = 1
            elif line[2:7] == id and counter == 1:
                line2 = line
                # print(line)
                break

    R_site_ECI, V_site_ECI = observer_position(observation_time, LONG, LAT, ALT)

    sat = satellite.get_sat(line1, line2)

    R_sat_ECI, V_sat_ECI = sat.propagate(observation_time.year, observation_time.month, observation_time.day, observation_time.hour, observation_time.minute,
                                         (observation_time.second + observation_time.microsecond * 10 ** (-6)))

    delta_R = np.array([[R_sat_ECI[0] - R_site_ECI[0]], [R_sat_ECI[1] - R_site_ECI[1]], [R_sat_ECI[2] - R_site_ECI[2]]])
    delta_V = np.array([[V_sat_ECI[0] - V_site_ECI[0]], [V_sat_ECI[1] - V_site_ECI[1]], [V_sat_ECI[2] - V_site_ECI[2]]])

    utc_time = dt2np(observation_time)

    lon = np.deg2rad(LONG)
    lat = np.deg2rad(LAT)

    theta = (astronomy.gmst(utc_time) + lon) % (2 * np.pi)

    sin_lat = np.sin(lat)
    cos_lat = np.cos(lat)
    sin_theta = np.sin(theta)
    cos_theta = np.cos(theta)

    top_s = sin_lat * cos_theta * delta_R[0] + \
            sin_lat * sin_theta * delta_R[1] - cos_lat * delta_R[2]
    top_e = -sin_theta * delta_R[0] + cos_theta * delta_R[1]
    top_z = cos_lat * cos_theta * delta_R[0] + \
            cos_lat * sin_theta * delta_R[1] + sin_lat * delta_R[2]

    az_ = np.arctan(-top_e / top_s)

    az_ = np.where(top_s > 0, az_ + np.pi, az_)
    az_ = np.where(az_ < 0, az_ + 2 * np.pi, az_)

    rg_ = np.sqrt(top_s * top_s + top_e * top_e + top_z * top_z)

    el_ = np.arcsin(top_z / rg_)

    AZ = np.rad2deg(az_)
    EL = np.rad2deg(el_)

    mag_delta_R = math.sqrt(delta_R[0] ** 2 + delta_R[1] ** 2 + delta_R[2] ** 2)
    unit_delta_R = np.array([delta_R[0] / mag_delta_R, delta_R[1] / mag_delta_R, delta_R[2] / mag_delta_R])

    V_orth_R_ECI = logical_cross(logical_cross(unit_delta_R, delta_V), unit_delta_R)

    total_look_angular_rate = (math.sqrt(V_orth_R_ECI[0] ** 2 + V_orth_R_ECI[1] ** 2 + V_orth_R_ECI[2] ** 2) / \
                               math.sqrt(delta_R[0] ** 2 + delta_R[1] ** 2 + delta_R[2] ** 2)) * (180.0 / math.pi)

    exposure_time = 0.955/total_look_angular_rate

    if exposure_time > 10:
        exposure_time = 10

    return [AZ[0], EL[0], total_look_angular_rate, exposure_time]