1 /* 2 * Copyright (c) 2009-2010 jMonkeyEngine 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are 7 * met: 8 * 9 * * Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 12 * * Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 16 * * Neither the name of 'jMonkeyEngine' nor the names of its contributors 17 * may be used to endorse or promote products derived from this software 18 * without specific prior written permission. 19 * 20 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 21 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 22 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 23 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 24 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 25 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 26 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 27 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 28 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 29 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 30 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 31 */ 32 package com.jme3.light; 33 34 import com.jme3.bounding.BoundingVolume; 35 import com.jme3.export.InputCapsule; 36 import com.jme3.export.JmeExporter; 37 import com.jme3.export.JmeImporter; 38 import com.jme3.export.OutputCapsule; 39 import com.jme3.math.Vector3f; 40 import com.jme3.scene.Spatial; 41 import java.io.IOException; 42 43 /** 44 * Represents a point light. 45 * A point light emits light from a given position into all directions in space. 46 * E.g a lamp or a bright effect. Point light positions are in world space. 47 * <p> 48 * In addition to a position, point lights also have a radius which 49 * can be used to attenuate the influence of the light depending on the 50 * distance between the light and the effected object. 51 * 52 */ 53 public class PointLight extends Light { 54 55 protected Vector3f position = new Vector3f(); 56 protected float radius = 0; 57 protected float invRadius = 0; 58 59 @Override computeLastDistance(Spatial owner)60 public void computeLastDistance(Spatial owner) { 61 if (owner.getWorldBound() != null) { 62 BoundingVolume bv = owner.getWorldBound(); 63 lastDistance = bv.distanceSquaredTo(position); 64 } else { 65 lastDistance = owner.getWorldTranslation().distanceSquared(position); 66 } 67 } 68 69 /** 70 * Returns the world space position of the light. 71 * 72 * @return the world space position of the light. 73 * 74 * @see PointLight#setPosition(com.jme3.math.Vector3f) 75 */ getPosition()76 public Vector3f getPosition() { 77 return position; 78 } 79 80 /** 81 * Set the world space position of the light. 82 * 83 * @param position the world space position of the light. 84 */ setPosition(Vector3f position)85 public void setPosition(Vector3f position) { 86 this.position.set(position); 87 } 88 89 /** 90 * Returns the radius of the light influence. A radius of 0 means 91 * the light has no attenuation. 92 * 93 * @return the radius of the light 94 */ getRadius()95 public float getRadius() { 96 return radius; 97 } 98 99 /** 100 * Set the radius of the light influence. 101 * <p> 102 * Setting a non-zero radius indicates the light should use attenuation. 103 * If a pixel's distance to this light's position 104 * is greater than the light's radius, then the pixel will not be 105 * effected by this light, if the distance is less than the radius, then 106 * the magnitude of the influence is equal to distance / radius. 107 * 108 * @param radius the radius of the light influence. 109 * 110 * @throws IllegalArgumentException If radius is negative 111 */ setRadius(float radius)112 public void setRadius(float radius) { 113 if (radius < 0) { 114 throw new IllegalArgumentException("Light radius cannot be negative"); 115 } 116 this.radius = radius; 117 if(radius!=0){ 118 this.invRadius = 1 / radius; 119 }else{ 120 this.invRadius = 0; 121 } 122 } 123 124 /** 125 * for internal use only 126 * @return the inverse of the radius 127 */ getInvRadius()128 public float getInvRadius() { 129 return invRadius; 130 } 131 132 @Override getType()133 public Light.Type getType() { 134 return Light.Type.Point; 135 } 136 137 @Override write(JmeExporter ex)138 public void write(JmeExporter ex) throws IOException { 139 super.write(ex); 140 OutputCapsule oc = ex.getCapsule(this); 141 oc.write(position, "position", null); 142 oc.write(radius, "radius", 0f); 143 } 144 145 @Override read(JmeImporter im)146 public void read(JmeImporter im) throws IOException { 147 super.read(im); 148 InputCapsule ic = im.getCapsule(this); 149 position = (Vector3f) ic.readSavable("position", null); 150 radius = ic.readFloat("radius", 0f); 151 if(radius!=0){ 152 this.invRadius = 1 / radius; 153 }else{ 154 this.invRadius = 0; 155 } 156 } 157 } 158