< prev index next >

modules/graphics/src/main/java/javafx/scene/shape/Box.java

Print this page




  46  * The {@code Box} class defines a 3 dimensional box with the specified size.
  47  * A {@code Box} is a 3D geometry primitive created with a given depth, width,
  48  * and height. It is centered at the origin.
  49  *
  50  * @since JavaFX 8.0
  51  */
  52 public class Box extends Shape3D {
  53     static {
  54          // This is used by classes in different packages to get access to
  55          // private and package private methods.
  56         BoxHelper.setBoxAccessor(new BoxHelper.BoxAccessor() {
  57             @Override
  58             public NGNode doCreatePeer(Node node) {
  59                 return ((Box) node).doCreatePeer();
  60             }
  61 
  62             @Override
  63             public void doUpdatePeer(Node node) {
  64                 ((Box) node).doUpdatePeer();
  65             }

















  66         });
  67     }
  68 
  69     private TriangleMesh mesh;
  70 
  71     /**
  72      * Creates a new instance of {@code Box} of dimension 2 by 2 by 2.
  73      */
  74 
  75     public static final double DEFAULT_SIZE = 2;
  76 
  77     {
  78         // To initialize the class helper at the begining each constructor of this class
  79         BoxHelper.initHelper(this);
  80     }
  81 
  82     public Box() {
  83         this(DEFAULT_SIZE, DEFAULT_SIZE, DEFAULT_SIZE);
  84     }
  85 


  99      * @defaultValue 2.0
 100      */
 101     private DoubleProperty depth;
 102 
 103     public final void setDepth(double value) {
 104         depthProperty().set(value);
 105     }
 106 
 107     public final double getDepth() {
 108         return depth == null ? 2 : depth.get();
 109     }
 110 
 111     public final DoubleProperty depthProperty() {
 112         if (depth == null) {
 113             depth = new SimpleDoubleProperty(Box.this, "depth", DEFAULT_SIZE) {
 114                 @Override
 115                 public void invalidated() {
 116                     NodeHelper.markDirty(Box.this, DirtyBits.MESH_GEOM);
 117                     manager.invalidateBoxMesh(key);
 118                     key = 0;
 119                     impl_geomChanged();
 120                 }
 121             };
 122         }
 123         return depth;
 124     }
 125 
 126     /**
 127      * Defines the height or the Y dimension of the Box.
 128      *
 129      * @defaultValue 2.0
 130      */
 131     private DoubleProperty height;
 132 
 133     public final void setHeight(double value) {
 134         heightProperty().set(value);
 135     }
 136 
 137     public final double getHeight() {
 138         return height == null ? 2 : height.get();
 139     }
 140 
 141     public final DoubleProperty heightProperty() {
 142         if (height == null) {
 143             height = new SimpleDoubleProperty(Box.this, "height", DEFAULT_SIZE) {
 144                 @Override
 145                 public void invalidated() {
 146                     NodeHelper.markDirty(Box.this, DirtyBits.MESH_GEOM);
 147                     manager.invalidateBoxMesh(key);
 148                     key = 0;
 149                     impl_geomChanged();
 150                 }
 151             };
 152         }
 153         return height;
 154     }
 155 
 156     /**
 157      * Defines the width or the X dimension of the Box.
 158      *
 159      * @defaultValue 2.0
 160      */
 161     private DoubleProperty width;
 162 
 163     public final void setWidth(double value) {
 164         widthProperty().set(value);
 165     }
 166 
 167     public final double getWidth() {
 168         return width == null ? 2 : width.get();
 169     }
 170 
 171     public final DoubleProperty widthProperty() {
 172         if (width == null) {
 173             width = new SimpleDoubleProperty(Box.this, "width", DEFAULT_SIZE) {
 174                 @Override
 175                 public void invalidated() {
 176                     NodeHelper.markDirty(Box.this, DirtyBits.MESH_GEOM);
 177                     manager.invalidateBoxMesh(key);
 178                     key = 0;
 179                     impl_geomChanged();
 180                 }
 181             };
 182         }
 183         return width;
 184     }
 185 
 186     /*
 187      * Note: This method MUST only be called via its accessor method.
 188      */
 189     private NGNode doCreatePeer() {
 190         return new NGBox();
 191     }
 192 
 193     /*
 194      * Note: This method MUST only be called via its accessor method.
 195      */
 196     private void doUpdatePeer() {
 197         if (NodeHelper.isDirty(this, DirtyBits.MESH_GEOM)) {
 198             NGBox peer = NodeHelper.getPeer(this);
 199             final float w = (float) getWidth();
 200             final float h = (float) getHeight();
 201             final float d = (float) getDepth();
 202             if (w < 0 || h < 0 || d < 0) {
 203                 peer.updateMesh(null);
 204             } else {
 205                 if (key == 0) {
 206                     key = generateKey(w, h, d);
 207                 }
 208                 mesh = manager.getBoxMesh(w, h, d, key);
 209                 mesh.updatePG();
 210                 peer.updateMesh(mesh.getPGTriangleMesh());
 211             }
 212         }
 213     }
 214 
 215     /**
 216      * @treatAsPrivate implementation detail
 217      * @deprecated This is an internal API that is not intended for use and will be removed in the next version
 218      */
 219     @Deprecated
 220     @Override
 221     public BaseBounds impl_computeGeomBounds(BaseBounds bounds, BaseTransform tx) {
 222         final float w = (float) getWidth();
 223         final float h = (float) getHeight();
 224         final float d = (float) getDepth();
 225 
 226         if (w < 0 || h < 0 || d < 0) {
 227             return bounds.makeEmpty();
 228         }
 229 
 230         final float hw = w * 0.5f;
 231         final float hh = h * 0.5f;
 232         final float hd = d * 0.5f;
 233 
 234         bounds = bounds.deriveWithNewBounds(-hw, -hh, -hd, hw, hh, hd);
 235         bounds = tx.transform(bounds, bounds);
 236         return bounds;
 237     }
 238 
 239     /**
 240      * @treatAsPrivate implementation detail
 241      * @deprecated This is an internal API that is not intended for use and will be removed in the next version
 242      */
 243     @Deprecated
 244     @Override
 245     protected boolean impl_computeContains(double localX, double localY) {
 246         double w = getWidth();
 247         double h = getHeight();
 248         return -w <= localX && localX <= w &&
 249                 -h <= localY && localY <= h;
 250     }
 251 
 252     /**
 253      * @treatAsPrivate implementation detail
 254      * @deprecated This is an internal API that is not intended for use and will be removed in the next version
 255      */
 256     @Deprecated
 257     @Override
 258     protected boolean impl_computeIntersects(PickRay pickRay, PickResultChooser pickResult) {
 259 
 260         final double w = getWidth();
 261         final double h = getHeight();
 262         final double d = getDepth();
 263         final double hWidth = w / 2.0;
 264         final double hHeight = h / 2.0;
 265         final double hDepth = d / 2.0;
 266         final Vec3d dir = pickRay.getDirectionNoClone();
 267         final double invDirX = dir.x == 0.0 ? Double.POSITIVE_INFINITY : (1.0 / dir.x);
 268         final double invDirY = dir.y == 0.0 ? Double.POSITIVE_INFINITY : (1.0 / dir.y);
 269         final double invDirZ = dir.z == 0.0 ? Double.POSITIVE_INFINITY : (1.0 / dir.z);
 270         final Vec3d origin = pickRay.getOriginNoClone();
 271         final double originX = origin.x;
 272         final double originY = origin.y;
 273         final double originZ = origin.z;
 274         final boolean signX = invDirX < 0.0;
 275         final boolean signY = invDirY < 0.0;
 276         final boolean signZ = invDirZ < 0.0;
 277 
 278         double t0 = Double.NEGATIVE_INFINITY;




  46  * The {@code Box} class defines a 3 dimensional box with the specified size.
  47  * A {@code Box} is a 3D geometry primitive created with a given depth, width,
  48  * and height. It is centered at the origin.
  49  *
  50  * @since JavaFX 8.0
  51  */
  52 public class Box extends Shape3D {
  53     static {
  54          // This is used by classes in different packages to get access to
  55          // private and package private methods.
  56         BoxHelper.setBoxAccessor(new BoxHelper.BoxAccessor() {
  57             @Override
  58             public NGNode doCreatePeer(Node node) {
  59                 return ((Box) node).doCreatePeer();
  60             }
  61 
  62             @Override
  63             public void doUpdatePeer(Node node) {
  64                 ((Box) node).doUpdatePeer();
  65             }
  66 
  67             @Override
  68             public BaseBounds doComputeGeomBounds(Node node,
  69             BaseBounds bounds, BaseTransform tx) {
  70                 return ((Box) node).doComputeGeomBounds(bounds, tx);
  71             }
  72 
  73             @Override
  74             public boolean doComputeContains(Node node, double localX, double localY) {
  75                 return ((Box) node).doComputeContains(localX, localY);
  76             }
  77 
  78             @Override
  79             public boolean doComputeIntersects(Node node, PickRay pickRay,
  80             PickResultChooser pickResult) {
  81                 return ((Box) node).doComputeIntersects(pickRay, pickResult);
  82             }
  83         });
  84     }
  85 
  86     private TriangleMesh mesh;
  87 
  88     /**
  89      * Creates a new instance of {@code Box} of dimension 2 by 2 by 2.
  90      */
  91 
  92     public static final double DEFAULT_SIZE = 2;
  93 
  94     {
  95         // To initialize the class helper at the begining each constructor of this class
  96         BoxHelper.initHelper(this);
  97     }
  98 
  99     public Box() {
 100         this(DEFAULT_SIZE, DEFAULT_SIZE, DEFAULT_SIZE);
 101     }
 102 


 116      * @defaultValue 2.0
 117      */
 118     private DoubleProperty depth;
 119 
 120     public final void setDepth(double value) {
 121         depthProperty().set(value);
 122     }
 123 
 124     public final double getDepth() {
 125         return depth == null ? 2 : depth.get();
 126     }
 127 
 128     public final DoubleProperty depthProperty() {
 129         if (depth == null) {
 130             depth = new SimpleDoubleProperty(Box.this, "depth", DEFAULT_SIZE) {
 131                 @Override
 132                 public void invalidated() {
 133                     NodeHelper.markDirty(Box.this, DirtyBits.MESH_GEOM);
 134                     manager.invalidateBoxMesh(key);
 135                     key = 0;
 136                     NodeHelper.geomChanged(Box.this);
 137                 }
 138             };
 139         }
 140         return depth;
 141     }
 142 
 143     /**
 144      * Defines the height or the Y dimension of the Box.
 145      *
 146      * @defaultValue 2.0
 147      */
 148     private DoubleProperty height;
 149 
 150     public final void setHeight(double value) {
 151         heightProperty().set(value);
 152     }
 153 
 154     public final double getHeight() {
 155         return height == null ? 2 : height.get();
 156     }
 157 
 158     public final DoubleProperty heightProperty() {
 159         if (height == null) {
 160             height = new SimpleDoubleProperty(Box.this, "height", DEFAULT_SIZE) {
 161                 @Override
 162                 public void invalidated() {
 163                     NodeHelper.markDirty(Box.this, DirtyBits.MESH_GEOM);
 164                     manager.invalidateBoxMesh(key);
 165                     key = 0;
 166                     NodeHelper.geomChanged(Box.this);
 167                 }
 168             };
 169         }
 170         return height;
 171     }
 172 
 173     /**
 174      * Defines the width or the X dimension of the Box.
 175      *
 176      * @defaultValue 2.0
 177      */
 178     private DoubleProperty width;
 179 
 180     public final void setWidth(double value) {
 181         widthProperty().set(value);
 182     }
 183 
 184     public final double getWidth() {
 185         return width == null ? 2 : width.get();
 186     }
 187 
 188     public final DoubleProperty widthProperty() {
 189         if (width == null) {
 190             width = new SimpleDoubleProperty(Box.this, "width", DEFAULT_SIZE) {
 191                 @Override
 192                 public void invalidated() {
 193                     NodeHelper.markDirty(Box.this, DirtyBits.MESH_GEOM);
 194                     manager.invalidateBoxMesh(key);
 195                     key = 0;
 196                     NodeHelper.geomChanged(Box.this);
 197                 }
 198             };
 199         }
 200         return width;
 201     }
 202 
 203     /*
 204      * Note: This method MUST only be called via its accessor method.
 205      */
 206     private NGNode doCreatePeer() {
 207         return new NGBox();
 208     }
 209 
 210     /*
 211      * Note: This method MUST only be called via its accessor method.
 212      */
 213     private void doUpdatePeer() {
 214         if (NodeHelper.isDirty(this, DirtyBits.MESH_GEOM)) {
 215             NGBox peer = NodeHelper.getPeer(this);
 216             final float w = (float) getWidth();
 217             final float h = (float) getHeight();
 218             final float d = (float) getDepth();
 219             if (w < 0 || h < 0 || d < 0) {
 220                 peer.updateMesh(null);
 221             } else {
 222                 if (key == 0) {
 223                     key = generateKey(w, h, d);
 224                 }
 225                 mesh = manager.getBoxMesh(w, h, d, key);
 226                 mesh.updatePG();
 227                 peer.updateMesh(mesh.getPGTriangleMesh());
 228             }
 229         }
 230     }
 231 
 232     /*
 233      * Note: This method MUST only be called via its accessor method.

 234      */
 235     private BaseBounds doComputeGeomBounds(BaseBounds bounds, BaseTransform tx) {


 236         final float w = (float) getWidth();
 237         final float h = (float) getHeight();
 238         final float d = (float) getDepth();
 239 
 240         if (w < 0 || h < 0 || d < 0) {
 241             return bounds.makeEmpty();
 242         }
 243 
 244         final float hw = w * 0.5f;
 245         final float hh = h * 0.5f;
 246         final float hd = d * 0.5f;
 247 
 248         bounds = bounds.deriveWithNewBounds(-hw, -hh, -hd, hw, hh, hd);
 249         bounds = tx.transform(bounds, bounds);
 250         return bounds;
 251     }
 252 
 253     /*
 254      * Note: This method MUST only be called via its accessor method.

 255      */
 256     private boolean doComputeContains(double localX, double localY) {


 257         double w = getWidth();
 258         double h = getHeight();
 259         return -w <= localX && localX <= w &&
 260                 -h <= localY && localY <= h;
 261     }
 262 
 263     /*
 264      * Note: This method MUST only be called via its accessor method.

 265      */
 266     private boolean doComputeIntersects(PickRay pickRay, PickResultChooser pickResult) {


 267 
 268         final double w = getWidth();
 269         final double h = getHeight();
 270         final double d = getDepth();
 271         final double hWidth = w / 2.0;
 272         final double hHeight = h / 2.0;
 273         final double hDepth = d / 2.0;
 274         final Vec3d dir = pickRay.getDirectionNoClone();
 275         final double invDirX = dir.x == 0.0 ? Double.POSITIVE_INFINITY : (1.0 / dir.x);
 276         final double invDirY = dir.y == 0.0 ? Double.POSITIVE_INFINITY : (1.0 / dir.y);
 277         final double invDirZ = dir.z == 0.0 ? Double.POSITIVE_INFINITY : (1.0 / dir.z);
 278         final Vec3d origin = pickRay.getOriginNoClone();
 279         final double originX = origin.x;
 280         final double originY = origin.y;
 281         final double originZ = origin.z;
 282         final boolean signX = invDirX < 0.0;
 283         final boolean signY = invDirY < 0.0;
 284         final boolean signZ = invDirZ < 0.0;
 285 
 286         double t0 = Double.NEGATIVE_INFINITY;


< prev index next >