Skip to content
Snippets Groups Projects
Commit e89e458a authored by Xin Yang's avatar Xin Yang
Browse files

NGLVieweR

parent 90a190cf
Branches
No related merge requests found
Showing
with 985 additions and 0 deletions
Package: shinyNGLVieweR
Title: Shiny application for the NGLVieweR package
Version: 1.0
Authors@R:
person(given = "Niels",
family = "van der Velden",
role = c("aut", "cre"),
email = "n.s.j.vandervelden@gmail.com")
Description: Load, edit and save Protein Database files (PDB) in the webbrowser.
License: MIT
Imports:
config,
golem,
shiny,
processx,
attempt,
DT,
glue,
htmltools,
shinydashboard,
shinyWidgets,
shinyjs,
readr,
tools,
dplyr,
shinydashboardPlus,
stringr,
tidyr,
colourpicker,
bsplus,
r2d3,
NGLVieweR,
shinyjqui,
uuid,
pkgload
Encoding: UTF-8
LazyData: true
RoxygenNote: 7.1.1
Suggests:
testthat (>= 3.0.0)
Config/testthat/edition: 3
# Base image
FROM continuumio/miniconda3:24.3.0-0
LABEL IMAGE="nglviewer" \
IMAGE_VERSION="1.0.0" \
AUTHORS="Xin Yang" \
EMAIL="biohpc-help@utsouthwestern.edu"
# Set working directory
WORKDIR /vizapp/
# Environment variables for the campus proxy.
ENV http_proxy="http://proxy.swmed.edu:3128" \
https_proxy="http://proxy.swmed.edu:3128"
# Update conda and create environment
RUN conda update conda -y && \
conda create -y -c bioconda -c defaults -c conda-forge -n r441 r-base=4.4.1 && \
echo "r-base ==4.4.1" >> /opt/conda/envs/r441/conda-meta/pinned && \
conda update --all -y
# Install required R packages
RUN conda run -n r441 R -e "install.packages('DT', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('shiny', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('shinyFiles', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('Matrix', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('MASS', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('mgcv', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('ggplot2', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('config', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('golem', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('processx', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('attempt', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('glue', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('htmltools', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('shinydashboard', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('shinyWidgets', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('shinyjs', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('readr', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('tools', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('dplyr', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('shinydashboardPlus', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('stringr', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('tidyr', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('colourpicker', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('bsplus', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('r2d3', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('NGLVieweR', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('shinyjqui', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('uuid', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('pkgload', repos='http://cran.us.r-project.org')"
RUN conda run -n r441 R -e "install.packages('testthat', repos='http://cran.us.r-project.org')"
# Copy application files into the container
COPY tests /vizapp/tests
COPY rsconnect /vizapp/rsconnect
COPY R /vizapp/R
COPY pkgdown /vizapp/pkgdown
COPY man /vizapp/man
COPY inst /vizapp/inst
COPY docs /vizapp/docs
COPY dev /vizapp/dev
COPY shinyNGLVieweR.Rproj /vizapp/
COPY NAMESPACE /vizapp/
COPY astrocyte_vizapp.R /vizapp/
COPY DESCRIPTION /vizapp/
COPY entrypoint.sh /vizapp/
RUN chmod +x /vizapp/entrypoint.sh
ENTRYPOINT ["/vizapp/entrypoint.sh"]
ARG VIZAPP_PORT=8123
ENV VIZAPP_PORT=$VIZAPP_PORT
# Default command
CMD ["conda", "run", "-n", "r441", "Rscript", "astrocyte_vizapp.R"]
# Generated by roxygen2: do not edit by hand
export(aa_clicked_to_ngl)
export(bs_input_modal)
export(bs_textInput)
export(insertUI_component)
export(insertUI_name)
export(insertUI_selection)
export(jsboxCollapse)
export(loadContacts)
export(loadLabels)
export(loadLigand)
export(loadSelections)
export(loadStage)
export(loadStructure)
export(loadSurface)
export(loadUI_component)
export(ngl_to_position)
export(readFile)
export(removeUI_component)
export(run_app)
export(selection_to_ngl)
export(sequence_df)
import(NGLVieweR)
import(bsplus)
import(colourpicker)
import(dplyr)
import(r2d3)
import(readr)
import(shiny)
import(shinyWidgets)
import(shinydashboard)
import(shinydashboardPlus)
import(shinyjqui)
import(shinyjs)
import(stringr)
import(uuid)
importFrom(bsplus,bs_attach_modal)
importFrom(bsplus,bs_modal)
importFrom(bsplus,shinyInput_label_embed)
importFrom(bsplus,shiny_iconlink)
importFrom(config,get)
importFrom(dplyr,case_when)
importFrom(dplyr,mutate)
importFrom(dplyr,rowwise)
importFrom(golem,activate_js)
importFrom(golem,add_resource_path)
importFrom(golem,bundle_resources)
importFrom(golem,favicon)
importFrom(golem,with_golem_options)
importFrom(htmltools,HTML)
importFrom(htmltools,tagAppendAttributes)
importFrom(htmltools,tagList)
importFrom(htmltools,tags)
importFrom(readr,read_csv)
importFrom(readr,read_lines)
importFrom(shiny,NS)
importFrom(shiny,column)
importFrom(shiny,htmlTemplate)
importFrom(shiny,shinyApp)
importFrom(shiny,tagList)
importFrom(shiny,textInput)
importFrom(tidyr,complete)
importFrom(tidyr,full_seq)
importFrom(tidyr,replace_na)
importFrom(tidyr,unnest)
importFrom(tools,file_ext)
# Disabling shiny autoload
# See ?shiny::loadSupport for more information
#' Access files in the current app
#'
#' @param ... Character vector specifying directory and or file to
#' point to inside the current package.
#'
#' @noRd
app_sys <- function(...){
system.file(..., package = "shinyNGLVieweR")
}
#' Read App Config
#'
#' @param value Value to retrieve from the config file.
#' @param config R_CONFIG_ACTIVE value.
#' @param use_parent Logical, scan the parent directory for config file.
#'
#' @importFrom config get
#'
#' @noRd
get_golem_config <- function(
value,
config = Sys.getenv("R_CONFIG_ACTIVE", "default"),
use_parent = TRUE
){
config::get(
value = value,
config = config,
# Modify this if your config file is somewhere else:
file = app_sys("golem-config.yml"),
use_parent = use_parent
)
}
#' The application server-side
#'
#' @param input,output,session Internal parameters for {shiny}.
#' DO NOT REMOVE.
#' @import shiny
#' @noRd
app_server <- function(input, output, session) {
r <- reactiveValues()
observe({
r$sequence <- input$`NGLVieweROutput_ui_1-structure_sequence`
r$resno <- input$`NGLVieweROutput_ui_1-structure_resno`
r$chainname <- input$`NGLVieweROutput_ui_1-structure_chainname`
r$sequence_df <- sequence_df(r$sequence, r$resno, r$chainname, selchain = r$sequenceOutput$selectedChain)
r$aa_clicked <- input$aa_clicked
r$PDB <- input$`NGLVieweROutput_ui_1-structure_PDB`
})
observe({
r$rendering <- input$`NGLVieweROutput_ui_1-structure_rendering`
})
observe({
r$sidebarItemExpanded <- input$sidebarItemExpanded #loading of UI_components from .ngl file
})
#Component handlers
observe({
r$selection$selectionRemove_id <- input$selectionRemove_id #handler defined in handlers.js
r$selection$selectionLink_id <- input$selectionLink_id
r$label$labelRemove_id <- input$labelRemove_id #handler defined in handlers.js
r$label$labelLink_id <- input$labelLink_id
r$contact$contactRemove_id <- input$contactRemove_id #handler defined in handlers.js
r$contact$contactLink_id <- input$contactLink_id
})
observe({
r$examples$example_link_id <- input$example_link_id
})
callModule(mod_fileInput_server, "fileInput_ui_1", r=r)
callModule(mod_fileOutput_server, "fileOutput_ui_1", r=r)
callModule(mod_examples_server, "examples_ui_1", r=r)
callModule(mod_structure_server, "structure_ui_1", globalSession = session, r=r) #Pass globalSession to access NGLViewer object
callModule(mod_surface_server, "surface_ui_1", globalSession = session, r=r)
callModule(mod_ligand_server, "ligand_ui_1", globalSession = session, r=r)
callModule(mod_selection_server, "selection_ui_1", globalSession = session, r=r)
callModule(mod_label_server, "label_ui_1", globalSession = session, r=r)
callModule(mod_contact_server, "contact_ui_1", globalSession = session, r=r)
callModule(mod_stage_server, "stage_ui_1", globalSession = session, r=r)
callModule(mod_snapshot_server, "snapshot_ui_1", globalSession = session)
callModule(mod_sidebarcontrols_server, "sidebarcontrols_ui_1", globalSession = session, r=r)
callModule(mod_labelcontrols_server, "labelcontrols_ui_1", globalSession = session, r=r)
callModule(mod_sequenceOutput_server, "sequenceOutput_ui_1", globalSession = session, r=r)
callModule(mod_NGLVieweROutput_server, "NGLVieweROutput_ui_1", r=r)
}
#' The application User-Interface
#'
#' @param request Internal parameter for `{shiny}`.
#' DO NOT REMOVE.
#' @import shiny
#' @import shinydashboard
#' @import shinydashboardPlus
#' @import colourpicker
#' @import bsplus
#' @import shinyWidgets
#' @import shinyjs
#' @import r2d3
#' @import NGLVieweR
#' @import shinyjqui
#' @import uuid
#' @import readr
#' @noRd
app_ui <- function(request) {
tagList(
# Leave this function for adding external resources
golem_add_external_resources(),
# List the first level UI elements here
dashboardPage(
title = "AphaFold Output",
skin = "purple",
dashboardHeader(
title = HTML("BioHPC protein viewer"),titleWidth = "100%"
),
dashboardSidebar(
minified = FALSE,
sidebarMenu(
mod_fileInput_ui("fileInput_ui_1"),
mod_structure_ui("structure_ui_1"),
mod_surface_ui("surface_ui_1"),
mod_ligand_ui("ligand_ui_1"),
mod_selection_ui("selection_ui_1"),
mod_label_ui("label_ui_1"),
mod_contact_ui("contact_ui_1"),
mod_stage_ui("stage_ui_1"),
mod_snapshot_ui("snapshot_ui_1"),
mod_sidebarcontrols_ui("sidebarcontrols_ui_1")
)
),
dashboardBody(
fillPage(
mod_labelcontrols_ui("labelcontrols_ui_1"),
mod_sequenceOutput_ui("sequenceOutput_ui_1"),
mod_NGLVieweROutput_ui("NGLVieweROutput_ui_1")
)
)
)
)
}
#' Add external Resources to the Application
#'
#' This function is internally used to add external
#' resources inside the Shiny application.
#'
#' @import shiny
#' @importFrom golem add_resource_path activate_js favicon bundle_resources
#' @noRd
golem_add_external_resources <- function() {
add_resource_path(
"www", app_sys("app/www")
)
tags$head(
favicon(
ext='ico'
),
bundle_resources(
path = app_sys("app/www"),
app_title = "shinyNGLVieweR"
),
useShinyjs(),
extendShinyjs(text = jsboxCollapse, functions = c("collapse")), #Collapse box when clicking on title
# Input modals
bsplus::use_bs_tooltip(),
bsplus::use_bs_popover(),
bs_input_modal("select_modal", "Selection Language", htmlTemplate(app_sys("app/www/selectionModal.html")), "medium"),
bs_input_modal("contact_modal", "Contact Selection", htmlTemplate(app_sys("app/www/contactModal.html")), "medium")
)
}
#' Clicked residues to NGL query
#'
#' @description
#' Match clicked residues to chain and transform to NGL query
#'
#' @param selected_aa selected aa in list format
#' @param chainnames all chainnames of the sequence
#' @param selchain selected chainname
#'
#' @examples
#' \dontrun{
#' NGLVieweR_proxy("structure") %>% updateSelection("aa_clicked",
#' sele = aa_clicked_to_ngl(aa_clicked(), structure_chainname(), selectedChain()))
#' }
#' @export
aa_clicked_to_ngl <- function(selected_aa, chainnames, selchain = NULL) {
aa_sel <- paste(selected_aa, collapse = " OR ")
if (!is.null(selchain) && nchar(selchain) != 0 && any(chainnames %in% selchain)) {
output <- sprintf(":%s and (%s)", selchain, aa_sel)
} else {
output <- aa_sel
}
return(output)
}
\ No newline at end of file
#' Insert components to UI
#'
#' @description
#' Function to add UI components on submission
#'
#' @param type type of components. E.g. label, selection, contact.
#' @param name name of the components. Use \code{insertUI_name()} to generate a unique name.
#' @param uu_id uniqueID used to name the UI components.
#'
#' @examples
#' \dontrun{
#' insertUI_component('selection', insertUI_name('ligand'),
#' counter = 3, uu_id = "575ceb43-9ff5-40fb-85a4-9a8e9e06ceff")
#' }
#' @export
insertUI_component <- function(type, name, uu_id){
insertUI(
selector = sprintf('#%sPlaceholder', type),
ui = tags$div(
style = 'display:flex;',
id = sprintf('%s-%s', type, uu_id),
class = sprintf("%sholder", type),
style = 'font-size: 100%; padding: 0;',
actionLink(
sprintf('%sLink-%s', type, uu_id),
label = name,
class = sprintf("%sLink btn-link", type),
),
actionLink(
sprintf('%sRemove-%s', type, uu_id),
label = NULL,
icon = icon('trash'),
class = sprintf("%sRemove", type),
style = 'color: red;'
)
)
)
}
#' component UI name
#'
#' @description
#' Function to add a unique name
#'
#' @param name name of the selection. Defaults to selection-\code{counter} if input is \code{NULL} or \code{""}
#' @param counter value to create unique \code{name} if none is provided
#' @param type type of selection. E.g. label, selection, contact.
#'
#' @examples
#' \dontrun{
#' insertUI_name('selection', '', 3)
#' "selection-3"
#' }
#' @export
insertUI_name <- function(type, name = NULL, counter = 0) {
if (is.null(name)) {
name <- type
} else if (nchar(name) < 1) {
name <- type
} else {
name <- name
}
if (name == type && counter != 0) {
name <- sprintf("%s-%s", name, counter)
}
return(name)
}
#' components UI selection
#'
#' @description
#' Function to transform ngl.js selection for UI component
#'
#' @param selection ngl.js query to be transformed. Uses \code{selection_to_ngl()}
#' @param sequence protein sequence in string format.
#'
#' @examples
#' \dontrun{
#' insertUI_selection("1-3 OR <GHK>", "NGLSDFGHK")
#' }
#' @export
insertUI_selection <- function(sequence, selection) {
if (nchar(isolate(selection)) > 0) {
selection <- selection_to_ngl(sequence, selection)
} else {
selection <- 'none'
}
return(selection)
}
\ No newline at end of file
#' Load contacts from a .ngl file
#'
#' @description
#' Load contacts from a .ngl file
#'
#' @param NGLVieweR NGLVIeweR object.
#' @param contacts data.frame of contacts loaded from .ngl file.
#' @param contactTypes list of all different contactTypes that should be matched.
#'
#' @import NGLVieweR
#' @import stringr
#' @export
loadContacts <- function(NGLVieweR, contacts, contactTypes = list(
"hydrogenBond",
"weakHydrogenBond", "waterHydrogenBond",
"backboneHydrogenBond", "hydrophobic",
"halogenBond", "ionicInteraction",
"metalCoordination", "cationPi",
"piStacking"
)) {
viewer <- NGLVieweR
if (!is.null(contacts)) {
for (n in 1:nrow(contacts)) {
# get selected contactTypes
cont_inp <- unlist(str_split(contacts[n, "contactTypes"], ","))
cont_df <- contactTypes %in% cont_inp
if (is.na(cont_inp)) {
cont_df[] <- TRUE
}
viewer <- addRepresentation(viewer, "contact",
param =
list(
name = paste(contacts[n, "id"]),
sele = paste(contacts[n, "selection"]),
filterSele = list(
contacts[n, "selectionA"],
contacts[n, "selectionB"]
),
labelVisible = contacts[n, "labelVisible"],
labelUnit = contacts[n, "labelUnit"],
hydrogenBond = cont_df[1],
weakHydrogenBond = cont_df[2],
waterHydrogenBond = cont_df[3],
backboneHydrogenBond = cont_df[4],
hydrophobic = cont_df[5],
halogenBond = cont_df[6],
ionicInteraction = cont_df[7],
metalCoordination = cont_df[8],
cationPi = cont_df[9],
piStacking = cont_df[10]
)
)
}
}
return(viewer)
}
\ No newline at end of file
#' Load labels from a .ngl file
#'
#' @description
#' Load labels from a .ngl file
#'
#' @param NGLVieweR NGLVIeweR object.
#' @param labels data.frame of labels loaded from .ngl file.
#'
#' @import NGLVieweR
#' @export
loadLabels <- function(NGLVieweR, labels) {
viewer <- NGLVieweR
if (!is.null(labels)) {
for (n in 1:nrow(labels)) {
viewer <- addRepresentation(viewer, "label",
param =
list(
name = labels[n, "id"],
sele = paste(labels[n, "selection"]),
labelType = "format",
labelFormat = labels[n, "labelFormat"],
labelGrouping = labels[n, "labelGrouping"],
color = labels[n, "textColor"],
showBackground = labels[n, "labelBackground"],
backgroundColor = labels[n, "labelbackgroundColor"],
backgroundOpacity = labels[n, "labelbackgroundOpacity"],
radiusType = 1,
xOffset = labels[n, "xOffset"],
yOffset = labels[n, "yOffset"],
zOffset = labels[n, "zOffset"],
radiusSize = labels[n, "labelSize"],
fixedSize = labels[n, "fixedSize"],
fontFamily = "sans-serif"
)
)
}
}
return(viewer)
}
\ No newline at end of file
#' Load structure from a .ngl file
#'
#' @description
#' Load structure from a .ngl file
#'
#' @param NGLVieweR NGLVIeweR object.
#' @param ligand data.frame of ligand loaded from .ngl file.
#'
#' @import NGLVieweR
#' @export
loadLigand <- function(NGLVieweR, ligand) {
viewer <- NGLVieweR
if (!is.null(ligand)) {
if (ligand$ligand != "hide") {
viewer <- addRepresentation(viewer,
ligand$ligand,
param = list(
name = "ligand",
sele = "( not polymer or not ( protein or nucleic ) ) and not ( water or ACE or NH2 or ion)",
colorScheme = ligand$colorScheme,
colorValue = ligand$colorValue
)
)
}
if (!is.na(ligand$waterIon)) {
if (grepl("Water", ligand$waterIon)) {
viewer <- addRepresentation(viewer,
"ball+stick",
param = list(
name = "water",
sele = "water"
)
)
}
if (grepl("Ion", ligand$waterIon)) {
viewer <- addRepresentation(viewer,
"ball+stick",
param = list(
name = "ion",
sele = "ion"
)
)
}
}
} else {
viewer <- NGLVieweR
}
return(viewer)
}
\ No newline at end of file
#' Load selections from a .ngl file
#'
#' @description
#' Load selections from a .ngl file
#'
#' @param NGLVieweR NGLVIeweR object.
#' @param selections data.frame of selections loaded from .ngl file.
#'
#' @import NGLVieweR
#' @export
loadSelections <- function(NGLVieweR, selections) {
viewer <- NGLVieweR
if (!is.null(selections)) {
for (n in 1:nrow(selections)) {
viewer <- addRepresentation(viewer, selections[n, "structureType"],
param =
list(
name = selections[n, "id"],
colorValue = selections[n, "colorValue"],
colorScheme = selections[n, "colorScheme"],
opacity = as.numeric(selections[n, "opacity"]),
sele = selections[n, "selection"]
)
)
}
}
return(viewer)
}
#' Load stage from a .ngl file
#'
#' @description
#' Load stage from a .ngl file
#'
#' @param NGLVieweR NGLVIeweR object.
#' @param stage data.frame of selections loaded from .ngl file.
#'
#' @import NGLVieweR
#' @export
loadStage <- function(NGLVieweR, stage) {
viewer <- NGLVieweR
if (!is.null(stage)) {
viewer <- stageParameters(
viewer,
cameraType = stage$cameraType,
backgroundColor = stage$backgroundColor,
lightIntensity = stage$lightIntensity,
clipNear = stage$clipNear,
clipFar = stage$clipFar
)
} else{
viewer <- stageParameters(
viewer,
cameraType = "orthographic",
backgroundColor = "black",
lightIntensity = 1,
clipNear = 0,
clipFar = 100
)
}
return(viewer)
}
#' Load structure from a .ngl file
#'
#' @description
#' Load structure from a .ngl file
#'
#' @param NGLVieweR NGLVIeweR object.
#' @param structure data.frame of structure loaded from .ngl file.
#' @param format File
#'
#' @import NGLVieweR
#' @export
loadStructure <- function(NGLVieweR, structure, fileName=NULL, format = NULL) {
viewer <- NGLVieweR
if (is.null(structure)) {
if (fileName=="biohpc") {
representation <- "ball+stick"
} else if(format == "pdb" || format == "ngl" || is.null(format)){
representation <- "cartoon"
} else {
representation <- "ball+stick"
}
viewer <- addRepresentation(viewer, representation, param = list(
name = "structure",
colorScheme = "residueindex"
))
} else if (!is.null(structure) && !structure$type == "hide") {
viewer <- addRepresentation(viewer,
structure$type,
param =
list(
name = "structure",
colorScheme = structure$colorScheme,
colorValue = structure$colorValue,
sele = structure$selection,
visible = structure$visible
)
)
} else if (structure$type == "hide") {
viewer <- addRepresentation(viewer, "cartoon", param = list(
name = "structure",
colorScheme = structure$colorScheme,
colorValue = structure$colorValue,
sele = structure$selection,
visible = structure$visible
))
} else {
viewer <- NGLVieweR
}
return(viewer)
}
#' Load surface from a .ngl file
#'
#' @description
#' Load surface from a .ngl file
#'
#' @param NGLVieweR NGLVIeweR object.
#' @param surface data.frame of surface loaded from .ngl file.
#'
#' @import NGLVieweR
#' @export
loadSurface <- function(NGLVieweR, surface) {
viewer <- NGLVieweR
if (!is.null(surface)) {
viewer <- addRepresentation(viewer,
"surface",
param =
list(
name = "surface",
colorScheme = surface$colorScheme,
colorValue = surface$colorValue,
sele = surface$selection,
opacity = surface$opacity,
visible = surface$visible
)
)
} else {
if (is.null(surface)) {
viewer <- addRepresentation(viewer, "surface", param = list(
visible = FALSE
))
}
}
return(viewer)
}
\ No newline at end of file
#' Load UI components
#'
#' @description
#' Function to load UI components
#'
#' @param data data.frame of saved components
#' @param type type of component. E.g. label, selection, contact
#'
#' @import stringr
#' @export
loadUI_component <- function(data, type) {
removeUI(selector = sprintf(".%sholder", type), multiple = TRUE)
if (!is.null(data)) {
for (n in 1:nrow(data)) {
uu_id <- stringr::str_replace(data[n, "id"], sprintf("%s-", type), "")
insertUI(
selector = sprintf("#%sPlaceholder", type),
ui = tags$div(
style = "display:flex;",
id = data[n, "id"],
class = sprintf("%sholder", type),
actionLink(
sprintf("%sLink-%s", type, uu_id),
label = data[n, "name"],
class = sprintf("%sLink btn-link", type),
),
actionLink(
sprintf("%sRemove-%s", type, uu_id),
label = NULL,
icon = icon("trash"),
class = sprintf("%sRemove", type),
style = "color: red;"
)
)
)
}
}
}
\ No newline at end of file
#' AA positions from NGL query
#'
#' @description
#' Find all AA positions in protein sequence from a NGL query. Returns a list of all matched positions.
#'
#' @param sequence Protein sequence in string format
#' @param input sequence to find the positions for
#'
#' @examples
#' ngl_to_position("ALAAGSDFG", "1-5 OR <DFG>")
#' @import stringr
#' @importFrom dplyr rowwise mutate
#' @importFrom tidyr full_seq unnest
#' @export
ngl_to_position <- function(sequence, input){
#Get string matches
strings <- stringr::str_extract_all(input, "(?<=\\<)(.*?)(?=\\>)", simplify = TRUE)[1,]
#Get sequence matches
seq_match <- stringr::str_extract_all(input, '\\d+-\\d+', simplify = TRUE) [1,]
if(length(seq_match) != 0){
seq_match <- stringr::str_replace_all(seq_match, "-", ":")
seq_match <- unlist(lapply(seq_match, function(x) {eval(parse(text = x))}))
seq_match <- unique(seq_match)
input <- stringr::str_replace_all(input, '\\d+-\\d+', "")
} else {
seq_match <- NULL
}
#get numeric matches
numeric_match <- as.numeric(stringr::str_extract_all(input, '[0-9]+', simplify = TRUE)[1,])
numeric <- unique(c(seq_match, numeric_match))
#Return NULL if no numeric or string matches
if(length(strings) == 0 && length(numeric) == 0){
return(NULL)
} else if(length(numeric) != 0 && length(strings) == 0) {
return(numeric)
} else {
#Find positions
matchPositions <- stringr::str_locate_all(sequence, strings)
matchPositions <- do.call(rbind, matchPositions)
if(nrow(matchPositions) == 0){
return(NULL)
}
matchPositions <- data.frame(matchPositions) %>% dplyr::rowwise() %>% dplyr::mutate(sequence = list(tidyr::full_seq(c(.data$start, .data$end), 1)))
matchPositions <- tidyr::unnest(matchPositions, sequence)
positions <- sort(unique(matchPositions$sequence))
if(length(numeric != 0)){
positions <- sort(unique(c(positions, numeric)))
}
return(positions)
}
}
\ No newline at end of file
#' Function to read structural files or NGL session
#'
#' @description
#' Function to read .PDB, .PQR, or .NGL files
#'
#' @param file The file input. Either a PDB/PQR code or structural file.
#'
#' @importFrom tools file_ext
#' @importFrom readr read_lines read_csv
#' @export
readFile <- function(file) {
File <- list(
PDB = NULL,
structure = NULL,
surface = NULL,
ligand = NULL,
stage = NULL,
selections = NULL,
labels = NULL,
contacts = NULL,
fileExt = NULL
)
#If code is entered
fileExt <- tools::file_ext(file)
if(nchar(file) < 8 && tools::file_ext(file) == ""){
File$PDB <- file
return(File)
}
# #If file is not NGL format
# if (fileExt != "ngl" && fileExt != "NGL") {
# File$PDB <- file
# File$fileExt <- fileExt
# return(File)
# }
# If file is not NGL format
if (fileExt != "ngl" && fileExt != "NGL") {
# Handle .pdb and .pqr files
if (fileExt == "pdb" || fileExt == "PDB" || fileExt == "pqr" || fileExt == "PQR") {
File$PDB <- readr::read_lines(file)
File$fileExt <- tolower(fileExt) # Normalize extension to lowercase
return(File)
} else {
stop("Unsupported file format")
}
}
NGL <- readr::read_lines(file)
File$fileExt <- "pdb"
File$PDB <- NGL
# Get file start
structure_start <- grep(pattern = "#STRUCTURE", x = NGL)
surface_start <- grep(pattern = "#SURFACE", x = NGL)
ligand_start <- grep(pattern = "#LIGAND", x = NGL)
sel_start <- grep(pattern = "#SELECTIONS", x = NGL)
labels_start <- grep(pattern = "#LABELS", x = NGL)
contacts_start <- grep(pattern = "#CONTACTS", x = NGL)
stage_start <- grep(pattern = "#STAGE", x = NGL)
PDB_start <- grep(pattern = "#PDB", x = NGL)
# load data frames
if(surface_start - structure_start > 1){
File$structure <- data.frame(readr::read_csv(file, skip = structure_start, n_max = surface_start - (structure_start + 2)))
}
if(ligand_start - surface_start > 1){
File$surface <- data.frame(readr::read_csv(file, skip = surface_start, n_max = ligand_start - (surface_start + 2)))
}
if(stage_start - ligand_start > 1){
File$ligand <- data.frame(readr::read_csv(file, skip = ligand_start, n_max = stage_start - (ligand_start + 2)))
}
if(sel_start - stage_start > 1){
File$stage <- data.frame(readr::read_csv(file, skip = stage_start, n_max = sel_start - (stage_start + 2)))
}
if ((labels_start - (sel_start +1)) > 1) {
File$selections <- data.frame(readr::read_csv(file, skip = sel_start, n_max = labels_start - (sel_start + 2)))
}
if ((contacts_start - (labels_start + 1)) > 1) {
File$labels <- data.frame(readr::read_csv(file, skip = labels_start, n_max = contacts_start - (labels_start + 2)))
}
if ((PDB_start - (contacts_start + 1)) > 1) {
File$contacts <- data.frame(readr::read_csv(file, skip = contacts_start, n_max = PDB_start - (contacts_start + 2)))
}
return(File)
}
\ No newline at end of file
#' Remove component from UI
#'
#' @description
#' Function to add a UI once a component has been submitted
#'
#' @param NGLVieweR viewer component
#' @param data data.frame of saved components
#' @param type type of component. E.g. label, selection, contact
#' @param id ID of selected remove link
#'
#' @examples
#' removeUI_component('selection', input$selectionRemove_id)
#' @import stringr
#' @export
removeUI_component <- function(NGLVieweR, data, type, id) {
id <- stringr::str_replace(id, sprintf("%sRemove-", type), "")
type_id <- sprintf("%s-%s", type, id)
# removeUI
removeUI(selector = sprintf("#%s", type_id))
# remove structure component
NGLVieweR %>% removeSelection(type_id)
# remove seletion from data.frame
data <- subset(data, id != type_id)
return(data)
}
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment