PolygonDomain.java :  » Java-2D » j2dparticles » com » j2dparticles » domains » Java Open Source

Java Open Source » Java 2D » j2dparticles 
j2dparticles » com » j2dparticles » domains » PolygonDomain.java
package com.j2dparticles.domains;

import com.j2dparticles.data.Particle;
import com.j2dparticles.data.Position;
import com.j2dparticles.data.Velocity;
import java.awt.Point;
import java.awt.Polygon;
import java.util.ArrayList;
import java.util.List;

/**
 * PolygonDomain
 *
 * @author  Michael Janner Marques
 * @version 0.1, 06/09/2010
 */
public class PolygonDomain implements Domain
{
    private Polygon polygon = new Polygon();
    
    private Segment[] segments;

    /**
     * PolygonDomain
     *
     * @param polygon Polygon
     */
    public PolygonDomain( Polygon polygon )
    {
        this.polygon = polygon;

        segments = new Segment[polygon.npoints];

        int[] xs = polygon.xpoints;
        int[] ys = polygon.ypoints;

        for ( int i = 0; i < polygon.npoints - 1; i++ )
        {
            segments[i] = new Segment( xs[i],   ys[i],
                                       xs[i+1], ys[i+1] );
        }

        segments[polygon.npoints-1] = new Segment( xs[polygon.npoints-1],   ys[polygon.npoints-1],
                                                   xs[0], ys[0] );
    }
    
    /**
     * contains
     *
     * @param x int
     * @param y int
     * @return boolean
     */
    @Override
    public boolean contains( int x, int y )
    {
        return polygon.contains( x, y );
    }

    /**
     * createParticles
     *
     * @param rate int
     * @return List<Particle>
     */
    @Override
    public List<Particle> createParticles( int rate )
    {
        List<Particle> list = new ArrayList<Particle>();

        for ( int i = 0; i < rate; i++ )
        {
            Particle p = new Particle();

            Point point = getValidPoint();

            p.setCurrentPosition( new Position( point.getX(), point.getY() ) );
            p.setPreviousPosition( new Position( point.getX(), point.getY() ) );

            list.add( p );
        }

        return list;
    }

    /**
     * getValidPoint
     *
     * @return Point
     */
    private Point getValidPoint()
    {
        Point point = new Point( (int) (polygon.getBounds().x + polygon.getBounds().width * Math.random()),
                                 (int) (polygon.getBounds().y + polygon.getBounds().height * Math.random()) );

        while ( !polygon.contains( point ) )
        {
            point = new Point( (int) (polygon.getBounds().x + polygon.getBounds().width * Math.random()),
                               (int) (polygon.getBounds().y + polygon.getBounds().height * Math.random()) );
        }

        return point;
    }

    /**
     * bounce
     *
     * @param p Particle
     * @param resilience float
     */
    @Override
    public void bounce( Particle p, float resilience )
    {
         for ( int i = 0; i < segments.length; i++ )
         {
            checkCollision( segments[i], p, resilience );
         }
    }

    /**
     * checkCollision
     *
     * @param segment Segment
     * @param p Particle
     * @param resilience float
     */
    private void checkCollision( Segment segment, Particle p, float resilience )
    {
        // Get difference between orb and ground
        double deltaX = p.getCurrentPosition().x - segment.x;
        double deltaY = p.getCurrentPosition().y - segment.y;

        // Precalculate trig values
        double cosine = Math.cos( segment.rot );
        double sine = Math.sin( segment.rot );

        /* Rotate ground and velocity to allow
        orthogonal collision calculations */
        double groundXTemp = cosine * deltaX + sine * deltaY;
        double groundYTemp = cosine * deltaY - sine * deltaX;
        double velocityXTemp = cosine * p.getCurrentVelocity().dx + sine * p.getCurrentVelocity().dy;
        double velocityYTemp = cosine * p.getCurrentVelocity().dy - sine * p.getCurrentVelocity().dx;

        /* Ground collision - check for surface
        collision and also that orb is within
        left/rights bounds of ground segment */
        if ( groundYTemp > -p.getSize()
                && p.getCurrentPosition().x > segment.x1
                && p.getCurrentPosition().x < segment.x2 )
        {
            // keep orb from going into ground
            groundYTemp = -p.getSize();
            // bounce and slow down orb
            velocityYTemp *= -1.0;
            velocityYTemp *= resilience;
        }

        // Reset ground, velocity and orb
        deltaX = cosine * groundXTemp - sine * groundYTemp;
        deltaY = cosine * groundYTemp + sine * groundXTemp;

        p.setCurrentVelocity( new Velocity( cosine * velocityXTemp - sine * velocityYTemp,
                                            cosine * velocityYTemp + sine * velocityXTemp ) );
    }

    /**
     * Segment
     *
     * @return class
     */
    public class Segment
    {
        float x1, y1, x2, y2;
        float x, y, len, rot;

        /**
         * Segment
         *
         */
        Segment()
        {
        }

        /**
         * Segment
         *
         * @param x1 float
         * @param y1 float
         * @param x2 float
         * @param y2 float
         */
        Segment( float x1, float y1, float x2, float y2 )
        {
            this.x1 = x1;
            this.y1 = y1;
            this.x2 = x2;
            this.y2 = y2;
            x = (x1 + x2) / 2;
            y = (y1 + y2) / 2;

            len = (float) Point.distance( x1, y1, x2, y2 );
            rot = (float) Math.atan2( (y2 - y1), (x2 - x1) );
        }
    }
}
java2s.com  | Contact Us | Privacy Policy
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.