Ejemplo n.º 1
0
// We tart it up with airframe and schedule data, trim out stale entries, and trim to fit box
func getAirspaceForDisplay(c context.Context, bbox geo.LatlongBox) (airspace.Airspace, error) {
	a := airspace.NewAirspace()
	if err := a.JustAircraftFromMemcache(c); err != nil {
		return a, err
	}

	airframes := ref.NewAirframeCache(c)
	schedules := ref.NewScheduleCache(c)
	for k, aircraft := range a.Aircraft {
		age := time.Since(a.Aircraft[k].Msg.GeneratedTimestampUTC)
		if age > kMaxStaleDuration {
			delete(a.Aircraft, k)
			continue
		}
		if !bbox.SW.IsNil() && !bbox.Contains(aircraft.Msg.Position) {
			delete(a.Aircraft, k)
			continue
		}
		if af := airframes.Get(string(k)); af != nil {
			// Update entry in map to include the airframe data we just found
			aircraft.Airframe = *af
			a.Aircraft[k] = aircraft
		}

		if schedules != nil && time.Since(schedules.LastUpdated) < kMaxStaleScheduleDuration {
			if fs := schedules.Get(string(k)); fs != nil {
				aircraft.Schedule = fs.Identity.Schedule
				a.Aircraft[k] = aircraft
			}
		}
	}

	return a, nil
}
Ejemplo n.º 2
0
func (t Track) TimesInBox(b geo.LatlongBox) (s, e time.Time) {
	inside := false

	for _, tp := range t {
		if tp.AltitudeFeet == 0 || tp.SpeedKnots == 0 {
			continue
		}
		if !inside && b.Contains(tp.Latlong) {
			s = tp.TimestampUTC
			inside = true

		} else if inside {
			e = tp.TimestampUTC // keep overwriting e until we're outside (or we've landed)
			if !b.Contains(tp.Latlong) {
				break
			}
		}
	}
	return
}
Ejemplo n.º 3
0
// WARNING: If we find something, we will annotate the track in-place
func (track Track) LevelFlightAcrossBox(maxAbsDelta float64, box geo.LatlongBox, name string) *LevelFlightEvent {

	iStart, iEnd := 0, 0
	for i, tp := range track {
		if iStart == 0 {
			if box.Contains(tp.Latlong) {
				iStart = i
			}
		} else {
			if !box.Contains(tp.Latlong) {
				iEnd = i - 1
				break
			}
		}
	}
	if iStart == 0 || iEnd == 0 || iStart == iEnd {
		return nil
	}

	ev := LevelFlightEvent{
		Start: track[iStart],
		End:   track[iEnd],
		I:     iStart,
		J:     iEnd,
	}

	if math.Abs(ev.End.AltitudeFeet-ev.Start.AltitudeFeet) > maxAbsDelta {
		return nil
	}

	for i := iStart; i <= iEnd; i++ {
		track[i].X_Annotation = fmt.Sprintf("\n** LEVEL FLIGHT across %s", name)
		track[i].X_MapIcon = "red"
	}

	return &ev
}