rspatial

Create ellipses based on dataframe


I have a dataframe with coordinates and radii for an ellipse in each row.

dat <- data.frame(id = c("a", "b", "c"),
                  x = c(1, 2, 3),
                  y = c(1, 2, 3),
                  sx = c(.3, .5, .7),
                  sy = c(.2, .4, .6))
> dat
  id x y  sx  sy
1  a 1 1 0.3 0.2
2  b 2 2 0.5 0.4
3  c 3 3 0.7 0.6

How can I create a spatial object with all ellipses?

I have tried the following, which results in an error.

library(dplyr)
library(sfdep)
    dat %>%
      rowwise() %>%
      ellipse(x = x, y = y, sx = sx, sy = sy, n = 10, rotation = 0)

Error in ellipse(., x = x, y = y, sx = sx, sy = sy, n = 10, rotation = 0) : 
  unused argument (.)

Solution

  • Try turning data.frame into sf object of points first, you can then use st_ellipse(). With rowwise() you still need to use mutate().

    library(sfdep)
    library(dplyr)
    library(sf)
    #> Linking to GEOS 3.13.1, GDAL 3.10.2, PROJ 9.5.1; sf_use_s2() is TRUE
    
    dat <- data.frame(id = c("a", "b", "c"),
                      x = c(1, 2, 3),
                      y = c(1, 2, 3),
                      sx = c(.3, .5, .7),
                      sy = c(.2, .4, .6))
    
    dat_sf <- 
      dat |> 
      st_as_sf(coords = c("x","y"), remove = FALSE) |> 
      rowwise() |> 
      mutate(geometry = st_ellipse(geometry, sx, sy, rotation = 0, n = 10)) |> 
      ungroup()
    
    dat_sf
    #> Simple feature collection with 3 features and 5 fields
    #> Geometry type: LINESTRING
    #> Dimension:     XY
    #> Bounding box:  xmin: 0.7 ymin: 0.8097887 xmax: 3.7 ymax: 3.570634
    #> CRS:           NA
    #> # A tibble: 3 × 6
    #>   id        x     y    sx    sy                                         geometry
    #>   <chr> <dbl> <dbl> <dbl> <dbl>                                     <LINESTRING>
    #> 1 a         1     1   0.3   0.2 (1.3 1, 1.242705 1.117557, 1.092705 1.190211, 0…
    #> 2 b         2     2   0.5   0.4 (2.5 2, 2.404508 2.235114, 2.154508 2.380423, 1…
    #> 3 c         3     3   0.7   0.6 (3.7 3, 3.566312 3.352671, 3.216312 3.570634, 2…
    
    plot(dat_sf[,"id"], axes = TRUE)