changeset 37:eeba17a4bd54

cleaning up the touch code
author Robert McIntyre <rlm@mit.edu>
date Thu, 03 Nov 2011 09:52:34 -0700
parents 91090f8a4414
children 99971a59b6ac
files org/skin.org
diffstat 1 files changed, 82 insertions(+), 54 deletions(-) [+]
line wrap: on
line diff
     1.1 --- a/org/skin.org	Thu Nov 03 08:42:39 2011 -0700
     1.2 +++ b/org/skin.org	Thu Nov 03 09:52:34 2011 -0700
     1.3 @@ -1,29 +1,38 @@
     1.4 -#+title: SKIN!
     1.5 +#+title: Simulated Sense of Touch
     1.6  #+author: Robert McIntyre
     1.7  #+email: rlm@mit.edu
     1.8 -#+description: Simulating touch in JMonkeyEngine
     1.9 +#+description: Simulated touch for AI research using JMonkeyEngine and clojure.
    1.10 +#+keywords: simulation, tactile sense, jMonkeyEngine3, clojure
    1.11  #+SETUPFILE: ../../aurellem/org/setup.org
    1.12  #+INCLUDE: ../../aurellem/org/level-0.org
    1.13 -#+babel: :mkdirp yes :noweb yes
    1.14  
    1.15 -let's see what checkboxes look like:
    1.16 +* Touch
    1.17  
    1.18 -* Skin!
    1.19 +My creatures need to be able to feel their environments. The idea here
    1.20 +is to thousands of small /touch receptors/ along the geometries which
    1.21 +make up the creature's body.  The number of touch receptors in a given
    1.22 +area is determined by how complicated that area is, as determined by
    1.23 +the total number of triangles in that region. This way, complicated
    1.24 +regions like the hands/face, etc. get more touch receptors than
    1.25 +simpler areas of the body.
    1.26  
    1.27  #+srcname: skin-main
    1.28  #+begin_src clojure
    1.29 -(ns body.skin)
    1.30 -(use 'cortex.world)
    1.31 -(use 'cortex.import)
    1.32 -(use 'clojure.contrib.def)
    1.33 -(cortex.import/mega-import-jme3)
    1.34 -(rlm.rlm-commands/help)
    1.35 -
    1.36 -(import java.util.logging.Level)
    1.37 -(import java.util.logging.Logger)
    1.38 -(use 'hello.brick-wall)
    1.39 -
    1.40 -(defn triangles [#^Geometry geom]
    1.41 +(ns cortex.touch
    1.42 +  "Simulate the sense of touch in jMonkeyEngine3. Enables any Geometry
    1.43 +  to be outfitted with touch sensors with density proportional to the
    1.44 +  density of triangles along the surface of the Geometry. Enables a
    1.45 +  Geometry to know what parts of itself are touching nearby objects."
    1.46 +  {:author "Robert McIntyre"}
    1.47 +  (:use (cortex world util))
    1.48 +  (:import com.jme3.scene.Geometry)
    1.49 +  (:import com.jme3.collision.CollisionResult)
    1.50 +  (:import com.jme3.math Triangle Vector3f Ray))
    1.51 +   
    1.52 +(defn triangles
    1.53 +  "Return a sequence of all the Triangles which compose a given
    1.54 +  Geometry." 
    1.55 +  [#^Geometry geom]
    1.56    (let
    1.57        [mesh (.getMesh geom)
    1.58         triangles (transient [])]
    1.59 @@ -31,26 +40,72 @@
    1.60       (for [n (range (.getTriangleCount mesh))]
    1.61         (let [tri (Triangle.)]
    1.62           (.getTriangle mesh n tri)
    1.63 -         (.calculateNormal tri)
    1.64 -         (.calculateCenter tri)
    1.65 +        ;; (.calculateNormal tri)
    1.66 +        ;; (.calculateCenter tri)
    1.67           (conj! triangles tri))))
    1.68      (persistent! triangles)))
    1.69     
    1.70  (defn get-ray-origin
    1.71 +  "Return the origin which a Ray would have to have to be in the exact
    1.72 +  center of a particular Triangle in the Geometry in World
    1.73 +  Coordinates."
    1.74    [geom tri]
    1.75    (let [new (Vector3f.)]
    1.76      (.calculateCenter tri)
    1.77 -    (.localToWorld geom (.getCenter tri) new)
    1.78 -    new))
    1.79 +    (.localToWorld geom (.getCenter tri) new) new))
    1.80  
    1.81  (defn get-ray-direction
    1.82 +  "Return the direction which a Ray would have to have to be in the
    1.83 +  exact center of a particular Triangle in the Geometry, pointing
    1.84 +  normal to the Triangle, in coordinates relative to the center of the
    1.85 +  Triangle."
    1.86    [geom tri]
    1.87    (let [n+c (Vector3f.)]
    1.88      (.calculateNormal tri)
    1.89      (.calculateCenter tri)
    1.90 -    (.localToWorld geom (.add (.getCenter tri) (.getNormal tri)) n+c)
    1.91 -    (.subtract n+c (get-ray-origin geom tri))
    1.92 -    ))
    1.93 +    (.localToWorld
    1.94 +     geom
    1.95 +     (.add (.getCenter tri) (.getNormal tri)) n+c)
    1.96 +    (.subtract n+c (get-ray-origin geom tri))))
    1.97 +
    1.98 +(defn normal-rays
    1.99 +  "For each Triangle which comprises the Geometry, returns a Ray which
   1.100 +  is centered on that Triangle, points outward in a normal direction,
   1.101 +  and extends for =limit= distance."
   1.102 +  [limit #^Geometry geom]
   1.103 +  (vec
   1.104 +   (map 
   1.105 +    (fn [tri]
   1.106 +      (doto 
   1.107 +          (Ray. (get-ray-origin geom tri)
   1.108 +                (get-ray-direction geom tri))
   1.109 +        (.setLimit limit)))
   1.110 +    (triangles geom))))
   1.111 +
   1.112 +(defn touch-percieve
   1.113 +  "Augment a Geometry with the sense of touch. Returns a sequence of
   1.114 +  non-negative integers, one for each triangle, with the value of the
   1.115 +  integer describing how many objects a ray of length =limit=, normal
   1.116 +  to the triangle and originating from its center, encountered. The
   1.117 +  Geometry itself is not counted among the results."
   1.118 +  [limit geom node]
   1.119 +  (let [normals  (normal-rays limit geom)]
   1.120 +    (doall
   1.121 +     (for [ray normals]
   1.122 +       (do
   1.123 +         (let [results (CollisionResults.)]
   1.124 +           (.collideWith node ray results)
   1.125 +           (let [touch-objects
   1.126 +                 (set (filter #(not (= geom %))
   1.127 +                              (map #(.getGeometry %) results)))]
   1.128 +             (count touch-objects))))))))
   1.129 +#+end_src
   1.130 +
   1.131 +
   1.132 +* Example
   1.133 +
   1.134 +#+begin_src clojure 
   1.135 +
   1.136    
   1.137  (defn ray-origin-debug
   1.138    [ray color]
   1.139 @@ -81,7 +136,7 @@
   1.140  (defn contact-color [contacts]
   1.141    (case contacts
   1.142      0 ColorRGBA/Gray
   1.143 -    1  ColorRGBA/Blue 
   1.144 +    1  ColorRGBA/Red 
   1.145      2  ColorRGBA/Green 
   1.146      3  ColorRGBA/Yellow 
   1.147      4  ColorRGBA/Orange 
   1.148 @@ -90,18 +145,6 @@
   1.149      7  ColorRGBA/Pink 
   1.150      8  ColorRGBA/White))
   1.151  
   1.152 -(defn normal-rays
   1.153 -  "returns rays"
   1.154 -  [limit #^Geometry geom]
   1.155 -  (vec
   1.156 -   (map 
   1.157 -    (fn [tri]
   1.158 -      (doto 
   1.159 -          (Ray. (get-ray-origin geom tri)
   1.160 -                (get-ray-direction geom tri))
   1.161 -        (.setLimit limit)))
   1.162 -    (triangles geom))))
   1.163 -
   1.164  (defn update-ray-debug [node ray contacts]
   1.165    (let [origin (.getChild node 0)]
   1.166      (.setLocalTranslation origin (.getOrigin ray))
   1.167 @@ -130,18 +173,7 @@
   1.168         (update-ray-debug
   1.169          (.getChild debug-node n) (nth rays n) (nth touch-data n))))))
   1.170  
   1.171 -(defn touch-percieve [limit geom node]
   1.172 -  (let [normals  (normal-rays limit geom)]
   1.173  
   1.174 -    (doall
   1.175 -     (for [ray normals]
   1.176 -       (do
   1.177 -         (let [results (CollisionResults.)]
   1.178 -           (.collideWith node ray results)
   1.179 -           (let [touch-objects (set (filter #(not (= geom %))
   1.180 -                                (map #(.getGeometry %) results)))]
   1.181 -               ;;(dorun (map #(println-repl (.getName %)) touch-objects))
   1.182 -             (count touch-objects))))))))
   1.183  
   1.184  (defn no-logging []
   1.185    (.setLevel (Logger/getLogger "com.jme3") Level/OFF))
   1.186 @@ -227,19 +259,15 @@
   1.187         (Thread/sleep 10)
   1.188         ))))
   1.189  
   1.190 +
   1.191  #+end_src
   1.192  
   1.193 -#+results: skin-main
   1.194 -: #'body.skin/test-skin
   1.195 -
   1.196 -
   1.197 -
   1.198  
   1.199  
   1.200  
   1.201    
   1.202  * COMMENT code generation
   1.203 -#+begin_src clojure :tangle ../src/body/skin.clj :noweb yes
   1.204 +#+begin_src clojure :tangle ../src/cortex/touch.clj :noweb yes
   1.205  <<skin-main>>
   1.206  #+end_src
   1.207