| //////////////////////////////////////////////////////////////////////////////// |
| // |
| // 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 spark.skins.mobile |
| { |
| import flash.display.DisplayObject; |
| import flash.display.Graphics; |
| |
| import mx.core.DPIClassification; |
| |
| import spark.components.BusyIndicator; |
| import spark.components.Group; |
| import spark.components.Image; |
| import spark.primitives.BitmapImage; |
| import spark.skins.mobile.supportClasses.MobileSkin; |
| import spark.skins.mobile120.assets.ImageInvalid; |
| import spark.skins.mobile160.assets.ImageInvalid; |
| import spark.skins.mobile240.assets.ImageInvalid; |
| import spark.skins.mobile320.assets.ImageInvalid; |
| import spark.skins.mobile480.assets.ImageInvalid; |
| import spark.skins.mobile640.assets.ImageInvalid; |
| |
| /** |
| * ActionScript-based skin for the Image component in mobile applications. |
| * |
| * @langversion 3.0 |
| * @playerversion Flash 10 |
| * @playerversion AIR 2.5 |
| * @productversion Flex 4.5 |
| */ |
| public class ImageSkin extends MobileSkin |
| { |
| //-------------------------------------------------------------------------- |
| // |
| // Constructor |
| // |
| //-------------------------------------------------------------------------- |
| |
| /** |
| * Constructor. |
| * |
| * @langversion 3.0 |
| * @playerversion Flash 10 |
| * @playerversion AIR 2.5 |
| * @productversion Flex 4.5 |
| * |
| */ |
| public function ImageSkin() |
| { |
| super(); |
| |
| // set the right assets and dimensions to use based on the screen density |
| switch (applicationDPI) |
| { |
| case DPIClassification.DPI_640: |
| { |
| imageInvalidClass = spark.skins.mobile640.assets.ImageInvalid; |
| break; |
| } |
| case DPIClassification.DPI_480: |
| { |
| imageInvalidClass = spark.skins.mobile480.assets.ImageInvalid; |
| break; |
| } |
| case DPIClassification.DPI_320: |
| { |
| imageInvalidClass = spark.skins.mobile320.assets.ImageInvalid; |
| break; |
| } |
| case DPIClassification.DPI_240: |
| { |
| imageInvalidClass = spark.skins.mobile240.assets.ImageInvalid; |
| break; |
| } |
| case DPIClassification.DPI_120: |
| { |
| imageInvalidClass = spark.skins.mobile120.assets.ImageInvalid; |
| break; |
| } |
| default: |
| { |
| // default DPI_160 |
| imageInvalidClass = spark.skins.mobile160.assets.ImageInvalid; |
| break; |
| } |
| |
| } |
| } |
| |
| //-------------------------------------------------------------------------- |
| // |
| // Properties |
| // |
| //-------------------------------------------------------------------------- |
| |
| /** |
| * @copy spark.skins.spark.ApplicationSkin#hostComponent |
| */ |
| public var hostComponent:Image; |
| |
| //-------------------------------------------------------------------------- |
| // |
| // Skin parts |
| // |
| //-------------------------------------------------------------------------- |
| |
| /** |
| * Image imageDisplay skin part that contains the image content |
| * |
| * @langversion 3.0 |
| * @playerversion Flash 10 |
| * @playerversion AIR 2.5 |
| * @productversion Flex 4.5 |
| */ |
| public var imageDisplay:BitmapImage; |
| |
| //-------------------------------------------------------------------------- |
| // |
| // Variables |
| // |
| //-------------------------------------------------------------------------- |
| |
| /** |
| * Container of the BitmapImage to be displayed |
| * |
| * @langversion 3.0 |
| * @playerversion Flash 10 |
| * @playerversion AIR 2.5 |
| * @productversion Flex 4.5 |
| */ |
| protected var imageHolder:Group; |
| |
| /** |
| * The currently displayed asset: either the intended image, |
| * the loading indicator, the "invalid image" icon, or null. |
| * |
| * @langversion 3.0 |
| * @playerversion Flash 10 |
| * @playerversion AIR 2.5 |
| * @productversion Flex 4.5 |
| */ |
| private var currentImage:DisplayObject; |
| |
| /** |
| * Specifies the FXG class to use in the "invalid" image state |
| * |
| * @langversion 3.0 |
| * @playerversion Flash 10 |
| * @playerversion AIR 2.5 |
| * @productversion Flex 4.5 |
| */ |
| protected var imageInvalidClass:Class; |
| |
| /** |
| * Specifies the DisplayObject to use in the "invalid" image state |
| * |
| * @langversion 3.0 |
| * @playerversion Flash 10 |
| * @playerversion AIR 2.5 |
| * @productversion Flex 4.5 |
| */ |
| private var imageInvalid:DisplayObject; |
| |
| /** |
| * Displayed if the "enableLoadingState" style is true |
| * |
| * @langversion 3.0 |
| * @playerversion Flash 10 |
| * @playerversion AIR 2.5 |
| * @productversion Flex 4.5 |
| */ |
| protected var loadingIndicator:BusyIndicator = null; |
| |
| //-------------------------------------------------------------------------- |
| // |
| // Overridden methods |
| // |
| //-------------------------------------------------------------------------- |
| |
| /** |
| * @private |
| */ |
| override protected function commitCurrentState():void |
| { |
| var alphaValue:Number = 1.0; |
| |
| if (currentState == "uninitialized") |
| { |
| if (imageInvalid) |
| { |
| removeChild(imageInvalid); |
| imageInvalid = null; |
| } |
| |
| if (loadingIndicator) |
| { |
| removeChild(loadingIndicator); |
| loadingIndicator = null; |
| } |
| |
| currentImage = null; |
| } |
| else if (currentState == "loading") |
| { |
| // turn off any other images |
| if (imageInvalid) |
| { |
| removeChild(imageInvalid); |
| imageInvalid = null; |
| } |
| |
| if (!loadingIndicator) |
| { |
| loadingIndicator = new BusyIndicator(); |
| addChild(loadingIndicator); |
| } |
| |
| currentImage = loadingIndicator; |
| } |
| else if (currentState == "ready") |
| { |
| if (imageInvalid) |
| { |
| removeChild(imageInvalid); |
| imageInvalid = null; |
| } |
| |
| if (loadingIndicator) |
| { |
| removeChild(loadingIndicator); |
| loadingIndicator = null; |
| } |
| |
| currentImage = imageHolder; |
| } |
| else if (currentState == "invalid") |
| { |
| if (loadingIndicator) |
| { |
| removeChild(loadingIndicator); |
| loadingIndicator = null; |
| } |
| |
| if (!imageInvalid) |
| { |
| imageInvalid = new imageInvalidClass(); |
| addChild(imageInvalid); |
| } |
| |
| currentImage = imageInvalid; |
| } |
| else if (currentState == "disabled") |
| { |
| alphaValue = 0.5; |
| |
| // remove any loading or invalid images |
| if (imageInvalid) |
| { |
| removeChild(imageInvalid); |
| imageInvalid = null; |
| } |
| |
| if (loadingIndicator) |
| { |
| removeChild(loadingIndicator); |
| loadingIndicator = null; |
| } |
| |
| currentImage = imageHolder; |
| } |
| else |
| { |
| // unexpected state; ignore |
| } |
| |
| alpha = alphaValue; |
| |
| invalidateSize(); |
| invalidateDisplayList(); |
| } |
| |
| /** |
| * @private |
| */ |
| override protected function createChildren():void |
| { |
| // create container for holding the currently displayed image |
| imageHolder = new Group(); |
| addChild(imageHolder); |
| |
| // required skin part; the Image component will set this directly |
| imageDisplay = new BitmapImage(); |
| imageDisplay.left = 0; |
| imageDisplay.right = 0; |
| imageDisplay.top = 0; |
| imageDisplay.bottom = 0; |
| |
| imageHolder.addElement(imageDisplay); |
| } |
| |
| /** |
| * @private |
| */ |
| override protected function measure():void |
| { |
| super.measure(); |
| |
| if (currentImage) |
| { |
| measuredHeight = getElementPreferredHeight(currentImage); |
| measuredWidth = getElementPreferredWidth(currentImage); |
| } |
| } |
| |
| /** |
| * @private |
| */ |
| override protected function updateDisplayList(unscaledWidth:Number, unscaledHeight:Number):void |
| { |
| super.updateDisplayList(unscaledWidth, unscaledHeight); |
| |
| var preferredWidth:Number; |
| var preferredHeight:Number; |
| |
| if (loadingIndicator && currentImage == loadingIndicator) |
| { |
| preferredWidth = loadingIndicator.getPreferredBoundsWidth(); |
| preferredHeight = loadingIndicator.getPreferredBoundsHeight(); |
| |
| // loading indicator will be no bigger than its preferred width/height |
| setElementSize(loadingIndicator, |
| Math.min(unscaledWidth, preferredWidth), |
| Math.min(unscaledHeight, preferredHeight)); |
| |
| // center the loading indicator |
| setElementPosition(loadingIndicator, |
| Math.max((unscaledWidth - preferredWidth) / 2, 0), |
| Math.max((unscaledHeight - preferredHeight) / 2, 0)); |
| } |
| else if (imageInvalid && currentImage == imageInvalid) |
| { |
| preferredWidth = getElementPreferredWidth(imageInvalid); |
| preferredHeight = getElementPreferredHeight(imageInvalid); |
| |
| // icon shrinks with any explicit image size |
| setElementSize(imageInvalid, |
| Math.min(preferredWidth, unscaledWidth), |
| Math.min(preferredHeight, unscaledHeight)); |
| |
| // center the invalid image icon |
| setElementPosition(imageInvalid, |
| Math.max((unscaledWidth - preferredWidth) / 2, 0), |
| Math.max((unscaledHeight - preferredHeight) / 2, 0)); |
| } |
| else if (currentImage == imageHolder) |
| setElementSize(imageHolder, unscaledWidth, unscaledHeight); |
| |
| // set the background rect if specified |
| var g:Graphics = graphics; |
| g.clear(); |
| if (!isNaN(getStyle("backgroundColor"))) |
| { |
| g.beginFill(getStyle("backgroundColor"), getStyle("backgroundAlpha")); |
| g.drawRect(0, 0, unscaledWidth, unscaledHeight); |
| } |
| } |
| } |
| } |