Skip to content

Commit

Permalink
Add VolumeUtils for slice positioning, clean up examples accordingly
Browse files Browse the repository at this point in the history
  • Loading branch information
skalarproduktraum committed Jan 30, 2024
1 parent e78bb91 commit 1064d30
Show file tree
Hide file tree
Showing 8 changed files with 55 additions and 59 deletions.
19 changes: 0 additions & 19 deletions src/main/kotlin/graphics/scenery/RichNode.kt
Original file line number Diff line number Diff line change
Expand Up @@ -13,23 +13,4 @@ open class RichNode(override var name: String = "Node") : DefaultNode (name), Ha
addMaterial()
addSpatial()
}

/**
* Positions [volumes] back-to-back without gaps, using their pixel-to-world ratio. Can, e.g., be used
* with [fromPathRawSplit] to load volume files greater than 2 GiB into sliced partitions and place
* the partitions back-to-back, emulating a single large volume in the scene.
*/
fun positionVolumeSlices(volumes: List<Volume>) {
val pixelToWorld = volumes.first().pixelToWorldRatio

var sliceIndex = 0
volumes.forEach { volume ->
val currentSlices = volume.getDimensions().z
logger.debug("Volume partition with z slices: $currentSlices")
volume.pixelToWorldRatio = pixelToWorld

volume.spatial().position = Vector3f(0f, 0f, 1.0f * (sliceIndex) * pixelToWorld)
sliceIndex += currentSlices
}
}
}
25 changes: 25 additions & 0 deletions src/main/kotlin/graphics/scenery/utils/extensions/VolumeUtils.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
package graphics.scenery.utils.extensions

import graphics.scenery.RichNode
import graphics.scenery.volumes.Volume
import graphics.scenery.volumes.Volume.Companion.fromPathRawSplit
import org.joml.Vector3f

/**
* Positions [volumes] back-to-back without gaps, using their pixel-to-world ratio. Can, e.g., be used
* with [fromPathRawSplit] to load volume files greater than 2 GiB into sliced partitions and place
* the partitions back-to-back, emulating a single large volume in the scene.
*/
fun RichNode.positionVolumeSlices(volumes: List<Volume>) {
val pixelToWorld = volumes.first().pixelToWorldRatio

var sliceIndex = 0
volumes.forEach { volume ->
val currentSlices = volume.getDimensions().z
logger.debug("Volume partition with z slices: $currentSlices")
volume.pixelToWorldRatio = pixelToWorld

volume.spatial().position = Vector3f(0f, 0f, 1.0f * (sliceIndex) * pixelToWorld)
sliceIndex += currentSlices
}
}
21 changes: 19 additions & 2 deletions src/main/kotlin/graphics/scenery/volumes/Volume.kt
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ import graphics.scenery.numerics.Random
import graphics.scenery.utils.lazyLogger
import graphics.scenery.utils.extensions.times
import graphics.scenery.utils.forEachIndexedAsync
import graphics.scenery.volumes.Volume.Companion.fromPathRawSplit
import graphics.scenery.volumes.Volume.VolumeDataSource.SpimDataMinimalSource
import io.scif.SCIFIO
import io.scif.filters.ReaderFilter
Expand Down Expand Up @@ -982,11 +983,26 @@ open class Volume(
}

/**
* Reads raw volumetric data from a [file].
* Reads raw volumetric data from a [file], assuming the input
* data is 16bit Unsigned Int.
*
* Returns the new volume.
*/
@JvmStatic @JvmOverloads
@JvmStatic
fun <T: RealType<T>> fromPathRaw(
file: Path,
hub: Hub
): BufferedVolume {
return fromPathRaw(file, hub, UnsignedShortType())
}

/**
* Reads raw volumetric data from a [file], with the [type] being
* explicitly specified.
*
* Returns the new volume.
*/
@JvmStatic
fun <T: RealType<T>> fromPathRaw(
file: Path,
hub: Hub,
Expand Down Expand Up @@ -1109,3 +1125,4 @@ open class Volume(
}
}


Original file line number Diff line number Diff line change
@@ -1,27 +1,19 @@
package graphics.scenery.tests.examples.cluster

import org.joml.Vector3f
import graphics.scenery.*
import graphics.scenery.backends.Renderer
import graphics.scenery.controls.InputHandler
import graphics.scenery.controls.TrackedStereoGlasses
import graphics.scenery.net.NodePublisher
import graphics.scenery.net.NodeSubscriber
import graphics.scenery.numerics.Random
import graphics.scenery.primitives.Cone
import graphics.scenery.proteins.Protein
import graphics.scenery.proteins.RibbonDiagram
import graphics.scenery.utils.Statistics
import graphics.scenery.utils.extensions.minus
import graphics.scenery.volumes.BufferedVolume
import graphics.scenery.volumes.Colormap
import graphics.scenery.volumes.TransferFunction
import graphics.scenery.volumes.Volume
import net.imglib2.type.numeric.integer.UnsignedByteType
import net.imglib2.type.numeric.integer.UnsignedShortType
import org.scijava.ui.behaviour.ClickBehaviour
import org.joml.Vector3f
import java.nio.file.Paths
import kotlin.concurrent.thread
import kotlin.math.PI
import kotlin.math.floor
import kotlin.math.roundToInt
Expand Down Expand Up @@ -103,7 +95,7 @@ class ClusterExample: SceneryBase("Clustered Volume Rendering example") {
val volume: BufferedVolume
val croc = false
if(croc) {
volume = Volume.fromPathRaw(Paths.get(basepath + "Croc/104B_08_side1_647_25p.raw"), hub, UnsignedShortType())
volume = Volume.fromPathRaw(Paths.get(basepath + "Croc/104B_08_side1_647_25p.raw"), hub)

volume.name = "volume"
volume.colormap = Colormap.get("viridis") // jet, hot, rainbow, plasma, grays
Expand All @@ -120,7 +112,7 @@ class ClusterExample: SceneryBase("Clustered Volume Rendering example") {
//volume.transferFunction.addControlPoint(0.1f, 0.5f)
scene.addChild(volume)
} else {
volume = Volume.fromPathRaw(Paths.get(basepath + "droso-royer-autopilot-transposed"), hub, UnsignedShortType())
volume = Volume.fromPathRaw(Paths.get(basepath + "droso-royer-autopilot-transposed"), hub)

volume.name = "volume"
volume.colormap = Colormap.get("hot") // jet, hot, rainbow, plasma, grays
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,6 @@ import graphics.scenery.attribute.material.Material
import graphics.scenery.volumes.Colormap
import graphics.scenery.volumes.TransferFunction
import graphics.scenery.volumes.Volume
import net.imglib2.type.numeric.integer.UnsignedByteType
import net.imglib2.type.numeric.integer.UnsignedShortType
import org.scijava.ui.behaviour.ClickBehaviour
import java.nio.file.Paths
import kotlin.concurrent.thread
Expand Down Expand Up @@ -71,8 +69,7 @@ class DemoReelExample: SceneryBase("Demo Reel") {

val histoneVolume = Volume.fromPathRaw(
Paths.get("$driveLetter:/ssd-backup-inauguration/CAVE_DATA/histones-isonet/stacks/default/"),
hub,
UnsignedShortType()
hub
)
histoneVolume.transferFunction = TransferFunction.ramp(0.1f, 1.0f)
histoneVolume.colormap = Colormap.get("hot")
Expand All @@ -82,8 +79,7 @@ class DemoReelExample: SceneryBase("Demo Reel") {

val drosophilaVolume = Volume.fromPathRaw(
Paths.get("$driveLetter:/ssd-backup-inauguration/CAVE_DATA/droso-royer-autopilot-transposed/"),
hub,
UnsignedShortType()
hub
)
drosophilaVolume.spatial {
rotation.rotateX(1.57f)
Expand All @@ -96,8 +92,7 @@ class DemoReelExample: SceneryBase("Demo Reel") {

val retinaVolume = Volume.fromPathRaw(
Paths.get("$driveLetter:/ssd-backup-inauguration/CAVE_DATA/retina_test2/"),
hub,
UnsignedShortType()
hub
)
retinaScene.addChild(retinaVolume)
retinaScene.visible = false
Expand Down
Original file line number Diff line number Diff line change
@@ -1,32 +1,21 @@
package graphics.scenery.tests.examples.cluster

import org.joml.Vector3f
import graphics.scenery.*
import graphics.scenery.backends.Renderer
import graphics.scenery.controls.InputHandler
import graphics.scenery.controls.TrackedStereoGlasses
import graphics.scenery.controls.behaviours.GamepadClickBehaviour
import graphics.scenery.controls.behaviours.GamepadRotationControl
import graphics.scenery.net.NodePublisher
import graphics.scenery.net.NodeSubscriber
import graphics.scenery.numerics.Random
import graphics.scenery.proteins.Protein
import graphics.scenery.proteins.RibbonDiagram
import graphics.scenery.utils.Statistics
import graphics.scenery.utils.extensions.minus
import graphics.scenery.volumes.BufferedVolume
import graphics.scenery.volumes.Colormap
import graphics.scenery.volumes.TransferFunction
import graphics.scenery.volumes.Volume
import net.imglib2.type.numeric.integer.UnsignedByteType
import net.imglib2.type.numeric.integer.UnsignedShortType
import net.java.games.input.Component
import org.scijava.ui.behaviour.ClickBehaviour
import org.joml.Vector3f
import java.nio.file.Paths
import kotlin.concurrent.thread
import kotlin.math.PI
import kotlin.math.floor
import kotlin.math.roundToInt

/**
* Example to demonstrate rendering on a cluster. Will display a grid of geometric options,
Expand Down Expand Up @@ -105,7 +94,7 @@ class GiovannisExample: SceneryBase("Clustered Volume Rendering example, Giovann

val croc = true
if(croc) {
volume = Volume.fromPathRaw(Paths.get(basepath + "Croc/104B_08_side1_647_25p.raw"), hub, UnsignedShortType())
volume = Volume.fromPathRaw(Paths.get(basepath + "Croc/104B_08_side1_647_25p.raw"), hub)

volume.name = "volume"
volume.colormap = Colormap.get("hot") // jet, hot, rainbow, plasma, grays
Expand All @@ -125,7 +114,7 @@ class GiovannisExample: SceneryBase("Clustered Volume Rendering example, Giovann
scene.addChild(volume)
volume.origin = Origin.FrontBottomLeft
} else {
volume = Volume.fromPathRaw(Paths.get(basepath + "droso-royer-autopilot-transposed"), hub, UnsignedShortType())
volume = Volume.fromPathRaw(Paths.get(basepath + "droso-royer-autopilot-transposed"), hub)

volume.name = "volume"
volume.colormap = Colormap.get("hot") // jet, hot, rainbow, plasma, grays
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import graphics.scenery.*
import graphics.scenery.backends.Renderer
import graphics.scenery.controls.TrackedStereoGlasses
import graphics.scenery.attribute.material.Material
import graphics.scenery.utils.extensions.positionVolumeSlices
import graphics.scenery.volumes.Colormap
import graphics.scenery.volumes.TransferFunction
import graphics.scenery.volumes.Volume
Expand Down Expand Up @@ -50,8 +51,6 @@ class SplitVolumeExample: SceneryBase("Split volume data", 1280, 720) {
val parent = pair.first as RichNode
val volumeList = pair.second

// Volume.positionSlices(volumeList, volumeList.first().pixelToWorldRatio)

parent.positionVolumeSlices(volumeList)

volumeList.forEachIndexed{ i, volume->
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,6 @@ import graphics.scenery.attribute.material.Material
import graphics.scenery.volumes.Colormap
import graphics.scenery.volumes.TransferFunction
import graphics.scenery.volumes.Volume
import net.imglib2.type.numeric.integer.UnsignedByteType
import net.imglib2.type.numeric.integer.UnsignedShortType
import org.joml.Vector3f
import java.nio.file.Paths
import kotlin.concurrent.thread
Expand Down Expand Up @@ -48,7 +46,7 @@ class VolumeExample: SceneryBase("Volume Rendering example", 1280, 720) {
s.material().diffuse = Vector3f(0.0f, 0.0f, 0.0f)
scene.addChild(s)

val volume = Volume.fromPathRaw(Paths.get(getDemoFilesPath() + "/volumes/box-iso/"), hub, UnsignedShortType())
val volume = Volume.fromPathRaw(Paths.get(getDemoFilesPath() + "/volumes/box-iso/"), hub)
volume.name = "volume"
volume.colormap = Colormap.get("viridis")
volume.spatial {
Expand Down

0 comments on commit 1064d30

Please sign in to comment.