comparison org/vision.org @ 306:7e7f8d6d9ec5

massive spellchecking
author Robert McIntyre <rlm@mit.edu>
date Sat, 18 Feb 2012 10:59:41 -0700
parents 23aadf376e9d
children 5d448182c807
comparison
equal deleted inserted replaced
305:19c43ec6958d 306:7e7f8d6d9ec5
9 9
10 * JMonkeyEngine natively supports multiple views of the same world. 10 * JMonkeyEngine natively supports multiple views of the same world.
11 11
12 Vision is one of the most important senses for humans, so I need to 12 Vision is one of the most important senses for humans, so I need to
13 build a simulated sense of vision for my AI. I will do this with 13 build a simulated sense of vision for my AI. I will do this with
14 simulated eyes. Each eye can be independely moved and should see its 14 simulated eyes. Each eye can be independently moved and should see its
15 own version of the world depending on where it is. 15 own version of the world depending on where it is.
16 16
17 Making these simulated eyes a reality is simple bacause jMonkeyEngine 17 Making these simulated eyes a reality is simple because jMonkeyEngine
18 already conatains extensive support for multiple views of the same 3D 18 already contains extensive support for multiple views of the same 3D
19 simulated world. The reason jMonkeyEngine has this support is because 19 simulated world. The reason jMonkeyEngine has this support is because
20 the support is necessary to create games with split-screen 20 the support is necessary to create games with split-screen
21 views. Multiple views are also used to create efficient 21 views. Multiple views are also used to create efficient
22 pseudo-reflections by rendering the scene from a certain perspective 22 pseudo-reflections by rendering the scene from a certain perspective
23 and then projecting it back onto a surface in the 3D world. 23 and then projecting it back onto a surface in the 3D world.
24 24
25 #+caption: jMonkeyEngine supports multiple views to enable split-screen games, like GoldenEye, which was one of the first games to use split-screen views. 25 #+caption: jMonkeyEngine supports multiple views to enable split-screen games, like GoldenEye, which was one of the first games to use split-screen views.
26 [[../images/goldeneye-4-player.png]] 26 [[../images/goldeneye-4-player.png]]
27 27
28 ** =ViewPorts=, =SceneProcessors=, and the =RenderManager=. 28 ** =ViewPorts=, =SceneProcessors=, and the =RenderManager=.
29 # =Viewports= are cameras; =RenderManger= takes snapshots each frame. 29 # =ViewPorts= are cameras; =RenderManger= takes snapshots each frame.
30 #* A Brief Description of jMonkeyEngine's Rendering Pipeline 30 #* A Brief Description of jMonkeyEngine's Rendering Pipeline
31 31
32 jMonkeyEngine allows you to create a =ViewPort=, which represents a 32 jMonkeyEngine allows you to create a =ViewPort=, which represents a
33 view of the simulated world. You can create as many of these as you 33 view of the simulated world. You can create as many of these as you
34 want. Every frame, the =RenderManager= iterates through each 34 want. Every frame, the =RenderManager= iterates through each
35 =ViewPort=, rendering the scene in the GPU. For each =ViewPort= there 35 =ViewPort=, rendering the scene in the GPU. For each =ViewPort= there
36 is a =FrameBuffer= which represents the rendered image in the GPU. 36 is a =FrameBuffer= which represents the rendered image in the GPU.
37 37
38 #+caption: =ViewPorts= are cameras in the world. During each frame, the =Rendermanager= records a snapshot of what each view is currently seeing; these snapshots are =Framebuffer= objects. 38 #+caption: =ViewPorts= are cameras in the world. During each frame, the =RenderManager= records a snapshot of what each view is currently seeing; these snapshots are =FrameBuffer= objects.
39 #+ATTR_HTML: width="400" 39 #+ATTR_HTML: width="400"
40 [[../images/diagram_rendermanager2.png]] 40 [[../images/diagram_rendermanager2.png]]
41 41
42 Each =ViewPort= can have any number of attached =SceneProcessor= 42 Each =ViewPort= can have any number of attached =SceneProcessor=
43 objects, which are called every time a new frame is rendered. A 43 objects, which are called every time a new frame is rendered. A
44 =SceneProcessor= recieves its =ViewPort's= =FrameBuffer= and can do 44 =SceneProcessor= receives its =ViewPort's= =FrameBuffer= and can do
45 whatever it wants to the data. Often this consists of invoking GPU 45 whatever it wants to the data. Often this consists of invoking GPU
46 specific operations on the rendered image. The =SceneProcessor= can 46 specific operations on the rendered image. The =SceneProcessor= can
47 also copy the GPU image data to RAM and process it with the CPU. 47 also copy the GPU image data to RAM and process it with the CPU.
48 48
49 ** From Views to Vision 49 ** From Views to Vision
50 # Appropriating Views for Vision. 50 # Appropriating Views for Vision.
51 51
52 Each eye in the simulated creature needs its own =ViewPort= so that 52 Each eye in the simulated creature needs its own =ViewPort= so that
53 it can see the world from its own perspective. To this =ViewPort=, I 53 it can see the world from its own perspective. To this =ViewPort=, I
54 add a =SceneProcessor= that feeds the visual data to any arbitray 54 add a =SceneProcessor= that feeds the visual data to any arbitrary
55 continuation function for further processing. That continuation 55 continuation function for further processing. That continuation
56 function may perform both CPU and GPU operations on the data. To make 56 function may perform both CPU and GPU operations on the data. To make
57 this easy for the continuation function, the =SceneProcessor= 57 this easy for the continuation function, the =SceneProcessor=
58 maintains appropriatly sized buffers in RAM to hold the data. It does 58 maintains appropriately sized buffers in RAM to hold the data. It does
59 not do any copying from the GPU to the CPU itself because it is a slow 59 not do any copying from the GPU to the CPU itself because it is a slow
60 operation. 60 operation.
61 61
62 #+name: pipeline-1 62 #+name: pipeline-1
63 #+begin_src clojure 63 #+begin_src clojure
64 (defn vision-pipeline 64 (defn vision-pipeline
65 "Create a SceneProcessor object which wraps a vision processing 65 "Create a SceneProcessor object which wraps a vision processing
66 continuation function. The continuation is a function that takes 66 continuation function. The continuation is a function that takes
67 [#^Renderer r #^FrameBuffer fb #^ByteBuffer b #^BufferedImage bi], 67 [#^Renderer r #^FrameBuffer fb #^ByteBuffer b #^BufferedImage bi],
68 each of which has already been appropiately sized." 68 each of which has already been appropriately sized."
69 [continuation] 69 [continuation]
70 (let [byte-buffer (atom nil) 70 (let [byte-buffer (atom nil)
71 renderer (atom nil) 71 renderer (atom nil)
72 image (atom nil)] 72 image (atom nil)]
73 (proxy [SceneProcessor] [] 73 (proxy [SceneProcessor] []
97 The continuation function given to =vision-pipeline= above will be 97 The continuation function given to =vision-pipeline= above will be
98 given a =Renderer= and three containers for image data. The 98 given a =Renderer= and three containers for image data. The
99 =FrameBuffer= references the GPU image data, but the pixel data can 99 =FrameBuffer= references the GPU image data, but the pixel data can
100 not be used directly on the CPU. The =ByteBuffer= and =BufferedImage= 100 not be used directly on the CPU. The =ByteBuffer= and =BufferedImage=
101 are initially "empty" but are sized to hold the data in the 101 are initially "empty" but are sized to hold the data in the
102 =FrameBuffer=. I call transfering the GPU image data to the CPU 102 =FrameBuffer=. I call transferring the GPU image data to the CPU
103 structures "mixing" the image data. I have provided three functions to 103 structures "mixing" the image data. I have provided three functions to
104 do this mixing. 104 do this mixing.
105 105
106 #+name: pipeline-2 106 #+name: pipeline-2
107 #+begin_src clojure 107 #+begin_src clojure
127 127
128 Note that it is possible to write vision processing algorithms 128 Note that it is possible to write vision processing algorithms
129 entirely in terms of =BufferedImage= inputs. Just compose that 129 entirely in terms of =BufferedImage= inputs. Just compose that
130 =BufferedImage= algorithm with =BufferedImage!=. However, a vision 130 =BufferedImage= algorithm with =BufferedImage!=. However, a vision
131 processing algorithm that is entirely hosted on the GPU does not have 131 processing algorithm that is entirely hosted on the GPU does not have
132 to pay for this convienence. 132 to pay for this convenience.
133 133
134 * Optical sensor arrays are described with images and referenced with metadata 134 * Optical sensor arrays are described with images and referenced with metadata
135 The vision pipeline described above handles the flow of rendered 135 The vision pipeline described above handles the flow of rendered
136 images. Now, we need simulated eyes to serve as the source of these 136 images. Now, we need simulated eyes to serve as the source of these
137 images. 137 images.
138 138
139 An eye is described in blender in the same way as a joint. They are 139 An eye is described in blender in the same way as a joint. They are
140 zero dimensional empty objects with no geometry whose local coordinate 140 zero dimensional empty objects with no geometry whose local coordinate
141 system determines the orientation of the resulting eye. All eyes are 141 system determines the orientation of the resulting eye. All eyes are
142 childern of a parent node named "eyes" just as all joints have a 142 children of a parent node named "eyes" just as all joints have a
143 parent named "joints". An eye binds to the nearest physical object 143 parent named "joints". An eye binds to the nearest physical object
144 with =bind-sense=. 144 with =bind-sense=.
145 145
146 #+name: add-eye 146 #+name: add-eye
147 #+begin_src clojure 147 #+begin_src clojure
182 color sensors, and a blind spot which has no sensors at all. Sensor 182 color sensors, and a blind spot which has no sensors at all. Sensor
183 density decreases in proportion to distance from the fovea. 183 density decreases in proportion to distance from the fovea.
184 184
185 I want to be able to model any retinal configuration, so my eye-nodes 185 I want to be able to model any retinal configuration, so my eye-nodes
186 in blender contain metadata pointing to images that describe the 186 in blender contain metadata pointing to images that describe the
187 percise position of the individual sensors using white pixels. The 187 precise position of the individual sensors using white pixels. The
188 meta-data also describes the percise sensitivity to light that the 188 meta-data also describes the precise sensitivity to light that the
189 sensors described in the image have. An eye can contain any number of 189 sensors described in the image have. An eye can contain any number of
190 these images. For example, the metadata for an eye might look like 190 these images. For example, the metadata for an eye might look like
191 this: 191 this:
192 192
193 #+begin_src clojure 193 #+begin_src clojure
213 213
214 The numbers that serve as keys in the map determine a sensor's 214 The numbers that serve as keys in the map determine a sensor's
215 relative sensitivity to the channels red, green, and blue. These 215 relative sensitivity to the channels red, green, and blue. These
216 sensitivity values are packed into an integer in the order =|_|R|G|B|= 216 sensitivity values are packed into an integer in the order =|_|R|G|B|=
217 in 8-bit fields. The RGB values of a pixel in the image are added 217 in 8-bit fields. The RGB values of a pixel in the image are added
218 together with these sensitivities as linear weights. Therfore, 218 together with these sensitivities as linear weights. Therefore,
219 0xFF0000 means sensitive to red only while 0xFFFFFF means sensitive to 219 0xFF0000 means sensitive to red only while 0xFFFFFF means sensitive to
220 all colors equally (gray). 220 all colors equally (gray).
221 221
222 For convienence I've defined a few symbols for the more common 222 For convenience I've defined a few symbols for the more common
223 sensitivity values. 223 sensitivity values.
224 224
225 #+name: sensitivity 225 #+name: sensitivity
226 #+begin_src clojure 226 #+begin_src clojure
227 (defvar sensitivity-presets 227 (defvar sensitivity-presets
381 Note that since each of the functions generated by =vision-kernel= 381 Note that since each of the functions generated by =vision-kernel=
382 shares the same =register-eye!= function, the eye will be registered 382 shares the same =register-eye!= function, the eye will be registered
383 only once the first time any of the functions from the list returned 383 only once the first time any of the functions from the list returned
384 by =vision-kernel= is called. Each of the functions returned by 384 by =vision-kernel= is called. Each of the functions returned by
385 =vision-kernel= also allows access to the =Viewport= through which 385 =vision-kernel= also allows access to the =Viewport= through which
386 it recieves images. 386 it receives images.
387 387
388 The in-game display can be disrupted by all the viewports that the 388 The in-game display can be disrupted by all the ViewPorts that the
389 functions greated by =vision-kernel= add. This doesn't affect the 389 functions generated by =vision-kernel= add. This doesn't affect the
390 simulation or the simulated senses, but can be annoying. 390 simulation or the simulated senses, but can be annoying.
391 =gen-fix-display= restores the in-simulation display. 391 =gen-fix-display= restores the in-simulation display.
392 392
393 ** The =vision!= function creates sensory probes. 393 ** The =vision!= function creates sensory probes.
394 394
570 "key-g" (colored-cannon-ball ColorRGBA/Green)) 570 "key-g" (colored-cannon-ball ColorRGBA/Green))
571 (fn [world] 571 (fn [world]
572 (light-up-everything world) 572 (light-up-everything world)
573 (speed-up world) 573 (speed-up world)
574 (.setTimer world timer) 574 (.setTimer world timer)
575 (display-dialated-time world timer) 575 (display-dilated-time world timer)
576 ;; add a view from the worm's perspective 576 ;; add a view from the worm's perspective
577 (if record? 577 (if record?
578 (Capture/captureVideo 578 (Capture/captureVideo
579 world 579 world
580 (File. 580 (File.
683 #+name: vision-header 683 #+name: vision-header
684 #+begin_src clojure 684 #+begin_src clojure
685 (ns cortex.vision 685 (ns cortex.vision
686 "Simulate the sense of vision in jMonkeyEngine3. Enables multiple 686 "Simulate the sense of vision in jMonkeyEngine3. Enables multiple
687 eyes from different positions to observe the same world, and pass 687 eyes from different positions to observe the same world, and pass
688 the observed data to any arbitray function. Automatically reads 688 the observed data to any arbitrary function. Automatically reads
689 eye-nodes from specially prepared blender files and instantiates 689 eye-nodes from specially prepared blender files and instantiates
690 them in the world as actual eyes." 690 them in the world as actual eyes."
691 {:author "Robert McIntyre"} 691 {:author "Robert McIntyre"}
692 (:use (cortex world sense util)) 692 (:use (cortex world sense util))
693 (:use clojure.contrib.def) 693 (:use clojure.contrib.def)