Поскольку фильтр не масштабируется, значения его параметров всегда должны соответствовать пиксельным единицам. Следовательно, вы просто должны масштабировать значения фильтра так же, как объект. Для этого просто переведите единичный вектор (длина == 1) в системе координат объектов в глобальную систему координат, и расстояние будет вашим глобальным коэффициентом масштабирования для фильтров объекта.
Каждый раз, когда ваш объект перемещается или масштабируется, изменяйте любые значения фильтра, которые должны масштабироваться, и повторно применяйте фильтры. Вот пример класса документа, показывающий квадрат с фильтрами свечения и тени, масштабируемыми с ним, в то время как он вложен в другой масштабируемый контейнер. Я также добавил слушателя изменения размера сцены, чтобы держать квадрат в центре сцены.
Вставьте это в действия на основной временной шкале нового документа и запустите его. Обратите внимание, что масштаб расстояния и размера тени, а также размытие фильтра свечения также масштабируются. Вы даже можете добавить математику для учета вращения, если у вас есть разные значения размытия x и y.
import flash.display.Sprite;
import flash.filters.GlowFilter;
import flash.events.Event;
import flash.display.StageScaleMode;
import flash.utils.getTimer;
import flash.geom.Point;
import flash.filters.DropShadowFilter;
//Fix the scale of the stage
stage.scaleMode = flash.display.StageScaleMode.NO_SCALE;
stage.frameRate = 60;
//Create a small green square centered at the origin
var r:Sprite = new Sprite();
r.graphics.beginFill( 0x00ff00 );
r.graphics.drawRect( -5, -5, 10, 10 );
r.graphics.endFill();
//Nest it in a container
var container:Sprite = new Sprite();
container.addChild( r )
addChild( container );
//Apply a glow filter
var GLOW_BLUR:Number = 10;
var SHADOW_DIST:Number = 5;
var SHADOW_BLUR:Number = 2;
var dropshadow:DropShadowFilter = new DropShadowFilter( SHADOW_DIST, 45, 0, 1, SHADOW_BLUR, SHADOW_BLUR, 1, 3 ); //new GlowFilter( 0x000000, 0.5, GLOW_BLUR, GLOW_BLUR, 2, 3 );
var glow:GlowFilter = new GlowFilter( 0x0000ff, 1, GLOW_BLUR, GLOW_BLUR, 1, 3 ); //new GlowFilter( 0x000000, 0.5, GLOW_BLUR, GLOW_BLUR, 2, 3 );
r.filters = [glow,dropshadow];
addEventListener( Event.ENTER_FRAME, enterFrame, false, 0, true );
addEventListener( Event.RESIZE, stageResized, false, 0, true );
var t:int = getTimer();
stageResized( null );
function enterFrame( e:Event ):void
{
var cycle_length:Number = 2000;
var cycle:Number = (((getTimer() - t) % cycle_length) / cycle_length) * Math.PI * 2.0;
var scale:Number = 2 + Math.sin( cycle );
r.scaleX = r.scaleY = scale;
container.scaleX = container.scaleY = scale * 2;
container.rotation = cycle / (Math.PI / 180);
var p0:Point = new Point( 0, 0 );
var p1:Point = new Point( 1, 0 );
p0 = r.localToGlobal( p0 );
p1 = r.localToGlobal( p1 );
var globalScale:Number = Point.distance( p0, p1 );
dropshadow.blurX = dropshadow.blurY = SHADOW_BLUR * globalScale;
dropshadow.distance = SHADOW_DIST * globalScale;
glow.blurX = glow.blurY = GLOW_BLUR * globalScale;
r.filters = [glow,dropshadow];
}
function stageResized( e:Event ):void
{
container.x = (stage.stageWidth / 2);
container.y = (stage.stageHeight / 2);
}