Package org.jbox2d.dynamics

Source Code of org.jbox2d.dynamics.Fixture

/*******************************************************************************
* Copyright (c) 2011, Daniel Murphy
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*     * Redistributions of source code must retain the above copyright
*       notice, this list of conditions and the following disclaimer.
*     * Redistributions in binary form must reproduce the above copyright
*       notice, this list of conditions and the following disclaimer in the
*       documentation and/or other materials provided with the distribution.
*     * Neither the name of the <organization> nor the
*       names of its contributors may be used to endorse or promote products
*       derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL DANIEL MURPHY BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
******************************************************************************/
package org.jbox2d.dynamics;

import org.jbox2d.collision.AABB;
import org.jbox2d.collision.RayCastInput;
import org.jbox2d.collision.RayCastOutput;
import org.jbox2d.collision.broadphase.BroadPhase;
import org.jbox2d.collision.broadphase.DynamicTreeNode;
import org.jbox2d.collision.shapes.MassData;
import org.jbox2d.collision.shapes.Shape;
import org.jbox2d.collision.shapes.ShapeType;
import org.jbox2d.common.Transform;
import org.jbox2d.common.Vec2;
import org.jbox2d.dynamics.contacts.Contact;
import org.jbox2d.dynamics.contacts.ContactEdge;

// updated to rev 100
// thread-safe pooling
/**
* A fixture is used to attach a shape to a body for collision detection. A fixture
* inherits its transform from its parent. Fixtures hold additional non-geometric data
* such as friction, collision filters, etc.
* Fixtures are created via b2Body::CreateFixture.
* @warning you cannot reuse fixtures.
*
* @author daniel
*/
public class Fixture {

  public final AABB m_aabb = new AABB();
 
  public float m_density;
 
  public Fixture m_next;
  public Body m_body;
 
  public Shape m_shape;
 
  public float m_friction;
  public float m_restitution;
 
  public DynamicTreeNode m_proxy;
  public final Filter m_filter;
 
  public boolean m_isSensor;
 
  public Object m_userData;
 
  public Fixture(){
    m_userData = null;
    m_body = null;
    m_next = null;
    m_proxy = null;
    m_shape = null;
    m_filter = new Filter();
  }
 
  /**
   * Get the type of the child shape. You can use this to down cast to the concrete shape.
   * @return the shape type.
   */
  public ShapeType getType(){
    return m_shape.getType();
  }
 
  /**
   * Get the child shape. You can modify the child shape, however you should not change the
   * number of vertices because this will crash some collision caching mechanisms.
   * @return
   */
  public Shape getShape(){
    return m_shape;
  }
  /**
   * Is this fixture a sensor (non-solid)?
   * @return the true if the shape is a sensor.
   * @return
   */
  public boolean isSensor(){
    return m_isSensor;
  }
 
  /**
   * Set if this fixture is a sensor.
   * @param sensor
   */
  public void setSensor(boolean sensor){
    m_isSensor = sensor;
  }
 
  /**
   * Set the contact filtering data. This is an expensive operation and should
   * not be called frequently. This will not update contacts until the next time
   * step when either parent body is awake.
   * @param filter
   */
  public void setFilterData(final Filter filter){
    m_filter.set(filter);
   
    if(m_body == null){
      return;
    }
   
    // Flag associated contacts for filtering.
    ContactEdge edge = m_body.getContactList();
    while (edge != null){
      Contact contact = edge.contact;
      Fixture fixtureA = contact.getFixtureA();
      Fixture fixtureB = contact.getFixtureB();
      if (fixtureA == this || fixtureB == this){
        contact.flagForFiltering();
      }
      edge = edge.next;
    }
  }
 
  /**
   * Get the contact filtering data.
   * @return
   */
  public Filter getFilterData(){
    return m_filter;
  }
 
  /**
   * Get the parent body of this fixture. This is NULL if the fixture is not attached.
   * @return the parent body.
   * @return
   */
  public Body getBody(){
    return m_body;
  }
 
  /**
   * Get the next fixture in the parent body's fixture list.
   * @return the next shape.
   * @return
   */
  public Fixture getNext(){
    return m_next;
  }
 
  public void setDensity(float density){
    assert(density >= 0f);
    m_density = density;
  }
 
  public float getDensity(){
    return m_density;
  }
 
  /**
   * Get the user data that was assigned in the fixture definition. Use this to
   * store your application specific data.
   * @return
   */
  public Object getUserData(){
    return m_userData;
  }

  /**
   * Set the user data. Use this to store your application specific data.
   * @param data
   */
  public void setUserData(Object data){
    m_userData = data;
  }
 
  /**
   * Test a point for containment in this fixture. This only works for convex shapes.
   * @param xf the shape world transform.
   * @param p a point in world coordinates.
   * @param p
   * @return
   */
  public boolean testPoint(final Vec2 p){
    return m_shape.testPoint( m_body.m_xf, p);
  }
 
  /**
   * Cast a ray against this shape.
   * @param output the ray-cast results.
   * @param input the ray-cast input parameters.
   * @param output
   * @param input
   */
  public boolean raycast(RayCastOutput output, RayCastInput input){
    return m_shape.raycast( output, input, m_body.m_xf);
  }

  /**
   * Get the mass data for this fixture. The mass data is based on the density and
   * the shape. The rotational inertia is about the shape's origin.
   * @return
   */
  public void getMassData(MassData massData){
    m_shape.computeMass(massData, m_density);
  }

  /**
   * Get the coefficient of friction.
   * @return
   */
  public float getFriction(){
    return m_friction;
  }

  /**
   * Set the coefficient of friction.
   * @param friction
   */
  public void setFriction(float friction){
    m_friction = friction;
  }

  /**
   * Get the coefficient of restitution.
   * @return
   */
  public float getRestitution(){
    return m_restitution;
  }

  /**
   * Set the coefficient of restitution.
   * @param restitution
   */
  public void setRestitution(float restitution){
    m_restitution = restitution;
  }
 
  /**
   * Get the fixture's AABB. This AABB may be enlarge and/or stale.
   * If you need a more accurate AABB, compute it using the shape and
   * the body transform.
   * @return
   */
  public AABB getAABB(){
    return m_aabb;
  }
 
 
  // We need separation create/destroy functions from the constructor/destructor because
  // the destructor cannot access the allocator (no destructor arguments allowed by C++).
 
  public void create(Body body, FixtureDef def){
    m_userData = def.userData;
    m_friction = def.friction;
    m_restitution = def.restitution;
   
    m_body = body;
    m_next = null;
   
    m_filter.set(def.filter);
   
    m_isSensor = def.isSensor;
   
    m_shape = def.shape.clone();
   
    m_density = def.density;
  }
 
  public void destroy(){
   
    // The proxy must be destroyed before calling this.
    assert(m_proxy == null);
   
    // Free the child shape.
    // yeah woo jvm
    // TODO djm should I pool this then?
    m_shape = null;
  }
 
  // These support body activation/deactivation.
  public void createProxy(BroadPhase broadPhase, final Transform xf){
    assert(m_proxy == null);
   
    // Create proxy in the broad-phase.
    m_shape.computeAABB( m_aabb, xf);
    m_proxy = broadPhase.createProxy( m_aabb, this);
  }
 
  /**
   * Internal method
   * @param broadPhase
   */
  public void destroyProxy(BroadPhase broadPhase){
    if(m_proxy == null){
      return;
    }
   
    broadPhase.destroyProxy( m_proxy);
    m_proxy = null;
  }
 
  private final AABB pool1 = new AABB();
  private final AABB pool2 = new AABB();
 
  /**
   * Internal method
   * @param broadPhase
   * @param xf1
   * @param xf2
   */
  protected void synchronize(BroadPhase broadPhase, final Transform transform1, final Transform transform2){
    if(m_proxy == null){
      return;
    }
   
    // Compute an AABB that covers the swept shape (may miss some rotation effect).
   
//    AABB aabb1 = tlaabb1.get();
//    AABB aabb2 = tlaabb2.get();
//   
//    m_shape.computeAABB( aabb1, transform1);
//    m_shape.computeAABB( aabb2, transform2);
//   
//    m_aabb.combine(aabb1, aabb2);
//   
//    Vec2 disp = tldisp.get();
//    disp.set( transform2.position).subLocal(transform1.position);
//   
//    broadPhase.moveProxy( m_proxy, m_aabb, disp);
   
    m_shape.computeAABB( pool1, transform1);
    m_shape.computeAABB( pool2, transform2);
    m_aabb.lowerBound.x = pool1.lowerBound.x < pool2.lowerBound.x ? pool1.lowerBound.x : pool2.lowerBound.x;
    m_aabb.lowerBound.y = pool1.lowerBound.y < pool2.lowerBound.y ? pool1.lowerBound.y : pool2.lowerBound.y;
    m_aabb.upperBound.x = pool1.upperBound.x > pool2.upperBound.x ? pool1.upperBound.x : pool2.upperBound.x;
    m_aabb.upperBound.y = pool1.upperBound.y > pool2.upperBound.y ? pool1.upperBound.y : pool2.upperBound.y;
   
    final Vec2 disp = pool1.lowerBound; // just use this vec for pooling
    disp.x = transform2.position.x - transform1.position.x;
    disp.y = transform2.position.y - transform1.position.y;
   
    broadPhase.moveProxy( m_proxy, m_aabb, disp);
  }
}
TOP

Related Classes of org.jbox2d.dynamics.Fixture

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.