Você está na página 1de 12

Tutorial de ActionScript 3

Joo Guilherme Brant


Esse tutorial dever para um leitor dar uma vaga ideia de como comear a
desenvolver aplicativos no Flash usando ActionScript. Esse tutorial foi
elaborado para rpida leitura e, para conhecimento aprofundado, assim como
para aplicaes especficas, novas pesquisas devero ser reali!adas. " pr#prio
flash tem um grande base da dados de a$uda, que pode ser utili!ada ao lado
desse tutorial.
%embrando que o conhecimento de ingl&s a$uda ' e muito ' na hora de
programar alguma coisa.
Esse tutorial foi pensado para pessoas de nvel bsico. (aso voc& $ programa,
pule as partes de Sinta)e, *ariveis e "peradores e Funes.
O que Actionscript
Fonte+ ,i-ipedia
ActionScript . uma linguagem de programao orientada a ob$etos baseada
em E(/AScript, utili!ada principalmente para construo de aplicaes 01A 2do
ingl&s 01A+ 0ich 1nternet Applications 2Aplicaes 0icas de 1nternet33. 4
e)ecutada em uma mquina virtual 2A*/ 5 6ActionScript *irtual /achine6,
atualmente na verso 7 que est disponvel no Adobe Flash 8la9er 2plug5
inencontrvel em navegadores ,eb3 e tamb.m no ambiente Adobe A10.
Sintaxe
8ara todo tipo de linguagem de programao e)istem regras para as quais
devem ser seguidas para que o computador entenda o que deve ser feito.
" c#digo . lido pelo computador linha a linha. 8ara maior entendimento 2mas
no . necessrio3, . usual ao final de cada linha colocar o ponto5e5vrgula2:;<3.
" ponto5e5vrgula tamb.m pode ser usado para terminar uma instruo no
meio de uma linha, pra colocar outra na mesma linha.
(ada linha aqui, . uma instruo. 1nstruo pode ser a declarao de uma
varivel, a manipulao de variveis de dados, uma chamada de uma funo.
2*eremos tudo adiante3. Enfim, saiba que o computador lida com o c#digo
instruo ap#s instruo, uma a uma.
*e$a+
//Comentrio
instruo1;
instruo2;
instruo3; instruo4; instruo5;
//...
Aqui, primeiro o computador l& a instruo=, depois a instruo>, e por a vai.
Esse :carinha< que vai lendo instruo ap#s instruo . o chamado flu)o de
e)ecuo. 4 possvel fa!er o flu)o de e)ecuo :pular< pra frente ou ainda
voltando pra trs. *eremos adiante como isso funciona.
%embrando outra coisa+ comentrios. ?udo seguido de duas barras 2:@@<3 ou
entre os smbolos @A e A@ chama5se comentrio. (omentrio . algo que no .
considerado pelo computador. (omentrios servem para indicar alguma coisa
para voc&, programador.
Bse e abuse de comentrios, . uma boa prtica. Sempre indique o que vai
fa!er em um pr#)imo trecho de comentrio. Fica mais fcil de lembrar o que
esse c#digo fa! para voc&, e fica mais fcil pra todo mundo que abrir para ler o
seu c#digo entender o que voc& fe!.
Al.m de tudo isso, o Actionscript 2assim como a gigantesca maioria das
linguagens de programao3 permite C voc& dar nome Cs coisas. /as e)istem
algumas palavras $ pr.5estabelecidas pelo actionscript que definem qual
instruo ser reali!ada, ou se$a, o que o computador dever fa!er, que no
podem ser usadas livremente. Essas palavras so chamadas de palavras
reservadas. *eremos muitas delas adiante. 8or e)emplo, var define que ser
declarado uma varivel, Dhile define que ali ter um loop. E medida que se vai
programando, essas palavras ficam cada ve! mais fceis de serem lembradas
2muitas linguagens de programao tem as mesmas palavras para as mesmas
coisas3.
(ada ve! que voc& testa sua aplicao 2(?0%FEG?E03 o c#digo que voc&
escreveu nos frames e nas classes importadas so compiladas. "u se$a, elas
so transformadas de c#digo entendvel por voc&, ser humano, para c#digo
que pode ser entendido pelo computador. Ap#s isso, o c#digo pronto 2que
chamamos de binrio3 . e)ecutado. As duas coisas ocorrem rapidamente, uma
ap#s a outra.
Variveis e Operadores
Huando programamos, guardamos e manipulamos vrios dados basicamente.
" :espao< no computador reservado para um dado que pode ser depois
manipulado . denominado varivel. 8ara se declarar uma varivel em
Actionscript deve5se escrever+
var nome_da_varivel:Tipo;
"nde nomeIdaIvarivel pode ser o nome que quiser 2a, b, banana, bla3. S#
no pode ser uma palavra reservada da linguagem 2var, class, etc...3. A
palavra reservada var indica que ali ser declarada uma nova varivel.
Go se pode guardar 2ou no se deve3 qualquer tipo de dado em uma varivel
qualquer. 4 necessrio identificar para o computador qual tipo . esse.
2GJmero, 8alavra, (aractere, "b$etos Kveremos mais tardeL3. Esse . o ?ipo
depois do :+<.
8ara o actionscript, e)istem vrios tipos primitivos. Em pouqussimas palavras,
tipos primitivos de uma linguagem so tipos que no podem ser separados em
nenhum outro tipo. Esses tipos so, por e)emplo+ int, char, etc. Go
actionscript, ao contrrio de outras linguagens, tipos primitivos so pouco
usados pelo programador comum. " programador comum usa tipos que usam
tipos primitivos 2mais sobre isso adiante3.
/ais um e)emplo+
var a:b;
Meclarei uma varivel a do tipo b.
Agora que uma varivel foi declarada, . possvel us5la de vrias formas.
(omo no e)emplo+
var a:int 5;
var b:int 1!;
a b;
b a " b;
a a # b " 42;
Aqui, declarei dois inteiros 2tipo primitivo3 a e b. 8ode5se igualar a com b, a
com uma operao que envolve a e b, e a com uma operao que envolve a e
b e mais uma constante.
E)iste tamb.m o uso de constantes na linguagem. *rios tipos 2primitivos ou
no3 possuem literais. %iterais so maneiras fceis de descrever valores e
dados. " N . uma literal que descreve o nJmero inteiro N. "utro e)emplo .
com palavras+ :abelha< . um literal que descreve a string :abelha<, ou se$a, a
palavra :abelha<. *e$a+
var palavra:$trin% &ovo';
Strings so palavras. Bm pouco mais formalmente, uma lista de caracteres.
*e$a tamb.m que e)istem operadores. "peradores so usados para manipular
dados+ literais e@ou variveis. ?odas as quatro operaes 2F, 5, A e @3 so
operadores para inteiros no actionscript. Gote que as funes dos operadores
depende dos tipos em que esto envolvidos. 8or e)emplo, . possvel utili!ar F
entre strings. " resultado . a concatenao das strings, ou se$a, :$unta5se< as
strings+
var novaString+String O :ome< F :lete<; @@ novaString torna5se :omelete<
trace2novaString3; @@ *ai imprimir omelete na tela
E)istem tamb.m alguns operadores que s# precisam de um parPmetro. 8or
e)emplo, o FF+
i"";
1sso significa que o i agora se torna i F =. 1sso . equivalente C escrever+
i i " 1;
E medida que vai utili!ando o actionscript, os diferentes tipos e operadores vo
sendo utili!ados mais frequentemente. Al.m disso, com uma breve pesquisa
na internet $ temos uma lista de tipos e de todos os operadores 2essa Jltima
no . to grande assim3.
exendo no !luxo de execu"o
(omo $ dito acima, o flu)o de e)ecuo vai lendo as instrues uma a uma,
linha a linha. /as ele no precisa ser totalmente linear. 4 possvel fa!er ele
:saltar< para vrias outras partes do seu c#digo. /as voc& no deveria fa!er
livremente.
(aso voc& queira que o computador e)ecute um c#digo se for estabelecida
uma condio, ou at. que e)ecute um outro quando no for estabelecida, voc&
pode usar o if...else...
*e$a+
// seu ()di%o..
i*+(ondio,
-
//se a (ondio *or satis*eita e.e(uta as instru/es da0ui
instru(ao1;
instru(ao3;
1
else
-
//(aso (ontrario e.e(uta as da0ui
instru(ao2;
1
//mais ()di%o..
/as como estabelecer uma condioQ E)iste um tipo de varivel, o tipo
booleano. ?ipos booleanos s# podem assumir dois valores, true 2verdadeiro3
ou false 2falso3. Gote que true e false so palavras reservadas pelo
actionscript. E)istem vrios operadores que resultam nesse tipo. Bma
e)presso ou instruo que resulta em um tipo booleano so chamadas de
e)presses booleanas. "s operadores mais comuns so+
a OO b igualdade. Ele resulta em true caso a for igual a b.
A R S maior que. Ele resulta em true caso A for maior que S 2d um erro se
A ou S no forem nJmeros3. E)iste tamb.m o menor que.
A RO S maior ou igual que. Ele resulta em true caso A for maior ou igual a S
2tamb.m d o mesmo erro3. E)iste tamb.m o igual ou menor que.
A TO S diferena. 0esulta em true caso A no for igual a S.
E)istem tamb.m os operadores booleanos, que so usados sobre booleanos ou
e)presses booleanas. Se e)istem duas e)presses booleanas ( e M+
( UU M E l#gico. 0esulta true se tanto ( tanto M forem true. E false caso
contrrio.
( VV M 'R "B l#gico. 0esulta true se ( ou M forem true. Se um dos dois for
false, no tem problema.
Bsando esses operadores voc& ter no final uma e)presso booleana tamb.m.
*oc& pode substituir o condio no if acima por uma e)presso booleana.
"utro $eito de mudar o flu)o de e)ecuo . fa!endo um loop+
23ile+(ondio,
-
//()di%o a0ui
1
//mais ()di%o..
Esse Dhile determina um loop. "u se$a, esse c#digo dentro do corpo do Dhile
2entre os WX3 ser rodado infinitamente, at. que a condio no se$a mais
satisfeita. Huando no for mais satisfeita, o flu)o de e)ecuo sai do loop e
continua normalmente.
/uito cuidado com o loop infinito+ o loop infinito . quando por algum erro seu
o Dhile nunca para 1sso significa que o flash do usurio vai travar caso
acontea isso. *oc& no quer que isso acontea.
#un"$es
E medida que o c#digo fica muito grande, fica necessrio fa!er partes de
c#digo que se$am reutili!veis. A . que entram as funes. *er que funes
so nada mais nada menos que fa!er o flu)o de e)ecuo pular para uma certo
trecho de c#digo.
"bserve o corpo de uma funo comum+
*un(tion nome_da_*un(ao+parametro1:Tipo14 parametro2:Tipo2,:Tipo_5e_6etorno
-
//C)di%o da *un(ao a0ui
1
?odas as funes iniciam com a palavra reservada function, seguido do nome
que voc& dese$a adicionar para a funo.
Mentro do corpo da funo 2entre os WX3 fica o c#digo dela. Esse c#digo ser
rodado toda ve! que funo for chamada. 8ara chamar uma funo, ve$a
adiante...
var a:int;
var b:7umber;
// 8....()di%o.......
nome_da_*un(ao+,;
//mais ()di%o..
(omo pode ver, qualquer nome seguido de par&nteses :23< . uma chamada de
funo. Huando o flu)o de e)ecuo chegar em uma chamada de funo, ele
:entrar< na funo e comeara a seguir o c#digo de dentro.
8rocure separar seu c#digo em funes o m)imo possvel. Al.m dele ficar
mais fcil de entender, fica muito mais fcil de encontrar erros.
A funo pode aceitar parPmetros, como acima. Go e)emplo acima, a funo
est esperando os parPmetros parametro= e parametro>. Mentro do c#digo da
funo. *oc& pode usar os parPmetros como variveis livremente. Ga chamada
da funo, voc& ?E/ que colocar os parPmetros dentro dos par&nteses, na
ordem que foram declarados na declarao da funo.
E)emplo+
*un(tion *un+i:int4 9:int,
-
//blabl
1
//()di%o
var a:int 2;
*un+a44,;
As funes tamb.m podem retornar coisas. Mepois do par&nteses da
declarao da funo, voc& pode definir o tipo de retorno assim como define
tipos de variveis, quando as declara. Esse . o tipo do dado que dever ser
retornado pela funo. *oc& retorna coisas com a palavra reservada return.
Huando o flu)o de e)ecuo chegar em um return, ele sai da funo na hora.
*oc& pode colocar returns sem nada para funes que no retornam nada,
caso s# queira sair dela naquela hora.
E)emplo+
*un(tion *un+,:int
-
var b:int 2;
return b;
1
var a:int *un+,;
(omo voc& pYde ver acima, quando voc& chama uma funo que retorna
alguma coisa, voc& pode pegar esse resultado. E colocar em uma varivel,
como feito acima. E)istem muitas utilidades. Bma funo pode retornar um
valor do tipo Soolean e ser colocada dentro de uma condio de um if, por
e)emplo. As utilidades so infinitas.
%lasses e &nst'ncias
*oc& tamb.m pode at. definir os seus pr#prios tipos. 4 a que classes entram
em ao.
*e$a o e)emplo+
(lass nome_da_(lasse
-
//:ariaveis
//;<todos
1
Bma classe define um tipo. 8or e)emplo, int, Soolean, Gumber, String, todas
essas so classes. ?oda classe s# tem duas modalidades de coisas+ campos e
m.todos.
(ampos . o nome de uma varivel em uma classe, e m.todo . apenas um
nome de uma funo em uma classe. "u se$a, toda classe s# tem variveis e
funes.
A primeira coisa sobre classes que voc& ir fa!er . como instanciar uma classe.
*oc& fa! isso a partir da palavra reservada neD+
var instancia+nomeIdaIclasse O neD nomeIdaIclasse23;
Esse :neD nomeIdaIclasse23;< parece uma chamada de funo. E ., uma
funo chamada construtor( " (onstrutor . um m.todo especial que toda
classe tem que retorna uma dado do tipo daquela classe. " construtor no
precisa ser definido, mas caso queira defini5lo, apenas crie um m.todo com o
mesmo nome da classe, olhe no e)emplo+
(lass min3aClasse
-
//:ariaveis
//Construtor
*un(tion min3aClasse+,
-
1
//;<todos
1
Metalhe que o construtor no pode retornar nada. Ele $ retorna o tipo da
pr#pria classe. /as voc& pode usar o return sem nada caso queira que a
funo acabe no meio.
Agora que voc& $ tem uma instPncia da sua classe 2ou varivel do tipo da sua
classe, chame5a do que quiser3, voc& $ pode us5la. *e$a no e)emplo+
(lass min3aClasse
-
//:ariaveis
publi( var a:int 2;
publi( var blabla:tipo_blabla;
//Construtor
*un(tion min3aClasse+,
-
1
//;<todos
*un(tion *oo+.:int,:7umber
-
return .=.;
1
1
var instan(ia:min3aClasse ne2 min3aClasse+,;
var (:int instan(ia.a " 2;
var d:7umber insta(ia.*oo+(,;
"bserve que utili!amos campos e m.todos da instPncia. ?odas as instPncias de
uma mesma classe tero os mesmos campos e m.todos 2voc& pode criar
vrias3. 8ara acessar um campo ou m.todo da instPncia, use o nome da
instPncia seguido de ponto2:.<3 seguido do nome do campo ou do m.todo.
Huando voc& chama um m.todo de uma instPncia, di!5se que voc& est
chamando o m.todo sobre essa instPncia.
(lasses tamb.m tem um poder muito grande, que . o de e)tender outras
classes, ve$a no e)emplo+
(lass Carro
-
var rodas;
var volante;
var motor;
*un(tion a(elerar+,
-
tra(e+&a(elerei',;
1
*un(tion *reiar+,
-
tra(e+&*rear',;
1
1
Mefini uma classe carro que tem vrias coisas que um carro tem 2campos3, e o
que um carro fa! 2m.todos3.
Agora sabemos que e)istem tipos mais especficos de carro, que ainda so
carros. Bm e)emplo+ o fusca+
(lass >us(a e.tends Carro
-
var idade:int;
var estra%ado:?oolean;
override *un(tion a(elerar+,
-
i*+estra%ado,
tra(e+&nem a(elerei',;
else
tra(e+&a(elerei (om di*i(uldade',;
1
*un(tion estra%ar+,
-
estra%ado true;
1
1
Esse fusca tem tudo o que o carro tem 2volante, rodas, etc3. /as ele tem umas
coisas a mais, que so especficas dele2idade de carro velho, se est estragado
ou no...3. Ele tamb.m pode fa!er mais coisa que um carro comum 2ele pode
estragar3 e ele tamb.m pode alterar o $eito como um carro comum fa! as
coisas 2agora ele no acelera to bem3.
8ara mudar a funcionalidade de um m.todo que $ foi declarado na classe pai
2no caso, o pai . o (arro3, usa5se a palavra reservada muito Jtil override.
Mentro dos m.todos, voc& tamb.m pode usar a palavra reservada this. Essa
palavra se refere C instPncia da qual o m.todo est sendo chamado. 8or
e)emplo, voc& pode acessar campos e outros m.todos dentro de um m.todo,
chamar uma outra funo com a instPncia como parPmetro, entre outros.
"utro conceito importante . o conceito de pacotes. 8ense um pacote como
uma pasta que cont.m classes. *oc& pode criar os seus pr#prios pacotes
quando estiver trabalhando em um pro$eto. " Flash separa as classes pr.
definidas em pacotes fceis de vi!uali!ar. 8or e)emplo, flash.displa9 . o pacote
de coisas grficas, flash.events . o pacote de coisas sobre eventos. "s dois
esto dentro do pacote flash, por isso o :.< entre os nomes.
(lasses podem parecer complicadas, mas uma ve! aprendidas, so um
importante aliado.
)ispla* O+,ects e como colocar -r!icos na tela
1mage uma Mispla9"b$ect como uma imagem, animao, etc. Go se pode
criar instPncias dessa classe diretamente 2o Flash no permite3. " que se fa! .
usar um filho dessa classe. As mais utili!adas so Sprite, /ovie(lip e
SimpleSutton.
Go Flash, os grficos so implementados atrav.s de uma rvore. Ga ra! da
rvore, fica o Stage, que . o espao em branco que vemos quando criamos um
novo arquivo flash. " stage . um Mispla9"b$ect(ontainer, ou se$a, uma classe
que . um Mispla9"b$ect que pode ter vrios Mispla9"b$ect como filhos, e at.
outros Mispla9"b$ect(onainers.
Ga hora da e)ibio, o Flash comea e)ibindo o Stage, depois e)ibe todos os
filhos, depois os filhos dos filhos em cima dos filhos e por a vai. "u se$a, para
adicionar alguma coisa na tela voc& tem que adicionar um filho no Stage, e
depois ir adicionando filhos. Ela fa! uma busca em largura na rvore e)ibindo
tudo, a cada frame.
(ada Mispla9"b$ect tem sua posio, ou se$a, o seu Z 2sua posio hori!ontal3
e seu [ 2sua posio vertical3. Algebricamente, . um vetor. Aumentando o Z
voc& arrasta o Mispla9"b$ect para a direita, diminuindo para esquerda. "
aumento do [ arrasta o Mispla9"b$ect para bai)o.
Ao adicionar um filho na rvore, a origem do filho torna5se a posio do pai.
Go flash, como me)emos em duas dimenses, a origem principal . a posio
do stage, que . a posio ) O \ e 9 O \. Essa posio . o ponto superior
esquerdo do espao em branco. Bm filho sempre tem sua origem na posio
do pai. "u se$a, mudando a posio do pai voc& tamb.m muda a posio do
filho, que depende da posio do pai. 1sso tamb.m acontece com outros
parPmetros, no s# posio. 8or e)emplo, transpar&ncia, altura e largura, etc.
Se interfere no pai interfere no filho.
8ara adicionar um filho no stage, voc& pode ir at. o timeline, e apertar F] para
adicionar c#digo Cquele frame. " m.todo add(hild2d+Mispla9"b$ect3 serve pra
isso. Ele . um m.todo tanto de um stage como de qualquer
Mispla9"b$ect(ontainer 2que inclui sprites e /ovie(lips3.
Exemplo:
var sprite:$prite ne2 $prite+,;
var movieClip:;ovieClip+,;
addC3ild+sprite,; // @sso *aA o sprite apare(er na tela
sprite.addC3ild+movieClip,; // @sso *aA um movie(lip apare(er tendo (omo base o sprite
Essa funo add(hild . a funo para colocar um filho em um
Mispla9"b$ect(ontainer. *oc& e)ecuta esse m.todo sobre a instPncia que voc&
quer que se$a pai, passando como parPmetro o filho.
8ara fa!er um desenho no flash e fa!er esse desenho aparecer na tela em
tempo de e)ecuo, ou se$a, no c#digo, voc& ter que lin-ar o smbolo no
actionscript.
(aso no saiba o que se$a smbolo, pesquise :flash neD s9mbol< ou o que
quiser na internet.
8ara lin-ar o smbolo para o actionscript, voc& deve fa!er o seguinte+
=. Abra um documento flash.
>. (rie o seu smbolo.
7. Abra a %ibrar92Siblioteca3.
^. (lique com o boto direito no smbolo.
N. /arque a opo :E)port for ActionScript< dentro de %in-age
_. (oloque o nome da classe que gostaria de que sua imagem tivesse
`. (oloque a classe que ser pai da imagem que voc& est criando. 2"
Mefault, /ovie(lip, . o mais usado, mas voc& tamb.m pode usar Sprite
se preferir gastar menos espao3.
a. 8rontoT Agora toda ve! que voc& chamar : neD nome5da5classe23; :,
voc& estar criando uma instPncia desse smbolo no c#digo. Funciona em
qualquer parte do c#digo, at. em classes, contando que elas este$am no
mesmo pro$eto.
Agora sim, voc& sabe como colocar imagens dentro do c#digo actionscript.
.ventos e &nteratividade
/as e sobre interatividade, como fa!erQ " Flash foi feito para ser interativo
com o seu usurio, e no uma coisa em que apenas . assistido. Fa!er alguma
coisa acontecer quando se movimenta o mouse ou aperta5se uma tecla, por
e)emplo, . importantssimo.
8ara comear a fa!er alguma coisa interativa, o programador tem que
entender alguma coisa de eventos. A classe Event e suas filhas so tipos de
eventos. As instPncias da classe Event so eventos mais geral 2e o que
normalmente voc& vai mais utili!ar3. /as e)istem tamb.m, por e)emplo, a
classe /ouseEvent, tem instPncias que so eventos ligados ao mouse, como
movimentao e clique. E por a vai.
A no ser que crie manualmente um evento, ele no vai ser criado
2instanciado3 por voc&. E sim pelo sistema. " que voc& fa! . que toda ve! que
um evento for criado 2isso . um pouco amplo, a e)plicao verdadeira . mais
complicada3 e detectado, uma chamada pra uma funo acontece. 4 essa
funo que voc& criar. " que acontecer quando o usurio clica em um
botoQ Ele chamar uma funo automaticamente, e voc& . quem criar essa
funo.
*e$a um e)emplo de como fa!er um evento funcionar, em uma frame do
timeline+
*un(tion *oo+,
-
tra(e+&*alae',;
1
addBventCistener+Bvent.B7TB6_>6D;B4*oo,;
Gesse c#digo, adicionamos ao de entrar em um novo frame 2um evento
utili!ado /B1?"3 a funo foo. "u se$a, o flash acabar imprimindo na tela
milhares de :falae< infinitamente. 1sso acontece porque a timeline principal
nunca para de entrar em novos eventos. Alis, nada para de entrar em novos
eventos.
Essa funo, addEvent%istener, . a funo principal para me)er com
interatividade. A instPncia sobre a qual voc& age o m.todo . a instPncia que
escuta. "u se$a, se voc& quer que um boto capture o evento
/ouseEvent.(%1(b, voc& fa! esse m.todo sobre esse boto. " primeiro
parPmetro . qual o tipo de evento de fato, ser escutado pela instPncia.
E)istem vrios tipos de eventos, que podem ser facilmente pesquisados.
" segundo parPmetro . o nome da funo da qual gostaria que fosse chamada
quando o evento especificado acontecesse sobre a instPncia especificada. "
bacana . que pode ser qualquer funo, at. um m.todo de outra instPncia que
no tenha nada a ver com o que de fato este$a acontece. A gama de
possibilidades . imensa.
Outras %lasses
E)istem muitas outras classes que podem ser usadas para e)plorar toda a
funcionalidade do Flash. (omo por e)emplo Sound para sons, /ouse para o
mouse, Accelerometer para acelerYmetro de dispositivos m#veis, entre outros.
/uitas dessas classes t&m seus pr#prios tipos de eventos.
Bma rpida pesquisa no arquivo de a$uda ou na internet tra!em classes e suas
descries para as mais vrias funcionalidades.
Sabendo de Mispla9"b$ectcs e Eventcs, garanto5lhe que uma boa parte do
caminho $ est percorrida.

Você também pode gostar