Copy link to clipboard
Copied
Hi,
is there a way to create a waving flag effect from the image loaded with an UIloader in ActionScript 3?
How can I do that? I found a lot of topics like this, but i can not understand well.
Thanks so much,
save it to a aether/utils/ subdirectory of the directory used to save your fla
Copy link to clipboard
Copied
Copy link to clipboard
Copied
I already tried with this code but i have problem with
import aether.utils.ImageUtil;
i got this error
Symbol 'Flagha', Layer 'Layer 1', Frame 1, Line 3, Column 25 | 1172: Definition aether.utils:ImageUtil could not be found. |
and i can not understand why.
Copy link to clipboard
Copied
did you download ImageUtil?
Copy link to clipboard
Copied
From where can I download? And where do I have to copy it?
Thanks
Copy link to clipboard
Copied
from wherever you got that code.
Copy link to clipboard
Copied
Yes I find it but I don't know where I have to copy it..
Copy link to clipboard
Copied
what is ImageUtil?
a .as file? a swc file?
Copy link to clipboard
Copied
As file
Copy link to clipboard
Copied
save it to a aether/utils/ subdirectory of the directory used to save your fla
Copy link to clipboard
Copied
Now looks like ok but still i have problem...
C:\Dropbox (Crionet)\RS & BJ\AS v3.0\Wave Flag\classes\FlagWaving.as, Line 24, Column 38 | 1017: The definition of base class AbstractImageLoader was not found. |
C:\Dropbox (Crionet)\RS & BJ\AS v3.0\Wave Flag\classes\FlagWaving.as, Line 46, Column 39 | 1020: Method marked override must override another method. |
i'm a newbie i never used package in AS3....
Copy link to clipboard
Copied
this fixes that code so it has no dependencies. to use it, import the FlagWave class and call the constructor passing a path/filename bitmap to load and the wind rate. eg,
import FlagWave;
var flagWave:FlagWave = new FlagWave('z_bitmaps/kg.png',30);
addChild(flagWave);
package {
import flash.display.BitmapData;
import flash.display.BitmapDataChannel;
import flash.display.BlendMode;
import flash.display.GradientType;
import flash.display.Shape;
import flash.events.Event;
import flash.filters.DisplacementMapFilter;
import flash.filters.DisplacementMapFilterMode;
import flash.geom.ColorTransform;
import flash.geom.Matrix;
import flash.geom.Point;
import flash.display.Loader;
import flash.net.URLRequest;
import flash.display.Bitmap;
import flash.display.Sprite
/**
* Demonstrates the use of Perlin noise and a displacement map to animate an image
* of a flag waving in the wind. In order to limit the amount of displacement,
* a gradient is drawn into the displacement map using medium gray.
*/
public class FlagWave extends Sprite{
// controls how fast flag will flap
private var WIND_RATE: Number;
private var loader:Loader= new Loader();
private var _loadedBitmap:Bitmap;
private var _gradient: BitmapData;
private var _flag: BitmapData;
private var _perlinNoise: BitmapData;
private var _perlinOffsets: Array;
private var _perlinSeed: int;
/**
* Constructor. Sends path of asset to super class to load.
*/
public function FlagWave(urlS:String,windRate:Number=30){
loader.contentLoaderInfo.addEventListener(Event.COMPLETE,loadCompleteF);
loader.load(new URLRequest(urlS));
WIND_RATE = windRate;
}
public function kill():void{
removeEventListener(Event.ENTER_FRAME,animateFlag);
}
private function loadCompleteF(e:Event):void{
_loadedBitmap = Bitmap(loader.content);
init();
}
private function init(): void {
makeFlag();
makeGradientOverlay();
makeNoise();
addEventListener(Event.ENTER_FRAME, animateFlag);
}
private function makeFlag(): void {
var stageWidth: Number = stage.stageWidth;
var stageHeight: Number = stage.stageHeight;
var bitmapData: BitmapData = _loadedBitmap.bitmapData;
var bitmapWidth: Number = bitmapData.width;
var bitmapHeight: Number = bitmapData.height;
// settings for the size and position of pole
var poleWidth: Number = 15;
var poleHeight: Number = 250;
var poleX: Number = 35;
var poleY: Number = stageHeight - poleHeight;
// draws a horizontal linera gradient for the pole
var matrix: Matrix = new Matrix();
matrix.createGradientBox(poleWidth, poleHeight);
var pole: Shape = new Shape();
pole.graphics.beginGradientFill(
GradientType.LINEAR, [0x333333, 0x999999, 0xCCCCCC, 0xAAAAAA, 0x666666], [1, 1, 1, 1, 1], [0, 50, 160, 200, 255],
matrix
);
pole.graphics.drawRect(0, 0, poleWidth, poleHeight);
pole.graphics.endFill();
pole.x = poleX;
pole.y = poleY;
addChild(pole);
// point at top left of flag
var point: Point = new Point(
(stageWidth - bitmapWidth) / 2, (stageHeight - bitmapHeight) / 2
);
// draws two cords from pole to flag's left side
var cord: Shape = new Shape();
cord.graphics.lineStyle(2, 0x333333);
cord.graphics.moveTo(poleX, poleY + 3);
cord.graphics.lineTo(point.x, point.y);
cord.graphics.moveTo(point.x, point.y + bitmapHeight);
cord.graphics.lineTo(poleX, poleY + bitmapHeight + 20);
// draws cord shape into bitmap data with flag, so that all can be distorted
_flag = new BitmapData(stageWidth, stageHeight, true, 0x00000000);
_flag.draw(cord);
_flag.copyPixels(bitmapData, bitmapData.rect, point);
_loadedBitmap.bitmapData = _flag;
addChild(_loadedBitmap);
}
/**
* Creates the bitmap data that will be used to draw into the displacement
* map in order to limit the amount of distortion. This is accomplished by
* drawing a gradient of medium gray going from full opacity to none over the
* left side of the displacement map, preventing displacement on the left of the image.
*/
private function makeGradientOverlay(): void {
var width: Number = stage.stageWidth;
var height: Number = stage.stageHeight;
var matrix: Matrix = new Matrix();
matrix.createGradientBox(width, height);
var shape: Shape = new Shape();
shape.graphics.beginGradientFill(
GradientType.LINEAR, [0x7F7F7F, 0x7F7F7F], [1, 0], [20, 80],
matrix
);
shape.graphics.drawRect(0, 0, width, height);
shape.graphics.endFill();
// draw gradient shape into bitmap data for use later
_gradient = new BitmapData(width, height, true, 0x00000000);
_gradient.draw(shape);
}
/**
* Initializes Perlin noise properties that will be used in flame animation.
*/
private function makeNoise(): void {
_perlinNoise = new BitmapData(stage.stageWidth, stage.stageHeight);
_perlinSeed = int(new Date());
// only one octave requires only one point
_perlinOffsets = [new Point()];
}
/**
* Applies the Perlin noise to the bitmap data, offsetting the octave displacement
* by the WIND_RATE each time this method is called.
*/
private function applyNoise(): void {
_perlinNoise.perlinNoise(
200,
200,
1,
_perlinSeed,
false,
true,
BitmapDataChannel.RED,
true,
_perlinOffsets
);
// altering offset contributes to horizontal animation of flag
(_perlinOffsets[0] as Point).x -= WIND_RATE;
}
/**
* Redraws the flag with new distortion to create animated effect of flapping.
*/
private function animateFlag(e:Event): void {
// generate new Perlin noise
applyNoise();
var flag: BitmapData = _flag.clone();
// copy the gradient overlay to limit the displacement
_perlinNoise.copyPixels(
_gradient,
_gradient.rect,
new Point(),
_perlinNoise,
new Point(),
true
);
// displace original flag with new displacement map
flag.applyFilter(flag, flag.rect, new Point(), new DisplacementMapFilter(_perlinNoise,new Point(),BitmapDataChannel.RED,BitmapDataChannel.RED,40,60));
_perlinNoise.copyChannel(flag,flag.rect,new Point(),BitmapDataChannel.ALPHA,BitmapDataChannel.ALPHA);
// overlay the displacement map for a lighting effect using darks and lights
flag.draw(
_perlinNoise,
null,
new ColorTransform(1, 1, 1, 0.5),
BlendMode.HARDLIGHT
);
_loadedBitmap.bitmapData = flag;
}
}
}
////////////////////////////
p.s. call the kill() method to stop the animation of the flag
Copy link to clipboard
Copied
Thanks you so much with this code i (you ) solved my problem.
Cheers,
Copy link to clipboard
Copied
you're welcome.
Copy link to clipboard
Copied
Hi, how can I use it with a Sprite instead of an image?
Copy link to clipboard
Copied
use the draw method of the bitmapdata class to access a bitmapdata instance or your sprite and use that instead of bitmapData in makeFlag().
Copy link to clipboard
Copied
Ok I'm trying to replace the loader with my sprite at the very beginning like this:
public function FlagWave(sp:Sprite,windRate:Number=30){
var bm:BitmapData = new BitmapData(sp.width,sp.height);
bm.draw(sp, sp.transform.matrix);
_loadedBitmap = new Bitmap(bm);
init();
WIND_RATE = windRate;
}
but I get this error:
TypeError: Error #1009: Cannot access a property or method of a null object reference. And it is pointing to:
private function makeFlag(): void {
var stageWidth: Number = stage.stageWidth; ---- this line
...
What is wrong?
Sorry if it is very obvious but I'm new in this...
Copy link to clipboard
Copied
you're calling init() before your sprite is added to the stage. use
sp.addEventListener(Event.ADDED_TO_STAGE,init);
//and add an event argument to init:
function init(e:Event):etc
Copy link to clipboard
Copied
Thanks, it's working now.
Copy link to clipboard
Copied
you're welcome.
(p.s when using the adobe forums, please mark helpful/correct responses, if there are any.)
Find more inspiration, events, and resources on the new Adobe Community
Explore Now