3D Lightning!
模拟了一个电光效果,同样使用了上回文章提及到的DisplacementMapFilter类,并且解决了消耗过大的问题。原因是提供给DisplacementMapFilter的源图像太大,导致在处理的时候消耗了大量CPU。假如能够获得3D对象每一帧所的矩形区域,只对这个区域进行处理就能大大减少消耗了。如何才能获得3D对象的区域?我们知道每个3D对象都保存了所有顶点坐标,每个顶点坐标是一个Vertex3D类,这个Vertex3D类里面有一个顶点实例属性,他是vertex3DInstance类型,这是投影到屏幕的最终坐标。OK,就拿这些坐标来求区域吧。
public override function postRender():void
{
var maxX:Number = - Number.MAX_VALUE;
var minX:Number = Number.MAX_VALUE;
var maxY:Number = - Number.MAX_VALUE;
var minY:Number = Number.MAX_VALUE;
for each (var v:Vertex3D in d3d.geometry.vertices)
{
var vi:Vertex3DInstance = v.vertex3DInstance;
maxX = maxX > vi.x ? maxX : vi.x;
minX = minX < vi.x ? minX : vi.x;
maxY = maxY > vi.y ? maxY : vi.y;
minY = minY < vi.y ? minY : vi.y;
}
var sx:Number = layer.canvas.width * .5 + minX;
var sy:Number = layer.canvas.height * .5 - maxY - 10;
var w:Number = maxX - minX + 16;
var h:Number = maxY - minY + 52;
offset_array[0].x -= 4;
offset_array[1].x -= 1;
var b:BitmapData = new BitmapData(w, h);
b.perlinNoise(baseX, baseY, numOctaves, 64, stitch, fractalNoise, 1, false, offset_array);
perlinNoise_bmd.copyPixels(b, b.rect, new Point(sx - 8, sy - 21));
b.dispose();
b = null;
layer.canvas.applyFilter(layer.canvas, new Rectangle(sx, sy, w, h), new Point(sx, sy), filter);
layer.canvas.applyFilter(layer.canvas, new Rectangle(sx, sy, w, h), new Point(sx, sy), new GlowFilter(0xFFE956, 1, 5, 5, 6, 15));
}
{
var maxX:Number = - Number.MAX_VALUE;
var minX:Number = Number.MAX_VALUE;
var maxY:Number = - Number.MAX_VALUE;
var minY:Number = Number.MAX_VALUE;
for each (var v:Vertex3D in d3d.geometry.vertices)
{
var vi:Vertex3DInstance = v.vertex3DInstance;
maxX = maxX > vi.x ? maxX : vi.x;
minX = minX < vi.x ? minX : vi.x;
maxY = maxY > vi.y ? maxY : vi.y;
minY = minY < vi.y ? minY : vi.y;
}
var sx:Number = layer.canvas.width * .5 + minX;
var sy:Number = layer.canvas.height * .5 - maxY - 10;
var w:Number = maxX - minX + 16;
var h:Number = maxY - minY + 52;
offset_array[0].x -= 4;
offset_array[1].x -= 1;
var b:BitmapData = new BitmapData(w, h);
b.perlinNoise(baseX, baseY, numOctaves, 64, stitch, fractalNoise, 1, false, offset_array);
perlinNoise_bmd.copyPixels(b, b.rect, new Point(sx - 8, sy - 21));
b.dispose();
b = null;
layer.canvas.applyFilter(layer.canvas, new Rectangle(sx, sy, w, h), new Point(sx, sy), filter);
layer.canvas.applyFilter(layer.canvas, new Rectangle(sx, sy, w, h), new Point(sx, sy), new GlowFilter(0xFFE956, 1, 5, 5, 6, 15));
}
这样做起来,似乎很“别扭”。但本人实在想不到更能节省CPU消耗的方法了。希望有能力的朋友和我共同讨论。
另外,这里有一个2D方面的demo。想知道原理的,可以看看源码。
Preview:http://niuniuzhu.cn/p/Lighting