Opprette en båndbredde Tester for Laster Video i Flash Med AS3

Creating en båndbredde Tester for Laster Video i Flash med AS3
Del
Del
Del
Share < .no> Dette Cyber ​​mandag Envato Tuts + kurs vil bli redusert til bare $ 3. Ikke gå glipp av.

I webutvikling og medieinnhold som serverer du ofte trenger en måte å sørge for at brukeren har en glatt seeropplevelse. For brukere med lite båndbredde og treg Internett-tilkoblinger du trenger for å betjene et mindre video enn for noen på en T1-forbindelse. Denne opplæringen vil lære deg hvordan å gjenkjenne brukerens båndbredde og tjene ham riktig Flash video. Vi skal bygge et grensesnitt som ligner på YouTube kvalitet velgeren, samtidig som de lærer litt om å bruke tilpassede arrangementer og gjenbrukbare klasser




Trinn 1:. BandwidthTester.as

Vi kommer til å lage en klasse som heter BandwidthTester som vil ta vare på måle båndbredde. Vi vil deretter bruke denne klassen i spilleren for å laste inn en bestemt film. Klassen er ikke så komplisert; vi vil laste en test fil og måle hvor mange bytes har blitt lastet hvert sekund, og deretter bruke disse dataene til å få den gjennomsnittlige hastigheten.

La oss komme i gang. Først opprette en mappe der vil vi sette alle kilder. Jeg har gitt, i den endelige kildefilen nedlasting, en mappe som heter videoer der det er tre FLV filer

I hoved mappen oppretter en fil som heter BandwidthTester.as og skriv følgende:.
Pakke {import flash.net. *; import flash.utils. *; import flash.events. *; public class BandwidthTester strekker EventDispatcher {public static konst BAND_TESTED = 'testet'; public static konst TEST = "test"; private Var båndbredde = 0; //endelig gjennomsnittlig båndbredde private Var peak_bandwidth = 0; //peak båndbredde private Var curr_bandwidth = 0; //nåværende take båndbredde private Var testfile = 'videoer /video_hq.flv'; private Var l; //loader private Var TM; //timer private Var last_bytes = 0; //bytes lastet siste gang private Var band; //registrert byte hastigheter private Var _latency = 1; //nettutnyttelse tilnærming offentlig funksjon BandwidthTester (latency = 0) {trace ("båndbredde tester lastet. '); }}}

Her har jeg opprettet pakken, importert de nødvendige pakkene og skapte hoved BandwidthTester klassen. Du vil merke klassen strekker EventDispatcher. Vi trenger dette for å sende hendelser til klasser som abonnerer. Jeg har laget et par variabler å holde de ulike elementene: de to konstanter vil holde to typer hendelser; båndbredden variabel vil holde den endelige gjennomsnittshastighet; den peak_bandwidth vil holde topp hastighet (den høyeste målte verdi); og curr_bandwidth vil bli brukt i TIMER begivenhet å holde den aktuelle målte hastighet.

Jeg har definert en testfile variabel som peker til video med den største størrelsen. Ideelt sett skulle du ønske å sette denne til en fil over 1MB på internett som ikke endres, for eksempel et google cdn bibliotek eller noe. Jeg har også definert variabler å holde URLLoader, timeren, en variabel som holder last_bytes lastet, bandets variabel som vil holde alle målinger og en egenskap kalt _latency som vil bli brukt som en tilnærming til nettverk overhead.
< hr>
Trinn 2: Constructor

La oss gjøre den viktigste funksjonaliteten båndbredden tester. Bytt konstruktøren funksjons innholdet med følgende:
offentlig funksjon BandwidthTester (latency = 0) {tm = new Timer (1000, 3); tm.addEventListener (TimerEvent.TIMER, get_band); tm.addEventListener (TimerEvent.TIMER_COMPLETE, timer_complete); band = new Array (); _latency = 1-latency;} offentlig funksjon start () {l = new URLLoader (); l.addEventListener (Event.OPEN, start_timer); l.addEventListener (Event.COMPLETE, end_download); l.load (ny URLRequest (testfile));} offentlig funksjon start_timer (e: Hendelses) {tm.start ();}

Jeg setter opp timeren med en forsinkelse på 1 sekund og 3 rapporter. Dette sikrer at vi vil ha tre timer hendelser på en ett sekund avstand i tid. Vi vil bruke den get_band () -funksjonen til å lagre bytes lastet. Jeg er også initialisering band matrise og sette ventetid fra konstruktøren argumenter. Hele testing starter ikke før jeg kaller start () metoden, som skaper en URLLoader og laster testfilen, etter å ha lagt hendelsen lyttere til ÅPEN og COMPLETE hendelser. Når filen har begynt å laste ned, starter vi timeren



Trinn 3:. Få Båndbredde

Vi må gjøre get_band () -funksjonen:
privat funksjon get_band ( e: Timerevent) {curr_bandwidth = Math.floor (((l.bytesLoaded-last_bytes) /125) * _latency); bands.push (curr_bandwidth); last_bytes = l.bytesLoaded; dispatchEvent (ny hendelse (BandwidthTester.TEST));}

Dette er hjertet av målingen kode. Vi beregner gjeldende hastighet etter første sekund ved å trekke last_bytes fra bytesLoaded eiendommen av URLLoader objekt, multiplisert med ventetid. Ventetiden er et tall mellom 0 og 1 så når vi setter for eksempel nettverk overhead tilnærming til 0,2, vil hastigheten bli multiplisert med 0,8 - det vil si 80 prosent av hastigheten.

Jeg også dele trekkes byte med 125 for å få antall kilobit /sekund. I nettverkshastigheten måles som antall kilobit per sekund (kB /s) og en kilobit tilsvarer 125 bytes. Når nettverk annonsere 1 Mb /s, de vanligvis bety 1 mega litt Twitter /sekund, noe som betyr at den maksimale nedlastingshastigheten ville være 125 kilo bytes Twitter /s. Jeg bruker Math.floor () for å få en heltall fra beregningene.

Deretter trykker vi den gjeldende hastighet (eller curr_bandwidth) i band array, setter vi de last_bytes til gjeldende bytesLoaded og sende en ny hendelse av type BandwidthTester.TEST. Denne funksjonen vil bli kalt hvert sekund i tre sekunder. På slutten av disse tre sekunder, har vi en 3-element array som inneholder fartsverdier



Trinn 4: Gjenværende Funksjoner

La oss lage de resterende funksjoner for å beregne den endelige båndbredde :
privat funksjon timer_complete (e: Timerevent) {l.close (); bands.sort (Array.NUMERIC | Array.DESCENDING); peak_bandwidth = band [0]; båndbredde = calc_avg_bandwidth (); dispatchEvent (ny hendelse (BandwidthTester.BAND_TESTED));} private funksjon end_download (e) {tm.stop (); l.close (); bands.sort (Array.NUMERIC | Array.DESCENDING); båndbredde = 10000; peak_bandwidth = (band [0])? band [0]: båndbredde; dispatchEvent (ny hendelse (BandwidthTester.BAND_TESTED));}

timer_complete () funksjonen kalles etter at timeren har fullført de tre timerprogrammer. Her stopper vi for lasting av URLLoader ved å ringe close (), og vi sortere band array. Sorterings () -funksjonen aksepterer noen verdier for oppførselen til sortering. Jeg har kombinert Array.NUMERIC, som sorterer basert på tall og Array.DESCENDING som setter sortering å være fra høyeste til laveste tall. Dette vil sortere band matrise slik at i band [0] vi vil ha den høyeste målte hastighet, som vi bruker til å sette peak_bandwidth. Jeg også sette båndbredden til resultatet av calc_avg_bandwidth (), som vi vil kode om kort tid. Jeg også sende en BAND_TESTED hendelse.

end_download () -funksjonen er nesten det samme, med unntak av at dersom band matrise ikke er fylt, setter jeg peak_bandwidth og båndbredden til 10000. Dette vil skje svært sjelden - kun hvis du er på en svært rask tilkobling, og nedlasting av filer på mindre enn et sekund - i så fall, er båndbredden ikke et problem



Trinn 5: Slutt Båndbredde

La oss beregne. den endelige båndbredde ved å lage et gjennomsnitt av de 3 verdiene i bandene [] rekke:
privat funksjon calc_avg_bandwidth () {var total = 0; Var len = bands.length; while (len--) {sum + = band [len]; } Returnere Math.round (total /bands.length);}

Denne funksjonen er en typisk gjennomsnitts funksjon: jeg legge alle verdiene i bandene [] array og dele resultatet med antall elementer i tabellen, og deretter returnere den avrundes til et heltall med Math.round (). Dette averaging funksjonen sikrer at dersom det er uregelmessigheter mellom hastigheter, får vi en bedre tilnærming av båndbredden.



Trinn 6: nyttefunksjoner

Det er noen flere nyttefunksjoner vi trenger for å lage:
offentlig funksjon satt latency (PRC) {this._latency = 1-PRC;} offentlig funksjon getBandwidth () {return båndbredde;} offentlig funksjon getPeak () {return peak_bandwidth;} offentlig funksjon last_speed () {return curr_bandwidth;}

Jeg har definert en setter funksjon for _latency eiendom, i tilfelle du trenger for å sette det etter oppretting. Det er ikke nødvendig, men det er kult :). Jeg har også definert en getBandwidth () -funksjonen som vi skal bruke for å få den endelige båndbredde og en getPeak () funksjon som returnerer peak_bandwidth; igjen jeg kunne ha gjort båndbredde og peak_bandwidth offentlig, men dette er mer standard. Den last_speed () -funksjonen returnerer curr_bandwidth variabel, slik at dette vil holde den siste målte hastighet.

Nå, getBandwidth () og getPeak () bør bare kalles etter at BAND_TESTED hendelsen har skutt, men vi får se hvordan du bruker denne klassen i et øyeblikk. Her er den endelige koden for denne klassen.
Pakke {import flash.net *; import flash.utils. *; import flash.events. *; public class BandwidthTester strekker EventDispatcher {public static konst BAND_TESTED = 'testet'; public static konst TEST = "test"; private Var båndbredde = 0; //endelig gjennomsnittlig båndbredde private Var peak_bandwidth = 0; //peak båndbredde private Var curr_bandwidth = 0; //nåværende take båndbredde private Var testfile = 'videoer /video_hq.flv'; private Var l; //loader private Var TM; //timer private Var last_bytes = 0; //bytes lastet siste gang private Var band; //registrert byte hastigheter private Var _latency = 1; //nettutnyttelse tilnærming offentlig funksjon BandwidthTester (latency = 0) {tm = new Timer (1000, 3); tm.addEventListener (TimerEvent.TIMER, get_band); tm.addEventListener (TimerEvent.TIMER_COMPLETE, timer_complete); band = new Array (); _latency = 1-latency; } Offentlig funksjon start () {l = new URLLoader (); l.addEventListener (Event.OPEN, start_timer); l.addEventListener (Event.COMPLETE, end_download); l.load (ny URLRequest (testfile)); } Offentlig funksjon start_timer (e: Hendelses) {tm.start (); } Private funksjon get_band (e: Timerevent) {curr_bandwidth = Math.floor (((l.bytesLoaded-last_bytes) /125) * _latency); bands.push (curr_bandwidth); last_bytes = l.bytesLoaded; dispatchEvent (ny hendelse (BandwidthTester.TEST)); } Private funksjon timer_complete (e: Timerevent) {l.close (); bands.sort (Array.NUMERIC | Array.DESCENDING); peak_bandwidth = band [0]; båndbredde = calc_avg_bandwidth (); dispatchEvent (ny hendelse (BandwidthTester.BAND_TESTED)); } Private funksjon end_download (e) {tm.stop (); l.close (); bands.sort (Array.NUMERIC | Array.DESCENDING); båndbredde = 10000; peak_bandwidth = (band [0])? band [0]: båndbredde; dispatchEvent (ny hendelse (BandwidthTester.BAND_TESTED)); } Private funksjon calc_avg_bandwidth () {var total = 0; Var len = bands.length; while (len--) {sum + = band [len]; } Returnere Math.round (total /bands.length); } Offentlig funksjon satt latency (PRC) {this._latency = 1-PRC; } Offentlig funksjon getBandwidth () {return båndbredde; } Offentlig funksjon getPeak () {return peak_bandwidth; }}}



Trinn 7: Testing

Vel, det var mye kode, og vi fortsatt ikke har testet dette hele testing klasse! Vi vil bruke denne klassen i en liten aktør som vil laste tre forskjellige Flvs basert på hastighet. I Flash, opprette en ny Flash dokument med dimensjoner på 640x480px og sette bildefrekvens 30 bilder i sekundet.

Jeg har satt bakgrunnsfargen på filmen til svart (# 000000). La oss lage dokumentet klassen. Opprett en ny Actionscript-fil og kall den BandwidthPlayerTest.as og oppgi følgende innsiden:
pakke {import flash.display. *; import flash.events. *; import flash.media. *; importere flash.xml. *; import flash.text. *; import flash.net. *; public class BandwidthPlayerTest strekker Sprite {var bt; //båndbredde tester Var finalvideo = ''; //url banen Var video_id = false; Var videoer = new Array ('videoer /video_lq.flv', 'videoer /video_mq.flv', 'videoer /video_hq.flv'); //video matrise Var nc //nettforbindelse Var stream //Netstream Var t; offentlig funksjon BandwidthPlayerTest () {t = new Textfield (); t.defaultTextFormat = new tekstformat ('Arial', 12,0xffffff); t.width = 200; t.autoSize = TextFieldAutoSize.LEFT; t.x = 10; hets = 10; t.selectable = false; t.text = 'Beregner hastighet ...'; addChild (t); this.bt = new BandwidthTester (0); this.bt.addEventListener (BandwidthTester.BAND_TESTED, play_video); this.bt.addEventListener (BandwidthTester.TEST, band_test); this.bt.start (); }}}

Dette er hoveddokumentet klasse for Flash Document. Jeg har importert flash.media og flash.net pakker, som vi vil bruke video klassen å spille av videoen. La oss gå gjennom de variablene jeg har satt for denne klassen:

bt vil holde båndbredden tester eksempel finalvideo vil holde valgte banen til videoen, vil video_id holde den valgte indeksen (vi trenger dette senere) , nc og strøm vil holde NetConnection og Netstream klasser, og videoer er en matrise som holder banene til videoer.

I konstruktøren, skaper vi en ny tekstfeltet (for testing) og vi oppretter en forekomst av den BandwidthTester klassen. Jeg har gitt en verdi fra 0 til ventetid som vi ikke trenger det akkurat nå



Trinn 8:. Band_test () og play_video ()

La oss lage band_test () og play_video () funksjoner:
privat funksjon band_test (e) {t.text + = '\\ ntest:' + e.target.last_speed () + 'kb /s'; } Private funksjon play_video (e) {var bw = e.target.getBandwidth (); t.text + = '\\ n \\ nFinal båndbredde:' + bw + 'kb /s'; t.text + = '\\ nPeak båndbredde:' + e.target.getPeak () + 'kb /s'; if (BW > 400) {video_id = 2; } Else if (BW > 128) {video_id = 1; } Else {video_id = 0; } Finalvideo = videoer [video_id]; nc = new NetConnection (); nc.addEventListener (NetStatusEvent.NET_STATUS, nc_status); nc.connect (null); }

Du kan se jeg har lagt til en lytter til BandwidthTester.TEST som vil utløse band_test () hvert sekund, slik at vi får den målte hastigheten og legge det til tekstfeltet. Selvfølgelig, på en live-program, dette ville være skjult, og du vil sannsynligvis bruke dette bare i debugging.

Den neste funksjonen, play_video (), er der vi velger riktig FLV. Jeg får gjennomsnittlig båndbredde i BW variabel, føyer noen resultater til tekstfeltet, og begynne å sammenligne hastighetene. Hvis vi får en hastighet høyere enn 400KB /s spiller vi den høyeste versjonen, ellers spiller vi de lavere versjoner. De VIDEO_ID variable lagrer indeksen i videoer [] rekke



Trinn 9:. Sette i FLV

La oss lage hjelpefunksjoner for å laste FLV:
privat funksjon nc_status (e) {switch (e.info.code) {case "NetConnection.Connect.Success": connect_stream (); gå i stykker; case "NetStream.Play.StreamNotFound": t.text = 'Kunne ikke finne videoen.'; gå i stykker; }} Privat funksjon connect_stream () {stream = ny Netstream (nc); stream.addEventListener (NetStatusEvent.NET_STATUS, nc_status); stream.addEventListener (AsyncErrorEvent.ASYNC_ERROR, funksjon (e) {}); Var video = new Video (stage.stageWidth, stage.stageHeight); addChildAt (video, 0); video.attachNetStream (stream); video.smoothing = true; stream.play (finalvideo); t.text + = '\\ nVideo' + finalvideo;}

den nc_status () -funksjonen er ganske standard i FLV lasting, kaller vi det connect_stream () -funksjonen hvis vi får NetConnection.Connect.Success, eller annet vi vise en feil i tekstfeltet (hvis filmen ikke kan lastes inn).

connect_stream () -funksjonen er der vi feste netconnection til Netstream. Jeg har lagt til et arrangement lytteren for AsyncErrorEvent.ASYNC_ERROR som jeg festet en tom funksjon for å stoppe sporing av async feil i sporet vinduet, så dette er egentlig ikke necesary.

Så neste, jeg har definert video objekt, har jeg festet bekken og jeg ringte play (). Ganske enkelt, eh? Jeg har også satt utjevning for å true så FLV ser bedre.

Tilbake i hoved Flash dokument, sette dokumentet klassen til BandwidthPlayerTest. Hvis du tester filmen nå, bør du få en tre andre måle tid, etter som FLV vil laste. På dette tidspunktet kan vi ikke akkurat simulere alle hastigheter, slik at du kan eksportere SWF og sette den på en server (sammen med videoer, selvfølgelig) og teste hastigheten. Du bør få den riktige filmen avhengig nedlastningshastigheten



Trinn 9:. Kvalitet Selector

Som en ekstra, vil jeg vise deg hvordan du oppretter en kvalitet velgeren for spilleren. I flash dokument, velger rektangel Tool (R), satt rektangelet rundhet til 100, og tegne et 90x25px rektangel med en fyllfarge av # 333333, som på bildet:



Trinn 10: video_selector

Trykk F8 for å opprette en ny MovieClip fra avrundet rektangel. Nevne dette klippet video_selector Hotell og klikk på Avansert. Sjekk Export for Actionscript og i Identifier feltet, skriv video_sel



Trinn 11:. Legg Layers

Dobbeltklikk på filmklipp å redigere den, og i tidslinjen, lage fire flere lag og navngi dem som står i bildet:



Trinn 12: Knapper rektangulært

knappene
lag, skaper en 30x25px rektangel med en fyllfarge av # CC0000. Med rektangelet valgt, trykker du F8 og skape en ny knapp med navnet knappen, som på bildet:



Trinn 13: Knapper States

Dobbeltklikk på det nylig opprettet knapp og flytt den første rammen til Over ramme; deretter, duplisere rammen (ved å holde Alt og dra rammen) til Down og Hit stater. Hvis du vil, kan du bruke en mørkere nyanse av rødt på Down tilstand, for å gjøre det mer interessant



Trinn 14:. Knapper forekomster

Tilbake i "video_selector" MovieClip , duplisere knappen to ganger mer, slik at du har tre knapper og plassere dem på 0, 30 og 60px hhv. Nevne de tre knappene b1
, b2 Hotell og b3



Trinn 15:. Knapper Sveve

Opprett en annen 30x25px rektangel med en fyllfarge av # CC0000 trykke F8, og slå den inn i en MovieClip heter hover
. Gå tilbake til video_selector filmklipp, legger en forekomst av denne hover
filmklipp, gir det en forekomst navn hover
, og plasser den på -30, 0px.
< hr>
Trinn 16: Knapper Mask

Velg avrundet rektangel fra bg lag og trykker Kopier (Ctrl + C) og lim inn (Ctrl + V) på maske
lag og setter masken lag som en maske, som på bildet. Still knappene Hotell og sveve
lag som maskerte lag, også. Hvis du tester filmen nå, får du en hyggelig bar med tre knapper. La oss lage en etikett for knappene



Trinn 17:. Knapper Etikett

På tekstlaget, opprette en ny statisk tekstfeltet og skriv LQ, MQ og HQ. La noen mellomrom for å justere hver etikett ovenfor den tilsvarende knappen, eller lage tre separate textfields; Uansett bør det se ut som dette bildet:



Trinn 18: Knapper Funksjonalitet

La oss lage funksjonaliteten. Vi ønsker å være i stand til å klikke på en kvalitet knapp og laste inn en bestemt film. Legg denne koden til BandwidthPlayerTest.as
, etter connect_stream () -funksjonen:
privat funksjon load_video_lq (e) {t.text = this.videos [0]; stream.play (this.videos [0]); video_selector.hover.x = 0;} private funksjon load_video_mq (e) {t.text = this.videos [1]; stream.play (this.videos [1]); video_selector.hover.x = 30;} private funksjon load_video_hq (e) {t.text = this.videos [2]; stream.play (this.videos [2]); video_selector.hover.x = 60;}

I utgangspunktet har jeg laget tre mer funksjoner for å laste de tre forskjellige filmer, og har nettopp hardkodet indeksen, for hensikten med denne opplæringen. Nå trenger vi å legge disse funksjonene til knappene i video_selector filmklipp



Trinn 19:. Riktig FLV

I konstruktøren Legg til denne linjen:
video_selector. alpha = 0;

Legg denne linjen til play_video () -funksjonen:
create_video_selector (video_id);

Og til slutt la oss lage create_video_selector () -funksjonen:
privat funksjon create_video_selector (hover) {video_selector. hover.x = hover * 30; video_selector.alpha = 1; video_selector.b1.addEventListener (MouseEvent.CLICK, load_video_lq); video_selector.b2.addEventListener (MouseEvent.CLICK, load_video_mq); video_selector.b3.addEventListener (MouseEvent.CLICK, load_video_hq);}

Vi passerer video_id til denne funksjonen; den inneholder enten 0, 1 eller 2. Vi deretter sette hover
rektangel til riktig posisjon ved hjelp av hover * 30. Vi endelig vise video_selector og legge de tre hendelsen lyttere til B1, B2 og B3 knappene.

Hvis du tester filmen nå, vil du se hvordan hover klippet går i riktig posisjon, avhengig av lastet filmen. Hvis du klikker på en annen knapp, laster spilleren den andre FLV. Selvfølgelig er dette på ingen måte en "komplett løsning" for å oppnå dette, spesielt siden vi hardcoding posisjonene i videoer matrise og rekke filmer.



Konklusjon

Dette er slutten av opplæringen, jeg håper du likte det! Legg igjen en kommentar hvis du har opprettet forbedret funksjonalitet for spilleren, vil jeg være interessert i å høre hva du gjorde
!