AS3 101: OOP - Vi presenterer Design Patterns
en
Del
to
Del
Dette Cyber mandag Envato Tuts + Kursene vil bli redusert til bare $ 3. Ikke gå glipp av
Dette innlegget er en del av en serie som heter AS3 101.AS3 101:. OOP - Introduksjon til InterfacesAS3 101: Events - Basix
Etter mange måneder med å lære å programmere fra grunnen av, du er klar til å sette det hele i bruk: vi kommer til å bygge en enkel tegning søknad. Vi vil fokusere på objektorientert programmering teknikker, spesielt bruken av grensesnitt. Ved å sette opp noen regler for programmering vår, vil vi gjøre utvide funksjonssettet og debugging prosjektet mye enklere.
Endelig resultat Forhåndsvisning
Du vil se at vår lille tegningen applikasjonen vil være ganske enkelt. Vær trygg, men at den interne logikk bare kan gjøre hjernen din eksplodere. Ikke bekymre deg, vi vil ta det ett skritt av gangen, som vi alltid gjør. Her er en topp på hva vi jobber mot i denne opplæringen:
Selv om resultatet er enkel, er den underliggende koden kompleks, og en av de tingene du vil forhåpentligvis lære underveis er at objektorientert Programmering kan holde deg organisert og holde prosjektet vedlikeholds
Trinn 1:. Opprett Prosjekt
Første ting først: vi trenger et hjem for vårt prosjekt. Start med å lage en hovedmappe for hele prosjektet. Bruk tilnærming som fungerer best for deg. Det kan være så enkelt som å opprette en mappe på datamaskinen, ved hjelp av OS, eller ved hjelp av Flash Builder for å opprette et nytt prosjekt for deg.
Det spiller ingen rolle hvor denne mappen er opprettet, så lenge du kan få til det når vi trenger å lagre eller åpne filer.
Jeg vil kalle dette programmet "Drawr", så jeg skal navngi mappen min deretter. Navnet er av liten betydning for resten av opplæringen, så hvis du føler fantasi komme opp med ditt eget navn
Trinn 2:. Lag Flash File
Åpne opp Flash CS3 eller høyere, og velg Fil > Ny og velg deretter Actionscript 3.0 alternativet. Dette vil være vår Flash-fil for prosjektet.
Lagre det til prosjektmappen som "Drawr.fla" (eller det navnet du mener er bedre)
Trinn 3:. Lag en Classes mappe og kildebanen
Vi vil organisere vår klasse filer i pakker, men for videre organisering, la oss lage en kildebane.
Lag en mappe i prosjektet mappe kalt "klasser". Alle våre klasser (og pakke mapper) vil gå inn her
I din Flash dokument, velger du Fil >.; Publish Settings (på Mac, Tilvalg-Skift-F12, på Windows Alt-Shift-F12). Klikk på "Flash" -kategorien, og deretter "Innstillinger ..." knappen ved siden av "Manus: Actionscript 3.0". Kontroller at "Source path" -kategorien er valgt, og klikk på "+" -knappen. I den nye oppføringen, skriv "./classes".
Hvis du ønsker å vite mer om denne fremgangsmåten, kan du se i "Kilde Paths" trinn i denne OOP opplæringen.
Trinn 4: Lag dokument Class
Vi vil selvfølgelig være omfavner class filer i denne opplæringen, slik at ingen kode i FLA! Opprett et dokument klassen som vår viktigste inngangspunktet i programmets logikk.
I tekstredigeringsprogram av ditt valg, opprette en ny fil, og lagre den som "Drawr.as" i klassene mappen. På dette punktet, anbefaler jeg at du følger min fil- og klasse navngi instruksjoner. Det er lett å bli forvirret om ditt navn er forskjellige, eller hvis du kopierer koden fra opplæringen som gjør bruk av ulike klassenavn enn det du bruker. Jeg tydeligvis ikke kan politiet det, men anser det som en vennlig og hjelpsom forslag.
Siden denne filen er dokumentet klasse, har vi noen flere deloppgaver å gjøre. Først pop i noen standardtekst kode (hvis du brukte Flash Builder, nesten alt dette vil være til stede allerede):
pakke {import flash.display.Sprite; public class Drawr strekker Sprite {offentlig funksjon Drawr () {trace ("Drawr har startet."); }}}
Nå sørge for at dette dokumentet klassen er koblet tilbake i Flash-fil. Med ingenting er valgt, åpner Egenskaper-panelet og skriv "Drawr" i "Class" -feltet
For å sikre at våre filer spiller pent så langt, velg Control >.; Test Movie å kjøre filmen. Du bør se spor i utdatapanelet:
Trinn 5: Lag en UI
Hvis du vil, kan du bare bruke starteren FLA i nedlastingspakken for de visuelle eiendeler (i "drawr-start" -mappen). Eller du kan lage din egen UI. Her er hva vi trenger:
Tre "Tool" knapper, a la Flash eller Photoshop verktøyknapper. Smallish i størrelse, med en slags ikon for å indikere verktøyet som skal aktiveres når knappen er valgt. De tre verktøyene som trengs er:
Rektangulære knappen
Oval knappen
Brush knappen
For eksempel kan de bli arrangert i Flash som så:
Du kan hente rett ut FLA, eller ved å laste ned de ovennevnte bildene som er PNG-24 bilder med en alfakanal.
En "lerret" området, som må først og fremst være et område av kunstverk på toppen som vi vil tegne. Selv om du gjør området transparent, pass på at området har piksler fylte det; vi vil være å bruke MOUSE_DOWN hendelsen som en viktig ingrediens i vår tegning logikk, og at arrangementet går ikke for en InteractiveObject hvis musen er ikke over en piksel okkupert av at InteractiveObject s piksler. Også, som en UI element, er det nyttig å ha noen form for område definert visuelt å vite hvor tegningen kan skje.
Alle disse elementene bør være movieclips . Nevne disse klippene som så:
rektangel Button: rectangle_mc
Oval Button: oval_mc
Brush Button: brush_mc
Lerret: canvas_mc
Trinn 6: Lag en verktøylinje Class
Vi kommer til å trenge en rekke klasser for å styre selv denne minimal UI. Som antydet tidligere, vil vi følge beste praksis og plassere våre klasser i pakker. Vi oppretter pakkene som vi trenger dem. I klasser mappen oppretter du en ny mappe som heter verktøylinjen. Vi vil holde verktøylinje relaterte klasser her (selvsagt).
Vi begynner med verktøylinjen klassen. Det ansvar vil være å håndtere brukergrensesnittet siden av ting med verktøyene. Lag en fil som heter Toolbar.as i verktøylinjen pakken.
Sett inn følgende kode i det.
pakke verktøylinjen {import flash.events *; importere flash.display. *; public class Toolbar strekker EventDispatcher {private Var _target: Sprite; offentlig funksjon Toolbar (mål: Sprite) {_target = målet; trace ("Toolbar:" + _target); }}}
Før vi kjøttet ut dette, trenger vi en annen klasse, ToolbarButton. Vi vil gjøre det i neste trinn. For nå, skjønt, kan du merke at jeg velger å komponere en Sprite snarere enn å utvide en. Dette er min personlige preferanse, så jeg synes det er mer fleksibel i det lange løp. Du kan føle seg annerledes, men kan du se denne forrige opplæringen i OOP serien for en lang diskusjon om sammensetningen. Uansett, jeg oppfordrer deg til å følge min bly på dette, som prøver å oppnå det samme, men med arv i stedet for sammensetning vil utvilsomt føre til problemer som vil være vanskelig å løse ved å sammenligne koden din til gruven.
La oss gjøre en rask test av Toolbar klassen. Først i FLA, velger de tre verktøylinjen knapper og trykke F8 for å gruppere dem til et symbol. Navn symbolet noe sånt som "Toolbar", men enda viktigere nevne den resulterende forekomsten "toolbar_mc"
Tilbake i Drawr.as, la oss legge til kode for å bruke et Toolbar. Lagt linjene er uthevet nedenfor:
pakke {import flash.display.Sprite; import toolbar.Toolbar; public class Drawr strekker Sprite {private Var _toolbar: Toolbar; offentlig funksjon Drawr () {_toolbar = ny verktøylinje (toolbar_mc); }}}
Og gå videre og teste filmen; du burde se et spor i utdatapanelet
Trinn 7:. Opprett ToolbarButton Class
Denne klassen vil være svært enkel, håndtering plikter for en enkelt knapp på verktøylinjen. Viktigst, vil det bære med seg et verktøy identifikator slik at et klikk på knappen til slutt vil resultere i riktig tegningen atferd.
I verktøylinjen pakken, opprette en fil som heter ToolbarButton.as. Plasser følgende kode i det:
pakke verktøylinjen {import flash.display.Sprite; import flash.events.EventDispatcher; import flash.events.MouseEvent; public class ToolbarButton strekker EventDispatcher {private Var _target: Sprite; private Var _toolType: String; offentlig funksjon ToolbarButton (mål: Sprite, toolType: String) {_target = målet; _toolType = toolType; _target.addEventListener (MouseEvent.ROLL_OVER, onOver); _target.addEventListener (MouseEvent.ROLL_OUT, onOut); _target.addEventListener (MouseEvent.CLICK, onClick); } Private funksjon onOver (e: MouseEvent): void {//Utfør rulle over effekten. } Private funksjon onOut (e: MouseEvent): void {//Utfør roll out effekt. } Private funksjon onClick (e: MouseEvent): void {dispatchEvent (e); } Offentlig funksjon får toolType (): String {return _toolType; }}}
Alt i alt ganske rett fram. Ta en Sprite og legge til noen museinteraksjons hendelser til det. Også ta et verktøy typen String, og lagre den i en eiendom og samtidig gi skrivebeskyttet tilgang til det gjennom en getter.
Jeg er ikke travelhet over selve roll og utrulling effekter for denne opplæringen. Føl deg fri til å sette din egen kode i de aktuelle metoder.
Vi kan nå lage verktøyknappene fra verktøylinjen klassen. Men vi trenger en toolType å passere i. Vi kunne bare gjøre opp strengverdier, men det ville være smartere å lage noen oppregnet statiske konstanter (se min Quick Tips på statiske medlemmer). Vi kan oppnå dette ved å lage en veldig enkel klasse
Trinn 8:. Opprett ToolType Class
Lag en ny klasse fil som heter ToolType.as i verktøylinjen pakken. Den trenger bare noen få statiske konstanter. Skriv inn følgende:
pakke verktøylinjen {public class ToolType {public static konst FIRKANT: String = "rektangel"; public static konst OVAL: String = "oval"; public static konst BØRSTE: String = "børste"; }}
Vi trenger ikke engang en konstruktør; den eneste hensikten med denne klassen er å bære med seg de ulike strengverdier som vi vil bruke til å identifisere de ulike redskapstypene.
Hvorfor ikke bare sette disse konstantene på, si, Toolbar klasse? Jeg tar en side fra Adobes bok om dette. Denne klassen har tilsvarende ansvar til klasser som StageScaleMode eller BlendMode (både i flash.display pakken). De bare erklære offentlige statiske konstanter som har Strengverdier for de gyldige verdiene for Stage.scaleMode og DisplayObject.blendMode egenskaper, henholdsvis.
En grunn til å vurdere dette tilnærming heller enn å sette konstantene på verktøylinjen klasse (eller Stage eller Displayobject klasser) er at det er en god sjanse for at vi vil få tilgang til disse verdiene uten å faktisk bry seg om Toolbar klasse . Dette lar oss bruke "type" klasse uten å bekymre seg en klasse med større funksjonalitet. Dette simulerer en nummerert type, som Action ikke har, og lar klassen bare fokusere på telling av gyldige verdier. Denne oppregning lett kan brukes på flere steder, så
Trinn 9:. Opprett ToolbarButton Objekter
Nå har vi noen birollene medlemmer, og vi kan la Toolbar står i sentrum. Vi skal fylle det ut for å skape ToolbarButton objekter, passerer verktøy typen verdier og trekke opp hendelser. Åpne Toolbar.as og gjøre de endringene uthevet nedenfor (inkludert fjerning av sporet () linjen som var der før).
Pakke verktøylinjen {import flash.display *; import flash.events. *; public class Toolbar strekker EventDispatcher {private Var _target: Sprite; offentlig funksjon Toolbar (mål: Sprite) {_target = målet; Var rect: ToolbarButton = new ToolbarButton (_target.getChildByName ("rectangle_mc") som Sprite, ToolType.RECTANGLE); Var oval: ToolbarButton = new ToolbarButton (_target.getChildByName ("oval_mc") som Sprite, ToolType.OVAL); Var børste: ToolbarButton = new ToolbarButton (_target.getChildByName ("brush_mc") som Sprite, ToolType.BRUSH); rect.addEventListener (MouseEvent.CLICK, onToolClick); oval.addEventListener (MouseEvent.CLICK, onToolClick); brush.addEventListener (MouseEvent.CLICK, onToolClick); } Private funksjon onToolClick (e: MouseEvent): void {trace ("Tool klikk:" + e.target.toolType); }}}
Fortsatt ingenting for forseggjort, men la oss oppsummering. Først oppretter vi tre knapper. Det er et mønster for hvordan de blir instansiert, så det å forstå én betyr at du forstår dem alle. Hvis du husker, tar ToolbarButton klasse to argumenter til sin konstruktør. Den første er en Sprite, så vi får knappesymbol instanser og passere dem i. Legg merke til at vi trenger å kaste et resultat av getChildByName () som en Sprite fordi resultatet er en Displayobject men vi trenger å passere i en Sprite. Det andre argumentet er en String betegner verktøytype, så her bruker vi vår ToolType opplisting klasse. Så nå har vi tre knapper, hver forbundet med en Sprite og gitt en type.
Deretter legger vi KLIKK hendelser til hver av knappene. Den handler for dette ganske enkelt (for nå) sporer ut litt informasjon
Hvis du tester filmen nå, bør du være i stand til å klikke på knappene og motta spor
Trinn 10..: utsending Tilbake til Document Class
Så langt så bra, men vi kan ikke stoppe her. Klikket hendelsen til slutt må komme tilbake til Drawr klassen, slik at det igjen kan gjøre noe med denne informasjonen. For dette, vil vi lage en egendefinert hendelse underklasse å indikere et verktøy utvalg. Det er en vanlig praksis å sette en prosjektets hendelses klasser i en enkelt hendelser pakke, og vi vil gjøre det samme. Lag en mappe kalt hendelser i ditt klasser mappe.
Deretter oppretter du en ny tekstfil og lagre den som ToolbarEvent.as.
Koden vil være som følger:
pakke hendelser {import flash.events.Event; public class ToolbarEvent strekker Hendelses {public static konst VELG: String = "velg"; private Var _toolType = toolType; offentlig funksjon ToolbarEvent (type: String, toolType: String, bobler: Boolean = false, cancelable: Boolean = false) {_toolType = toolType; super (type, bobler, cancelable); } Offentlig funksjon toString (): String {return formatToString ("ToolbarEvent", "type", "toolType"); } Offentlig funksjon klone (): Hendelses {return new ToolbarEvent (type, toolType, bobler, cancelable); } Offentlig funksjon får toolType (): String {return _toolType; }}}
Hvis du jobbet gjennom forrige tutorial der vi bygget en bildeviser, subclassing hendelse for å lage en egendefinert hendelse bør ikke være noe nytt. Våre viktigste formål for å gjøre dette er å opprette en hendelse med en toolType eiendom. Det er også praktisk å lagre hendelsen typenavn i en statisk konstant her, samt
Med dette arrangementet klassen opprettet, flytter tilbake til Toolbar.as og importere ToolbarEvent klassen.
Pakke verktøylinjen {import hendelser .ToolbarEvent;
Og endre onToolClick metode for å fjerne spor og sende en ToolbarEvent:
privat funksjon onToolClick (e: MouseEvent): void {dispatchEvent (ny ToolbarEvent (ToolbarEvent.SELECT, e.target.toolType));}
Den siste oppgaven i dette trinnet er å lytte til denne hendelsen fra Drawr klassen. I den klassen, importere ToolbarEvent klassen og legge til en hendelse lytteren til verktøylinjen objekt:
pakke {import events.ToolbarEvent; import flash.display.Sprite; import toolbar.Toolbar; public class Drawr strekker Sprite {private Var _toolbar: Toolbar; offentlig funksjon Drawr () {_toolbar = ny verktøylinje (toolbar_mc); _toolbar.addEventListener (ToolbarEvent.SELECT, onToolbarSelect); } Private funksjon onToolbarSelect (e: ToolbarEvent): void {trace ("Toolbar velg:" + e.toolType); }}}
Dette vil bare litt modifisere atferden for akkurat nå; men hvis du fortsatt får sporings når du tester filmen, så er du med hell utsending fra verktøylinjen objekt til dokumentet klassen. Vi vil komme tilbake til dette i bare litt
Trinn 11:. Lag et lerret Class
Vi vil gå videre til den andre viktig del av UI, området der vi vil tegne skisser. Lag en annen pakke (mappe) kalt lerret i klassene mappen.
Deretter oppretter du en ny Actionscript-fil og lagre den som Canvas.as i den nylig opprettede "lerret" -mappen.
Tast inn følgende kode:.
pakke lerret {import flash.display *; import flash.events. *; importere flash.geom. *; public class Canvas {private Var _target: Sprite; offentlig funksjon Canvas (mål: Sprite) {_target = målrette; _target.addEventListener (MouseEvent.MOUSE_DOWN, onCanvasDown); } Private funksjon onCanvasDown (meg: MouseEvent): void {trace ("onCanvasDown"); _target.stage.addEventListener (MouseEvent.MOUSE_MOVE, onCanvasMove); _target.stage.addEventListener (MouseEvent.MOUSE_UP, onCanvasUp); } Private funksjon onCanvasMove (meg: MouseEvent): void {var newX: Number = _target.mouseX; Var newy: Number = _target.mouseY; trace ("onCanvasMove:" + newX + "," + newy); } Private funksjon onCanvasUp (meg: MouseEvent): void {trace ("onCanvasUp"); _target.stage.removeEventListener (MouseEvent.MOUSE_MOVE, onCanvasMove); _target.stage.removeEventListener (MouseEvent.MOUSE_UP, onCanvasUp); }}}
Vi skal jobbe i denne klassen ganske mye i løpet av opplæringen, men for nå, er det lurt å få noen nøkkelfunksjonalitet går. Tegningen logikken vil foregå på lerretet, men bare etter at brukeren klikker på musen ned på lerretet. Så det første vi satt opp er en MOUSE_DOWN lytteren på lerretet målet (legg merke til at vi bruker sammensetning igjen, ikke arv. Dette objektet vil har et I så MOUSE_DOWN lytteren, vi legge til to begivenheter: MOUSE_MOVE og MOUSE_UP. Vi ønsker ikke disse hendelsene til å skyte på noen gamle tid, ellers kan vi være tegning bare fordi musen flyttes, om ikke et klikk på lerretet oppstått. Så vi legger disse hendelsene etter MOUSE_DOWN inntraff. I MOUSE_MOVE lytteren, for nå er vi bare å få den posisjonen til musen i forhold til lerretet Sprite, og spore den ut. Vi kommer til å gjøre mye mer her om kort tid. Til slutt, i MOUSE_UP handler, det viktigste å gjøre, med tanke på at vår tegningen er gjort på dette punktet, er å fjerne disse MOUSE_MOVE og MOUSE_UP lyttere, forlater bare MOUSE_DOWN lytteren, som kan starte prosessen på nytt. Dette er bra greier, men det er ingenting å teste ennå. Vi må skape et lerret objektet først. Det er neste Hop tilbake til Drawr klassen, og legge inn de markerte linjer i følgende kode:. Vi er bare importerer klassen, og skaper en eiendom, og forekomster et lerret objekt i at eiendom; bør være ganske rett fram så langt. Gå videre og teste filmen. Når du kjører, kan du klikke og dra i lerretsområdet. Du bør få en hel haug-o-spor Vi har vår grunnleggende lerret, nå hvordan skal vi trekke inn i det? La oss tenke på de generelle mekanikken i tegningen, sier en rektangel. La oss dele fasene av å tegne et rektangel i tre forskjellige faser. For det første er startfasen. Det er ikke før denne fasen skjer at vi faktisk begynne å tegne (du kan si at det er en fase før startfasen, kalt ikke doin 'Nuthin' fase). Den andre fasen er på tegningen fase; her, vi bevege musen rundt for å trekke midlertidige rektangler som vi avgjøre på rektangelet vi faktisk ønsker. Endelig har vi den begå fasen. Det er der vi endelig velge rektangel som vi ønsker observant blant dere vil ha lagt merke til at disse tre fasene justere pent med de tre hendelsene som vi har satt opp i Canvas klassen. De MOUSE_DOWN hendelses faller sammen med startfasen, og i så fall handler vi trenger å utføre noen sette opp vi må begynne å tegne. Tegningen fasen matchet til MOUSE_MOVE arrangement, hvor vi beveger musen rundt og prøve å få størrelsen på vår rektangel til høyre. Og MOUSE_UP hendelsen tilsvarer begå fase; når museknappen går opp, er vi ferdige tegning og vi har vår rektangel. I stedet for generelle termer, da, her er hva vi må gjøre i hver av disse fasene /hendelser. Nå, tenk om en oval verktøy. Hva slags tegne faser ville vi ha med å tegne ovaler? Hvis du sa "akkurat den samme typen," da er du en slags veiviser, fordi det er riktig. De ovennevnte tre trinnene kan like gjerne gjelde for tegning ovaler, eller for den saks skyld, linjer, eller de fleste noen geometrisk form som stjerner eller regulære polygoner. Den eneste virkelige forskjellen vil være logisk for tegningen av formen, under tegningen fase ... i MOUSE_MOVE handler og tegne forskjellige figurer tilsvarende? Jada, vi kan Hva om vi hadde forskjellige gjenstander for hvert verktøy? En RectangleTool klasse, en OvalTool klasse, etc? Så vi kan kapsle Men dette skaper et annet problem. Hvis det er en enkelt "gjeldende verktøy objekt" eiendom i Canvas objekt, hvordan kan vi muligens sette ulike datatyper i det; det vil si hvordan gjøre for å vi skriver eiendommen slik at den kan motta både RectangleTool og OvalTool gjenstander som verdier? For ikke å nevne andre verktøy som kan til slutt bli bygget? Svaret er grensesnittene, og til tross for min dramatisk oppbygging, bør det ikke være overraskende gitt tema for denne opplæringen. Hvis vi kan definere et grensesnitt som mer generelt erklærer metoder som kan kalles av Canvas klassen, så vi kan bruke grensesnittet som datatype for den "gjeldende verktøy objekt" i Canvas, og sørge for at hver selve verktøyet objekt implementerer grensesnittet. Sound bra? . Selvfølgelig den gjør (hvis den ikke gjør det, prøv å lese dette trinnet Hvis det fortsatt ikke fornuftig etter det, deretter prøve å ta en porsjon tro og videre med opplæringen, det vil sannsynligvis være mer fornuftig som vi bygge den ut bit-for-bit) Opprett en annen pakke i prosjektet, denne gangen kalt verktøy. Dette vil være konseptuelt forskjellig klasser i verktøylinjen pakken: verktøylinje klasser er UI elementer; verktøy klasser vil innebære logikk rundt tegning ting på lerretet. Lag en ny tekstfil og lagre den til verktøy mappe som ITool.as . Dette vil være vårt grensesnitt fil, og så det vil ikke være for lang: Vi vil utnytte disse tre faser i de tre første metodene: mousedown, mousemove, og mouseup. Hver vil forvente musens x og y posisjon. Den mousedown metoden vil også bli passert fyllfargen til å bruke. Det er en ekstra metode her at vi har egentlig ikke diskutert ennå, men jeg legger det inn her for å unngå å måtte legge den i seinere. Vi skal få til det øyeblikk, men en rask beskrivelse av det er at verktøyet faktisk skaper kunstverk, og lerret vil hente at kunstverket som en "lag" for å vise La oss sette dette grensesnittet til å fungere. Opprett en ny klasse kalt RectangleTool i verktøy-pakke (det vil skape en "Rectangle.as" filen i "verktøy" -mappen). Vi kan spire i en grunnleggende klasse. Fordi vi skal gjennomføre ITool, kan vi sikre at vi får de nødvendige metoder på plass, selv om de er tom Selv om vi ikke egentlig gjør noe i denne klassen, har vi i det minste oppfylt kontrakten av ITool og skapte metodene som kreves. Vi skal få til en mer praktisk implementering i et øyeblikk, men vår neste oppgave blir å sette dette RectangleTool å bruke Fordi Canvas mottar muse hendelser, er det objektet som må fortelle RectangleTool om disse tre faser. Og fordi Drawr objektet er en som mottar hendelser fra verktøylinjen objekt når et verktøy er valgt, kan vi bruke Drawr klassen å fortelle Canvas som verktøy å bruke. For at dette skal skje, lerretet behov en offentlig eiendom (eller en privat eiendom med en offentlig setter og getter) som holder en referanse til RectangleTool. Det må da satt av Drawr når et verktøy er valgt. I Canvas.as, legge til følgende uthevet linjer. Legg merke til at jeg har også fjernet de tre spor som var i denne filen tidligere Alle disse endringene sentrum rundt å legge en ny _currentTool eiendom. Innførsel, eiendom erklæring, og setter og getter skal ikke kreve noen forklaring. De andre linjene involvere med Men vi kan ikke teste ennå.; vi trenger at _currentTool eiendom skal settes før vi ser noe nytt. Så, i Drawr.as, legge denne biten av koden til onToolbarSelect metode: Og du ønsker å importere ikke bare RectangleTool klassen, men ganske mye annet i de verktøyene Nå gå videre og teste filmen. Klikk på rektangel verktøyknappen (eller noen av verktøyene, for å være rettferdig), og deretter "tegne" på lerretet området. Du vil ikke se noen rektangler dukke opp, men du vil se sporene fra RectangleTool klassen showet opp. For å oppsummere hva som skjer, vi forsyner Canvas objekt med et ITool objekt. Det skjer for å være den RectangleTool akkurat nå. Så når musen hendelser oppstår, og lerret er å svare på dem, spør den også ITool objekt å gjøre sine ting, ved å kalle metoder på dem. Dette vil bli mer fleshed ut som vi går sammen, så hvis det ikke gjør forstand akkurat nå, prøver å følge hendelsesforløpet gjennom kodelinjer i de ulike klassene. Hvis det gjør forstand, men bare virker som for mye arbeid for lite resultat, bare henge der. Den store sammenhengen har ennå ikke avslørt Åpne opp RectangleTool.as igjen. Fjerne spor, og erstatte dem med følgende kode:
Sprite).
Steg 12: Opprett Canvas Object
Pakke {import canvas.Canvas; import events.ToolbarEvent; import flash.display.Sprite; import toolbar.Toolbar; public class Drawr strekker Sprite {private Var _canvas: Lerret; private Var _toolbar: Toolbar; offentlig funksjon Drawr () {_canvas = new Canvas (canvas_mc); _toolbar = new Toolbar (toolbar_mc); _toolbar.addEventListener (ToolbarEvent.SELECT, onToolbarSelect); } Private funksjon onToolbarSelect (e: ToolbarEvent): void {trace ("Toolbar velg:" + e.toolType); }}}
Trinn 13:. Tenker Tools
start. Som ett hjørne av rektangelet er alltid forankret til musen posisjon i denne fasen, trenger vi å fange mus posisjon i MOUSE_DOWN arrangementet og cache det i en variabel for senere bruk
tegning: Det motsatte hjørne av rektangelet følger musen rundt i denne fasen. Vi må kontinuerlig oppdatere trukket rektangel basert på kontinuerlig oppdatere stedet. Det er viktig å merke seg at det betyr at vi faktisk tegne figurer i denne fasen. Vi skal bruke Action tegning API for å oppnå dette
begå. Det er faktisk ikke så mye å gjøre her, annet enn å rydde opp våre hendelsesbehandlinger (som allerede nevnt i noen få skritt siden i forhold til lerret klasse). Formen er allerede trukket fra tegnefasen, vi trenger bare å slutte å tegne og la figuren være. Du kan imidlertid være oppmerksom på at Flash er tegneverktøy har en "lett" omriss trukket under tegningen fasen, som deretter blir riktig gjengitt med fyll og strøk en gang begått. Så, er det tenkelig at du kanskje ønsker å utføre en enkel tegning rutine i tegningen fase og tegne den "ekte" i forplikte fasen. Vi vil ikke gjøre det, men jeg tenkte jeg skulle nevne muligheten.
Trinn 14:.? Kan vi bare gjøre en stor hvis erklæringen
. Men det er ikke en veldig objektorientert tilnærming til problemet på hånden.
logikken i å tegne et bestemt verktøy i en enkelt klasse, og holde Canvas relatert logikk separert. Canvas objekt kan beholde en egenskap av "gjeldende verktøy objekt" og utsette tegningen logikken til dette objektet. Den nåværende objekt kan bli oppdatert når det er hensiktsmessig - si, når du klikker på ett verktøy eller en annen. Denne strategien høres tiltalende (minst, gjør den til meg, og jeg håper at ved nå, gjør det for deg også).
Trinn 15:. Opprette Interface
pakkeverktøy {import flash.display.DisplayObject; felles grensesnitt ITool {funksjon mousedown (x: Antall, y: Antall, fillColor: uint): void; funksjon mousemove (x: Antall, y: Number): void; funksjon mouseup (x: Antall, y: Number): void; funksjonen får art (): Displayobject; }}
Step. 16: Implementering Grensesnittet med rektangelverktøyet
pakkeverktøy {import flash.display *..; public class RectangleTool implementerer ITool {offentlig funksjon RectangleTool () {} offentlig funksjon mousedown (x: Antall, y: Antall, fillColor: uint): void {trace ("mousedown:" + x + "," + y + "," + fillColor.toString (16)); } Offentlig funksjon mousemove (x: Antall, y: Number): void {trace ("mousemove:" + x + "," + y); } Offentlig funksjon mouseup (x: Antall, y: Number): void {trace ("mouseup:" + x + "," + y); } Offentlig funksjon får art (): Displayobject {return new Shape (); }}}
Trinn 17:. Å gi Canvas en ITool
pakke lerret {import flash.display *..; import flash.events. *; importere flash.geom. *; import tools.ITool; public class Canvas {private Var _target: Sprite; private Var _currentTool: ITool offentlig funksjon Canvas (mål: Sprite) {_target = målet; _target.addEventListener (MouseEvent.MOUSE_DOWN, onCanvasDown); } Private funksjon onCanvasDown (meg: MouseEvent): void {if (! _currentTool) Tilbake; _target.stage.addEventListener (MouseEvent.MOUSE_MOVE, onCanvasMove); _target.stage.addEventListener (MouseEvent.MOUSE_UP, onCanvasUp); _currentTool.mouseDown (_target.mouseX, _target.mouseY, 0xff0000); } Private funksjon onCanvasMove (meg: MouseEvent): void {var newX: Number = _target.mouseX; Var newy: Number = _target.mouseY; _currentTool.mouseMove (newX, newy); } Private funksjon onCanvasUp (meg: MouseEvent): void {_target.stage.removeEventListener (MouseEvent.MOUSE_MOVE, onCanvasMove); _target.stage.removeEventListener (MouseEvent.MOUSE_UP, onCanvasUp); _currentTool.mouseUp (_target.mouseX, _target.mouseY); } Offentlig funksjon får currentTool (): ITool {return _currentTool; } Offentlig funksjon satt currentTool (verdi: ITool): void {_currentTool = verdi; }}}
_currentTool eiendommen. Og hva skjer her bør ikke være en stor overraskelse; vi bare kaller de tre "fase" metoder på riktig tidspunkt i henhold til brukermedvirkning. Som en side note, vi også sjekke - på linje 20 - for eksistensen av en _currentTool objekt før du fortsetter med alt dette. Hvis det ikke finnes, ikke legge til noen hendelsen lyttere eller ring noen metoder på _currentTool eiendommen, fordi vi ville få feil hvis vi gjorde
privat funksjon onToolbarSelect (e: ToolbarEvent): void {trace ("Toolbar velg:" + e.toolType); _canvas.currentTool = new RectangleTool ();..}
pakken import verktøy *;
Step. 18: Tegne et rektangel
pakkeverktøy {import flash.display. *; import flash.geom.Point; public class RectangleTool implementerer ITool {private Var _art: Shape; private Var _fillColor: UINT; offentlig funksjon RectangleTool () {} offentlig funksjon mousedown (x: Antall, y: Antall, fillColor: uint): void {_art = new Shape (); _art.x = x; _art.y = y; _fillColor = fillColor; import flash.geom.Point; gå i stykker; gå i stykker; gå i stykker; gå i stykker; gå i stykker; import flash.display.Sprite; import flash.events.Event; gå i stykker; gå i stykker; gå i stykker;