Usamos cookies para medir audiência e melhorar sua experiência. Você pode aceitar ou recusar a qualquer momento. Veja sobre o iMasters.
Atenção: versão mais atual disponível aqui
Montando um sistema de tickers com Flash + XML + PHP + MySQL
(isso mesmo! igual o do ig!)
Olá amigos e amigas! Esse tutorial abranje duas áreas distintas que se interligam pelo XML. A primeira delas será entre o Flash e o XML, a montagem final dos tickers. Depois explicarei como mudar esse XML dinamicamente através do cadastro em BD.
Veja nesse link uma prévia de como ficará o nosso sistema.
Segue agora a primeira parte:
Relacionando o Flash com XML
Esse tutorial é de nível básico-intermediário, pois alguns conceitos de Flash e de programação são exigidos.
Vamos ver agora como ler os dados do xml e transformar as informações em aplicações práticas.
1. Vamos criar o arquivo xml antes de tudo.
<?xml version="1.0" encoding="utf-8"?><tickers> <ticker> <titulo>Uma vista</titulo> <area>Montanhas</area> <texto>Table Mountain and Cape Town</texto> <foto>foto1.jpg</foto> <link>[http://www.ponha-o-link-que-quiser.com.br](http://www.ponha-o-link-que-quiser.com.br) </ticker> <ticker> <titulo>Manobra Radical</titulo> <area>Esportes</area> <texto>Inline Skater on Vertical Rise of Ramp</texto> <foto>foto2.jpg</foto> <link>[http://www.ponha-o-link-que-quiser.com.br](http://www.ponha-o-link-que-quiser.com.br) </ticker> <ticker> <titulo>Com grande angular</titulo> <area>Cidade</area> <texto>View of Ibiza Town</texto> <foto>foto3.jpg</foto> <link>[http://www.ponha-o-link-que-quiser.com.br](http://www.ponha-o-link-que-quiser.com.br) </ticker></tickers>Providenciei um [zip](http://tutoriais.arpix.com.br/tickers/tickers.zip) com o xml e as fotos para ficar mais fácil.
Reparem na estrutura do arquivo. Ele tem uma tag que cobre todas as outras e tags menores (<ticker>), cada uma com os dados de uma notícia, foto, ou qualquer coisa para que você utilize o sistema.
2. Agora nós vamos preparar a interface no flash. Abra um novo documento e adicione:
Misture bem até que se tenha uma massa homogênea e reserve. /applications/core/interface/imageproxy/imageproxy.php?img=http://forum.imasters.com.br/public/style_emoticons/default/tongue.gif&key=8d11c3c7c03c7a5a294e250694d100848a0423dc34ef2af8d774f49d1b969fde" alt="Imagem Postada" /> Dá uma olhada:
/applications/core/interface/imageproxy/imageproxy.php?img=http://tutoriais.arpix.com.br/tickers/screen1.jpg&key=09ffa9b4db7e0e0823f10589d3e105dde6bb161c56127f734fd519874b60694e" alt="Imagem Postada" />
2.1. Crie um quadradinho, que servirá de botão para o menu, e transforme-o num mc de nome de instância "menu". Dentro dele crie uma nova layer e coloque um botão invisível (com conteúdo apenas do frame HIT) do tamanho do quadradinho e chame-o de "botao". Numa layer mais acima coloque um Dynamic Text com o nome "numero_txt". Adicione esse mc que você acabou de criar no layout do flash (não importa o lugar).
/applications/core/interface/imageproxy/imageproxy.php?img=http://tutoriais.arpix.com.br/tickers/screen2.jpg&key=9d41bc8dbe449125bc3caa3720712cad9443c2e0dddad63c15d3c1cf95233deb" alt="Imagem Postada" />
2.2. A última coisa a ser criada agora é o mc da legenda. Desenhe um retângulo da largura das fotos (360 px) e transforme-o num mc chamado "fundo_mc". Agora pegue o fundo_mc e crie outro mc chamando-o de "legenda_mc". Dentro dele crie dois Dynamic Texts chamando-os de "titulo_txt" e "texto_txt". Crie uma camada acima e desenhe um quadrado que ocupará a área do fundo_mc, depois coloque o tipo da layer como Mask. Para ficar mais claro dê uma olhada na screen:
/applications/core/interface/imageproxy/imageproxy.php?img=http://tutoriais.arpix.com.br/tickers/screen3.jpg&key=33a2e77e97e593a3d619ac982b8d44321da1f12636917ffe6d55f8edae889ebe" alt="Imagem Postada" />
Agora posicione o legenda_mc no palco. O resultado final deverá ser esse:
/applications/core/interface/imageproxy/imageproxy.php?img=http://tutoriais.arpix.com.br/tickers/screen4.jpg&key=8e139312d639ae7a4de0b0fd1c3c45d6a209537a921fad11c01a09cb92cfe87c" alt="Imagem Postada" />
Ah! Todos os nomes de instância que eu falei devem ser grafados sem aspas, viu?
3. Enquanto o layout fica fermentando, vamos avançar na parte mais temida: a programação! Vou fazer aos poucos pra irmos entendendo a lógica do código.
3.1. Captando os dados do xml, importando classes e já ajustando os botões vai e volta. Na timeline principal crie uma layer chamada Actions e adicione:
//Importando as classes para fazer os movimentos dinâmicosimport mx.transitions.;import mx.transitions.easing.;//Criando o xml e fazendo ele ignorar espaços em brancovar tickersXML:XML = new XML();tickersXML.ignoreWhite = true;//Quando o xml carregar com sucesso executar as funçõestickersXML.onLoad = function(success:Boolean):Void { //(o xml é carregado na última linha do script) if (success) { //Número total de tickers n_tickers = tickersXML.firstChild.childNodes.length; /O ticker_atual será o último pois ao executar a função de proximoTicker() ele passará automaticamente para o 1º resultado/ ticker_atual = n_tickers; //Acertando as funções dos botões prox_btn.onRelease = function():Void { //Se o fade das fotos tiver terminado if (fotoIn.position == fotoIn.finish) { proximoTicker(); //Programando para chamar o próximo daqui e a cada 5 seg clearInterval(ticker_intervalo); ticker_intervalo = setInterval(proximoTicker, 5000); } }; ant_btn.onRelease = function():Void { if (fotoIn.position == fotoIn.finish) { anteriorTicker(); clearInterval(ticker_intervalo); ticker_intervalo = setInterval(proximoTicker, 5000); } }; /***************************************************** Códigos do passo 3.2 serão adicionados aqui ***************************************************/ //Chamando o primeiro ticker proximoTicker(); //Programando para chamar o próximo a cada 5 seg ticker_intervalo = setInterval(proximoTicker, 5000); } else { //Caso dê errado o carregamento, avise sobeLegenda(); legenda_mc.titulo_txt.text = "Ocorreu um erro"; legenda_mc.texto_txt.text = "Por favor entre em contato com a administração"; }};/*************************************************** Códigos do passo 3.3 em diante serão adicionados aqui*****************************************************///Carregando o XML e dando início ao processotickersXML.load("tickers.xml");Vamos às considerações sobre o AS até agora. Primeiro a gente cria o objeto XML e a função que será executada quando carregar. Nela vem a parte "se tudo der certo" e depois "se acontecer algum erro". Repare que nessa segunda parte existe uma função chamada sobeLegenda() que ainda não criamos, mas já dá pra ter a idéia de o que ela faz, certo?
Depois de carregarmos o XML contamos quantos tickers temos. A idéia é:
tickersXML - todo o documento
firstChild - o primeiro nó do xml (<tickers>) que contém todas as informações
childNodes - uma array que contém todos os nós com as informações (<ticker>)
length - o tamanho da array, ou seja, quantos ticker
Se ficar alguma dúvida faça testes com o trace(), e sempre! Por exemplo: trace(tickersXML.firstChild) Veja a diferença do resultado do trace quando vai se adicionando as palavras-chave.
Vejamos agora a função do prox_btn.onRelease. Ela é inteira dentro de um if, que verifica se o fade das fotos já terminou (para não dar mais de um fade ao mesmo tempo e dar pau). Se tiver terminado (o fade) ele passa para o próximo ticker e programa para que fique passando automaticamente para o próximo de 5 em 5 segundos. A mesma coisa é para o botão ant_btn, porém com a função de voltar um ticker.
Depois de programados os botões, o script chama o primeiro ticker e já vai programando a passagem dos outros.
3.2. Montando o menu para o internauta ir direto para algum dos tickers. Substitua o comentário do código anterior por:
//Criando o menu duplicando o quadradinho existente//Deixando o quadradinho base invisívelmenu._visible = false;//Criando um laço que gerará os botões do menu. Ele executa uma vez para cada ticker.for (var i:Number = 0; i < n_tickers; i++) { //Duplicando o movieclip menu //O depth é i+5 porque até o depth 4 existem mcs ocupando [fotomc1, fotomc2, legenda_mc, area_mc] var menubtn:MovieClip = menu.duplicateMovieClip("menu" + i, i + 5); //Movendo o botão duplicado no eixo x. O '+58' é a margem da esquerda menubtn._x = i 25 + 58; //Número do ticker menubtn.numero = i; //Texto do botãozinho menubtn.numero_txt.text = i + 1; //Quando apertar o botão, mudar para ticker indicado menubtn.botao.onRelease = function():Void { //Se o fade tiver terminado if (fotoIn.position == fotoIn.finish) { vaiParaTicker(this._parent.numero); clearInterval(ticker_intervalo); ticker_intervalo = setInterval(proximoTicker, 5000); } };}Dentro do laço for são criados cópias do botãozinho e são adicionadas as propriedades deles. Primeiro a gente move o botão para onde queremos. Funciona assim: da primeira vez que o for é executado a variavel i vale 0. Então o primeiro botãozinho será colocado na posição x=(0 25 + 58)=58. O segundo será colocado na posição x=(1 * 25 + 58)=83 e assim por diante.
Cada mc recebe uma variável (numero) com o numero do ticker que ele tem que chamar. Recebe também o texto que é colocado no DynamicText. O botão invisível funciona de modo parecido com o prox_btn. A diferença é que usa a função que vai direto para um ticker. Obs: o this._parent.numero pega a variável numero do pai do botão invisível, o mc.
3.3. As funções de avanço e retrocesso. Agora vamos finalmente criar as funções proximoTicker(), anteriorTicker() e vaiParaTicker(numero_ticker). Substitua o comentário do primeiro código por:
//Função que passa para o próximo tickerfunction proximoTicker():Void { //Se o ticker atual não for o último, aumenta em 1, se for ele vai para 0 ticker_atual < n_tickers - 1 ? ticker_atual++ : ticker_atual = 0; //Colocando titulo e texto na legenda legenda_mc.titulo_txt.text = tickersXML.firstChild.childNodes[ticker_atual].childNodes[1].firstChild.nodeValue + " > " + tickersXML.firstChild.childNodes[ticker_atual].childNodes[0].firstChild.nodeValue; legenda_mc.texto_txt.text = tickersXML.firstChild.childNodes[ticker_atual].childNodes[2].firstChild.nodeValue; //Carregando a foto carregaFoto(tickersXML.firstChild.childNodes[ticker_atual].childNodes[3].firstChild.nodeValue); //Definindo o link para quando clicar na foto area_mc.onRelease = function():Void { getURL(tickersXML.firstChild.childNodes[ticker_atual].childNodes[4].firstChild.nodeValue, "_self"); };}//Função que passa para o ticker anteriorfunction anteriorTicker():Void { //Mesmo esquema da outra função ticker_atual > 0 ? ticker_atual-- : ticker_atual = n_tickers - 1; legenda_mc.titulo_txt.text = tickersXML.firstChild.childNodes[ticker_atual].childNodes[1].firstChild.nodeValue + " > " + tickersXML.firstChild.childNodes[ticker_atual].childNodes[0].firstChild.nodeValue; legenda_mc.texto_txt.text = tickersXML.firstChild.childNodes[ticker_atual].childNodes[2].firstChild.nodeValue; carregaFoto(tickersXML.firstChild.childNodes[ticker_atual].childNodes[3].firstChild.nodeValue); area_mc.onRelease = function():Void { getURL(tickersXML.firstChild.childNodes[ticker_atual].childNodes[4].firstChild.nodeValue, "_self"); };}//Função que vai direto para um ticker, é o mesmo esquema das outrasfunction vaiParaTicker(numero_ticker:Number):Void { ticker_atual = numero_ticker; legenda_mc.titulo_txt.text = tickersXML.firstChild.childNodes[ticker_atual].childNodes[1].firstChild.nodeValue + " > " + tickersXML.firstChild.childNodes[ticker_atual].childNodes[0].firstChild.nodeValue; legenda_mc.texto_txt.text = tickersXML.firstChild.childNodes[ticker_atual].childNodes[2].firstChild.nodeValue; carregaFoto(tickersXML.firstChild.childNodes[ticker_atual].childNodes[3].firstChild.nodeValue); area_mc.onRelease = function():Void { getURL(tickersXML.firstChild.childNodes[ticker_atual].childNodes[4].firstChild.nodeValue, "_self"); };}Vamos entender como funciona a primeira linha do próximoTicker(). Ela é na verdade um if(){}else{} reduzido. Veja ele "desenvolvido":
//Desenvolvidoif(ticker_atual < n_tickers - 1) { ticker_atual++;} else { ticker_atual = 0;}//Reduzidoticker_atual < n_tickers - 1 ? ticker_atual++ : ticker_atual = 0;Isso pode ser visto apenas como um capricho, mas acho interessante mostrar essa outra forma para que reconhecam-na caso vejam em outro código. As demais linhas da função seguem colocando os textos na legenda, o link no onRelease da area_mc e chamando a função de carregar a foto, a próxima que veremos. Para ir esclarecendo as dúvidas em relação ao endereçamento das informações no xml, use e abuse do trace(). Coloque só a primeira palavra-chave e depois vá testando adicionando as demais. Assim ficará mais fácil ter clareza de como o ActionScript trabalha.
As duas outras funções são bem parecidas com a primeira, exeto pela manipulação da variável ticker_atual.
3.4. Carregando as fotos. Essa parte é um pouco complicada, tem que sacar como funciona o esquema de dois movieclips para carregar as fotos e dar os fades. Adicione esse código embaixo do código do passo 3.3.
//Criando os dois movieclips para carregar as fotosthis.createEmptyMovieClip("fotomc1", 2);this.createEmptyMovieClip("fotomc2", 1);//Posicionando os mcs no palcofotomc1._x = fotomc2._x = 20;fotomc1._y = fotomc2._y = 15;//Definindo qual está em cima (por causa dos fades)fotoCima = fotomc1;//Colocando a legenda por cima das fotoslegenda_mc.swapDepths(3);//Função que carrega a foto e cria os fadesfunction carregaFoto(scr:String):Void { //Parando o fade da foto anterior caso ainda esteja ocorrendo fotoIn.stop(); //Criando o mcloader var mclFoto:MovieClipLoader = new MovieClipLoader(); //Carregando a foto mclFoto.loadClip(scr, fotoCima); //Quando terminar de carregar a foto this.onLoadInit = function():Void { //Fazer o fadeIn com a foto de cima fotoIn = new Tween(fotoCima, "_alpha", None.easeNone, 0, 100, 1, true); //Quando terminar a transição de fotos fotoIn.onMotionFinished = function():Void { //Pegar a foto de cima e jogar para trás if (fotoCima == fotomc1) { //Tirando o clip do fotomc2 que irá para frente mclFoto.unloadClip(fotomc2); fotomc1.swapDepths(fotomc2); //Ao ir pra frente estará preparado para receber outra foto fotoCima = fotomc2; } else { //Mesma coisa, caso seja o fotomc2 que estiver em cima mclFoto.unloadClip(fotomc1); fotomc2.swapDepths(fotomc1); fotoCima = fotomc1; } }; }; //Adicionando o listener ao mcloader mclFoto.addListener(this);}Primeiro criamos os mcs nos níveis 1 e 2, e colocamos a legenda por cima deles, no nível 4. Dentro da função nós criamos uma instância do MovieClipLoader. Dê uma lida nesse tutorial do portal iMasters para saber mais. Após isso mandamos o MCL carregar a foto e definimos que quando o carregamento terminar o fade deve ser executado. O fade é feito através da classe Tween, tem um tutorial do Imasters que explica essa classe bem detalhadamente também.
Quando o fade termina nós temos a seguinte situação:
Dependendo de qual estiver por cima, nós descarregamos a foto do mc que estiver atrás e trocamos os dois de lugar, assim a gente terá um mc vazio pronto para receber outra foto e dar o fade.
3.5. Finalizando o código com as funções da legenda. Vamos criar agora as funções de sobeLegenda() e desceLegenda(), além de configurar estados padrão e o aparecimento da legenda.
//Fazendo com que a legenda suba quando o mouse estiver em cima da fotoarea_mc.onRollOver = sobeLegenda;area_mc.onRollOut = desceLegenda;area_mc._alpha = 0;area_mc.swapDepths(4);//Função que esconde a legenda com Tweensfunction desceLegenda():Void { var desceTween1:Tween = new Tween(legenda_mc.fundo_mc, "_y", Strong.easeOut, legenda_mc.fundo_mc._y, 36, 1.5, true); var desceTween2:Tween = new Tween(legenda_mc.titulo_txt, "_y", Strong.easeOut, legenda_mc.titulo_txt._y, 36, 1.5, true); var desceTween3:Tween = new Tween(legenda_mc.texto_txt, "_y", Strong.easeOut, legenda_mc.texto_txt._y, 54, 1.5, true);}//Função que mostra a legenda com Tweensfunction sobeLegenda():Void { var sobeTween1:Tween = new Tween(legenda_mc.fundo_mc, "_y", Strong.easeOut, legenda_mc.fundo_mc._y, 0, 1.5, true); var sobeTween2:Tween = new Tween(legenda_mc.titulo_txt, "_y", Strong.easeOut, legenda_mc.titulo_txt._y, 0, 1.5, true); var sobeTween3:Tween = new Tween(legenda_mc.texto_txt, "_y", Strong.easeOut, legenda_mc.texto_txt._y, 18, 1.5, true);}//Abaixando a legenda por padrãolegenda_mc.fundo_mc._y = legenda_mc.titulo_txt._y = 36;legenda_mc.texto_txt._y = 54;Não tem muito segredo aqui. Apenas definimos quando a legenda aparece e como. Estude a classe Tween do Flash que você poderá aperfeiçoar e personalizar tanto o movimento da legenda quanto o aparecimento das fotos. É só trocar os parâmetros na hora de criar o Tween, o resto continua configurado. Prático, não?
Salve seu aquivo e dê um Ctrl+Enter para gerar e swf. Certifique-se de que o swf, as fotos e o xml estejam na mesma pasta. Agora está finalizada a parte de Flash! Pode testar que você verá seu lindo sisteminha já funcionando!
Uma observação sobre algumas medidas no AS. Na função desceLegenda, por exemplo, eu coloquei para o txt descer até o y:36, mas dependendo do seu layout o número com certeza vai mudar. O mesmo vale para o espaçamento dos botõezinhos do menu, o lugar dos mc fotomc1 e fotomc2, e também para o tempo de um ticker para o outro. Eu coloquei 5 segundos apenas para teste, é bem rapidinho. Pra colocar online mesmo é melhor aumentar esse tempo.
Outras observações sobre práticas de organização do AS. Esse pode não ser o exemplo mais (com o perdão da expressão) "webstandard" de Flash. Mas algumas coisas podem ser ressaltadas:
//Adequadon_tickers = tickersXML.firstChild.childNodes.length;for (var i:Number = 0; i < n_tickers; i++) {}//Não adequadofor (var i:Number = 0; i < tickersXML.firstChild.childNodes.length; i++) {}Isso aumenta o processamento desnecessariamente.- Usar uma variável para se referir a um mc dinamicamente:
//Recomendadovar menubtn:MovieClip = menu.duplicateMovieClip("menu" + i, i + 5);menubtn._x = i 25 + 58;//Não recomendadomenu.duplicateMovieClip("menu" + i, i + 5);_root["menu"+i]._x = i 25 + 58;Pela mesma razão de carregar o processador desnecessariamente.
Bom galera, espero que tenham curtido essa primeira parte do tutorial e que o aproveitem para muitas coisas, inclusive para criar uma galeria de fotos! Se quiser é só tirar as partes de chamar a função proximoTicker() automaticamente que você terá uma ótima opção para mostrar seu portifólio!
Mas ainda não acabou! Vamos ver agora como gerar o xml por PHP pegando dados do MySQL!
Gerando o XML com PHP e MySQL
Esse tutorial é de nível básico-intermediário, pois alguns conceitos de PHP e de MySQL são exigidos.
Bom galera, vamos começar criando e populando a nossa tabela. Baixe as instruções em SQL para ficar mais fácil.
Depois de ter a tabela configurada, vamos criar o arquivo PHP que gerará o xml:
<? //conectando ao mysql $conn = @mysql_connect("localhost", "SEU LOGIN","SUA SENHA"); $db = @mysql_select_db("SEU BD", $conn); //Selecionando todos os registros da tabela tickers $sql = "SELECT * FROM `tickers` ORDER BY `id` ASC"; //Executando a instrução sql $sql = @mysql_query($sql); //Pegando o numero de registros $rst = mysql_num_rows($sql); //Se tiver algum registro if($rst > 0) { //Abre/cria o arquivo tickers.xml com permissão para escrever $xml = fopen("tickers.xml", "w"); //Escreve o cabeçalho e o primeiro nó do xml fwrite($xml, "<?xml version="1.0" encoding="utf-8"?>rn"); fwrite($xml, "<tickers>rn"); //Para cada registro que tiver for($i=0; $i<$rst; $i++) { //Pegamos o valor de cada registro $titulo = utf8_encode(mysql_result($sql,$i,"titulo")); $area = utf8_encode(mysql_result($sql,$i,"area")); $texto = utf8_encode(mysql_result($sql,$i,"texto")); $foto = utf8_encode(mysql_result($sql,$i,"foto")); $link = utf8_encode(mysql_result($sql,$i,"link")); //Guardamos na variavel $conteudo as tags e os valores do xml $conteudo = "<ticker>rn"; $conteudo .= "<titulo>$titulo</titulo>rn"; $conteudo .= "<area>$area</area>rn"; $conteudo .= "<texto>$texto</texto>rn"; $conteudo .= "<foto>$foto</foto>rn"; $conteudo .= "<link>$link</link>rn"; $conteudo .= "</ticker>rn"; //Escrevendo no tickers.xml fwrite($xml, $conteudo); } //Finalizando com a última tag fwrite($xml, "</tickers>"); //Fechando o arquivo fclose($xml); }?>Salve como xml.php e teste. Pronto, só isso. Depois você pode criar algum sistema para dar um update do MySQL e logo após chamar esse aquivo php para gerar novamente o XML. Mas não vou explicar isso aqui pois foge do objetivo do ticker em Flash. /applications/core/interface/imageproxy/imageproxy.php?img=http://forum.imasters.com.br/public/style_emoticons/default/smile.gif&key=15294d64c22e9e9c4ae0bf82a62ec27d13f27d6ba7078a5f7982077798029364" alt="Imagem Postada" />
Bom pessoal, agora está finalizado o tutorial! :clap:
Espero que tenham gostado e que aproveitem bastante.
Abraço, até a próxima! :graduated:
Carregando comentários...