Manipulate Package
The manipulate
from RStudio allows you to create simple Tcl/Tk operators for interactive visualization. I will use it for a simple slider to view different slices of an image.
library(manipulate)
fslr package
I'm calling the fslr
package because I know that if you have it installed, you will likely have FSL and have a 1mm T1 template from MNI in a specific location. fslr
also loads the oro.nifti
package so that readNIfTI
is accessible after loading fslr
. You can download a test NIfTI image here if you don't have access to any and don't have FSL downlaoded.
Here I will read in the template image:
library(fslr) options(fsl.path='/usr/local/fsl') template = file.path(fsldir(), "data/standard", "MNI152_T1_1mm_brain.nii.gz") img = readNIfTI(template)
The iplot function
The iplot
function defined below takes in a nifti
object, the specific plane to be plotted and additional options to be passed to oro.nifti::image
. The function is located on my GitHub here.
iplot = function(img, plane = c("axial", "coronal", "sagittal"), ...){ ## pick the plane plane = match.arg(plane, c("axial", "coronal", "sagittal")) # Get the max number of slices in that plane for the slider ns= switch(plane, "axial"=dim(img)[3], "coronal"=dim(img)[2], "sagittal"=dim(img)[1]) ## run the manipulate command manipulate({ image(img, z = z, plot.type= "single", plane = plane, ...) # this will return mouse clicks (future experimental work) pos <- manipulatorMouseClick() if (!is.null(pos)) { print(pos) } }, ## make the slider z = slider(1, ns, step=1, initial = ceiling(ns/2)) ) }
Example plots
Here are some examples of how this iplot
function would be used:
iplot(img) iplot(img, plane = "coronal") iplot(img, plane = "sagittal")
The result will be a plotted image of the slice with a slider. This is most useful if you run it within RStudio.
Below are 2 example outputs of what you see in RStudio:
Slice 91:
Slice 145:
Conclusions
The iplot
function allows users to interactively explore neuroimages. The plotting is not as fast as I'd like, I may try to speed up the oro.nifti::image
command or implement some subsampling. It does however show a proof of concept how interactive neuroimaging visualization can be done in R
.
Note
manipulate
must be run in RStudio for manipulation. The fslr
function fslview
will call FSLView from FSL for interactive visualization. This is an option of interactive neuroimaging “in R
”, but not a real or satisfactory implementation for me (even though I use it frequently). If anyone has implemented such a solution in R
, I'd love to hear about it.
John,
Great post! I think we definitely need some tools for fMRI visualization in R, and I like your idea of use of manipulate function!
The current iPlot function though seems to be a little bit too slow. Interestingly if you run manipulate by it self without iplot wrapper it is thee times as fast (my guess there are issues with memory allocation):
plane = “axial”
plane = match.arg(plane, c(“axial”, “coronal”, “sagittal”))
# Get the max number of slices in that plane for the slider
ns = switch(plane,
“axial”=dim(img)[3],
“coronal”=dim(img)[2],
“sagittal”=dim(img)[1])
manipulate({
image(img, z = z, plot.type= “single”)
# this will return mouse clicks (future experimental work)
pos <- manipulatorMouseClick()
if (!is.null(pos)) {
print(pos)
}
},
## make the slider
z = slider(1, ns, step=1, initial = ceiling(ns/2))
)
###############################################################
I was also able to speed it up even more by using "rasterPlot" function
###############################################################
plane = "axial"
plane = match.arg(plane, c("axial", "coronal", "sagittal"))
# Get the max number of slices in that plane for the slider
ns = switch(plane,
"axial"=dim(img)[3],
"coronal"=dim(img)[2],
"sagittal"=dim(img)[1])
manipulate({
# Draw a slice
#==========================================================
simg = img[,,z];
simg = simg/max(simg) #Normalize simg to be between 0 and 1
simg2 = t(simg[,ncol(simg):1]) # Rotate Matrix
w = dim(simg2)[1];
h = dim(simg2)[2];
plot(c(0, h), c(0, w), type = "n", xlab = "", ylab = "", axes = F)
rasterImage(as.raster(simg2), 0, w, h, 0)
#==========================================================
# this will return mouse clicks (future experimental work)
pos <- manipulatorMouseClick()
if (!is.null(pos)) {
print(pos)
}
},
## make the slider
z = slider(1, ns, step=1, initial = ceiling(ns/2))
)
Let me know what you think,
Best,
~Max
Pingback: A better interactive neuroimage plotter in R | A HopStat and Jump Away