2008-04-17

Popup Modal MovieClip for Flash/AS3

Flex 有 PopUpManager 可以 pop-up window 或 custom component
Flash CS3/AS3 則沒有 :(
若只是用個 PopUpManager, 以 Flex 發佈後實在有點肥大...

我在網路上找了老半天, 只找到 Yahoo ASTRA Flash Components 裡提供的 AlertManager. 不過功能實在太陽春, 想說做點客制化, 改著改著幾乎跟重寫差不多了. 版權 follow BSD.

Demo:


ModalDisplayManager.as
/*
Copyright (c) 2008 Yahoo! Inc. All rights reserved.
The copyrights embodied in the content of this file are licensed under the BSD (revised) open source license

shinder modified
refer com.yahoo.astra.fl.managers.AlertManager

shinder.lin@gmail.com
http://qops.blogspot.com/
*/

package lin.shinder.fl.managers
{
import flash.display.DisplayObject;
import flash.display.MovieClip;
import flash.display.Graphics;
import flash.display.Stage;
import flash.display.StageScaleMode;
import flash.display.StageAlign;
import flash.events.Event;
import flash.events.MouseEvent;
import flash.filters.BitmapFilterQuality;
import flash.filters.BlurFilter;
import flash.filters.BitmapFilter;

public class ModalDisplayManager extends MovieClip
{
private static var _alertQueue:Array = [];
private static var _alert:MovieClip;
private static var _displayManager:ModalDisplayManager;
private static var _stage:Stage;
public static var overlayAlpha:Number = .16;
public static var modalBackgroundBlur:int = 3;
private static var _overlay:MovieClip;
protected var container:DisplayObject;
protected var parentFilters:Array;

public function ModalDisplayManager(container:DisplayObject)
{
if (! _displayManager) {
if (container != null) {
_stage = container.stage;
} else {
trace("ModalDisplayManager: the 1st parameter cannot be null !");
}
if ( _stage.scaleMode != StageScaleMode.NO_SCALE ) {
// trace("ModalDisplayManager prefers: stage.scaleMode = StageScaleMode.NO_SCALE !");
}
if ( _stage.align != StageAlign.TOP_LEFT ) {
trace("ModalDisplayManager prefers: stage.align = StageAlign.TOP_LEFT !");
}
_stage.addChild(this);
_stage.addEventListener(Event.RESIZE, stageResizeHandler);
_stage.addEventListener(Event.FULLSCREEN, stageResizeHandler);
}
}

public static function createModalDisplay(container:DisplayObject,
content:Class = null,
promp:Object = null):ModalDisplayManager
{
if (! _displayManager) {
_displayManager = new ModalDisplayManager(container);
}
_overlay = new MovieClip();
var g:Graphics = _overlay.graphics as Graphics;
g.beginFill(0xeeeeee, overlayAlpha);
g.moveTo(0,0);
g.lineTo(100, 0);
g.lineTo(100, 100);
g.lineTo(0, 100);
g.lineTo(0, 0);
g.endFill();
_displayManager.addChild(_overlay);

_overlay.stageResizeHandler = function() {
this.width = _stage.stageWidth;
this.height = _stage.stageHeight;
if (this._alert != null ) {
this._alert.x = (_stage.stageWidth-this._alert.width)/2;
this._alert.y = (_stage.stageHeight-this._alert.height)/2;
}
};

_alert = new content() as MovieClip;
_overlay._alert = _alert;
_overlay.stageResizeHandler();
if (_alert.init) {
_alert.init(promp);
} else {
// trace("ModalDisplayManager: the 2nd parameter should define a function named init(promp:Object) !");
}
_displayManager.addChild(_alert);
_displayManager.container = container;
var newFilters:Array = _displayManager.container.filters.concat();
var oldFilters:Array = _displayManager.container.filters.concat();

if(_alertQueue.length == 0) {
newFilters.push(_displayManager.getBlurFilter());
_displayManager.container.filters = newFilters;
}
for(var i:int=0; i < _alertQueue.length; i++) {
_alertQueue[i]['_alert'].filters = [_displayManager.getBlurFilter()];
}

var alertParams:Object = {
container:container,
content:content,
promp:promp,
_overlay:_overlay,
_alert:_alert,
_filters:oldFilters
};
_alertQueue.push(alertParams);
return _displayManager;
}

public function manageQueue():void
{
if(_alertQueue.length == 0){
return;
}
var obj:Object = _alertQueue.pop();
obj.container.filters = obj._filters;
_displayManager.removeChild(obj._alert);
_displayManager.removeChild(obj._overlay);
if(_alertQueue.length>0) {
_alertQueue[_alertQueue.length-1]['_alert'].filters = [];
}
}

public function getBlurFilter():BitmapFilter
{
var blurFilter:BlurFilter = new BlurFilter();
blurFilter.blurX = modalBackgroundBlur;
blurFilter.blurY = modalBackgroundBlur;
blurFilter.quality = BitmapFilterQuality.HIGH;
return blurFilter;
}

private function stageResizeHandler(evt:Event):void
{
for each(var o:Object in _alertQueue) {
o._overlay.stageResizeHandler();
}
}
}
}

Frame Actions:
import lin.shinder.fl.managers.ModalDisplayManager;
stage.align = StageAlign.TOP_LEFT;
b_btn.addEventListener(MouseEvent.CLICK, onClick);
y_btn.addEventListener(MouseEvent.CLICK, onClick);
function onClick(evt:MouseEvent):void
{
if (evt.currentTarget==b_btn) {
ModalDisplayManager.createModalDisplay(this, mc_gear);
} else {
ModalDisplayManager.createModalDisplay(this, mc_gear2, {a:"abc"});
ModalDisplayManager.createModalDisplay(this, mc_gear3);
}
}
測試範例原始檔

3 則留言:

匿名 提到...

您好,
function onClick(evt:MouseEvent):void
{
if (evt.currentTarget==a_btn) {
ModalDisplayManager.createModalDisplay(this, mc_gear);
}
}

这段代码中,mc_gear在主场景中的x、y坐标如何定位呢?

harumi 提到...

不好意思~想請教一下~
您所修改的彈出訊息視窗畫面的圖形,
是修改那個參數呢?
我看了好久都看不出來~可以麻煩指點一下嗎~
感謝您!!

Mishael 提到...

Hi, thanks for share this component!.. is easy and configurable! Greetings!

FB 留言