package příklady;

import rup.česky.společně.P;
import rup.česky.tvary.Barva;
import rup.česky.tvary.Kreslítko;
import rup.česky.tvary.Kruh;


/*******************************************************************************
 * Třída Balón_12a simuluje pružný padající balón, který padá zrychleně dolů
 * a po dopadu se odrazí zmenšenou rychlostí, takže o nějaké době doskáče.
 *
 * @author    Rudolf Pecinovský
 * @version   0.00.000,  0.0.2003
 */
public final class Balón_13 extends Kruh implements IAnimovaný
{
//== KONSTANTNÍ ATRIBUTY TŘÍDY =================================================

    /** Změna rychlosti za jeden snímek. */
    private static final int IMPLICITNÍ_VELIKOST = 20;

    /** Změna rychlosti za jeden snímek. */
    private static final Barva IMPLICITNÍ_BARVA = Barva.ČERVENÁ;

    private static final Animátor ANIMÁTOR = Animátor.getInstance();

    /** Gravitační zrychlení. **/
    private static final double GRAVITAČNÍ_ZRYCHLENÍ  = 400;

    /** Změna rychlosti za jeden snímek. */
    private static final double ÚTLUM = 0.85;

    /** Změna rychlosti za jeden snímek. */
    private static final double MINIMÁLNÍ_RYCHLOST = 50;



//== PROMĚNNÉ ATRIBUTY TŘÍDY ===================================================
//== KONSTANTNÍ ATRIBUTY INSTANCÍ ==============================================

    private final double konečné_y = AP.getBVýška() - getVýška();


//== PROMĚNNÉ ATRIBUTY INSTANCÍ ================================================

    private double rychlost;
    private double y;



//== PŘÍSTUPOVÉ METODY VLASTNOSTÍ TŘÍDY ========================================
//== OSTATNÍ METODY TŘÍDY ======================================================

//##############################################################################
//== KONSTRUKTORY A TOVÁRNÍ METODY =============================================

    /***************************************************************************
     * Implicitní konstruktor vytvoří v levém horním rohu aktivního plátna
     * balón o průměru 25 a nechá jej spadnout.
     */
    public Balón_13()
    {
        this( 0, 0, IMPLICITNÍ_VELIKOST, IMPLICITNÍ_BARVA );
    }


    /***************************************************************************
     * Vytvoří nový balón na zadané pozici a o zadaném průměru
     * a nechá jej spadnout.
     */
    public Balón_13(int x, int y, int průměr, Barva barva)
    {
        super( x, y, průměr, barva );
        AP.přidej( this );
        spadni();
    }



//== PŘÍSTUPOVÉ METODY VLASTNOSTÍ INSTANCÍ =====================================
//== PŘEKRYTÉ METODY IMPLEMENTOVANÝCH ROZHRANÍ =================================

    public void nakresli( rup.česky.tvary.Kreslítko kr )
    {
        super.nakresli(kr);
    }

    /***************************************************************************
     * Simuluje poskakování balónu v gravitačním poli.
     * Balón se po dopadu odrazí po dopadu se odrazí zmenšenou rychlostí,
     * takže o nějaké době doskáče.
     */
    public boolean popojeď()
    {
        if( y < konečné_y )
        {
            rychlost += GRAVITAČNÍ_ZRYCHLENÍ * ANIMÁTOR.getUplynulo() /1000;
            y += rychlost * ANIMÁTOR.getUplynulo() /1000;
        }
        else
        {
            y = konečné_y - 1;
            rychlost = -rychlost * ÚTLUM;
            if( -rychlost < MINIMÁLNÍ_RYCHLOST )
            {
                return true;
            }
        }
        //Rodičovská verze setPozice vyžaduje celočíselné parametry -
        // aktuální svislou souřadnici proto musíme přetypovat
        setPozice( xPos, (int)y );
        return false;
    }


//== PŘEKRYTÉ ABSTRAKTNÍ METODY RODIČOVSKÉ TŘÍDY ===============================
//== PŘEKRYTÉ KONKRÉTNÍ METODY RODIČOVSKÉ TŘÍDY ================================
//== NOVĚ ZAVEDENÉ METODY INSTANCÍ =============================================

    /***************************************************************************
     * Přesune balón do zadané pozice a nechá jej odtud spadnout.
     */
    public void přesuňNa( int x, int y )
    {
        setPozice( x, y );  //Nastavení pozice můžeš svěřit rodiči
        spadni();           //Začni padat
    }


    /***************************************************************************
     * Simuluje poskakování balónu v gravitačním poli.
     * Balón se po dopadu odrazí po dopadu se odrazí zmenšenou rychlostí,
     * takže o nějaké době doskáče.
     */
    private void spadni()
    {
        this.y = y;
        this.rychlost = 0;
        ANIMÁTOR.start();
        ANIMÁTOR.přidej( this );
    }



//== SOUKROMÉ A POMOCNÉ METODY TŘÍDY ===========================================
//== SOUKROMÉ A POMOCNÉ METODY INSTANCÍ ========================================
//== VNOŘENÉ A VNITŘNÍ TŘÍDY ===================================================
//== TESTY A METODA MAIN =======================================================

    /***************************************************************************
     * Test vytvoří implicitní balón a nechá jej spadnout.
     * Pak vytvoří druhý balón a po jeho dopadu přesune první do nové pozice
     * a opět jej odtud nechá spadnout.
     */
    public static void test()
    {
        AP.odstraňVše();
        //Velikost aktivního plátna ne nastavena na obrazovku 1024×768
        AP.setKrokRozměr( 50, 3 , 15 );
        AP.setMřížka( true );

        Balón_13 b1 = new Balón_13();
        P.čekej( 1000 );
        Balón_13 b2 = new Balón_13( 50, 50, 100, Barva.ZELENÁ );
        P.čekej( 1000 );
        Balón_13 b3 = new Balón_13( 100, 100, 50, Barva.MODRÁ );
    }


}

