#! /usr/bin/env Rscript # Copyright (C) Yueqiong Ni # Author: Yueqiong Ni # University of Hong Kong # School of Biological Sciences # Date: 2016/05 # ## Description: # Users of COMAN (a web server for COmprehensive Metatranscriptomics Analysis) can use this script to visualise the # co-expression network, using their preferred styles (e.g. node size and color, cutoff for correlations, network layout). # (Notice: For a most updated version of this script, please go to http://sbb.hku.hk/COMAN/files/) # ## Citation for COMAN (http://sbb.hku.hk/COMAN/) # For the latest citation information, pleae check http://sbb.hku.hk/COMAN/citation.psp # ## Inputs: # 1. Pairwise correlations between two functional groups (nodes) (in one condition); # 2. A subset of functional groups (nodes) of interest, with fold-change as the additional column # ## Outputs: # 1. (Static) co-expression network (both PDF and PNG formats); # 2. The correlations that have been visualised in the network (i.e. after the filtering); # 3. The nodes in the network, with their belonged communities and degree connectivity; # 4. (Interactive) co-expression network. # ## Other requirements: # To make full use of this script, you need to have three key R packages (as well as their dependencies, maybe) installed. # You may use this command in R to install them: install.packages(c("igraph", "network", "ndtv")) # ################################################# ### Run as command line: R --slave --args correlation_Treatment_DE.txt ../../DE_analysis/COG/FunctionalGroups_of_interest.txt < visualise_co-expression_network_COMAN.R ################################################ library(igraph) # This script utilise igraph package to visualise the static network. input.net <- commandArgs()[4] input.DElist <- commandArgs()[5] #input.net <- "correlation_Treatment_DE.txt" #input.DElist <- "DE_analysis/COG/FunctionalGroups_of_interest.txt" #################### Read into the pairwise correlations myntwk <- read.table(input.net,sep='\t',header=F) colnames(myntwk) <- c("source","target","weights") #################### Read into the list of "most varied functional groups" (and the fold-change information) node_info <- read.table(input.DElist,header=T,sep='\t',stringsAsFactors=F) #################### Create and edit the network #help(graph_from_data_frame) raw_mygraph <- graph.data.frame(myntwk,directed=F,vertices=node_info) is_simple(raw_mygraph) raw_mygraph <- simplify(raw_mygraph,remove.multiple=T,remove.loops=T,edge.attr.comb="first") #################### Filter the network based on cutoff of correlations (Users may define this value; this script uses the 90% percentile of all absolute values) cut.off <- as.numeric(quantile(abs(E(raw_mygraph)$weights),0.9)) filtered_mygraph <- delete_edges(raw_mygraph, E(raw_mygraph)[abs(weights)1, "circle", "square") V(mygraph)$community <- my_member V(mygraph)$degree <- degree(mygraph) e_transp <- ((abs(E(mygraph)$weights)-min(abs(E(mygraph)$weights))+0.1) / (max(abs(E(mygraph)$weights))-min(abs(E(mygraph)$weights))+0.1) )/3 # Use the above to adjust the width and transparency of the edges in the network E(mygraph)$color <- ifelse(E(mygraph)$weights>0, rgb(0,0,1,e_transp), rgb(1,0,0,e_transp)) E(mygraph)$width <- ((abs(E(mygraph)$weights)-min(abs(E(mygraph)$weights))+0.1) / (max(abs(E(mygraph)$weights))-min(abs(E(mygraph)$weights))+0.1) ) *0.7 layout_force <- layout_with_fr(mygraph,weights=E(mygraph)$weights) # force-directed layout algorithm within the igraph package #################### output to file with legend out.name <- strsplit(input.net, "_",fixed=T)[[1]][2] pdf(paste("coexpression_network_",out.name,".pdf",sep="")) layout(matrix(c(1,2), 1,2), widths=c(3,1)) par(mai=c(0.25,0.25,0.25,0.25)) plot(mygraph, layout=layout_force,vertex.color=V(mygraph)$community, vertex.label=NA, vertex.frame.color="black",palette=color25) plot.new() non_zero_community <- V(mygraph)$community[V(mygraph)$community!=0] labels <- paste("Community",sort(unique(non_zero_community)),sep='') palette(color25) legend("center",legend=labels, col=sort(unique(non_zero_community)), pch=19,title="Network Communities",cex=085) dev.off() ####################################################################################################################################### ############################## Output the network and the table containing node network properties ####################################################################################################################################### out_network <- as_data_frame(mygraph, what="edges")[,1:3] out_network_filename <- paste("coexpression_network_",out.name,".tsv",sep="") write.table(out_network,file= out_network_filename, quote=F,sep='\t',row.names=F,col.names=T) out_nodes <- as_data_frame(mygraph, what="vertices")[,c("name","Treatment_vs_Control","community","degree")] out_nodes_filename <- paste("coexpression_network_Nodes_",out.name,".tsv",sep="") write.table(out_nodes,file= out_nodes_filename, quote=F,sep='\t',row.names=F,col.names=T) ####################################################################################################################################### ############################## Extra: interactive network for web use ####################################################################################################################################### # In order to generate the interactive network, you need to have the following packages installed and loaded. library(network) library(ndtv) #################### create the network object net_inter <- network(out_network,vertex.attr=out_nodes,loops=F,multiple=F,bipartite=F,matrix.type="edgelist",ignore.eval=F) #################### change the visualisation styles # edge transparency and width e_transp <- ((abs(net_inter %e% "weights")-min(abs(net_inter %e% "weights"))) / (max(abs(net_inter %e% "weights"))-min(abs(net_inter %e% "weights"))) )*0.4 net_inter_edge_width <- ((abs(net_inter %e% "weights")-min(abs(net_inter %e% "weights"))+0.1) / (max(abs(net_inter %e% "weights"))-min(abs(net_inter %e% "weights"))+0.1) )*4 # use the same layout (node positions) as the static network above net_inter %v% "myx" <- layout_force[,1] net_inter %v% "myy" <- layout_force[,2] net_inter.dyn <- networkDynamic(base.net=net_inter) compute.animation(net_inter.dyn,animation.mode='useAttribute',layout.par=list(x="myx",y="myy")) #################### Generate the web-based interactive network palette(color25) render.d3movie(net_inter.dyn, d3.options=list(slider=F,playControls=F), usearrows = F, displaylabels = F, bg="#111111", vertex.border="#ffffff", vertex.col = (net_inter %v% "community"), vertex.cex = (net_inter %v% "degree")/max(net_inter %v% "degree")*2+1, vertex.sides=ifelse((net_inter %v% 'Treatment_vs_Control')>1,3,4), vertex.rot=ifelse((net_inter %v% 'Treatment_vs_Control')>1,0,45), edge.col = rgb(0,1,1,e_transp), edge.lwd= net_inter_edge_width, vertex.tooltip = paste("Name:", (net_inter %v% 'name') , "
", "Degree:", (net_inter %v% 'degree'), "
", "Fold-Change:", round(net_inter %v% 'Treatment_vs_Control',digits=3), "
", "Community:", (net_inter %v% 'community')), edge.tooltip = paste("Edge weight:", (net_inter %e% "weights" )), launchBrowser=F, filename=paste("Interactive_coexpression_network_",out.name,".html",sep=""), output.mode='HTML')