package doprava;

import rup.česky.společně.P;

import rup.česky.tvary.Barva;
import rup.česky.tvary.AktivníPlátno;
import rup.česky.tvary.Elipsa;
import rup.česky.tvary.IPosuvný;
import rup.česky.tvary.IMultiposuvný;
import rup.česky.tvary.Kreslítko;
import rup.česky.tvary.Multipřesouvač;
import rup.česky.tvary.Pozice;
import rup.česky.tvary.Text;


/*******************************************************************************
 * Instance třídy Kabina_9a představují kabiny pohybující se po linkách.
 *
 * Oproti třídě Kabina_7a se v ní změnily pouze přístupová práva atributů,
 * která jsou nyní nastavená na protected
 *
 * @author  Rudolf Pecinovský
 * @version 1.00,  29.02.2004
 */
public class Kabina_9a implements IMultiposuvný
{
//== KONSTANTNÍ ATRIBUTY TŘÍDY =================================================
    
    protected static final Barva BARVA   = Barva.ČERNÁ;
    protected static final Barva BARVAX  = Barva.ŽLUTÁ;
    protected static final int   PRŮMĚR  = 20;            
    protected static final int   POLOMĚR = PRŮMĚR / 2;
    protected static final int   XPOSUN  = 6;             
    
    protected static final AktivníPlátno  AP = AktivníPlátno.getPlátno();
    protected static final Multipřesouvač mp = Multipřesouvač.getInstance();
    
    
//== PROMĚNNÉ ATRIBUTY TŘÍDY ===================================================

    /** Počet dosud vytvořených instancí. */
    protected static int počet = 0;


//== KONSTANTNÍ ATRIBUTY INSTANCÍ ==============================================

    /** Pořadí vytvoření dané instance v rámci třídy. */
    protected final int pořadí = ++počet;
    
    /** Linka, po níž se kabina pohybuje - 
     *  od ní si při žádosti o přesun zjišťuje svoji rychlost
     *  a v zastávkách pak dobu čekání. */
    protected final Linka linka;
     
    /** Obrazec, který představuje kabinu. 
     *  Obecně to může být libovolný posuvný obrazec */
    protected final IPosuvný kabina;
    
    protected final Text text;
    


//== PROMĚNNÉ ATRIBUTY INSTANCÍ ================================================
    
    /** Zastávka, na kterou se kabina přesouvá. Až tam dojede, zjistí si od ní,
     *  kdo je její následník a ke k tomu se pak přesune. */
    protected IZastávka další;
    
    
//== PŘÍSTUPOVÉ METODY VLASTNOSTÍ TŘÍDY ========================================
//== OSTATNÍ METODY TŘÍDY ======================================================

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

    /***************************************************************************
     * Vytvoří kruhovou kabinu, která se bude pohybovat zadanou rychlostí
     * po zadané lince.
     * 
     * @param linka    Linka, po které se kabina pohybuje.
     */
    public Kabina_9a(Linka linka)
    {
        this.linka = linka;
        
        //Souřadnice ještě neznáme => vytvoříme kruh např. v počátku
        kabina = new Elipsa( 0, 0, PRŮMĚR, PRŮMĚR, BARVA );
        text   = new Text( ""+pořadí, 0, 0, BARVAX );
        
        //Kruh umístíme na souřadnice první zastávky linky
        další = linka.getPrvní();
        Pozice pozice = další.getPozice();
        setPozice( pozice.x, pozice.y );
        
        //Když je kabina umístěna, můžeme ji zobrazit
        //(i když bychom to mohli nechat na multipřesouvači)
        AktivníPlátno.getPlátno().přidej( this );

        //Necháme kabinu přesunout na další zastávku
        přesunuto();
    }



//== PŘÍSTUPOVÉ METODY VLASTNOSTÍ INSTANCÍ =====================================

    /***************************************************************************
     * Vrátí x-ovou souřadnici pozice instance.
     *
     * @return  x-ová souřadnice.
     */
    public int getX()
    {
        return kabina.getX() + POLOMĚR;
    }


    /***************************************************************************
     * Vrátí y-ovou souřadnici pozice instance.
     *
     * @return  y-ová souřadnice.
     */
    public int getY()
    {
        return kabina.getY() + POLOMĚR;
    }


    /***************************************************************************
     * Vrátí instanci třídy Pozice s pozicí instance.
     *
     * @return   Pozice s pozicí instance.
     */
    public Pozice getPozice()
    {
        return new Pozice( getX(), getY() );
    }


    /***************************************************************************
     * Nastaví novou pozici instance.
     *
     * @param x   Nová x-ová pozice instance
     * @param y   Nová y-ová pozice instance
     */
    public void setPozice( int x, int y )
    {
        AP.nekresli();
            kabina.setPozice( x-POLOMĚR,   y-POLOMĚR   );
            text.setPozice  ( x-POLOMĚR/2, y-POLOMĚR/2 );
        AP.vraťKresli();
    }
    
    

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

    /***************************************************************************
     * Za pomoci dodaného kreslítka vykreslí obraz své instance
     * na animační plátno.
     *  
     * @param kreslítko   Kreslítko, kterým se instance nakreslí na plátno.     
     */
    public void nakresli( Kreslítko kreslítko )
    {
        kabina.nakresli( kreslítko );
        text.  nakresli( kreslítko );
    }


    /***************************************************************************
     * Metoda vyžadovaná rozhraním IMultiposuvný: definuje akci, 
     * která se má provést v okamžiku, 
     * kdy je objekt doveden do požadované cílové pozicie.
     * 
     * @param mp   Multipřesouvač, který kabinku dovedl do cíle.
     *             Ten bude pravděpodobně požádán, aby kabinku dovezl zase dál
     *             a v případě doražení do cílové stanice
     */
    public void přesunuto()
    {
        //Zastávka, kam jsme dorazili, musí znát svého následovníka
        další = další.getNásledující();
        
        P.čekej( linka.getČekání() );
        
        //Necháme kabinu přesunout na další zastávku
        Multipřesouvač mp = Multipřesouvač.getInstance();
        mp.přesuň( this,  další.getPozice(),  linka.getRychlost() );
    }



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

    /***************************************************************************
     * Převede instanci na řetězec. Používá se především při ladění.
     *
     * @return Řetězcová reprezentace dané instance.
     */
    public String toString()
    {
        return P.názevTřídy( this ) + "_" + pořadí;
    }



//== NOVĚ ZAVEDENÉ METODY INSTANCÍ =============================================
    
    /***************************************************************************
     * 
     */
    public void skonči()
    {
        mp.zastav( this );
        AP.odstraň( this );
    }
    
    
    
//== SOUKROMÉ A POMOCNÉ METODY TŘÍDY ===========================================
//== SOUKROMÉ A POMOCNÉ METODY INSTANCÍ ========================================
//== VNOŘENÉ A VNITŘNÍ TŘÍDY ===================================================
//== TESTY A METODA MAIN =======================================================
}

