flightpathr

Tools to analyze aircraft and flight path data.
git clone https://git.eamoncaddigan.net/flightpathr.git
Log | Files | Refs | README | LICENSE

commit 653e59268223de4704bd6ae2d5c59f291b6dcf50
parent ecebba57703c4810a5ef7c43b8ffea21c4096558
Author: eamoncaddigan <eamon.caddigan@gmail.com>
Date:   Wed, 21 Sep 2016 14:51:46 -0400

get3dCoords() rewritten for trajectories and paths, with tests.

Diffstat:
MR/get3dCoords.R | 42+++++++++++++-----------------------------
Mman/get3dCoords.Rd | 16+++++++++++-----
Mtests/testthat/test_get3dCoords.R | 53+++++++++++++++++++++--------------------------------
3 files changed, 45 insertions(+), 66 deletions(-)

diff --git a/R/get3dCoords.R b/R/get3dCoords.R @@ -1,33 +1,17 @@ -#' Checks for appropriate input and coerces it into a nx3 coordinate matrix. +#' Checks for a \code{flighttrajectory} or \code{flightpath} object and returns +#' it's position in a 3D matrix. #' -#' @param obj An object that hopefully contains some coordinates. -#' @return A nx3 coordinate matrix. Should be longitude/latitude/altitude. -get3dCoords <- function(obj) { - # Get/check for a matrix representation - if (is(obj, "SpatialPoints")) { - if (!requireNamespace("sp", quietly = TRUE)) { - # I have no idea how this would happen, but people do funky things. - stop("Package sp must be installed to handle SpatialPoints objects") - } - # TODO: check projection string to make sure this is latitude/longitude and - # not easting/northing data. - warning("Assuming lat/long data in SpatialPoints object's coordinates") - coordMat <- sp::coordinates(obj) - } else if (is.data.frame(obj)) { - coordMat <- as.matrix.data.frame(obj) - } else if (is.matrix(obj)) { - coordMat <- obj - } else { - stop("obj must be an object of class SpatialPoints (or subclass), data.frame, or matrix") - } - - # Check the dimensions, adding altitude if necessary - if (ncol(coordMat) == 2) { - # Add fake altitude info (AGL) - coordMat <- cbind(coordMat, 0) - } else if (ncol(coordMat) != 3) { - stop("Coordinates must be in 2D or 3D") +#' @param coordObject An object that hopefully contains some coordinates. +#' @return A nx3 coordinate matrix giving longitude/latitude/altitude. +#' +#' @details It'll be safer to access \code{flighttrajectory} and +#' \code{flightpath} objects' coordinates through this. +get3dCoords <- function(coordObject) { + if (!is.flighttrajectory(coordObject) & !is.flightpath(coordObject)) { + stop("trajectory must be an instance of 'flighttrajectory' or 'flightpath'") } - return(coordMat) + return(cbind(coordObject$longitude, + coordObject$latitude, + coordObject$altitude)) } diff --git a/man/get3dCoords.Rd b/man/get3dCoords.Rd @@ -2,17 +2,23 @@ % Please edit documentation in R/get3dCoords.R \name{get3dCoords} \alias{get3dCoords} -\title{Checks for appropriate input and coerces it into a nx3 coordinate matrix.} +\title{Checks for a \code{flighttrajectory} or \code{flightpath} object and returns +it's position in a 3D matrix.} \usage{ -get3dCoords(obj) +get3dCoords(coordObject) } \arguments{ -\item{obj}{An object that hopefully contains some coordinates.} +\item{coordObject}{An object that hopefully contains some coordinates.} } \value{ -A nx3 coordinate matrix. Should be longitude/latitude/altitude. +A nx3 coordinate matrix giving longitude/latitude/altitude. } \description{ -Checks for appropriate input and coerces it into a nx3 coordinate matrix. +Checks for a \code{flighttrajectory} or \code{flightpath} object and returns +it's position in a 3D matrix. +} +\details{ +It'll be safer to access \code{flighttrajectory} and + \code{flightpath} objects' coordinates through this. } diff --git a/tests/testthat/test_get3dCoords.R b/tests/testthat/test_get3dCoords.R @@ -1,46 +1,35 @@ library(flightpathr) context("get3dCoords") +library(geosphere) -# data and helper functions ----------------------------------------------- - -coords3d <- matrix(rnorm(100*3), ncol = 3) - -check_sp <- function () { - if (!requireNamespace("sp", quietly = TRUE)) { - skip("sp is not available") - } -} +kacy <- c(-74.5771667, 39.4575833) +k17n <- c(-75.0330031, 39.7054758) +vcn <- c(-74.9671439, 39.5376711) expect_unnamed_equal <- function(mat1, mat2) { eval(bquote(expect_equal(unname(.(mat1)), unname(.(mat2))))) } - -# tests ------------------------------------------------------------------- - -test_that("different input objects are handled", { - expect_equal(get3dCoords(coords3d), coords3d) - expect_unnamed_equal(get3dCoords(as.data.frame(coords3d)), coords3d) - expect_error(get3dCoords(as.numeric(coords3d))) +test_that("flighttrajectories are recognized", { + distMeters <- distHaversine(kacy, k17n) + # distMeters m * (1 hr / 100 nmi) * (1 nmi / 1852 m) * (3600 s / 1 hr) + timeSec <- round(distMeters * (1/100) * (3600/1852)) + trajectoryMat <- cbind(gcIntermediate(kacy, k17n, n = timeSec-2, addStartEnd = TRUE), + alt = rep(2500, timeSec)) + trajectory <- createTrajectory(trajectoryMat[, "lon"], + trajectoryMat[, "lat"], + trajectoryMat[, "alt"]) + + expect_unnamed_equal(get3dCoords(trajectory), trajectoryMat) }) -test_that("different dimensions are handled", { - coords2d <- coords3d[, c(1,2)] - coords2dFixed <- cbind(coords2d, 0) - - expect_equal(get3dCoords(coords2d), coords2dFixed) - expect_error(get3dCoords(coords3d[, 1, drop = FALSE]), - "Coordinates must be in 2D or 3D") -}) +test_that("flightpaths are recognized", { + pathMat <- rbind(kacy, vcn, k17n) -test_that("SpatialPoints are handled", { - check_sp() - coordsSP <- sp::SpatialPoints(coords3d) - coordsSPDF <- sp::SpatialPointsDataFrame(coords3d, as.data.frame(coords3d)) + path1 <- createPath(pathMat[, 1], pathMat[, 2]) + path2 <- createPath(pathMat[, 1], pathMat[, 2], 7500) - expect_warning(get3dCoords(coordsSP)) - expect_unnamed_equal(get3dCoords(coordsSP), coords3d) - expect_unnamed_equal(get3dCoords(coordsSPDF), coords3d) + expect_unnamed_equal(get3dCoords(path1), cbind(pathMat, NA)) + expect_unnamed_equal(get3dCoords(path2), cbind(pathMat, 7500)) }) -