http://git-wip-us.apache.org/repos/asf/flex-asjs/blob/77148f4a/frameworks/projects/MX/src/main/flex/mx/controls/ToolTip.as ---------------------------------------------------------------------- diff --cc frameworks/projects/MX/src/main/flex/mx/controls/ToolTip.as index ab63cd4,0000000..99f6dd3 mode 100644,000000..100644 --- a/frameworks/projects/MX/src/main/flex/mx/controls/ToolTip.as +++ b/frameworks/projects/MX/src/main/flex/mx/controls/ToolTip.as @@@ -1,529 -1,0 +1,529 @@@ +//////////////////////////////////////////////////////////////////////////////// +// +// Licensed to the Apache Software Foundation (ASF) under one or more +// contributor license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright ownership. +// The ASF licenses this file to You under the Apache License, Version 2.0 +// (the "License"); you may not use this file except in compliance with +// the License. You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +//////////////////////////////////////////////////////////////////////////////// + +package mx.controls +{ + - COMPILE::AS3 ++COMPILE::SWF +{ + import flash.display.DisplayObject; + import flash.text.TextFieldAutoSize; + import flash.text.TextFormat; +} +COMPILE::JS +{ + import flex.display.DisplayObject; + import flex.text.TextFormat; +} +import mx.core.EdgeMetrics; +import mx.core.IFlexDisplayObject; +import mx.core.IFlexModuleFactory; +import mx.core.IFontContextComponent; +import mx.core.IRectangularBorder; +import mx.core.IToolTip; +import mx.core.IUITextField; +import mx.core.UIComponent; +import mx.core.UITextField; +import mx.core.mx_internal; +import mx.styles.ISimpleStyleClient; + +use namespace mx_internal; + +//-------------------------------------- +// Styles +//-------------------------------------- + +/* + Note: ToolTip is affected by the following styles: + + backgroundColor + borderColor + borderStyle + color + fontFamily + fontSize + fontStyle + fontWidth + paddingBottom + paddingLeft + paddingRight + paddingTop + shadowColor (when borderStyle is "toolTip") + textAlign + textDecoration +*/ + +include "../styles/metadata/ContainerBackgroundStyles.as" +include "../styles/metadata/BorderStyles.as" +include "../styles/metadata/LeadingStyle.as" +include "../styles/metadata/PaddingStyles.as" +include "../styles/metadata/TextStyles.as" + +/** + * Radius of component corners. + * + * @default 2 + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +[Style(name="cornerRadius", type="Number", format="Length", inherit="no", theme="halo, spark, mobile")] + +/** + * Number of pixels between the container's bottom border and its content area. + * The default value is -1, so the bottom border of the last header + * overlaps the Accordion container's bottom border. + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +[Style(name="paddingBottom", type="Number", format="Length", inherit="no")] + +/** + * Number of pixels between the container's top border and its content area. + * The default value is -1, so the top border of the first header + * overlaps the Accordion container's top border. + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +[Style(name="paddingTop", type="Number", format="Length", inherit="no")] + +/** + * Because this component does not define a skin for the mobile theme, Adobe + * recommends that you not use it in a mobile application. Alternatively, you + * can define your own mobile skin for the component. For more information, + * see <a href="http://help.adobe.com/en_US/flex/mobileapps/WS19f279b149e7481c698e85712b3011fe73-8000.html">Basics of mobile skinning</a>. + */ +[DiscouragedForProfile("mobileDevice")] + +/** + * The ToolTip control lets you provide helpful information to your users. + * When a user moves the mouse pointer over a graphical component, the ToolTip + * control pops up and displays text that provides information about the + * component. + * You can use ToolTips to guide users as they work with your application + * or customize the ToolTip controls to provide additional functionality. + * + * @see mx.managers.ToolTipManager + * @see mx.styles.CSSStyleDeclaration + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +public class ToolTip extends UIComponent implements IToolTip, IFontContextComponent +{ + include "../core/Version.as"; + + //-------------------------------------------------------------------------- + // + // Class properties + // + //-------------------------------------------------------------------------- + + [Inspectable(category="Other")] + + /** + * Maximum width in pixels for new ToolTip controls. + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public static var maxWidth:Number = 300; + + //-------------------------------------------------------------------------- + // + // Constructor + // + //-------------------------------------------------------------------------- + + /** + * Constructor. + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public function ToolTip() + { + super(); + - COMPILE::AS3 ++ COMPILE::SWF + { + // InteractiveObject variables. + // Make the ToolTip invisible to the mouse so that it doesn't + // interfere with the ToolTipManager's mouse-tracking. + mouseEnabled = false; + } + } + + //-------------------------------------------------------------------------- + // + // Variables + // + //-------------------------------------------------------------------------- + + /** + * The internal object that draws the border. + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + mx_internal var border:IFlexDisplayObject; + + //-------------------------------------------------------------------------- + // + // Properties + // + //-------------------------------------------------------------------------- + + //---------------------------------- + // borderMetrics + //---------------------------------- + + /** + * @private + */ + private function get borderMetrics():EdgeMetrics + { + if (border is IRectangularBorder) + return IRectangularBorder(border).borderMetrics; + + return EdgeMetrics.EMPTY; + } + + //---------------------------------- + // fontContext + //---------------------------------- + + /** + * @private + */ + public function get fontContext():IFlexModuleFactory + { + return moduleFactory; + } + + /** + * @private + */ + public function set fontContext(moduleFactory:IFlexModuleFactory):void + { + this.moduleFactory = moduleFactory; + } + + //---------------------------------- + // text + //---------------------------------- + + /** + * @private + * Storage for the text property. + */ + private var _text:String; + + /** + * @private + */ + private var textChanged:Boolean; + + /** + * The text displayed by the ToolTip. + * + * @default null + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public function get text():String + { + return _text; + } + + /** + * @private + */ + public function set text(value:String):void + { + _text = value; + textChanged = true; + + invalidateProperties(); + invalidateSize(); + invalidateDisplayList(); + } + + //---------------------------------- + // textField + //---------------------------------- + + /** + * The internal UITextField that renders the text of this ToolTip. + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + protected var textField:IUITextField; + + //-------------------------------------------------------------------------- + // + // Overridden methods + // + //-------------------------------------------------------------------------- + + /** + * @private + */ + override protected function createChildren():void + { + super.createChildren(); + + // Create the border/background. + createBorder(); + + // Create the TextField that displays the tooltip text. + createTextField(-1); + } + + /** + * @private + */ + override protected function commitProperties():void + { + super.commitProperties(); + + // if the font changed and we already created the label, we will need to + // destory it so it can be re-created, possibly in a different swf context. + if (hasFontContextChanged() && textField != null) + { + var index:int = getChildIndex(DisplayObject(textField)); + removeTextField(); + createTextField(index); + invalidateSize(); + textChanged = true; + } + + if (textChanged) + { + // In general, we want the ToolTip style to be applied. + // However, we don't want leftMargin and rightMargin + // of the TextField's TextFormat to be set to the + // paddingLeft and paddingRight of the ToolTip style. + // We want these styles to affect the space between the + // TextField and the border, but not the space within + // the TextField. + var textFormat:TextFormat = textField.getTextFormat(); + textFormat.leftMargin = 0; + textFormat.rightMargin = 0; + textField.defaultTextFormat = textFormat; + + textField.text = _text; + textChanged = false; + } + } + + /** + * @private + */ + override protected function measure():void + { + super.measure(); + + var bm:EdgeMetrics = borderMetrics; + + var leftInset:Number = bm.left + getStyle("paddingLeft"); + var topInset:Number = bm.top + getStyle("paddingTop"); + var rightInset:Number = bm.right + getStyle("paddingRight"); + var bottomInset:Number = bm.bottom + getStyle("paddingBottom"); + + var widthSlop:Number = leftInset + rightInset; + var heightSlop:Number = topInset + bottomInset; + + textField.wordWrap = false; + + if (textField.textWidth + widthSlop > ToolTip.maxWidth) + { + textField.width = ToolTip.maxWidth - widthSlop; + textField.wordWrap = true; + } + + measuredWidth = textField.width + widthSlop; + measuredHeight = textField.height + heightSlop; + } + + /** + * @private + */ + override protected function updateDisplayList(unscaledWidth:Number, + unscaledHeight:Number):void + { + super.updateDisplayList(unscaledWidth, unscaledHeight); + + var bm:EdgeMetrics = borderMetrics; + + var leftInset:Number = bm.left + getStyle("paddingLeft"); + var topInset:Number = bm.top + getStyle("paddingTop"); + var rightInset:Number = bm.right + getStyle("paddingRight"); + var bottomInset:Number = bm.bottom + getStyle("paddingBottom"); + + var widthSlop:Number = leftInset + rightInset; + var heightSlop:Number = topInset + bottomInset; + + border.setActualSize(unscaledWidth, unscaledHeight); + + textField.move(leftInset, topInset); + textField.setActualSize(unscaledWidth - widthSlop, unscaledHeight - heightSlop); + } + + /** + * @private + */ + override public function styleChanged(styleProp:String):void + { + // This will take care of doing invalidateSize() if styleProp + // is "styleName" or a registered layout style such as "borderStyle". + super.styleChanged(styleProp); + + // However, if the borderStyle changes from "errorTipAbove" to + // "errorTipBelow" or vice versa, the measured size won't change. + // (The pointy part of the skin simply changes from the bottom + // to the top or vice versa.) This means that the LayoutManager + // won't call updateDisplayList() because the size hasn't changed. + // But the TextField has to be repositioned, so we need to + // invalidate the layout as well as the size. + if (styleProp == "styleName" || + styleProp == "borderSkin" || + styleProp == null) + { + //if the border skin has changed then rebuild it. + if(border) + { + removeChild(DisplayObject(border)); + border = null; + } + + createBorder(); + } + else if (styleProp == "borderStyle") + { + invalidateDisplayList(); + } + } + + //-------------------------------------------------------------------------- + // + // Methods + // + //-------------------------------------------------------------------------- + + /** + * @private + * Creates the text field child and adds it as a child of this component. + * + * @param childIndex The index of where to add the child. + * If -1, the text field is appended to the end of the list. + */ + mx_internal function createTextField(childIndex:int):void + { + if (!textField) + { + textField = IUITextField(createInFontContext(UITextField)); + - COMPILE::AS3 ++ COMPILE::SWF + { + textField.autoSize = TextFieldAutoSize.LEFT; + textField.mouseEnabled = false; + textField.multiline = true; + textField.selectable = false; + textField.wordWrap = false; + textField.styleName = this; + } + + if (childIndex == -1) + addChild(DisplayObject(textField)); + else + addChildAt(DisplayObject(textField), childIndex); + } + } + + /** + * @private + * Removes the text field from this component. + */ + mx_internal function removeTextField():void + { + if (textField) + { + removeChild(DisplayObject(textField)); + textField = null; + } + } + + + /** + * @private + */ + mx_internal function getTextField():IUITextField + { + return textField; + } + + /** + * @private + */ + private function createBorder():void + { + if (!border) + { + var borderClass:Class = getStyle("borderSkin"); + + if (borderClass != null) + { + border = new borderClass(); + + if (border is ISimpleStyleClient) + ISimpleStyleClient(border).styleName = this; + + // Add the border behind all the children. + addChildAt(DisplayObject(border), 0); + + invalidateDisplayList(); + } + } + } +} + +}
http://git-wip-us.apache.org/repos/asf/flex-asjs/blob/77148f4a/frameworks/projects/MX/src/main/flex/mx/core/Application.as ---------------------------------------------------------------------- diff --cc frameworks/projects/MX/src/main/flex/mx/core/Application.as index ea036f0,0000000..431e56b mode 100644,000000..100644 --- a/frameworks/projects/MX/src/main/flex/mx/core/Application.as +++ b/frameworks/projects/MX/src/main/flex/mx/core/Application.as @@@ -1,1905 -1,0 +1,1905 @@@ +//////////////////////////////////////////////////////////////////////////////// +// +// Licensed to the Apache Software Foundation (ASF) under one or more +// contributor license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright ownership. +// The ASF licenses this file to You under the Apache License, Version 2.0 +// (the "License"); you may not use this file except in compliance with +// the License. You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +//////////////////////////////////////////////////////////////////////////////// + +package mx.core +{ + - COMPILE::AS3 ++COMPILE::SWF +{ + import flash.display.DisplayObject; + import flash.display.InteractiveObject; + import flash.events.ContextMenuEvent; + import flash.events.ErrorEvent; + import flash.events.Event; + import flash.external.ExternalInterface; + import flash.net.URLRequest; + import flash.net.navigateToURL; + import flash.system.Capabilities; + import flash.ui.ContextMenu; + import flash.ui.ContextMenuItem; + import flash.utils.setInterval; +} +COMPILE::JS +{ + import flex.display.DisplayObject; + import flex.display.InteractiveObject; + import flex.events.Event; +} + +import mx.containers.utilityClasses.ApplicationLayout; +import mx.effects.EffectManager; +import mx.events.FlexEvent; +import mx.managers.FocusManager; +import mx.managers.IActiveWindowManager; +import mx.managers.ILayoutManager; +import mx.managers.ISystemManager; +import mx.styles.CSSStyleDeclaration; +import mx.styles.IStyleClient; +import mx.utils.LoaderUtil; +import mx.utils.Platform; + +use namespace mx_internal; + +//-------------------------------------- +// Events +//-------------------------------------- + +/** + * Dispatched after the Application has been initialized, + * processed by the LayoutManager, and attached to the display list. + * + * @eventType mx.events.FlexEvent.APPLICATION_COMPLETE + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +[Event(name="applicationComplete", type="mx.events.FlexEvent")] + +/** + * Dispatched when an HTTPService call fails. + * + * @eventType flash.events.ErrorEvent.ERROR + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +[Event(name="error", type="flash.events.ErrorEvent")] + +//-------------------------------------- +// Styles +//-------------------------------------- + +include "../styles/metadata/ModalTransparencyStyles.as"; + +/** + * Specifies the alpha transparency values used for the background gradient fill of the application. + * You should set this to an Array of two numbers. + * Elements 0 and 1 specify the start and end values for an alpha gradient. + * + * @default [ 1.0, 1.0 ] + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +[Style(name="backgroundGradientAlphas", type="Array", arrayType="Number", inherit="no", theme="halo")] + +/** + * Specifies the colors used to tint the background gradient fill of the application. + * You should set this to an Array of two uint values that specify RGB colors. + * Elements 0 and 1 specify the start and end values for a color gradient. + * For a solid-color background, set the same color value for elements 0 and 1. + * A value of <code>undefined</code> means background gradient is generated + * based on the <code>backgroundColor</code> property. + * + * @default undefined + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +[Style(name="backgroundGradientColors", type="Array", arrayType="uint", format="Color", inherit="no", theme="halo")] + +/** + * Number of pixels between the application's bottom border + * and its content area. + * + * @default 24 + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +[Style(name="paddingBottom", type="Number", format="Length", inherit="no")] + +/** + * Number of pixels between the application's top border + * and its content area. + * + * @default 24 + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +[Style(name="paddingTop", type="Number", format="Length", inherit="no")] + +//-------------------------------------- +// Excluded APIs +//-------------------------------------- + +[Exclude(name="direction", kind="property")] +[Exclude(name="icon", kind="property")] +[Exclude(name="label", kind="property")] +[Exclude(name="tabIndex", kind="property")] +[Exclude(name="toolTip", kind="property")] +[Exclude(name="x", kind="property")] +[Exclude(name="y", kind="property")] + +//-------------------------------------- +// Other metadata +//-------------------------------------- + +/** + * The frameworks must be initialized by SystemManager. + * This factoryClass will be automatically subclassed by any + * MXML applications that don't explicitly specify a different + * factoryClass. + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +[Frame(factoryClass="mx.managers.SystemManager")] + +[ResourceBundle("core")] + +[Alternative(replacement="spark.components.Application", since="4.0")] + +/** + * Flex defines a default, or Application, container that lets you start + * adding content to your application without explicitly defining + * another container. + * Flex creates this container from the <code><mx:Application></code> + * tag, the first tag in an MXML application file. + * While you might find it convenient to use the Application container + * as the only container in your application, in most cases you explicitly + * define at least one more container before you add any controls + * to your application. + * + * <p>Applications support a predefined plain style that sets + * a white background, left alignment, and removes all margins. + * To use this style, do the following:</p> + * + * <pre> + * <mx:Application styleName="plain" /> + * </pre> + * + * <p>This is equivalent to setting the following style attributes:</p> + * + * <pre> + * backgroundColor="0xFFFFFF" + * horizontalAlign="left" + * paddingLeft="0" + * paddingTop="0" + * paddingBottom="0" + * paddingRight="0" + * </pre> + * + * @mxml + * + * <p>The <code><mx:Application></code> tag inherits all of the tag + * attributes of its superclass and adds the following tag attributes:</p> + * + * <pre> + * <mx:Application + * <strong>Properties</strong> + * application="<i>No default</i>" + * controlBar="null" + * frameRate="24" + * historyManagementEnabled="true|false" + * layout="vertical|horizontal|absolute" + * pageTitle"<i>No default</i>" + * preloader="<i>No default</i>" + * resetHistory="false|true" + * scriptRecursionLimit="1000" + * scriptTimeLimit="60" + * usePreloader="true|false" + * viewSourceURL="" + * xmlns:<i>No default</i>="<i>No default</i>" + * + * <strong>Styles</strong> + * backgroundGradientAlphas="[ 1.0, 1.0 ]" + * backgroundGradientColors="undefined" + * horizontalAlign="center|left|right" + * horizontalGap="8" + * modalTransparency="0.5" + * modalTransparencyBlur="3" + * modalTransparencyColor="#DDDDDD" + * modalTransparencyDuration="100" + * paddingBottom="24" + * paddingTop="24" + * verticalAlign="top|bottom|middle" + * verticalGap="6" + * + * <strong>Events</strong> + * applicationComplete="<i>No default</i>" + * error="<i>No default</i>" + * /> + * </pre> + * + * @includeExample examples/SimpleApplicationExample.mxml + * + * @see mx.managers.CursorManager + * @see mx.managers.LayoutManager + * @see mx.managers.SystemManager + * @see flash.events.EventDispatcher + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ +public class Application extends LayoutContainer +{ + include "../core/Version.as"; + + //-------------------------------------------------------------------------- + // + // Class variables + // + //-------------------------------------------------------------------------- + + /** + * @private + */ + mx_internal static var useProgressiveLayout:Boolean = false; + + //-------------------------------------------------------------------------- + // + // Class properties + // + //-------------------------------------------------------------------------- + + /** + * A reference to the top-level application. + * + * <p>In general, there can be a hierarchy of Application objects, + * because an Application can use a SWFLoader control to dynamically + * load another Application. + * The <code>parentApplication</code> property of a UIComponent can be + * used to access the sub-Application in which that UIComponent lives, + * and to walk up the hierarchy to the top-level Application.</p> + * + * <p>This property has been deprecated starting in Flex4. Note that this + * property will still return applications of type mx.core.Application and + * mx.core.WindowedApplication as in previous versions. Starting in Flex 4 + * it will also return applications of type spark.components.Application or + * spark.components.WindowedApplication.</p> + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + /* + * Note: here are two reasons that 'application' is typed as Object + * rather than as Application. The first is for consistency with + * the 'parentApplication' property of UIComponent. That property is not + * typed as Application because it would make UIComponent dependent + * on Application, slowing down compile times not only for SWCs + * for also for MXML and AS components. Second, if it were typed + * as Application, authors would not be able to access properties + * and methods in the <Script> of their <Application> without + * casting it to their application's subclass, as in + * MyApplication(Application.application).myAppMethod(). + * Therefore we decided to dispense with strict typing for + * 'application'. + */ + [Deprecated(replacement="FlexGlobals.topLevelApplication", since="4.0")] + + public static function get application():Object + { + return FlexGlobals.topLevelApplication; + } + + //-------------------------------------------------------------------------- + // + // Constructor + // + //-------------------------------------------------------------------------- + + /** + * Constructor. + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public function Application() + { + UIComponentGlobals.layoutManager = ILayoutManager( + Singleton.getInstance("mx.managers::ILayoutManager")); + UIComponentGlobals.layoutManager.usePhasedInstantiation = true; + + if (!FlexGlobals.topLevelApplication) + FlexGlobals.topLevelApplication = this; + + super(); + + layoutObject = new ApplicationLayout(); + layoutObject.target = this; + boxLayoutClass = ApplicationLayout; + + showInAutomationHierarchy = true; + // Flex's auto-generated init() override has set the + // documentDescriptor property for the application object. + // We get the id and the creationPolicy, which we want to + // set very early, from that descriptor. + + initResizeBehavior(); + } + + //-------------------------------------------------------------------------- + // + // Variables + // + //-------------------------------------------------------------------------- + + /** + * @private + */ + private var resizeHandlerAdded:Boolean = false; + + /** + * @private + */ + private var percentBoundsChanged:Boolean; + + /** + * @private + * Placeholder for Preloader object reference. + */ + private var preloadObj:Object; + + /** + * @private + * Used in progressive layout. + */ + private var creationQueue:Array = []; + + /** + * @private + * Used in progressive layout. + */ + private var processingCreationQueue:Boolean = false; + + /** + * @private + * The application's view metrics. + */ + private var _applicationViewMetrics:EdgeMetrics; + + /** + * @private + * This flag indicates whether the width of the Application instance + * can change or has been explicitly set by the developer. + * When the stage is resized we use this flag to know whether the + * width of the Application should be modified. + */ + private var resizeWidth:Boolean = true; + + /** + * @private + * This flag indicates whether the height of the Application instance + * can change or has been explicitly set by the developer. + * When the stage is resized we use this flag to know whether the + * height of the Application should be modified. + */ + private var resizeHeight:Boolean = true; + + /** + * @private + */ + private var synchronousResize:Boolean = false; + + /** + * @private + * (Possibly null) reference to the View Source context menu item, + * so that we can update it for runtime localization. + */ - COMPILE::AS3 ++ COMPILE::SWF + private var viewSourceCMI:ContextMenuItem; + + //-------------------------------------------------------------------------- + // + // Compile-time pseudo-properties + // + //-------------------------------------------------------------------------- + + // These declarations correspond to the MXML-compile-time attributes + // allowed on the <mx:Application> tag. These attributes affect the MXML + // compiler, but they aren't actually used in the runtime framework. + // The declarations appear here in order to provide metadata about these + // attributes for Flash Builder. + + //---------------------------------- + // frameRate + //---------------------------------- + + [Inspectable(defaultValue="24")] + + /** + * Specifies the frame rate of the application. + * <p>Note: This property cannot be set by ActionScript code; it must be set in MXML code.</p> + * + * @default 24 + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public var frameRate:Number; + + //---------------------------------- + // pageTitle + //---------------------------------- + + /** + * Specifies a string that appears in the title bar of the browser. + * This property provides the same functionality as the + * HTML <code><title></code> tag. + * + * <p>Note: This property cannot be set by ActionScript code; it must be set in MXML code. + * The value set in MXML code is designed to be used by a tool to update the HTML templates + * provided with the SDK.</p> + * + * @default "" + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public var pageTitle:String; + + //---------------------------------- + // preloader + //---------------------------------- + + [Inspectable(defaultValue="mx.preloaders.DownloadProgressBar")] + + /** + * The application container supports an application preloader that + * uses a download progress bar to show the download and initialization progress + * of an application SWF file. + * By default, the application preloader is enabled. + * The preloader tracks how many bytes have been downloaded and continually + * updates the progress bar. + * + * <p>Use this property to specify the path of a component that + * defines a custom progress indicator. + * To create a custom progress indicator, you typically create a subclass of the + * DownloadProgressBar class, or create a subclass of + * the flash.display.Sprite class that implements the + * mx.preloaders.IPreloaderDisplay interface. </p> + * + * <p><b>Note:</b> This property cannot be set by ActionScript code; it must be set in MXML code.</p> + * + * @see mx.preloaders.DownloadProgressBar + * @see flash.display.Sprite + * @see mx.preloaders.IPreloaderDisplay + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public var preloader:Object; + + //---------------------------------- + // preloaderChromeColor + //---------------------------------- + + [Inspectable(defaultValue="0xCCCCCC", format="Color")] + + /** + * Specifies the base color used by the default preloader component. This property + * has the same effect as the <code>chromeColor</code> style used by the Spark skins. + * Typically this property should be set to the same value as the <code>chromeColor</code> + * style used by the application. + * + * <p>Note: This property cannot be set by ActionScript code; it must be set in MXML code.</p> + * + * @langversion 3.0 + * @playerversion Flash 10 + * @playerversion AIR 1.5 + * @productversion Flex 4 + */ + + /* This property is not directly read by the download progress bar (preloader) + * component. It is here so that it gets picked up by the compiler and included + * in the info() structure for the generated system manager. The download progress bar + * grabs the value directly from the info() structure. */ + public var preloaderChromeColor:uint; + + //---------------------------------- + // scriptRecursionLimit + //---------------------------------- + + [Inspectable(defaultValue="1000")] + + /** + * Specifies the maximum depth of Flash Player or AIR + * call stack before the player stops. + * This is essentially the stack overflow limit. + * <p>Note: This property cannot be set by ActionScript code; it must be set in MXML code.</p> + * + * @default 1000 + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public var scriptRecursionLimit:int; + + //---------------------------------- + // scriptTimeLimit + //---------------------------------- + + [Inspectable(defaultValue="60")] + + /** + * Specifies the maximum duration, in seconds, that an ActionScript + * event handler can execute before Flash Player or AIR assumes + * that it is hung, and aborts it. + * The maximum allowable value that you can set is 60 seconds. + * + * @default 60 + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public var scriptTimeLimit:Number; + + //---------------------------------- + // usePreloader + //---------------------------------- + + [Inspectable(defaultValue="true")] + + /** + * If <code>true</code>, specifies to display the application preloader. + * <p>Note: This property cannot be set by ActionScript code; it must be set in MXML code.</p> + * + * @default true + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public var usePreloader:Boolean; + + //-------------------------------------------------------------------------- + // + // Overridden properties (to block metadata from superclasses) + // + //-------------------------------------------------------------------------- + + //---------------------------------- + // enabled + //---------------------------------- + + [Inspectable(category="General", enumeration="true,false", defaultValue="true")] + + /** + * @private + */ + override public function set enabled(value:Boolean):void + { + super.enabled = value; + + // controlBar must be enabled/disabled when this container is. + if (controlBar) + controlBar.enabled = value; + } + + //---------------------------------- + // icon + //---------------------------------- + + [Inspectable(environment="none")] + + /** + * @private + */ + override public function set icon(value:Class):void + { + } + + //---------------------------------- + // id + //---------------------------------- + + [Inspectable(environment="none")] + + /** + * @private + */ + override public function get id():String + { - COMPILE::AS3 ++ COMPILE::SWF + { + if (!super.id && + this == FlexGlobals.topLevelApplication && + ExternalInterface.available) + { + return ExternalInterface.objectID; + } + } + + return super.id; + } + + //---------------------------------- + // label + //---------------------------------- + + [Inspectable(environment="none")] + + /** + * @private + */ + override public function set label(value:String):void + { + } + + //---------------------------------- + // percentHeight + //---------------------------------- + + /** + * @private + */ + override public function set percentHeight(value:Number):void + { + if (value != super.percentHeight) + { + super.percentHeight = value; + percentBoundsChanged = true; + invalidateProperties(); + } + } + + //---------------------------------- + // percentWidth + //---------------------------------- + + /** + * @private + */ + override public function set percentWidth(value:Number):void + { + if (value != super.percentWidth) + { + super.percentWidth = value; + percentBoundsChanged = true; + invalidateProperties(); + } + } + + //---------------------------------- + // tabIndex + //---------------------------------- + + [Inspectable(environment="none")] + + /** + * @private + */ + override public function set tabIndex(value:int):void + { + } + + //---------------------------------- + // toolTip + //---------------------------------- + + [Inspectable(environment="none")] + + /** + * @private + */ + override public function set toolTip(value:String):void + { + } + + //---------------------------------- + // viewMetrics + //---------------------------------- + + /** + * @private + * Returns the thickness of the edges of the object, including + * the border, title bar and scroll bars, if visible. + * + * @return EdgeMetrics object with left, right, top, and bottom + * properties containing the edge thickness, in pixels. + */ + override public function get viewMetrics():EdgeMetrics + { + // This function needs to return an object. + // Rather than allocating a new one each time, + // we'll allocate one once and then hold a reference to it. + if (!_applicationViewMetrics) + _applicationViewMetrics = new EdgeMetrics(); + var vm:EdgeMetrics = _applicationViewMetrics; + + var o:EdgeMetrics = super.viewMetrics; + + var thickness:Number = getStyle("borderThickness"); + + vm.left = o.left; + vm.top = o.top; + vm.right = o.right; + vm.bottom = o.bottom; + + if (controlBar && controlBar.includeInLayout) + { + vm.top -= thickness; + vm.top += Math.max(controlBar.getExplicitOrMeasuredHeight(), + thickness); + } + + return vm; + } + + //-------------------------------------------------------------------------- + // + // Properties + // + //-------------------------------------------------------------------------- + + /** + * The ApplicationControlBar for this Application. + * + * @see mx.containers.ApplicationControlBar + * @default null + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public var controlBar:IUIComponent; + + //---------------------------------- + // historyManagementEnabled + //---------------------------------- + + [Inspectable(defaultValue="true")] + + /** + * If <code>false</code>, the history manager will be disabled. + * Setting to false is recommended when using the BrowserManager. + * + * @default true + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public var historyManagementEnabled:Boolean = true; + + //---------------------------------- + // parameters + //---------------------------------- + + /** + * @private + * Storage for the parameters property. + * This variable is set in the initialize() method of SystemManager. + */ + mx_internal var _parameters:Object; + + /** + * The parameters property returns an Object containing name-value + * pairs representing the parameters provided to this Application. + * + * <p>You can use a for-in loop to extract all the names and values + * from the parameters Object.</p> + * + * <p>There are two sources of parameters: the query string of the + * Application's URL, and the value of the FlashVars HTML parameter + * (this affects only the main Application).</p> + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public function get parameters():Object + { + return _parameters; + } + + //---------------------------------- + // resetHistory + //---------------------------------- + + [Inspectable(defaultValue="true")] + + /** + * If <code>true</code>, the application's history state is reset + * to its initial state whenever the application is reloaded. + * Applications are reloaded when any of the following occurs: + * <ul> + * <li>The user clicks the browser's Refresh button.</li> + * <li>The user navigates to another web page, and then clicks + * the browser's Back button to return to the Flex application.</li> + * <li>The user loads a Flex application from the browser's + * Favorites or Bookmarks menu.</li> + * </ul> + * + * @default true + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public var resetHistory:Boolean = true; + + //---------------------------------- + // unscaledHeight + //---------------------------------- + + /** + * @private + */ + override mx_internal function setUnscaledHeight(value:Number):void + { + // we invalidate so we can properly add/remove the resize + // event handler (SDK-12664) + invalidateProperties(); + + super.setUnscaledHeight(value); + } + + //---------------------------------- + // unscaledWidth + //---------------------------------- + + /** + * @private + */ + override mx_internal function setUnscaledWidth(value:Number):void + { + // we invalidate so we can properly add/remove the resize + // event handler (SDK-12664) + invalidateProperties(); + + super.setUnscaledWidth(value); + } + + //---------------------------------- + // url + //---------------------------------- + + /** + * @private + * Storage for the url property. + * This variable is set in the initialize() method. + */ + mx_internal var _url:String; + + /** + * The URL from which this Application's SWF file was loaded. + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public function get url():String + { + return _url; + } + + //---------------------------------- + // usePadding + //---------------------------------- + + /** + * @private + */ + override mx_internal function get usePadding():Boolean + { + // We use padding for all layouts except absolute. + return layout != ContainerLayout.ABSOLUTE; + } + + //---------------------------------- + // viewSourceURL + //---------------------------------- + + /** + * @private + * Storage for viewSourceURL property. + */ + private var _viewSourceURL:String; + + /** + * URL where the application's source can be viewed. Setting this + * property inserts a "View Source" menu item into the application's + * default context menu. Selecting the menu item opens the + * <code>viewSourceURL</code> in a new window. + * + * <p>You must set the <code>viewSourceURL</code> property + * using MXML, not using ActionScript, as the following example shows:</p> + * + * <pre> + * <mx:Application viewSourceURL="http://path/to/source"> + * ... + * </mx:Application></pre> + * + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public function get viewSourceURL():String + { + return _viewSourceURL; + } + + /** + * @private + */ + public function set viewSourceURL(value:String):void + { + _viewSourceURL = value; + } + + //-------------------------------------------------------------------------- + // + // Overridden methods: DisplayObjectContainer + // + //-------------------------------------------------------------------------- + + /** + * @private + */ + override public function getChildIndex(child:DisplayObject):int + { + // For control bar focus management, return -1 to indicate + // "before the first child". + if (controlBar && child == controlBar) + return -1; + + return super.getChildIndex(child); + } + + //-------------------------------------------------------------------------- + // + // Overridden methods: UIComponent + // + //-------------------------------------------------------------------------- + + /** + * @private + */ + override protected function invalidateParentSizeAndDisplayList():void + { + if (!includeInLayout) + return; + + var p:IInvalidating = parent as IInvalidating; + if (!p) + { + if (parent is ISystemManager) + ISystemManager(parent).invalidateParentSizeAndDisplayList(); + + return; + } + + super.invalidateParentSizeAndDisplayList(); + } + + /** + * @private + */ + override public function initialize():void + { + // trace("app initialize app"); + + var sm:ISystemManager = systemManager; + - COMPILE::AS3 ++ COMPILE::SWF + { + _url = LoaderUtil.normalizeURL(root.loaderInfo); + _parameters = root.loaderInfo.parameters; + } + COMPILE::JS + { + _url = LoaderUtil.normalizeURL(window.location.href); + _parameters = makeParameters(window.location.search); + } + + initManagers(sm); + _descriptor = null; + + if (documentDescriptor) + { + creationPolicy = documentDescriptor.properties.creationPolicy; + if (creationPolicy == null || creationPolicy.length == 0) + creationPolicy = ContainerCreationPolicy.AUTO; + + var properties:Object = documentDescriptor.properties; + + if (properties.width != null) + { + width = properties.width; + delete properties.width; + } + if (properties.height != null) + { + height = properties.height; + delete properties.height; + } + + // Flex auto-generated code has already set up events. + documentDescriptor.events = null; + } + + // Setup the default context menu here. This allows the application + // developer to override it in the initialize event, if desired. - COMPILE::AS3 ++ COMPILE::SWF + { + initContextMenu(); + } + + super.initialize(); + + addEventListener(Event.ADDED, addedHandler); + - COMPILE::AS3 ++ COMPILE::SWF + { + // Stick a timer here so that we will execute script every 1.5s + // no matter what. + // This is strictly for the debugger to be able to halt. + // Note: isDebugger is true only with a Debugger Player. + if (sm.isTopLevelRoot() && Capabilities.isDebugger == true) + setInterval(debugTickler, 1500); + } + } + + /** + * @private + */ + override protected function commitProperties():void + { + super.commitProperties(); + + resizeWidth = isNaN(explicitWidth); + resizeHeight = isNaN(explicitHeight); + + if (resizeWidth || resizeHeight) + { + resizeHandler(new Event(Event.RESIZE)); + + if (!resizeHandlerAdded) + { + // weak reference + COMPILE::LATER + { + systemManager.addEventListener(Event.RESIZE, resizeHandler, false, 0, true); + } + systemManager.addEventListener(Event.RESIZE, resizeHandler); + + resizeHandlerAdded = true; + } + } + else + { + if (resizeHandlerAdded) + { + systemManager.removeEventListener(Event.RESIZE, resizeHandler); + resizeHandlerAdded = false; + } + } + + if (percentBoundsChanged) + { + updateBounds(); + percentBoundsChanged = false; + } + } + + /** + * @private + * Calculates the preferred, mininum and maximum sizes of the + * Application. See the <code>UIComponent.measure()</code> method for more + * information. + * <p> + * The <code>measure()</code> method first calls + * <code>Box.measure()</code> method, then makes sure the + * <code>measuredWidth</code> and <code>measuredMinWidth</code> + * are wide enough to display the application's control bar. + */ + override protected function measure():void + { + super.measure(); + + var bm:EdgeMetrics = borderMetrics; + + if (controlBar && controlBar.includeInLayout) + { + var controlWidth:Number = controlBar.getExplicitOrMeasuredWidth() + + bm.left + bm.right; + + measuredWidth = Math.max(measuredWidth, controlWidth); + measuredMinWidth = Math.max(measuredMinWidth, controlWidth); + } + } + + /** + * @private + */ + override protected function updateDisplayList(unscaledWidth:Number, + unscaledHeight:Number):void + { + super.updateDisplayList(unscaledWidth, unscaledHeight); + + // Wait to layout the border after all the children + // have been positioned. + createBorder(); + } + + /** + * @private + */ + override public function styleChanged(styleProp:String):void + { + super.styleChanged(styleProp); + + if (styleProp == "backgroundColor" && + getStyle("backgroundImage") == getStyle("defaultBackgroundImage")) + { + clearStyle("backgroundImage"); + } + } + + /** + * @private + * Prepare the Object for printing. + * + * @see mx.printing.FlexPrintJob + */ + override public function prepareToPrint(target:IFlexDisplayObject):Object + { + var objData:Object = {}; + + if (target == this) + { + objData.width = width; + objData.height = height; + + COMPILE::LATER + { + objData.verticalScrollPosition = verticalScrollPosition; + objData.horizontalScrollPosition = horizontalScrollPosition; + + objData.horizontalScrollBarVisible = (horizontalScrollBar != null); + objData.verticalScrollBarVisible = (verticalScrollBar != null); + + objData.whiteBoxVisible = (whiteBox != null); + + setActualSize(measuredWidth, measuredHeight); + + horizontalScrollPosition = 0; + verticalScrollPosition = 0; + + if (horizontalScrollBar) + horizontalScrollBar.visible = false; + + if (verticalScrollBar) + verticalScrollBar.visible = false; + } + if (whiteBox) + whiteBox.visible = false; + + updateDisplayList(unscaledWidth, unscaledHeight); + } + + objData.scrollRect = super.prepareToPrint(target); + + return objData; + } + + /** + * @private + * Should be called after printing is done for post-processing and clean up. + * + * @see mx.printing.FlexPrintJob + */ + override public function finishPrint(obj:Object, target:IFlexDisplayObject):void + { + if (target == this) + { + setActualSize(obj.width, obj.height); + + COMPILE::LATER + { + if (horizontalScrollBar) + horizontalScrollBar.visible = obj.horizontalScrollBarVisible; + if (verticalScrollBar) + verticalScrollBar.visible = obj.verticalScrollBarVisible; + + if (whiteBox) + whiteBox.visible = obj.whiteBoxVisible; + + horizontalScrollPosition = obj.horizontalScrollPosition; + verticalScrollPosition = obj.verticalScrollPosition; + } + updateDisplayList(unscaledWidth, unscaledHeight); + } + + // obj is the Object created in prepare to print above, + // it just stores the scrollRect Rectangle object sent from Container + // obj doesnt have to be DisplayObject + super.finishPrint(obj.scrollRect, target); + } + + /** + * @private + * Application also handles themeColor defined + * on the global selector. + */ + override mx_internal function initThemeColor():Boolean + { + if (FlexVersion.compatibilityVersion >= FlexVersion.VERSION_4_0) + return true; + + var result:Boolean = super.initThemeColor(); + + if (!result) + { + var tc:Object; // Can be number or string + var rc:Number; + var sc:Number; + var globalSelector:CSSStyleDeclaration = + styleManager.getMergedStyleDeclaration("global"); + + if (globalSelector) + { + tc = globalSelector.getStyle("themeColor"); + rc = globalSelector.getStyle("rollOverColor"); + sc = globalSelector.getStyle("selectionColor"); + } + + if (tc && isNaN(rc) && isNaN(sc)) + { + setThemeColor(tc); + } + result = true; + } + + return result; + } + + /** + * @private + */ + override protected function resourcesChanged():void + { + super.resourcesChanged(); + - COMPILE::AS3 ++ COMPILE::SWF + { + // "View Source" on the context menu + if (viewSourceCMI) + { + viewSourceCMI.caption = resourceManager.getString("core", "viewSource"); + } + } + } + + //-------------------------------------------------------------------------- + // + // Overridden methods: Container + // + //-------------------------------------------------------------------------- + + /** + * @private + */ + override protected function layoutChrome(unscaledWidth:Number, + unscaledHeight:Number):void + { + super.layoutChrome(unscaledWidth, unscaledHeight); + + // When Container.autoLayout is false, updateDisplayList() + // is not called, but layoutChrome() is still called. + // In that case, we still need to position the border. + if (!doingLayout) + createBorder(); + + // Remove the borderThickness from the border metrics, + // since the header and control bar overlap any solid border. + var bm:EdgeMetrics = borderMetrics; + var thickness:Number = getStyle("borderThickness"); + + var em:EdgeMetrics = new EdgeMetrics(); + + em.left = bm.left - thickness; + em.top = bm.top - thickness; + em.right = bm.right - thickness; + em.bottom = bm.bottom - thickness; + + if (controlBar && controlBar.includeInLayout) + { + if (controlBar is IInvalidating) + IInvalidating(controlBar).invalidateDisplayList(); + controlBar.setActualSize(width - (em.left + em.right), + controlBar.getExplicitOrMeasuredHeight()); + controlBar.move(em.left, em.top); + } + } + + /** + * @private + * + * Container implements addChild in terms of addChildAt. + */ + override public function addChildAt(child:DisplayObject, + index:int):DisplayObject + { + super.addChildAt(child, index); + if (child == controlBar && + "dock" in child && child["dock"] && + "resetDock" in controlBar) + { + controlBar["resetDock"](true); + } + + return child; + } + + /** + * @private + * + * Container implements removeChildAt in terms of removeChild. + */ + override public function removeChild(child:DisplayObject):DisplayObject + { + if (child == controlBar && + "dock" in child && child["dock"]) + { + dockControlBar(IUIComponent(child), false); + } + + return super.removeChild(child); + } + + //-------------------------------------------------------------------------- + // + // Methods + // + //-------------------------------------------------------------------------- + + /** + * @private + * This is here so we get the this pointer set to Application. + */ + private function debugTickler():void + { + // We need some bytes of code in order to have a place to break. + var i:int = 0; + } + + /** + * @private + */ + private function initManagers(sm:ISystemManager):void + { + if (sm.isTopLevel()) + { + focusManager = new FocusManager(this); + var awm:IActiveWindowManager = + IActiveWindowManager(sm.getImplementation("mx.managers::IActiveWindowManager")); + if (awm) + awm.activate(this); + else + focusManager.activate(); + } + } + + /** + * @private + * Disable all the built-in items except "Print...". + */ - COMPILE::AS3 ++ COMPILE::SWF + private function initContextMenu():void + { + // context menu already set + // nothing to init + if (flexContextMenu != null) + { + // make sure we set it back on systemManager b/c it may have been overridden by now + if (systemManager is InteractiveObject) + InteractiveObject(systemManager).contextMenu = contextMenu; + return; + } + + var defaultMenu:ContextMenu = new ContextMenu(); + defaultMenu.hideBuiltInItems(); + defaultMenu.builtInItems.print = true; + + if (_viewSourceURL) + { + // don't worry! this gets updated in resourcesChanged() + const caption:String = resourceManager.getString("core", "viewSource"); + + viewSourceCMI = new ContextMenuItem(caption, true); + viewSourceCMI.addEventListener(ContextMenuEvent.MENU_ITEM_SELECT, menuItemSelectHandler); + + // Append custom option, validating customItems first as in the + // mobile context this is null. + if (defaultMenu.customItems) + defaultMenu.customItems.push(viewSourceCMI); + } + + contextMenu = defaultMenu; + + if (systemManager is InteractiveObject) + InteractiveObject(systemManager).contextMenu = defaultMenu; + } + + /** + * Add a container to the Application's creation queue. + * + * <p>Use this mechanism to instantiate and draw the contents + * of a container in an ordered manner. + * The container should have the <code>creationPolicy</code> property + * set to <code>"none"</code> prior to calling this function.</p> + * + * @param id The id of the container to add to the queue or a + * pointer to the container itself + * + * @param preferredIndex (optional) A positive integer that determines + * the container's position in the queue relative to the other + * containers presently in the queue. + * + * @param callbackFunc This parameter is ignored. + * + * @param parent This parameter is ignored. + * + * @langversion 3.0 + * @playerversion Flash 9 + * @playerversion AIR 1.1 + * @productversion Flex 3 + */ + public function addToCreationQueue(id:Object, preferredIndex:int = -1, + callbackFunc:Function = null, + parent:IFlexDisplayObject = null):void + { + //trace("App.addToCreationQueue id",id,"index",preferredIndex,"parent",parent); + + var queueLength:int = creationQueue.length; + var queueObj:Object = {}; + var insertedItem:Boolean = false; + + queueObj.id = id; + queueObj.parent = parent; + queueObj.callbackFunc = callbackFunc; + queueObj.index = preferredIndex; + + //trace("addToCreationQueue id",id,"index",queueObj.index,"parent",queueObj.parent,"nestLevel",queueObj.parent.nestLevel,"initialized",initialized); + + var insertIndex:int; + var pointerIndex:int; + var pointerLevel:int; + + // Find out where to place this item + for (var i:int = 0; i < queueLength; i++) + { + pointerIndex = creationQueue[i].index; + pointerLevel = creationQueue[i].parent ? creationQueue[i].parent.nestLevel : 0; + + /* + trace("addToCreationQueue queueItem",queueItemPointer.id,"queueItem.level",pointerLevel,"obj.level",queueObj.parent.nestLevel, + "queueItem.index",pointerIndex,"obj.index",queueObj.index); + */ + // If our new item has a preferredIndex + if (queueObj.index != -1) + { + // Place at index i if the queued index is -1 or if the new item's index is before the queued index + if (pointerIndex == -1 || queueObj.index < pointerIndex) + { + insertIndex = i; + insertedItem = true; + break; + } + } + else + { + // Place at index i if queued index is -1 and the new item is deeper in the component tree + // than the queued item. (Inner-most components should reveal first) + var parentLevel:int = queueObj.parent ? queueObj.parent.nestLevel : 0; + if (pointerIndex == -1 && pointerLevel < parentLevel) + { + insertIndex = i; + insertedItem = true; + break; + } + } + } + + if (!insertedItem) + { + creationQueue.push(queueObj); // Just add it to the end of the queue + insertedItem = true; + } + else + { + creationQueue.splice(insertIndex, 0, queueObj); // Insert into a specific place in the queue + } + + //printCreationQueue(); + + // Check if we need to trigger queue processing + if (initialized && !processingCreationQueue) + { + //trace("App.addToCreationQueue KICKING the queue processer"); + doNextQueueItem(); + } + } + + /** + * @private + */ + private function doNextQueueItem(event:FlexEvent = null):void + { + processingCreationQueue = true; + + Application.useProgressiveLayout = true; + + // The doNextQueueItem function is usually called + // when a creationComplete event is dispatched. + // Wait for other creationComplete listeners to fire + // before we start processing the next item, + // in case one of those listeners plays an effect. + callLater(processNextQueueItem); + } + + /** + * @private + */ + private function processNextQueueItem():void + { + if (EffectManager.effectsPlaying.length > 0) + { + // Wait for effects to finish playing before processing the + // next item in the queue. + callLater(processNextQueueItem); + } + else if (creationQueue.length > 0) + { + //trace("processNextQueueItem START length", creationQueue.length); + //printCreationQueue(); + + var queueItem:Object = creationQueue.shift(); + try + { + var nextChild:IUIComponent = (queueItem.id is String + ? document[queueItem.id] + : queueItem.id); + if (nextChild is Container) + Container(nextChild).createComponentsFromDescriptors(true); + if (nextChild is Container && + Container(nextChild).creationPolicy == ContainerCreationPolicy.QUEUED) + doNextQueueItem(); + else + nextChild.addEventListener("childrenCreationComplete", doNextQueueItem); + } + catch(e:Error) + { + //trace("Exception in processNextQueue",e); + // Can't find the id in the document. Just move on to the next item. + processNextQueueItem(); + } + + //trace("processNextQueueItem id", queueItem. id, "index", queueItem. index); + } + else + { + processingCreationQueue = false; + Application.useProgressiveLayout = false; + } + } + + /** + * @private + */ + private function printCreationQueue():void + { + var msg:String = ""; + + var n:Number = creationQueue.length; + for (var i:int = 0; i < n; i++) + { + var child:Object = creationQueue[i]; + msg += " [" + i + "] " + child.id + " " + child.index; + } + + //trace("creationQueue =>" + msg); + } + + /** + * @private + */ + private function setControlBar(newControlBar:IUIComponent):void + { + if (newControlBar == controlBar) + return; + + if (controlBar && controlBar is IStyleClient) + { + IStyleClient(controlBar).clearStyle("cornerRadius"); + IStyleClient(controlBar).clearStyle("docked"); + } + + controlBar = newControlBar; + if (controlBar && controlBar is IStyleClient) + { + IStyleClient(controlBar).setStyle("cornerRadius", 0); + IStyleClient(controlBar).setStyle("docked", true); + } + + invalidateSize(); + invalidateDisplayList(); + invalidateViewMetricsAndPadding(); + } + + /** + * @private + */ + mx_internal function dockControlBar(controlBar:IUIComponent, + dock:Boolean):void + { + if (dock) + { + try + { + removeChild(DisplayObject(controlBar)); + } + catch(e:Error) + { + return; + } + + rawChildren.addChildAt(DisplayObject(controlBar), firstChildIndex); + setControlBar(controlBar); + } + else // undock + { + try + { + rawChildren.removeChild(DisplayObject(controlBar)); + } + catch(e:Error) + { + return; + } + + setControlBar(null); + addChildAt(DisplayObject(controlBar), 0); + } + } + + /** + * @private + * Check to see if we're able to synchronize our size with the stage + * immediately rather than deferring (dependent on WATSON 2200950). + */ + private function initResizeBehavior():void + { - COMPILE::AS3 ++ COMPILE::SWF + { + var version:Array = Capabilities.version.split(' ')[1].split(','); + + synchronousResize = (parseFloat(version[0]) > 10 || + (parseFloat(version[0]) == 10 && parseFloat(version[1]) >= 1)) && !Platform.isAir; + } + } + + //-------------------------------------------------------------------------- + // + // Event handlers + // + //-------------------------------------------------------------------------- + + /** + * @private + * Called after all children are drawn. + */ + private function addedHandler(event:Event):void + { + //trace("creationComplete +++++++++ check if queue has any items", creationQueue.length, "initialized", initialized); + if (event.target == this && creationQueue.length > 0) + doNextQueueItem(); + } + + /** + * @private + * Triggered by a resize event of the stage. + * Sets the new width and height. + * After the SystemManager performs its function, + * it is only necessary to notify the children of the change. + */ + private function resizeHandler(event:Event):void + { + // If we're already due to update our bounds on the next + // commitProperties pass, avoid the redundancy. + if (!percentBoundsChanged) + { + updateBounds(); + + // Update immediately when stage resizes so that we may appear + // in synch with the stage rather than visually "catching up". + if (synchronousResize) + UIComponentGlobals.layoutManager.validateNow(); + } + } + + /** + * @private + * Called when the "View Source" item in the application's context menu is + * selected. + */ - COMPILE::AS3 ++ COMPILE::SWF + protected function menuItemSelectHandler(event:Event):void + { + navigateToURL(new URLRequest(_viewSourceURL), "_blank"); + } + + /** + * @private + * Sets the new width and height after the Stage has resized + * or when percentHeight or percentWidth has changed. + */ + private function updateBounds():void + { + // When user has not specified any width/height, + // application assumes the size of the stage. + // If developer has specified width/height, + // the application will not resize. + // If developer has specified percent width/height, + // application will resize to the required value + // based on the current SystemManager's width/height. + // If developer has specified min/max values, + // then application will not resize beyond those values. + + var w:Number; + var h:Number + + if (resizeWidth) + { + if (isNaN(percentWidth)) + { + w = DisplayObject(systemManager).width; + } + else + { + super.percentWidth = Math.max(percentWidth, 0); + super.percentWidth = Math.min(percentWidth, 100); + + if (FlexVersion.compatibilityVersion >= FlexVersion.VERSION_4_0) + w = percentWidth * DisplayObject(systemManager).width/100; + else + w = percentWidth * screen.width/100; + } + + if (!isNaN(explicitMaxWidth)) + w = Math.min(w, explicitMaxWidth); + + if (!isNaN(explicitMinWidth)) + w = Math.max(w, explicitMinWidth); + } + else + { + w = width; + } + + if (resizeHeight) + { + if (isNaN(percentHeight)) + { + h = DisplayObject(systemManager).height; + } + else + { + super.percentHeight = Math.max(percentHeight, 0); + super.percentHeight = Math.min(percentHeight, 100); + + if (FlexVersion.compatibilityVersion >= FlexVersion.VERSION_4_0) + h = percentHeight * DisplayObject(systemManager).height/100; + else + h = percentHeight * screen.height/100; + } + + if (!isNaN(explicitMaxHeight)) + h = Math.min(h, explicitMaxHeight); + + if (!isNaN(explicitMinHeight)) + h = Math.max(h, explicitMinHeight); + } + else + { + h = height; + } + + if (w != width || h != height) + { + invalidateProperties(); + invalidateSize(); + } + + setActualSize(w, h); + + invalidateDisplayList(); + } + + COMPILE::JS + private function makeParameters(url:String):Object + { + if (url == null || url.length == 0) + return {}; + + url = url.substring(1); // remove leading ? + var parts:Array = url.split("&"); + var parms:Object = {}; + for each (var part:String in parts) + { + var subParts:Array = part.split("="); + parms[subParts[0]] = subParts[1]; + } + return parms; + } +} + +}
