Mostenirea este unul din cele mai utile instrumente ale Programarii Orientate pe Obiect - OOP.
Prin mostenire se intelege transmiterea proprietatilor, constanttelor si a functiilor de la o clasa la alta, intr-o structura ierarhica. Prima clasa este clasa de baza, denumita "parinte", legata de aceasta se poate crea o sub-clasa, denumita "copil"; sub-clasa 'copil' mosteneste proprietatile si metodele clasei 'parinte', le poate folosi in instructiunile din propriul cod si le transmite cand se creaza o instanta de obiect la ea. Precum in natura copii mostenesc genele parintilor.
Iata cum se aplica acest procedeu in programarea ActionScript 3. Vom folosi urmatoarea clasa de baza, "Mover", prin care se pot misca obiecte in prezentarea Flash. Obiectul care trebuie miscat si viteza de miscare pe axa X/Y sunt transferati ca argumente la crearea instantei clasei (explicatii gasiti in cod).

// Se creaza package simplu (fara nume)
package {
  // Importare clase predefinite ActionSscript 3 folosite in aceasta
  import flash.events.Event;
  import flash.display.MovieClip;

  // Start definire clasa Mover
  public class Mover
  {
    // Setare proprietati
    // 'insMC' - pt. instanta MovieCpli, 'xVel' - pt. viteza pe orizontala, 'yVel' - pt. viteza pe verticala
    public var insMC:MovieClip;
    public var xVel:Number;
    public var yVel:Number;

    // Creare metoda constructor, preia ca argumente o instanta si 2 valoari numerice
    function Mover(inMC:MovieClip, xV:Number, yV:Number)
    {
      // Atribuie proprietatilor clasei valorie din parametri
      this.insMC = inMC;
      this.xVel = xV;
      this.yVel = yV;
    }

    // Creare metoda cu atribut "protected" (poate fi utilizata doar in aceasta clasa si sub-clasele ei)
    protected function updatePosition(evtObj:Event):void
    {
      // Incrementeaza distanta 'x' si 'y' a lui "insMC" cu valoarea proprietatilor "xVel" si "yVel"
      this.insMC.x += this.xVel;
      this.insMC.y += this.yVel;
    }

    // Definire metoda publica pt. start miscare
    public function startMove():void
    {
      // Aplica detectare Eveniment ENTER_FRAME la 'insMC'
      // si apeleaza metoda protejata, updatePosition
      this.insMC.addEventListener(Event.ENTER_FRAME, this.updatePosition);
    }

    // Definire metoda publica pt. stop miscare
    public function stopMove():void
    {
      // Sterge detectarea evenimentului setat in "startMove()"
      insMC.removeEventListener(Event.ENTER_FRAME, this.updatePosition);
    }
  }
}
- Ca sa testati aceasta clasa, efectuati urmatorii pasi:
1. Deschideti de la File -> New un document nou "ActionScript 3.0 Class". In fereastra pentru numele clasei, ce apare la deschidere, scrieti Mover. Stergeti codul care apare initial in document si copiati-l pe cel de sus, apoi salvati-l cu numele "Mover.as".
2. Deschideti si un document Flash nou, desenati in Scena o figura geometrica sau orice desen doriti si transformati-l in Movie Clip (de la Modify - Convert to Symbol, asigurati-va ca punctul bifat de la Registration e cel din mijloc, acesta seteaza locatia centrului de coordonate a lui). Dati instantei din Scena (desenului transformat in MovieClip) un nume, aici e folosit "sfer" (in panoul Properties, in casuta de sus, unde e scris "<Insance Name>")
3. Dati click-dreapta pe Cadru 1 din Timeline, alegeti Actions si in panoul pt. script ActionScript adaugati urmatorul cod:
// Creare instanta la clasa Mover
var obj:Mover = new Mover(sfer, 2, 3);
obj.startMove();         // Apelare metoda "startMove()"

// Apeleaza metoda "stopMove" dupa 3 secunde (3000 milisecunde)
// "stopMove" sterge inregistrarea evenimentului ENTER_FRAME, fapt ce opreste miscarea
setTimeout(obj.stopMove, 3000);
  - "setTimeout()" apeleaza o functie /metoda dupa un anumit timp (dat in milisecunde).
4. Salvati documentul in acelasi director unde e salvat si "Mover.as", apoi apasati Ctr+Enter. Va apare ceva similar cu prezentarea urmatoare (click pe imagine).
as3_oop_clase_obiecte_mostenire0
- Aceasta clasa misca obiectul in aceeasi directie pana iese din Scena (sau pana se da o comanda de oprire cu "stopMove()"), dar poate dorim ca unele obiecte sa se miste continuu in cadrul scenei, ricosand din marginile ei. Pentru aceasta, in loc de a crea de la inceput o alta clasa sau de a modifica /strica pe aceasta, definim o sub-clasa copil legata de ea, care va mosteni proprietatile si metodele de miscare. In clasa copil trebuie doar inclusa (importata) clasa parinte si scrise instructiunile noi pt. schimbarea directiei de miscare cand obiecul ajunge in margini.

• Pentru a crea o sub-clasa 'copil' legata de una 'parinte', se foloseste cuvantul extends cu urmatoarea sintaxa: - Cand intr-o clasa trebuie apelate proprietati si /sau metode din alta clasa, aceasta trebuie inclusa (importata) cu instructiunea import.

Iata cum se poate crea o sub-clasa copil (denumita aici "MoverChild") legata de cea definita mai sus, "Mover".
Deschideti un alt document "ActionScript 3.0 Class", dati-i numele de clasa MoverChild, stergeti codul initial din el si copiati-l pe urmatorul:
// Se creaza package simplu (fara nume)
package {
  // Importare clase a caror proprietati si metode vor fi apelate in aceasta clasa
  import flash.display.MovieClip;
  import flash.events.Event;
  import Mover;               // Importare clasa de baza (parinte)

  // Incepere definire sub-clasa (copil) a clasei Mover
  public class MoverChild extends Mover
  {
    // Metoda constructor a clasei copil (primeste 3 argumente, un obiect Movie Clip si 2 numere)
    public function MoverChild(inMC:MovieClip, xV:Number, yV:Number)
    {
      // Apeleaza Metoda Constrctor a clasei parinte, cu argumentele primite la parametri
      super(inMC,xV,yV);
    }

    // Functie pentru schimbarea directiei de miscare cand obiectul ajunge la margine
    // Cu 4 if-uri pt. verificarea pozitiei obiectului pt. fiecare latura
    private function bounceAtBorder():void
    {
      // Verifica daca obiectul a ajuns in marginea din dreapta
      // Scazand din lungimea Scenei (this.insMC.stage.stageWidth) jumatate din lungimea obiectului (this.insMC.width/2)
      // (jumatate deoarece se considera obiecul MovieClip respectiv creat cu centrul de inregistrare in mijloc)
      if(this.insMC.x > this.insMC.stage.stageWidth-(this.insMC.width/2))
      {
        // Seteaza distanta 'x' cu valoarea data de lungimea Scenei minus jumate din lungimea obiectului
        // Face negativa valoarea proprietatii pt. viteza de miscare orizontala (pt. a schimba directia)
        this.insMC.x = this.insMC.stage.stageWidth-(this.insMC.width/2);
        xVel *= -1;
      }

      // Verifica daca obiectul a ajuns in marginea de jos
      // Scazand din inaltimea Scenei (this.insMC.stage.stageHeight) jumatate din inaltimea obiectului (this.insMC.height/2)
      if (this.insMC.y > this.insMC.stage.stageHeight-(this.insMC.height/2))
      {
        // Seteaza distanta 'y' cu valoarea data de inaltimea Scenei minus jumate din inaltimea obiectului
        // Face negativa valoarea proprietatii pt. viteza de miscare verticala (pt. a schimba directia)
        this.insMC.y = this.insMC.stage.stageHeight-(this.insMC.height/2);
        yVel *= -1;
      }

      // Verifica daca obiectul a ajuns in marginea din stanga
      //(distanta 'x' mai mica decat jumatate din lungimea oiectului)
      if (this.insMC.x < this.insMC.width/2)
      {
        // Seteaza distanta 'x' cu valoarea data de jumatatea lungimii obiectului
        // Face negativa valoarea proprietatii pt. viteza de miscare orizontala
        this.insMC.x = this.insMC.width/2;
        xVel *= -1;
      }

      // Verifica daca obiectul a ajuns in marginea de sus
      //(distanta 'y' mai mica decat jumatate din inaltimea oiectului)
      if (this.insMC.y < this.insMC.height/2)
      {
        // Seteaza distanta 'y' cu valoarea data de jumatatea inaltimii obiectului
        // Face negativa valoarea proprietatii pt. viteza de miscare verticala
        this.insMC.y = this.insMC.height/2;
        yVel *= -1;
      }
    }

    // Rescrie metoda "updatePosition()", definita in clasa parinte, Mover
    override protected function updatePosition(evtObj:Event):void
    {
      // Apeleaza /Include codul metodei "updatePosition()" din clasa de baza
      super.updatePosition(evtObj);
      bounceAtBorder();            // Adauga apelarea metodei "bounceAtBorder()" definita mai sus
    }
  }
}
- Despre rolul instructiunilor folosite gasiti explicatii in cod.
- Salvati aceasta clasa cu numele "MoverChild.as" in acelasi director unde e si "Mover.as".
- In documentul FLA (din acelasi director) in care e creata instanta Movie Clip "sfer", dati click-dreapta pe primul Frame din Timeline si alegeti "Actions", stergeti daca e ceva adaugat in panoul pt. cod ActionScript si adaugati-l pe urmatoru:
// Creare instanta la clasa MoverChild
var obj2:MoverChild = new MoverChild(sfer, 2, 3);
obj2.startMove();         // Apelare metoda "startMove()"
- Observati ca, desi nu exista metoda "startMove()" in clasa "MoverChild", aceasta este apelata prin instanta acestei clase, si functioneaza deoarece e mostenita de la clasa parinte ca si cum ar fi scrisa si in ea.
- Daca apasati "Ctrl+Enter", rezultatul va fi miscarea obiectului precum se vede in prezentarea urmatoare.

• Pe langa posibiliatea utilizarii proprietatilor si metodelor din clasa parinte, acestea pot fi si modificate (rescrise) in clasa copil, dupa cum puteti vedea in codul clasei "MoverChild" ca sunt modificate valorile proprietatilor 'xVel', 'yVel' si rescrisa metoda 'updatePosition()'; toate definite initial in clasa parinte "Mover". Aici s-a adaugat inca o instructiune la "updatePosition()", dupa ce a inclus cu "super.updatePosition(evtObj)" si codul ei original.
Rescrierea unei metode se face folosind cuvantul override la definirea acelei metode in clasa copil. Sintaxa generala este:
                override atribut function numeMetoda() {
                    // Codul care-l va inlocui pe cel original, din clasa parinte
                }

  - Rescrierea unei metode nu afecteaza cu nimic pe cea originala, modificarile efectuate sunt valabile doar in clasa copil in care se face rescrierea, respectiv, in alte sub-clase ale ei.
  - Pentru a include si codul initial (din clasa parinte) in functia rescrisa, se foloseste formula super.numeMetoda(); in corpul functie care face rescrierea (tehnica folosita si in exemplu de sus).
Important:
          super() apeleaza metoda constructor a clasei parinte, aceasta trebuie sa contina un numar de argumente egal cu numarul de parametri ai metodei constructor din clasa parinte. Daca aceasta nu e adaugata in corpul clasei copil, va fi automat inclusa de program, dar fara argumente. Prin urmare, daca metoda constructor a clasei de baza contine parametri, trebuie adaugat "super(parametri)" in sub-clasa copil, altfel, ea oricum va fi inclusa, dar fiind fara argumente, va genera eroare.
- "super.numeMetoda()" apeleaza /include "numeMetoda()" din clasa parinte.

Creare sub-clasa din clasa copil

Dupa formula prezentata mai sus se pot defini mai multe clase copil ca extinderi a clasei de baza, dar se pot crea si subclase ale clasei copil, astfel, clasa copil devine "parinte" a sub-claselor extinse din ea, acestea fiind ca niste nepoti a clasei principale, de baza.
• Clasele "nepot" nu pot mosteni direct proprietatile si metodele clasei "bunic", ci prin intermediul clasei din care sunt extinse.


Pentru a arata practic cum se construieste si functioneaza o sub-clasa extinsa din alta sub-clasa, vom continua cu exemplul prezentat pana acum in aceasta lectie.
Clasa de baza, "Mover", face miscarea si oprirea obiectelor, cea extinsa din ea, "MoverChild", schimba directia de miscare cand obiectul ajunge in margini. Acum, vom defini o clasa copil din "MoverChild", denumita "MoverChildG". Cu aceasta se intentioneaza adaugarea unui efect de "gravitatie" care sa traga in jos obiectul si sa-l incetineasca pana la oprire.
- Se creaza clasa "MoverChildG" din "MoverChild" si nu direct din cea de baza deoarece astfel mosteneste capacitatea ei de a nu lasa obiectul sa iasa din margini.
Deschideti un nou document "ActionScript 3.0 Class", dati pt. numele clasei "MoverChildG", stergeti codul initial din el si copiati-l pe urmatorul:
// Se creaza package simplu (fara nume)
package {
  // Importare clase a caror proprietati si metode vor fi apelate in aceasta clasa
  import flash.display.MovieClip;
  import flash.events.Event;
  import MoverChild;           // Importare clasa din care va fi extinsa

  // Incepere definire sub-clasa MoverChildG (copil) a clasei MoverChild
  public class MoverChildG extends MoverChild
  {
    // Se definesc proprietatile proprii acestei clase
    // cu atribut "private" deoarece se folosesc doar in codul ei
    private var streng: Number;
    private var lastPosX: Number;
    private var lastPosY: Number;

    // Metoda constructor a clasei
    // Pe langa atributele necesare clasei din care este extinsa, mai adauga un parametru "streng" (pt. puterea de miscare)
    // ('stren' avand atribuita si o valoare, face optionala adauarea lui la crearea instantei in script)
    public function MoverChildG(inMC:MovieClip, xV:Number, yV:Number, streng:Number=1)
    {
      // Apeleaza Metoda Constrctor a clasei parinte (la care este extinsa)
      super(inMC, xV, yV);

      // Atribuie proprietatii 'streng' valoarea parametrului "streng"
      // S-a dat parametrului acelasi nume cu al proprietatii pt. a se sti mai bine rolul lui (dar poate avea si alt nume)
      this.streng = streng;
    }

    // Rescrie metoda "updatePosition()", definita (tot ca rescriere) in clasa parinte, MoverChild
    override protected function updatePosition(evtObj:Event):void
    {
      // Include /Pastreaza codul initial al acestei metode si adauga alte 3 instructiuni (apelari a unor functii interne)
      super.updatePosition(evtObj);
      this.applyGravity();
      this.applyFriction();
      this.checkForStop();
    }

          /* Se definesc functiile interne, private, deoarece sunt necesare doar in interiorul acestui cod */

    // Mareste viteza pe axa Y cu valoare proprietatii 'streng'
    private function applyGravity():void
    {
      this.yVel += this.streng;
    }

    // Adauga coeficientul de gravitate G (0.98) la viteza de pe axele X si Y
    // care, prin inmultire (fiind mai mica decat 1) are ca rezultat micsorarea valori lor
    private function applyFriction():void
    {
      this.xVel *= 0.98;
      this.yVel *= 0.98;
    }

    // Functia pt. verificarea momentului cand miscarea s-a oprit
    // In acel moment apeleaza metoda "stopMove" din clasa de baza (pt. eficientizarea codului)
    // ("stopMove" sterge inregistrarea evenimentului de detectare ENTER_FRAME,
    // ne fiind necesar dupa oprire, elibereaza memoria ocupata de acest eveniment)
    private function checkForStop():void
    {
      // Daca pozitia X si Y a obiectului este aceeasi cu ultima inregistrata
      if(this.insMC.x == this.lastPosX && this.insMC.y == this.lastPosY)
      {
        this.stopMove();          // Apeleaza metoda "stopMove"
      }

      // Retine in proprietatile 'lastPosX' si 'lastPosY' ultima pozitie a obiectului
      this.lastPosX = this.insMC.x;
      this.lastPosY = this.insMC.y;
    }
  }
}
- Explicatii despre instructiunile folosite gasiti in documentatia din cod.
- Salvati aceasta clasa cu numele "MoverChildG.as" in acelasi director unde e "Mover.as" si "MoverChild.as".
- In documentul FLA (din acelasi director) in care e creata instanta Movie Clip "sfer", dati click-dreapta pe primul Frame din Timeline si alegeti "Actions", stergeti daca e ceva adaugat in panoul pt. cod ActionScript si adaugati-l pe urmatoru:
// Creare instanta la clasa MoverChildG
var obj3:MoverChildG = new MoverChildG(sfer, 15, 30, 2);
obj3.startMove();         // Apelare metoda "startMove()"
- Daca apasati "Ctrl+Enter", rezultatul va fi miscarea obiectului precum se vede in prezentarea urmatoare (click pe imagine).
as3_oop_clase_obiecte_mostenire

• Din toate aceste exemple se vede cat de eficienta e folosirea mostenirii. Pot fi create /adaugate lucruri noi la ceea ce face o clasa, fara a trebui rescris tot codul sau sa fie aceasta modificata. Si oricand poate fi utilizata oricare din clase (parinte, copil, nepot).

Exista posibilitatea de a bloca extinderea unei clase, sa nu mai transfere proprietatile si metodele ei vreunei sub-clase legata de ea. Pentru aceasta se adauga termenul final inaintea cuvantului class
De exemplu:
            package {
                public final class numeClasa {
                    // Instructiuni ...
                }
            }


- Fisierele FLA si AS cu exemplele din aceasta lectie pot fi descarcate de la: OOP - Clase si obiecte - utilizare Mostenire

Un Test simplu in fiecare zi

HTML
CSS
JavaScript
PHP-MySQL
Engleza
Spaniola
Care tag defineste zona de click intr-o harta creata dintr-o imagine?
<map> <img> <area>
<img src="image.jpg" usemap="#map1">
<map name="map1">
  <area shape="rect" coords="9, 120, 56, 149" href="#">
  <area shape="rect" coords="100, 200, 156, 249" href="#">
</map>
Ce proprietate CSS indica ce sa se intample cand continutul unui element depaseste dimensiunile lui?
display overflow position
#id {
  overflow: auto;
}
Clic pe evenimentul care este declansat cand mouse-ul e deasupra unui obiect.
onclick onmouseover onmouseout
document.getElementById("id").onmouseover = function(){
  document.write("Sa ai Viata Buna");
}
Indicati variabila PHP ce contine datele adaugate in adresa URL, dupa caracterul "?".
$_SESSION $_GET $_POST
if(isset($_GET["id"])) {
  echo $_GET["id"];
}
Clic pe pronumele reflexiv care e potrivit in propozitia: "Marc is the boy ... won the prize".
who which whoever
Marc is the boy who won the prize.
- Marc e baiatul care a castigat premiul.
Clic pe pronumele reflexiv care e potrivit in propozitia: "Voy a ver al pintor de ... les hablé ayer".
que quien cuyo
Voy a ver al pintor de quien les hablé ayer.
- Ma duc sa vad pictorul despre care ti-am vorbit ieri.
OOP - Clase si Obiecte - Folosire Mostenire

Last accessed pages

  1. Exercitii engleza - English Tests and exercises - Grammar (27660)
  2. Adjective - Exercitii si teste engleza incepatori (5238)
  3. Download carti electronice si programe pentru Limba Engleza (17548)
  4. Conditional IF in Limba Engleza - Fraze Conditionale (40187)
  5. Verbe modale - SHALL, SHOULD, OUGHT TO, WILL, WOULD, USED TO, BE TO, DARE (14497)

Popular pages this month

  1. Prezentul simplu si continuu - Present Tense Simple and Continuous (3706)
  2. Cursuri si Tutoriale: Engleza, Spaniola, HTML, CSS, Php-Mysql, JavaScript, Ajax (3277)
  3. Gramatica limbii engleze - Prezentare Generala (2797)
  4. Prezent perfect si Prezent perfect continuu - Present perfect and Continuous (2397)
  5. Trecutul simplu si continuu - Past Tense Simple and Continuous (2005)