Skip to content

Commit

Permalink
Merge pull request #33 from jiajic/dev
Browse files Browse the repository at this point in the history
Next steps:
Consider `across_spat_units` and `across_feat_types` params for finer control over subsets.
Could have a special ':all:' input that will then tell it to apply the subset to all spat_units/feat_types

How should hierarchical subsetting be done?
  • Loading branch information
jiajic authored Sep 22, 2023
2 parents fdf14be + 5d9ef94 commit e877abd
Show file tree
Hide file tree
Showing 8 changed files with 419 additions and 161 deletions.
2 changes: 1 addition & 1 deletion DESCRIPTION
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
Package: GiottoClass
Title: Giotto Suite object definitions and framework
Version: 0.0.0.9004
Version: 0.0.0.9005
Authors@R: c(
person("Ruben", "Dries", email = "rubendries@gmail.com",
role = c("aut", "cre")),
Expand Down
2 changes: 2 additions & 0 deletions NEWS.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@
## Breaking Changes

## Added
- Added `ext<-()` method for `giottoPolygon`, `giottoPoints`
- Added `crop()` method for `giottoLargeImage`, `giottoPoints`

## Changes
- Improved performance of gefToGiotto()
3 changes: 2 additions & 1 deletion R/methods-coerce.R
Original file line number Diff line number Diff line change
Expand Up @@ -56,8 +56,9 @@ as.data.table.giottoPoints <- function(x, ...) {


# DT -> SpatVector ####

# TODO
# as.points / as.polygon generics from terra are an option, but terra deals with
# this kind of conversion using vect() usually



Expand Down
81 changes: 80 additions & 1 deletion R/methods_crop.R
Original file line number Diff line number Diff line change
@@ -1,15 +1,23 @@

# documentation ####

#' @name crop-generic
#' @title Crop to a spatial subset
#' @description see [terra::crop]. Object x will be cropped using object y.
#' @param x object
#' @param y any object that has a SpatExtent or returns a SpatExtent
#' @param ... additional params to pass to terra::crop
#' @param \dots additional params to pass to terra::crop
NULL






# methods ####



#' @describeIn crop-generic Crop a giottoLargeImage
#' @export
setMethod('crop', signature('giottoLargeImage'), function(x, y, ...) {
Expand All @@ -21,3 +29,74 @@ setMethod('crop', signature('giottoLargeImage'), function(x, y, ...) {

x
})


#' @describeIn crop-generic Crop a giottoPoints
#' @param DT logical. Use alternative DT subsetting for crop operation
#' @param xmin,xmax,ymin,ymax only used if DT = TRUE. Set extent bounds
#' independently
#' @export
setMethod('crop', signature('giottoPoints'), function(
x, y, DT = TRUE, xmin = NULL, xmax = NULL, ymin = NULL, ymax = NULL, ...
) {
checkmate::assert_logical(DT)
if(DT) {
# converting to DT, subsetting, then regeneration of SpatVector with vect()
# is currently faster than using terra::crop() as of 9/21/23
missing_y = missing(y)
n_single_bounds = 4 - sum(sapply(list(xmin, xmax, ymin, ymax), is.null))

# check cropping params
# ONLY y OR the single spat bounds can be used at any one time
if((missing_y && n_single_bounds == 0) ||
(!missing_y && n_single_bounds > 0)) {
stop(wrap_txt('Crop bounds must be supplied through either a SpatExtent passed to \'y\'
or single numerical bounds passed to one or more of \'xmin\',\'xmax\', \'ymin\', \'ymax\''))
}

# 1. Get full set of cropping bounds
if(!missing_y) {
# if y is available, use y values directly.
# only the extent of y is usable for the DT method
if(!inherits(y, 'SpatExtent')) {
warning(wrap_txt('Only the extent of y is used when cropping with DT = TRUE'))
y = ext(y)
}

xmin = terra::xmin(y)
xmax = terra::xmax(y)
ymin = terra::ymin(y)
ymax = terra::ymax(y)

} else {
# otherwise, fill in any spatial subset bounds that may not have been
# supplied with the current extent value(s)
current_ext = ext(x)
if(is.null(xmin)) xmin = terra::xmin(current_ext)
if(is.null(xmax)) xmax = terra::xmax(current_ext)
if(is.null(ymin)) ymin = terra::ymin(current_ext)
if(is.null(ymax)) ymax = terra::ymax(current_ext)
}

# 2. convert to DT
sv = x@spatVector
spatDT = as.data.table(sv, geom = 'XY')

# 3. spatial subset then vect() to SpatVector again
spatDT_subset = spatDT[x >= xmin & x <= xmax & y >= ymin & y <= ymax]
sv_subset = terra::vect(spatDT_subset, c('x', 'y'))

# 4. update x
x@spatVector = sv_subset

} else {
x@spatVector = terra::crop(x@spatVector, y, ...)
}

# update ID cache and return
x@unique_ID_cache = unique(terra::values(x@spatVector)$feat_ID)
x
})



Loading

0 comments on commit e877abd

Please sign in to comment.