Skip to content

Commit a4a8776

Browse files
committed
Issue #65: Add basic docs.
1 parent 148582b commit a4a8776

5 files changed

Lines changed: 168 additions & 3 deletions

File tree

README.rst

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,7 @@ Open a terminal, load your virtual environment and run the application as `pytho
5454
* sksurgeryreslice.py - DICOM reslice widget demo.
5555
* sksurgerytextoverlay.py - VTK text overlay demo.
5656
* sksurgerytransformpolydata.py - Read a surface mesh (.vtk,.vtp,.stl,.ply file), transform by 4x4 matrix and write as .vtk.
57-
* sksurgerystereorenderer.py - Reads a set of meshes, overlays on stereo video.
57+
* sksurgerystereorenderer.py - Reads a set of meshes, overlays on stereo video. `Documentation <stereo_renderer_demo.rst>`_.
5858

5959
.. features-end
6060
@@ -93,7 +93,7 @@ You can install dependencies and run the unit tests by installing and running to
9393
tox -e docs
9494
tox -e lint
9595

96-
Tox will create a separate venv in ```.tox/test```. See ```tox.ini``` for commands that tox runs.
96+
Tox will create a separate venv in ``.tox/test``. See ``tox.ini`` for commands that tox runs.
9797

9898
Encountering Problems?
9999
^^^^^^^^^^^^^^^^^^^^^^

docs/index.rst

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ scikit-surgeryutils documentation
1212
:maxdepth: 2
1313

1414
readme
15+
stereo_renderer_demo
1516

1617
.. toctree::
1718
:maxdepth: 2

docs/stereo_renderer_demo.rst

Lines changed: 157 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,157 @@
1+
Stereo Renderer Demo
2+
^^^^^^^^^^^^^^^^^^^^
3+
4+
Features
5+
6+
- Loads left intrinsics, right intrinsics, left-to-right extrinsics
7+
- Loads a set of models, using a single .json file
8+
- Plays video, or loads a single static image
9+
- Overlays models on top of video
10+
- Creates 2 windows.
11+
- One for interacting
12+
- One for a stereo display, either interlaced or stacked
13+
- Allows interacting with models, changing the model-to-world transform
14+
- Camera defaults to origin
15+
16+
Usage
17+
^^^^^
18+
19+
Create .json descriptor
20+
-----------------------
21+
22+
A set of models (.vtk, .vtp, .stl, .ply) can be loaded.
23+
Rather than have many command line args, we use a .json file.
24+
The format is::
25+
26+
{
27+
"surfaces": {
28+
"kidney": {
29+
"file": "kidney.vtk",
30+
"colour": [213, 142, 119],
31+
"opacity": 0.5,
32+
"visibility": true,
33+
"pickable": true
34+
},
35+
"artery": {
36+
"file": "artery.vtk",
37+
"colour": [203, 81, 54],
38+
"opacity": 0.5,
39+
"visibility": true,
40+
"pickable": false
41+
},
42+
"cyst": {
43+
"file": "cyst.vtk",
44+
"colour": [144, 221, 157],
45+
"opacity": 0.5,
46+
"visibility": true,
47+
"pickable": false
48+
},
49+
"renalsinusfat": {
50+
"file": "renalSinusFat.vtk",
51+
"colour": [161, 115, 220],
52+
"opacity": 0.5,
53+
"visibility": true,
54+
"pickable": false
55+
},
56+
"vein": {
57+
"file": "vein.vtk",
58+
"colour": [54, 109, 188],
59+
"opacity": 0.5,
60+
"visibility": true,
61+
"pickable": false
62+
}
63+
}
64+
}
65+
66+
Note: There should only ever be 1 "pickable" object.
67+
The pickable object is the one you interact with.
68+
69+
You can set colour ``[R, G, B]``, opacity ``[0, 1]`` and visibility ``[true|false]``, as shown above.
70+
71+
Calibration Files
72+
-----------------
73+
74+
Camera calibration files should be plain text, ASCII files, as would
75+
be compatible with ``numpy.loadtxt(filename)``.
76+
77+
- Intrinsics: [3x3]
78+
- Stereo extrinsics: [4x4]
79+
80+
Note: We do not load distortion parameters. Therefore, video must be undistorted.
81+
82+
83+
Usage
84+
-----
85+
86+
If you have ``pip install``-ed the whole package, you can see the usage message by
87+
running the ``sksurgerystereorenderer`` entry point with ``-h``.
88+
89+
For example::
90+
91+
promt% sksurgerystereorenderer -h
92+
usage: sksurgerystereorenderer [-h] -li LEFT_INTRINSICS -ri RIGHT_INTRINSICS -l2r LEFT_TO_RIGHT -m MODELS -r CLIPPING_RANGE -lv LEFT_VIDEO -rv RIGHT_VIDEO [-m2w MODEL_TO_WORLD] [-c2w CAMERA_TO_WORLD]
93+
[-s {stacked,interlaced}] [-v]
94+
95+
sksurgerystereorenderer - Stereo augmented reality renderer with interactive model manipulation.
96+
97+
options:
98+
-h, --help show this help message and exit
99+
-li, --left_intrinsics LEFT_INTRINSICS
100+
File path to left camera 3x3 intrinsics matrix.
101+
-ri, --right_intrinsics RIGHT_INTRINSICS
102+
File path to right camera 3x3 intrinsics matrix.
103+
-l2r, --left_to_right LEFT_TO_RIGHT
104+
File path to 4x4 stereo left-to-right extrinsic matrix.
105+
-m, --models MODELS Path to models .json configuration file.
106+
-r, --clipping_range CLIPPING_RANGE
107+
Near,far clipping range (e.g. '1,1000').
108+
-lv, --left_video LEFT_VIDEO
109+
Left video source: integer device index, video file path, or static image (.png/.jpg).
110+
-rv, --right_video RIGHT_VIDEO
111+
Right video source: integer device index, video file path, or static image (.png/.jpg).
112+
-m2w, --model_to_world MODEL_TO_WORLD
113+
File path to a 4x4 model-to-world matrix applied to all models on startup.
114+
-c2w, --camera_to_world CAMERA_TO_WORLD
115+
File path to a 4x4 camera-to-world matrix for the initial camera pose.
116+
-s, --stereo_mode {stacked,interlaced}
117+
Stereo display mode: 'stacked' (left=top, right=bottom) or 'interlaced'. Default: stacked.
118+
-v, --version show program's version number and exit
119+
120+
Alternatively, if you are running a development environment::
121+
122+
prompt% source .tox/test/bin/activate
123+
prompt% python sksurgerystereorenderer.py -h
124+
125+
gives the same output as the above help message.
126+
127+
An example would be::
128+
129+
prompt% source .tox/test/bin/activate
130+
prompt% python sksurgerystereorenderer.py \
131+
-m patient.json \
132+
-li davinci_intrinsics_undistorted.txt \
133+
-ri davinci_intrinsics_undistorted.txt \
134+
-l2r left_to_right.txt \
135+
-lv leftVideo_undistorted.avi \
136+
-rv rightVideo_undistorted.avi \
137+
-r 1,1000
138+
139+
Screens
140+
-------
141+
142+
The app can make use of a 2-monitor setup.
143+
144+
- If you have 2 monitors, the primary (e.g. laptop) shows a window for interacting, and the secondary (e.g. external 3D monitor) shows the stereo display. Both maximised.
145+
- If you have 1 monitor, both windows appear on the same monitor, both unmaximised.
146+
147+
148+
Interation Controls
149+
-------------------
150+
151+
Similar to standard VTK controls, and you need a 3-button mouse.
152+
153+
- Left button and move left-right: Rotate about centroid, left-right
154+
- Left button and move up-down: Rotate about centroid, up-down
155+
- Scroll wheel: Zoom in/out, by moving the model towards/away from camera
156+
- Right button and move: spin about forward axis
157+
- Middle button and move: pan (i.e. translation)

setup.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,7 @@
7272
'sksurgeryvideocalibration=sksurgeryutils.ui.sksurgeryvideocalibration_command_line:main',
7373
'sksurgeryvideocalibrationchecker=sksurgeryutils.ui.sksurgeryvideocalibrationchecker_command_line:main',
7474
'sksurgeryrenderoverlay=sksurgeryutils.ui.sksurgeryrenderoverlay_command_line:main',
75+
'sksurgerystereorenderer=sksurgeryutils.ui.sksurgerystereorenderer_command_line:main',
7576
],
7677
},
7778
)

sksurgeryutils/ui/sksurgerystereorenderer_demo.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -259,6 +259,7 @@ def __init__(self,
259259
self.set_model_to_world(model_to_world)
260260

261261
# Apply initial camera pose if provided
262+
self.camera_to_world = None
262263
if camera_to_world is not None:
263264
self.set_camera_to_world(camera_to_world)
264265
else:
@@ -345,6 +346,10 @@ def update(self):
345346
LOGGER.warning("Could not read frame from video source.")
346347
return
347348

349+
# For now, the camera is at the origin, and we move the model.
350+
# So, we can also defend against the user interacting with the 3D window.
351+
self.set_camera_to_world(np.eye(4))
352+
348353
# Set left image on the interactive overlay
349354
self.overlay_window.set_video_image(left_frame)
350355
self.overlay_window.Render()
@@ -447,11 +452,12 @@ def set_camera_to_world(self, camera_to_world):
447452
:param camera_to_world: 4x4 numpy ndarray, left camera to world.
448453
"""
449454
# Set left camera on overlay
455+
self.camera_to_world = camera_to_world
450456
self.overlay_window.set_camera_pose(camera_to_world)
451457

452458
# Set stereo cameras using the left-to-right extrinsic
453459
self.stereo_window.set_poses_from_left_camera(
454-
camera_to_world, self.left_to_right)
460+
self.camera_to_world, self.left_to_right)
455461

456462
def set_model_to_world(self, model_to_world):
457463
"""

0 commit comments

Comments
 (0)