Efeito de sombra dinâmica com Flash

01/01/2007 por

O Flash já disponibiliza alguns filtros para criar sombras para os objetos através da interface e no Actionscript é possível utilizar a classe DropShadowFilter para aplicar o mesmo filtro durante a execução.

O Exemplo

Abaixo o exemplo que será explicado neste tutorial, passe o mouse sobre para visualizar a mudança de sombras de acordo com a posição da lâmpada.

Passo 1. Criando os objetos

Para iniciar crie um novo documento do tipo Actionscript 3.0, também alguns objetos do tipo MovieClip e coloque-os em posições variadas do espaço de trabalho. Só utilizaremos um frame neste documento, não crie mais frames para impedir um loop.

Para a lâmpada será necessário criar um objeto MovieClip especial, que deve ser exportado para o Actionscript no primeiro frame com o nome de Lampada. Você pode definir estas opções clicando com o botão direito sobre o objeto na listagem da biblioteca e selecionar a opção propriedades, não esqueça de marcar tanto a caixa de Exportar para o Actionscript como a caixa Exportar no primeiro frame. O nome do objeto deve ser Lampada com o primeiro caractere maiúsculo.

Tente posicionar as imagens dentro do MovieClip bem centralizadas para que o efeito não fique com uma "sombra desregulada".

Passo 2. Colocando a lâmpada para andar junto com o mouse

Após clicar no primeiro frame da timeline, abra o painel de ações e cole o REF{cod-lamp}.

// Importando os objetos necessários
import flash.events.MouseEvent;
import flash.display.MovieClip;

// Criando a lâmpada e posicionando ela dentro do filme principal
var lampada:MovieClip = new Lampada();
this.addChild(lampada);

// Esta é a função que irá posicionar a lâmpada nas coordenadas do mouse
function atualizaPosicaoLampada(e=null){
    lampada.x = this.mouseX;
    lampada.y = this.mouseY;
}

// Colocamos um evento para que a posição seja atualizada a cada frame executado
MovieClip(root).addEventListener(Event.ENTER_FRAME, atualizaPosicaoLampada);

Se você pressionar Ctrl+Enter já poderá ver a lâmpada na mesma posição do ponteiro do mouse.

Passo 3. Criando as sombras

Agora basta incluir uma função para recalcular a posição das sombras a cada frame. Basta copiar e colar o REF{cod-sombra} logo após o código anterior, no primeiro frame.

// Importando o objeto que fará a sombra
import flash.filters.DropShadowFilter;

// Algumas propriedades configuráveis
var cor_da_sombra:Number = 0x000000; // A cor RGB da sombra
var qualidade:Number = 2;// de 1 a 3, quanto menor menos qualidade

// Estes atenuadores ajudam a dar o efeito de posicionamento e perda de foco e
// vai do gosto de cada um, faça alguns testes!
var atenuador_de_intensidade:Number = .10;
var atenuador_de_distancia:Number = .21;
var atenuador_de_foco:Number = .035;

// Esta função varrerá pelos MovieClips disponíveis na tela e colocará a sombra em todos
function atualizaSombras(e=null){
    for (var i:uint = 0; i < this.numChildren; i++){ // Para cada filho
        var children = this.getChildAt(i); 
        // Só insere sombra nos objetos MovieClip e que não seja a lâmpada
        if (children is MovieClip && children!=lampada){ 
            // Calcula a distância em pixels do objeto
            var distancia_x:Number = lampada.x - children.x;
            var distancia_y:Number = lampada.y - children.y;
            // Calcula a hipotenusa com o teorema de Pitágoras
            var distancia:Number = Math.sqrt(distancia_x * distancia_x + 
                                             distancia_y * distancia_y);
            // Calcula a intensidade de acordo com a distância
            var intensidade:Number = (80-(atenuador_de_intensidade*distancia))/100;
            // Calcula a distância da sombra
            var distancia_da_sombra:Number = 0-(atenuador_de_distancia*distancia);
            // Calcula como fica o foco da sombra de acordo com a distância também
            var blur:Number = 5+(atenuador_de_foco*distancia);
            // A trigonometria nos dá o ângulo da sombra com relação à lâmpada
            var angulo:Number = Math.atan2(distancia_y, distancia_x)*(180/Math.PI);
            // Criamos o filtro
            var filter:DropShadowFilter = new DropShadowFilter(distancia_da_sombra, angulo,
                cor_da_sombra, 100, blur, blur, intensidade, qualidade, false, false, false);
            // Aplicamos o filtro dentro de um array
            children.filters = [filter];
        }
    }
}
// Colocamos um evento para que seja atualizada a cada frame executado
MovieClip(root).addEventListener(Event.ENTER_FRAME, atualizaSombras);

Depois de inserir este código o efeito já está pronto, não é necessário colocar as sombras através da aba de efeitos. É importante lembrar que o código Actionscript irá remover todos os filtros adicionados no objeto, não só as sombras, a cada atualização de sombras.

Você pode baixar o arquivo .fla do efeito acima clicando aqui.