Manipularea mișcării particulelor cu motorul Stardust Particle - Partea 2

Aceasta este a doua parte a acestui tutorial. Vă voi arăta cum să manipulați mișcarea particulelor cu deflectori.

Este necesară cunoașterea prealabilă a elementelor de bază ale mișcării și a câmpurilor vectoriale. Vă recomandăm să completați prima parte a acestui tutorial înainte de a vă deplasa.


Rezultatul final al rezultatelor

Aruncati o privire la rezultatul final la care vom lucra. Este un exemplu al unui efect de pardoseală, cu particule care coboară de pe podea.


deflectoare

Destul de mult ca câmpurile de gravitație, un deflector ia datele de mișcare ale particulelor ca intrări. Apoi, deflectorul suprascrie mișcarea particulei cu ieșirea sa, numai că ieșirea conține acum date de viteză în plus față de datele de poziție. Astfel, în spațiul 2D, ieșirea unui deflector este un vector 4D; primele două componente ale vectorului 4D reprezintă componentele x și y ale vectorului de poziție (denotate X și y), iar ultimele două componente reprezintă componentele x și y ale vectorului de viteză (notat vx și vy).


Cum să utilizați deflectori

Amintiți-vă Camp clasa și Gravitatie acțiune din prima parte a acestui tutorial? Procedura este similară. Tu creezi deflectorul obiecte care manipulează mișcările de particule și apoi le adăugați la Devia acțiune, la fel cum ați adăuga Camp obiecte la Gravitatie acțiune. Acum, să ne uităm la un exemplu rapid.


Efectul Etajului

În acest exemplu, vom folosi LineDeflector clasa pentru a crea un efect de particule-bouncing-off-floor. Un deflector de linie simulează în esență o linie infinit de lungă în spațiul 2D, cu o parte fiind spațiu deschis, iar cealaltă parte solidă; particulele sunt permise numai în spațiul deschis și nu sunt permise în spațiul solid. Atunci când particulele provin din partea spațiului deschis, lovind linia, ei vor sări înapoi. Particle.collisionRadius proprietatea, reprezentând raza unei particule, este luată în considerare.

Deflectorul de linie utilizează un vector normal și un punct în care linia trece prin spațiul 2D pentru a determina linia. Iată o ilustrație care vă oferă o idee mai bună.


Pasul 1: Simbolul Cercului Efectelor la Etaj

Creați un nou document Flash, trageți un cerc cu o rază de 10 și transformați-l într-un simbol, exportat pentru ActionScript cu un nume de clasă Cerc.


Pasul 2: Efectul etajului Clasa de documente

Creați un fișier AS pentru clasa de documente. Clasa creează un emițător și un renderer. Dacă aveți nevoie de o reîmprospătare a utilizării de bază a Stardust, puteți consulta acest tutorial.

 pachet import flash.display.Sprite; importul flash.events.Event; import idv.cjcat.stardust.common.emitters.Emitter; import idv.cjcat.stardust.common.renderers.Renderer; import idv.cjcat.stardust.twoD.renderers.DisplayObjectRenderer; clasa publica FloorEffect extinde Sprite private var emitter: Emitter; privat var renderer: Renderer; funcția publică FloorEffect () emitter = new CircleEmitter (); renderer = nou DisplayObjectRenderer (acest lucru); renderer.addEmitter (emițător); addEventListener (Event.ENTER_FRAME, mainLoop);  funcția privată mainLoop (e: Event): void emitter.step (); 

Clasa emițătorului este prezentată mai jos. În mod normal, împușcă particule de cerc și particulele sunt afectate de un câmp de gravitație uniform, îndreptat în jos.

 pachet import idv.cjcat.stardust.common.actions.Age; import idv.cjcat.stardust.common.actions.DeathLife; import idv.cjcat.stardust.common.actions.ScaleCurve; import idv.cjcat.stardust.common.clocks.SteadyClock; import idv.cjcat.stardust.common.initializers.Life; import idv.cjcat.stardust.common.initializers.Scale; import idv.cjcat.stardust.common.math.UniformRandom; import idv.cjcat.stardust.twoD.actions.Gravity; import idv.cjcat.stardust.twoD.actions.Move; import idv.cjcat.stardust.twoD.emitters.Emitter2D; import idv.cjcat.stardust.twoD.fields.Field; import idv.cjcat.stardust.twoD.fields.UniformField; import idv.cjcat.stardust.twoD.initializers.DisplayObjectClass; import idv.cjcat.stardust.twoD.initializers.Position; import idv.cjcat.stardust.twoD.initializers.Velocity; import idv.cjcat.stardust.twoD.zones.LazySectorZone; import idv.cjcat.stardust.twoD.zones.SinglePoint; clasa publică CircleEmitter extinde Emitter2D funcția publică CircleEmitter () super (noul SteadyClock (1)); // inițializatorii addInitializer (noul DisplayObjectClass (Circle)); addInitializer (viata noua (noul UniformRandom (60, 10))); addInitializer (noua poziție (noul SinglePoint (320, 100))); addInitializer (noua Velocitate (noua LazySectorZone (8, 4))); addInitializer (noua scară (noul UniformRandom (1, 0.4))); addInitializer (noul CollisionRadius (10)); // actions addAction (new Age ()); addAction (noul DeathLife ()); addAction (new Move ()); addAction (noua ScaleCurve (0, 10)); câmpul gravitational var: câmp = nou UniformField (0, 0,5); Var gravitate: gravitatea = noua gravitate (); gravity.addField (câmp); addAction (gravitate); 

Acum ați creat un efect cu particule care se împușcă din centrul scenei, fiind tras în jos de gravitație. Asa arata:

Milestone Vizualizați-l online

Pasul 3: Efectul etajului Adăugați Deflectorul

Adăugați codul următor în constructorul emițătorului. Creează un deflector de linie, îl adaugă la deflectorul acțiune, apoi adaugă acțiunea la emițător, activând astfel efectul deflectorului. Primele două parametri constructori pentru LineDeflector clasa este coordonatul unui punct pe linie, iar ultimii doi parametri sunt componentele x și y ale vectorului normal al liniei. Deflector.bounce proprietatea determină "bounciness" liniei, 1 provocând revenire completă, iar 0 nu înseamnă nici o revenire.

 // crea un deflector de linie care trece prin punctul (320, 320) și deflectorul normal (0, -1): Deflector = nou LineDeflector (320, 320, 0, -1); deflector.bounce = 0,6; var deflect: Deflect = new Deflect (); deflect.addDeflector (deflector); addAction (devia);

Puteți, de asemenea, să desenați o reprezentare vizuală a liniei pe scenă pentru a avea o imagine mai bună.

Bine, am terminat cu acest exemplu. Acum, să aruncăm o privire asupra rezultatului nostru final.

Milestone Vizualizați-l online

Casetă de încadrare

În acest exemplu, vom folosi Casetă de încadrare deflector pentru a constrânge particulele într-o zonă dreptunghiulară.


Pasul 1: Caseta de legare Emitter Class

Clasa de documente rămâne aceeași ca și exemplul anterior, dar vom schimba clasa emițătorului. Aceasta este clasa emițător de bază a acestui exemplu. În comparație cu clasa emițător din exemplul precedent, SteadClock este schimbat în a ImpulseClock pentru a crea instantaneu 20 de particule la început, zona de poziție este schimbată dintr-un singur punct într-o zonă dreptunghiulară care se potrivește cu dimensiunea scenei, Viteză inițializatorul este încetinit puțin, Viaţă inițializatorul este eliminat deoarece dorim ca particulele să rămână permanent pe scenă Vârstă și DeathLife acțiunile nu sunt, la rândul lor, necesare și eliminate, și ScaleCurve este, de asemenea, eliminat. Unele importuri sunt, de asemenea, adăugate și eliminate; puteți să copiați codul de mai jos pentru comoditate.

 pachet import idv.cjcat.stardust.common.clocks.ImpulseClock; import idv.cjcat.stardust.common.initializers.CollisionRadius; import idv.cjcat.stardust.common.initializers.Scale; import idv.cjcat.stardust.common.math.UniformRandom; import idv.cjcat.stardust.twoD.actions.Deflect; import idv.cjcat.stardust.twoD.actions.Move; import idv.cjcat.stardust.twoD.deflectors.BoundingBox; import idv.cjcat.stardust.twoD.deflectors.Deflector; import idv.cjcat.stardust.twoD.emitters.Emitter2D; import idv.cjcat.stardust.twoD.initializers.DisplayObjectClass; import idv.cjcat.stardust.twoD.initializers.Position; import idv.cjcat.stardust.twoD.initializers.Velocity; import idv.cjcat.stardust.twoD.zones.LazySectorZone; import idv.cjcat.stardust.twoD.zones.RectZone; import idv.cjcat.stardust.twoD.zones.SinglePoint; clasa publică CircleEmitter extinde Emitter2D private var impulseClock: ImpulseClock; funcția publică CircleEmitter () super (impulseClock = nou ImpulseClock (20)); impulseClock.impulse (); // inițializatorii addInitializer (noul DisplayObjectClass (Circle)); addInitializer (noua poziție (noua RectZone (0, 0, 640, 400))); addInitializer (noua Velocity (noua LazySectorZone (3, 2))); addInitializer (noua scară (noul UniformRandom (1, 0.4))); addInitializer (noul CollisionRadius (10)); // acțiuni addAction (new Move ()); 

Pasul 2: Caseta de îmbinare Adăugați deflectorul

Destul de mult ca în exemplul anterior, adăugăm acum codul următor în constructorul emițătorului pentru a utiliza Devia acțiune, doar că de data aceasta vom folosi Casetă de încadrare deflectorul pentru a constrânge particulele într-o regiune dreptunghiulară care se potrivește cu dimensiunea scenei.

 // deflector var deflector: Deflector = nou BoundingBox (0, 0, 640, 400); var deflect: Deflect = new Deflect (); deflect.addDeflector (deflector); addAction (devia);

Pasul 3: Bounding Box Testați filmul

Asta e. Nimic nu se schimbă și acum avem constrânse particule într-o cutie de legătură. Testați filmul și veți vedea rezultatul.

Milestone Vizualizați-l online

Deflectoare personalizate

Acum, vom crea deflectori personalizați pe cont propriu. Să înțelegem prima dată deflectorul clasa pe care o vom prelungi.

deflectorul clasa este baza pentru toate deflectorii. Pentru a crea deflectori personalizați, ar trebui să extindeți această clasă și să suprascrieți calculateMotionData4D () și apoi returnați a MotionData4D obiect reprezentând ieșirea vectorului 4D a deflectorului. Contribuția la dispoziția dumneavoastră, la fel ca și Camp clasa, este inclus în Particle2D obiect trecut în metoda ca parametru. Puteți folosi acest lucru Particle2D obiect pentru a determina ieșirea dvs. Apropo, dacă această metodă returnează a nul valoare, Devia acțiunea ar presupune că nu doriți să modificați mișcarea curentă a particulelor, să ignorați particula și apoi să continuați să procesați următoarea particulă.

De exemplu, următorul deflector ar roti vectorul de viteză al fiecărei particule cu un grad în ceas.

 pachet import idv.cjcat.stardust.twoD.geom.Vec2D; import idv.cjcat.stardust.twoD.particles.Particle2D; import idv.cjcat.stardust.twoD.deflectors.Deflector; import idv.cjcat.stardust.twoD.geom.MotionData4D; clasa publica Rotator extinde Deflector suprascriere functie protejata calculateMotionData4D (particula: Particle2D): MotionData4D var viteza: Vec2D = Vec2D noi (particle.vx, particle.vy); velocity.rotateThis (1); returnează MotionData4D (particle.x, particle.y, viteza.x, viteza.y); 

Efectul de deflectoare a tubului

În acest exemplu, vom extinde deflectorul clasa și de a crea propriul nostru deflector, simularea unui tub, care este, în esență, două deflectori de linie sandwiching un spațiu liber în formă de tub.


Pasul 1: Efectul Deflector al tubului Clasa emițătorului

Copiați documentul Flash împreună cu Cerc simbolul și documentul din primul exemplu. Aici vom crea o altă clasă de emițători, încă numită CircleEmitter. De această dată emițătorul emite particule din centrul treptei și nu se aplică un câmp de gravitație.

 pachet import idv.cjcat.stardust.common.actions.Age; import idv.cjcat.stardust.common.actions.DeathLife; import idv.cjcat.stardust.common.actions.ScaleCurve; import idv.cjcat.stardust.common.clocks.SteadyClock; import idv.cjcat.stardust.common.initializers.CollisionRadius; import idv.cjcat.stardust.common.initializers.Life; import idv.cjcat.stardust.common.initializers.Scale; import idv.cjcat.stardust.common.math.UniformRandom; import idv.cjcat.stardust.twoD.actions.Deflect; import idv.cjcat.stardust.twoD.actions.Move; import idv.cjcat.stardust.twoD.deflectors.Deflector; import idv.cjcat.stardust.twoD.emitters.Emitter2D; import idv.cjcat.stardust.twoD.initializers.DisplayObjectClass; import idv.cjcat.stardust.twoD.initializers.Position; import idv.cjcat.stardust.twoD.initializers.Velocity; import idv.cjcat.stardust.twoD.zones.LazySectorZone; import idv.cjcat.stardust.twoD.zones.SinglePoint; clasa publică CircleEmitter extinde Emitter2D funcția publică CircleEmitter () super (noul SteadyClock (1)); // inițializatorii addInitializer (noul DisplayObjectClass (Circle)); addInitializer (viata noua (noul UniformRandom (60, 10))); addInitializer (poziție nouă (noul SinglePoint (320, 200))); / / center stage addInitializer (noua Velocity (noua LazySectorZone (8, 4))); addInitializer (noua scară (noul UniformRandom (1, 0.4))); addInitializer (noul CollisionRadius (10)); // actions addAction (new Age ()); addAction (noul DeathLife ()); addAction (new Move ()); addAction (noua ScaleCurve (0, 10)); 

Pasul 2: Efectul deflector al tubului Deflectorul tubului

Acum vom crea clasa deflectoarelor cu tuburi. Detaliile sunt explicate în comentarii.

 pachet import idv.cjcat.stardust.twoD.particles.Particle2D; import idv.cjcat.stardust.twoD.deflectors.Deflector; import idv.cjcat.stardust.twoD.geom.MotionData4D; clasa publică TubeDeflector extinde Deflector private var y1: Number; privat var y2: Număr; funcția publică TubeDeflector (y1: Număr, y2: Număr) // y2 ar trebui să fie mai mare decât y2 dacă (y1> y2) // swap y1 și y2 dacă y1 este mai mare var temp: Number = y1; y1 = y2; y2 = temp;  this.y1 = y1; acest y2 = y2;  suprascrie funcția protejată calculateMotionData4D (particulă: Particle2D): MotionData4D // componentele de ieșire, inițializate la datele originale ale particulei de mișcare var x: Number = particle.x; var y: Numărul = particle.y; var vx: Număr = particle.vx; var vy: Numărul = particle.vy; // calculează raza de coliziune efectivă var rază: Number = particle.collisionRadius * particle.scale; // semnalizează dacă deflectorul intră în vigoare var deflected: Boolean = false; dacă (particle.y < (y1 + radius))  //particle y-coordinate is less than lower limit //set proper new y-coordinate y = y1 + radius; //set flag deflected = true;  else if (particle.y > (y2 - radius)) // coordonata y a particulei este mai mare decât limita superioară // se stabilește noua coordonată y y = y2 - raza; // set flag flagged = true;  dacă (deflectat) returnează noua MotionData4D (x, y, vx, vy);  altceva // ignora particula și nu își actualizează datele de mișcare returnează null; 

Pasul 3: Efectul deflectorului tubului Adăugați deflectorul

Ar trebui să știți ce vom face acum foarte bine până acum. Așa e, vom adăuga deflectorul la a Devia acțiune și apoi adăugați acțiunea la emițător. Adăugați următorul cod în constructorul emițătorului.

 // creați un deflector de tub var deflector: Deflector = nou TubeDeflector (100, 300); var deflect: Deflect = new Deflect (); deflect.addDeflector (deflector); addAction (devia);

Pasul 4: Efectul deflector al tubului Testați filmul

Acum puteți testa filmul. Din nou, puteți trage și o reprezentare vizuală a deflectorului pe scenă pentru o privire mai bună.

Milestone Vizualizați-l online

Concluzie

Acesta este sfârșitul întregului tutorial. În prima parte ați învățat despre câmpurile gravitaționale. În cea de-a doua parte, ați învățat conceptul deflectorilor și utilizarea efectivă a acestora Devia acțiune. De asemenea, ați învățat cum să extindeți deflectorul pentru a crea deflectori personalizați. Acum puteți să efectuați o manipulare avansată a mișcării particulelor în Stardust.

Vă mulțumesc foarte mult pentru lectură!

Cod