Skip to content

Commit

Permalink
Merge pull request #397 from ncborcherding/dev
Browse files Browse the repository at this point in the history
v2.0.5
  • Loading branch information
ncborcherding authored Aug 9, 2024
2 parents 9f6ef41 + 17fecff commit 0d4ace6
Show file tree
Hide file tree
Showing 25 changed files with 9,438 additions and 9,162 deletions.
13 changes: 7 additions & 6 deletions DESCRIPTION
Original file line number Diff line number Diff line change
@@ -1,20 +1,21 @@
Package: scRepertoire
Title: A toolkit for single-cell immune receptor profiling
Version: 2.0.4
Version: 2.0.5
Authors@R: c(
person(given = "Nick", family = "Borcherding", role = c("aut", "cre"), email = "[email protected]"),
person(given = "Qile", family = "Yang", role = c("aut"), email = "[email protected]"),
person(given = "Qile", family = "Yang", role = c("aut"), email = "[email protected]"),
person(given = "Ksenia", family = "Safina", role = c("aut"), email = "[email protected]"))
Description: scRepertoire is a toolkit for processing and analyzing single-cell T-cell receptor (TCR) and immunoglobulin (Ig). The scRepertoire framework supports use of 10x, AIRR, BD, MiXCR, Omniscope, TRUST4, and WAT3R single-cell formats. The functionality includes basic clonal analyses, repertoire summaries, distance-based clustering and interaction with the popular Seurat and SingleCellExperiment/Bioconductor R workflows.
License: MIT + file LICENSE
Encoding: UTF-8
LazyData: true
RoxygenNote: 7.3.1
RoxygenNote: 7.3.2
biocViews: Software, ImmunoOncology, SingleCell, Classification, Annotation, Sequencing
Depends:
ggplot2,
R (>= 4.0)
ggplot2,
R (>= 4.0)
Imports:
assertthat,
cubature,
dplyr,
evmix,
Expand Down Expand Up @@ -60,5 +61,5 @@ Config/testthat/edition: 3
Language: en-US
LinkingTo:
Rcpp
URL: https://www.borch.dev/uploads/screpertoire/
URL: https://www.borch.dev/uploads/scRepertoire/
BugReports: https://github.com/ncborcherding/scRepertoire/issues
3 changes: 3 additions & 0 deletions NAMESPACE
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,9 @@ importFrom(SingleCellExperiment,reducedDim)
importFrom(SummarizedExperiment,"colData<-")
importFrom(SummarizedExperiment,colData)
importFrom(VGAM,dpareto)
importFrom(assertthat,assert_that)
importFrom(assertthat,is.flag)
importFrom(assertthat,is.string)
importFrom(cubature,adaptIntegrate)
importFrom(dplyr,"%>%")
importFrom(dplyr,across)
Expand Down
10 changes: 10 additions & 0 deletions NEWS.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,10 @@
# scRepertoire VERSION 2.0.5

## UNDERLYING CHANGES
* added type checks using assertthat
* updated conditional statements in constructConDFAndparseTCR.cpp
* Fixed issue in ```clonalQuant()``` and factor-based **group.by** variable

# scRepertoire VERSION 2.0.4

## UNDERLYING CHANGES
Expand All @@ -8,7 +15,10 @@
* ```clonalCompare()``` now retains the original clonal info if using **relabel.clones**
* Add Dandelion support in to ```loadContigs()``` and testthat
* Fixed issue with ```positionalProperty()``` assumption that the clones will all have 20 amino acids.
* Fixed issue with ```positionalProperty()``` and removing non-amino acids.
* Fixed IGH/K/L mistaking gene issue in ```vizGenes()```
* Add error message for NULL results in ```clonalCluster()``` with **export.graph = TRUE**
* Fixed issue with "full.clones" missing in ```combineExpression()``` when using 1 chain


# scRepertoire VERSION 2.0.3
Expand Down
33 changes: 19 additions & 14 deletions R/clonalCluster.R
Original file line number Diff line number Diff line change
Expand Up @@ -130,23 +130,28 @@ clonalCluster <- function(input.data,

#Returning the igraph object if exportGraph = TRUE
if(exportGraph) {
cluster <- do.call(igraph::union, output.list)
vertex <- names(V(cluster))
data_df <- unique(data.frame(
id = vertex
))
data_df <- merge(data_df, graph.variables, by = 1)
cluster <- set_vertex_attr(cluster,
name = "size",
index = data_df$id,
value = data_df[,2])
if(ncol(data_df) == 3) { #add grouping variable
if(length(is.null(output.list)) == length(output.list)) {
stop("No clusters detected with current parameters.")
} else {
output.list <- output.list[lapply(output.list,length)>0]
cluster <- do.call(igraph::union, output.list)
vertex <- names(V(cluster))
data_df <- unique(data.frame(
id = vertex
))
data_df <- merge(data_df, graph.variables, by = 1)
cluster <- set_vertex_attr(cluster,
name = "group",
name = "size",
index = data_df$id,
value = data_df[,3])
value = data_df[,2])
if(ncol(data_df) == 3) { #add grouping variable
cluster <- set_vertex_attr(cluster,
name = "group",
index = data_df$id,
value = data_df[,3])
}
return(cluster)
}
return(cluster)
}

cluster.list <- lapply(seq_len(length(output.list)), function(x) {
Expand Down
2 changes: 1 addition & 1 deletion R/clonalQuant.R
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ clonalQuant <- function(input.data,
mat[i,3] <- length(na.omit(input.data[[i]][,cloneCall]))
if (!is.null(group.by)) {
location <- which(colnames(input.data[[i]]) == group.by)
mat[i,4] <- input.data[[i]][1,location]
mat[i,4] <- as.vector(input.data[[i]][1,location])
}
}
if (scale) {
Expand Down
20 changes: 20 additions & 0 deletions R/combineContigs.R
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ utils::globalVariables(c(
#' nonproductive chains if the variable exists in the contig data. Default
#' is set to TRUE to remove nonproductive contigs.
#'
#' @importFrom assertthat assert_that is.flag
#' @export
#' @concept Loading_and_Processing_Contigs
#' @return List of clones for individual cell barcodes
Expand All @@ -58,6 +59,14 @@ combineTCR <- function(input.data,
removeMulti = FALSE,
filterMulti = FALSE,
filterNonproductive = TRUE) {

# rudimentary input checking
assert_that(is.character(samples) || is.null(samples))
assert_that(is.character(ID) || is.null(ID))
assert_that(is.flag(removeNA))
assert_that(is.flag(removeMulti))
assert_that(is.flag(filterMulti))

input.data <- .checkList(input.data)
input.data <- .checkContigs(input.data)
out <- NULL
Expand Down Expand Up @@ -185,6 +194,7 @@ combineTCR <- function(input.data,
#' nonproductive chains if the variable exists in the contig data. Default
#' is set to TRUE to remove nonproductive contigs.
#' @importFrom dplyr %>% mutate
#' @importFrom assertthat assert_that is.flag
#' @export
#' @concept Loading_and_Processing_Contigs
#' @return List of clones for individual cell barcodes
Expand All @@ -200,6 +210,16 @@ combineBCR <- function(input.data,
if(is.null(samples)) {
stop("combineBCR() requires the samples paramter for the calculation of edit distance.")
}

# rudimentary input checking
assert_that(is.character(samples) || is.null(samples))
assert_that(is.character(ID) || is.null(ID))
assert_that(is.flag(call.related.clones))
assert_that(is.numeric(threshold))
assert_that(is.flag(removeNA))
assert_that(is.flag(removeMulti))
assert_that(is.flag(filterMulti))

input.data <- .checkList(input.data)
input.data <- .checkContigs(input.data)
out <- NULL
Expand Down
29 changes: 16 additions & 13 deletions R/combineExpression.R
Original file line number Diff line number Diff line change
Expand Up @@ -49,11 +49,12 @@
#' @importFrom rlang %||% sym :=
#' @importFrom SummarizedExperiment colData<- colData
#' @importFrom S4Vectors DataFrame
#' @importFrom assertthat assert_that is.string is.flag
#' @export
#' @concept SC_Functions
#' @return Single-cell object with clone information added to meta data
#' information
#'
#'
combineExpression <- function(input.data,
sc.data,
cloneCall ="strict",
Expand All @@ -64,6 +65,17 @@ combineExpression <- function(input.data,
cloneSize = c(Rare = 1e-4,Small = 0.001,Medium = 0.01,Large = 0.1,Hyperexpanded = 1),
addLabel = FALSE) {
call_time <- Sys.time()

# rudimentary type checking
assert_that(isAnyValidProductOfCombineContigs(input.data))
assert_that(is_seurat_or_se_object(sc.data))
assert_that(is.string(cloneCall))
assert_that(is.string(chain))
assert_that(is.string(group.by) || is.null(group.by))
assert_that(is.flag(proportion))
assert_that(is.flag(filterNA))
assert_that(is_named_numeric(cloneSize))
assert_that(is.flag(addLabel))

options( dplyr.summarise.inform = FALSE )
if (!proportion && any(cloneSize < 1)) {
Expand All @@ -76,8 +88,9 @@ combineExpression <- function(input.data,
#Retain the full clone information
full.clone <- lapply(input.data, function(x) {
x[,c("barcode", cloneCall)]
full.clone <- bind_rows(full.clone)
})
full.clone <- bind_rows(full.clone)
for(i in seq_along(input.data)) {
input.data[[i]] <- .off.the.chain(input.data[[i]], chain, cloneCall)
}
Expand Down Expand Up @@ -179,7 +192,7 @@ combineExpression <- function(input.data,
clone_sym <- sym(cloneCall)
PreMeta <- PreMeta %>%
left_join(full.clone, by = "barcode", suffix = c("", ".from_full_clones")) %>%
mutate(!!column_sym := coalesce(!!sym(paste0(cloneCall, ".from_full_clones")), !!column_sym)) %>%
mutate(!!clone_sym := coalesce(!!sym(paste0(cloneCall, ".from_full_clones")), !!clone_sym)) %>%
select(-all_of(paste0(cloneCall, ".from_full_clones")))
}
barcodes <- PreMeta$barcode
Expand Down Expand Up @@ -226,14 +239,4 @@ combineExpression <- function(input.data,
return(sc.data)
}


.warn_str <- "< 1% of barcodes match: Ensure the barcodes in the single-cell object match the barcodes in the combined immune receptor output from scRepertoire. If getting this error, please check https://www.borch.dev/uploads/screpertoire/articles/faq."









3 changes: 3 additions & 0 deletions R/positionalProperty.R
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@
#' @export
#' @concept Summarize_Repertoire
#' @return ggplot of line graph of diversity by position
#' @author Florian Bach, Nick Borcherding

positionalProperty <- function(input.data,
chain = "TRB",
Expand Down Expand Up @@ -83,6 +84,8 @@ positionalProperty <- function(input.data,
#Getting AA Counts
aa.count.list <- .aa.counter(input.data, cloneCall, aa.length)

aa.count.list <- lapply(aa.count.list, function(x)subset(x, x$AA %in% c("A", "R", "N", "D", "C", "Q", "E", "G", "H", "I", "L", "K", "M", "F", "P", "S", "T", "W", "Y", "V")))

#Calculating properties and melting data
lapply(seq_along(aa.count.list), function(x) {
lapply(seq_len(nrow(aa.count.list[[x]]))[-1], function(y) {
Expand Down
56 changes: 56 additions & 0 deletions R/typecheck.R
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
# scRepertoire objects

isCombineContigsOutput <- function(obj) {
is.list(obj) && all(sapply(obj, is.data.frame))
}
assertthat::on_failure(isCombineContigsOutput) <- function(call, env) {
paste0(deparse(call$obj), " is not an output of combineTCR or combineBCR")
}

isListOfTwoCombineContigsOutputs <- function(obj) {
is.list(obj) && length(obj) == 2 && all(sapply(obj, isCombineContigsOutput))
}
assertthat::on_failure(isListOfTwoCombineContigsOutputs) <- function(call, env) {
paste0(
deparse(call$obj),
" is not a list of two outputs of combineTCR and combineBCR"
)
}

isAnyValidProductOfCombineContigs <- function(obj) {
isCombineContigsOutput(obj) || isListOfTwoCombineContigsOutputs(obj)
}
assertthat::on_failure(isAnyValidProductOfCombineContigs) <- function(call, env) {
paste0(
deparse(call$obj),
" is not a valid output of combineTCR or combineBCR, nor a list of them"
)
}

# bio objects

is_seurat_object <- function(obj) inherits(obj, "Seurat")
assertthat::on_failure(is_seurat_object) <- function(call, env) {
paste0(deparse(call$obj), " is not a Seurat object")
}

is_se_object <- function(obj) inherits(obj, "SummarizedExperiment")
assertthat::on_failure(is_se_object) <- function(call, env) {
paste0(deparse(call$obj), " is not a SummarizedExperiment object")
}

is_seurat_or_se_object <- function(obj) {
is_seurat_object(obj) || is_se_object(obj)
}
assertthat::on_failure(is_seurat_or_se_object) <- function(call, env) {
paste0(deparse(call$obj), " is not a Seurat or SummarizedExperiment object")
}

# general objects

is_named_numeric <- function(obj) {
is.numeric(obj) && !is.null(names(obj))
}
assertthat::on_failure(is_named_numeric) <- function(call, env) {
paste0(deparse(call$obj), " is not a named numeric vector")
}
16 changes: 8 additions & 8 deletions R/utils.R
Original file line number Diff line number Diff line change
@@ -1,10 +1,5 @@
# readability functions
# readability functions with appropriate assertthat fail messages
"%!in%" <- Negate("%in%")
is_seurat_object <- function(obj) inherits(obj, "Seurat")
is_se_object <- function(obj) inherits(obj, "SummarizedExperiment")
is_seurat_or_se_object <- function(obj) {
is_seurat_object(obj) || is_se_object(obj)
}

#'@importFrom stringr str_sort
.ordering.function <- function(vector,
Expand Down Expand Up @@ -148,7 +143,7 @@ is_seurat_or_se_object <- function(obj) {
.checkList <- function(df) {
df <- tryCatch(
{
if (!inherits(df, "list")) {
if (!inherits(df, "list")) {
df <- list(df)
}
df
Expand Down Expand Up @@ -629,7 +624,12 @@ is_df_or_list_of_df <- function(x) {
edge.list <- do.call(rbind, edge.list)

if(exportGraph) {
graph <- graph_from_edgelist(as.matrix(edge.list)[,c(1,2)])
if(!is.null(edge.list)) {
graph <- graph_from_edgelist(as.matrix(edge.list)[,c(1,2)])

} else {
graph <- NULL
}
return(graph)
}

Expand Down
2 changes: 2 additions & 0 deletions _pkgdown.yml
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,8 @@ navbar:
- text: Quantifying Clonal Bias
href: articles/Clonal_Bias.html
- text: '-------'
- text: Making Deep Learning Models with immApex
href: articles/immApex.html
- text: Combining Deep Learning and TCRs with Trex
href: articles/Trex.html
- text: Combining Deep Learning and BCRs with Ibex
Expand Down
5 changes: 3 additions & 2 deletions inst/pkgdown.yml
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
pandoc: 3.1.1
pkgdown: 2.0.9
pkgdown: 2.0.7
pkgdown_sha: ~
articles:
Attaching_SC: Attaching_SC.html
Expand All @@ -18,8 +18,9 @@ articles:
Running_Escape: Running_Escape.html
SC_Visualizations: SC_Visualizations.html
Trex: Trex.html
immApex: immApex.html
vignette: vignette.html
last_built: 2024-05-17T17:28Z
last_built: 2024-07-15T18:40Z
urls:
reference: https://www.borch.dev/uploads/scRepertoire/reference
article: https://www.borch.dev/uploads/scRepertoire/articles
Expand Down
3 changes: 3 additions & 0 deletions man/positionalProperty.Rd

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 2 additions & 2 deletions man/scRepertoire-package.Rd

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading

0 comments on commit 0d4ace6

Please sign in to comment.