def hdf_getitem(self, key, **kwargs):
     if key == 'Airspeed':
         return Parameter('Airspeed',
                          array=airspeed_array,
                          frequency=airspeed_frequency)
     elif key == 'Frame Counter':
         return Parameter('Frame Counter',
                          array=dfc_array,
                          frequency=0.25)
     elif key == 'Heading':
         # TODO: Give heading specific data.
         return Parameter('Heading',
                          array=heading_array,
                          frequency=heading_frequency)
     elif key == 'Eng (1) N1' and eng_array is not None:
         return Parameter('Eng (1) N1',
                          array=eng_array,
                          frequency=eng_frequency)
     elif key == 'Segment Split':
         seg_split = M('Segment Split',
                       array=np.ma.zeros(len(heading_array), dtype=int),
                       frequency=heading_frequency,
                       values_mapping={
                           0: "-",
                           1: "Split"
                       })
         seg_split.array[390 / heading_frequency] = "Split"
         return seg_split
     else:
         raise KeyError
 def get(key):
     if key == 'Collective':
         return Parameter(
             key,
             array=load_array(
                 'segment_type_and_slice_3_collective.npz'),
             frequency=8.)
 def hdf_getitem(self, key, **kwargs):
     if key == 'Airspeed':
         return Parameter('Airspeed', array=airspeed_array,
                          frequency=airspeed_frequency)
     elif key == 'Frame Counter':
         return Parameter('Frame Counter', array=dfc_array,
                          frequency=0.25)
     elif key == 'Heading':
         # TODO: Give heading specific data.
         return Parameter('Heading', array=heading_array,
                          frequency=heading_frequency)
     elif key == 'Eng (1) N1' and eng_array is not None:
         return Parameter('Eng (1) N1', array=eng_array,
                          frequency=eng_frequency)
     else:
         raise KeyError
 def hdf_get_param(key, valid_only=False):
     # Pretend that we recorded Heading True only on this aircraft
     if key == 'Heading':
         raise KeyError
     elif key == 'Heading True':
         return Parameter('Heading True', array=heading_array,
                          frequency=heading_frequency)
Example #5
0
def csv_flight_details(hdf_path,
                       kti_list,
                       kpv_list,
                       phase_list,
                       dest_path=None,
                       append_to_file=True):
    """
    Currently writes to csv and prints to a table.
    
    Phase types have a 'duration' column
    
    :param dest_path: Outputs CSV to dest_path (removing if exists). If None,
      collates results by appending to a single file: 'combined_test_output.csv'
    """
    rows = []
    params = ['Airspeed', 'Altitude AAL']
    attrs = ['value', 'datetime', 'latitude', 'longitude']
    header = ['path', 'type', 'index', 'duration', 'name'] + attrs + params
    if not dest_path:
        header.append('Path')
    formats = {
        'index': '%.3f',
        'value': '%.3f',
        'duration': '%.2f',
        'latitude': '%.4f',
        'longitude': '%.4f',
        'Airspeed': '%d kts',
        'Altitude AAL': '%d ft',
    }
    for value in kti_list:
        vals = value.todict()  # recordtype
        vals['path'] = hdf_path
        vals['type'] = 'Key Time Instance'
        rows.append(vals)

    for value in kpv_list:
        vals = value.todict()  # recordtype
        vals['path'] = hdf_path
        vals['type'] = 'Key Point Value'
        rows.append(vals)

    for value in phase_list:
        vals = value._asdict()  # namedtuple
        vals['name'] = value.name + ' [START]'
        vals['path'] = hdf_path
        vals['type'] = 'Phase'
        vals['index'] = value.start_edge
        vals['duration'] = value.stop_edge - value.start_edge  # (secs)
        rows.append(vals)
        # create another at the stop of the phase
        end = copy(vals)
        end['name'] = value.name + ' [END]'
        end['index'] = value.stop_edge
        rows.append(end)

    # Append values of useful parameters at this time
    with hdf_file(hdf_path) as hdf:
        for param in params:
            # Create DerivedParameterNode to utilise the .at() method
            if param not in hdf:
                continue
            p = hdf[param]
            dp = Parameter(name=p.name,
                           array=p.array,
                           frequency=p.frequency,
                           offset=p.offset)
            for row in rows:
                row[param] = dp.at(row['index'])

    # sort rows
    rows = sorted(rows, key=lambda x: x['index'])

    skip_header = False

    # print to CSV
    if not dest_path:
        dest_path = 'combined_test_output.csv'
    elif os.path.isfile(dest_path):
        if not append_to_file:
            logger.info("Deleting existing copy of: %s", dest_path)
            os.remove(dest_path)
        else:
            # If we are appending and the file exista, we don't want to output
            # the header again
            skip_header = True

    with open(dest_path, 'ab') as dest:
        writer = TypedWriter(dest,
                             fieldnames=header,
                             fieldformats=formats,
                             skip_header=skip_header,
                             extrasaction='ignore')
        writer.writerows(rows)
        # print to Debug I/O
        logger.info(
            indent([header] + writer.rowlist(rows),
                   hasHeader=True,
                   wrapfunc=lambda x: str(x)))
    return rows
Example #6
0
def track_to_kml(hdf_path,
                 kti_list,
                 kpv_list,
                 approach_list,
                 plot_altitude=None,
                 dest_path=None):
    '''
    Plot results of process_flight onto a KML track.
    
    :param flight_attrs: List of Flight Attributes
    :type flight_attrs: list
    :param plot_altitude: Name of Altitude parameter to use in KML
    :type plot_altitude: String
    '''
    one_hz = Parameter()
    kml = simplekml.Kml()
    with hdf_file(hdf_path) as hdf:
        # Latitude param, Longitude param, track name, colour
        coord_params = (
            {
                'lat': 'Latitude Smoothed',
                'lon': 'Longitude Smoothed',
                'track': 'Smoothed',
                'colour': 'ff7fff7f'
            },
            {
                'lat': 'Latitude Prepared',
                'lon': 'Longitude Prepared',
                'track': 'Prepared',
                'colour': 'A11EB3'
            },
            {
                'lat': 'Latitude',
                'lon': 'Longitude',
                'track': 'Recorded',
                'colour': 'ff0000ff'
            },
            {
                'lat': 'Latitude (Coarse)',
                'lon': 'Longitude (Coarse)',
                'track': 'Coarse',
                'colour': 'ff0000ff'
            },
        )
        altitude_absolute_params = ('Altitude QNH', 'Altitude STD',
                                    'Altitude AAL')
        altitude_relative_params = ('Altitude Radio', )
        # Check latitude and longitude pair exist.
        if not any(c['lat'] in hdf and c['lon'] in hdf for c in coord_params):
            logger.error(
                "Cannot write track as coordinate paarmeters not in hdf")
            return False
        # Choose best altitude parameter if not specified.
        if not plot_altitude:
            altitude_params = itertools.chain(altitude_absolute_params,
                                              altitude_relative_params)
            try:
                plot_altitude = next(p for p in altitude_params if p in hdf)
            except StopIteration:
                logger.warning("Disabling altitude on KML plot as it is "
                               "unavailable.")
        # Get altitude param from hdf.
        if plot_altitude:
            alt = derived_param_from_hdf(
                hdf[plot_altitude]).get_aligned(one_hz)
            alt.array = repair_mask(alt.array,
                                    frequency=alt.frequency,
                                    repair_duration=None) / METRES_TO_FEET
        else:
            alt = None

        if plot_altitude in altitude_absolute_params:
            altitude_mode = simplekml.constants.AltitudeMode.absolute
        elif plot_altitude in altitude_relative_params:
            altitude_mode = simplekml.constants.AltitudeMode.relativetoground
        else:
            altitude_mode = simplekml.constants.AltitudeMode.clamptoground

        ## Get best latitude and longitude parameters.
        best_lat = None
        best_lon = None

        for coord_config in coord_params:
            lat_name = coord_config['lat']
            lon_name = coord_config['lon']
            if not lat_name in hdf or not lon_name in hdf:
                continue
            lat = hdf[lat_name]
            lon = hdf[lon_name]
            best = not best_lat or not best_lon
            add_track(kml,
                      coord_config['track'],
                      lat,
                      lon,
                      coord_config['colour'],
                      alt_param=alt,
                      alt_mode=altitude_mode,
                      visible=best)
            add_track(kml,
                      coord_config['track'] + ' On Ground',
                      lat,
                      lon,
                      coord_config['colour'],
                      visible=best)
            if best:
                best_lat = derived_param_from_hdf(lat).get_aligned(one_hz)
                best_lon = derived_param_from_hdf(lon).get_aligned(one_hz)

    # Add KTIs.
    for kti in kti_list:
        kti_point_values = {'name': kti.name}
        if kti.name in SKIP_KTIS:
            continue

        altitude = alt.at(kti.index) if plot_altitude else None
        kti_point_values['altitudemode'] = altitude_mode
        if altitude:
            kti_point_values['coords'] = ((kti.longitude, kti.latitude,
                                           altitude), )
        else:
            kti_point_values['coords'] = ((kti.longitude, kti.latitude), )
        kml.newpoint(**kti_point_values)

    # Add KPVs.
    for kpv in kpv_list:

        # Trap kpvs with invalid latitude or longitude data (normally happens
        # at the start of the data where accelerometer offsets are declared,
        # and this avoids casting kpvs into the Atlantic.
        kpv_lat = best_lat.at(kpv.index)
        kpv_lon = best_lon.at(kpv.index)
        if kpv_lat == None or kpv_lon == None or \
           (kpv_lat == 0.0 and kpv_lon == 0.0):
            continue

        if kpv.name in SKIP_KPVS:
            continue

        style = simplekml.Style()
        style.iconstyle.color = simplekml.Color.red
        kpv_point_values = {'name': '%s (%.3f)' % (kpv.name, kpv.value)}
        altitude = alt.at(kpv.index) if plot_altitude else None
        kpv_point_values['altitudemode'] = altitude_mode
        if altitude:
            kpv_point_values['coords'] = ((kpv_lon, kpv_lat, altitude), )
        else:
            kpv_point_values['coords'] = ((kpv_lon, kpv_lat), )

        pnt = kml.newpoint(**kpv_point_values)
        pnt.style = style

    # Add approach centre lines.
    for app in approach_list:
        try:
            draw_centreline(kml, app.runway)
        except:
            pass

    if not dest_path:
        dest_path = hdf_path + ".kml"
    kml.save(dest_path)
    return dest_path
 def get(key):
     array = load_compressed(
         os.path.join(test_data_path,
                      'segment_type_and_slice_2_gog.npz'))
     return Parameter('Gear on Ground', array=array)
 def hdf_getitem(self, key, **kwargs):
     return Parameter(key, array=arrays[key], frequency=1)
def csv_flight_details(hdf_path, kti_list, kpv_list, phase_list,
                       dest_path=None, append_to_file=True):
    """
    Currently writes to csv and prints to a table.

    Phase types have a 'duration' column

    :param dest_path: Outputs CSV to dest_path (removing if exists). If None,
      collates results by appending to a single file: 'combined_test_output.csv'
    """
    rows = []
    params = ['Airspeed', 'Altitude AAL']
    attrs = ['value', 'datetime', 'latitude', 'longitude']
    header = ['path', 'type', 'index', 'duration', 'name'] + attrs + params
    if not dest_path:
        header.append('Path')
    formats = {'index': '%.3f',
               'value': '%.3f',
               'duration': '%.2f',
               'latitude': '%.4f',
               'longitude': '%.4f',
               'Airspeed': '%d kts',
               'Altitude AAL': '%d ft',
               }
    for value in kti_list:
        vals = value._asdict()  # recordtype
        vals['path'] = hdf_path
        vals['type'] = 'Key Time Instance'
        rows.append( vals )

    for value in kpv_list:
        vals = value._asdict()  # recordtype
        vals['path'] = hdf_path
        vals['type'] = 'Key Point Value'
        rows.append( vals )

    for value in phase_list:
        vals = value._asdict()  # namedtuple
        vals['name'] = value.name + ' [START]'
        vals['path'] = hdf_path
        vals['type'] = 'Phase'
        vals['index'] = value.start_edge
        vals['duration'] = value.stop_edge - value.start_edge  # (secs)
        rows.append(vals)
        # create another at the stop of the phase
        end = copy(vals)
        end['name'] = value.name + ' [END]'
        end['index'] = value.stop_edge
        rows.append(end)

    # Append values of useful parameters at this time
    with hdf_file(hdf_path) as hdf:
        for param in params:
            # Create DerivedParameterNode to utilise the .at() method
            if param not in hdf:
                continue
            p = hdf[param]
            dp = Parameter(name=p.name, array=p.array,
                           frequency=p.frequency, offset=p.offset)
            for row in rows:
                row[param] = dp.at(row['index'])

    # sort rows
    rows = sorted(rows, key=lambda x: x['index'])

    skip_header = False

    # print to CSV
    if not dest_path:
        dest_path = 'combined_test_output.csv'
    elif os.path.isfile(dest_path):
        if not append_to_file:
            logger.info("Deleting existing copy of: %s", dest_path)
            os.remove(dest_path)
        else:
            # If we are appending and the file exista, we don't want to output
            # the header again
            skip_header = True

    with open(dest_path, 'a') as dest:
        writer = TypedWriter(dest, fieldnames=header, fieldformats=formats,
                             skip_header=skip_header, extrasaction='ignore')
        writer.writerows(rows)
        # print to Debug I/O
        logger.debug(indent([header] + writer.rowlist(rows), hasHeader=True, wrapfunc=lambda x:str(x)))
    return rows
 def hdf_get(key):
     return Parameter(key, array=arrays[key], frequency=1)
 def get(key):
     if key == 'Gear On Ground':
         return Parameter(
             'Gear on Ground',
             array=load_array('segment_type_and_slice_2_gog.npz'))