You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@flex.apache.org by bi...@apache.org on 2014/11/24 22:12:54 UTC
[04/44] git commit: [flex-sdk] [refs/heads/develop] - Adding new
branch for working on ios7 skins.
http://git-wip-us.apache.org/repos/asf/flex-sdk/blob/3fd6027d/frameworks/projects/mobiletheme/src/spark/skins/ios7/CalloutSkin.as
----------------------------------------------------------------------
diff --git a/frameworks/projects/mobiletheme/src/spark/skins/ios7/CalloutSkin.as b/frameworks/projects/mobiletheme/src/spark/skins/ios7/CalloutSkin.as
new file mode 100644
index 0000000..95fefef
--- /dev/null
+++ b/frameworks/projects/mobiletheme/src/spark/skins/ios7/CalloutSkin.as
@@ -0,0 +1,825 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+// 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.android4
+{
+import flash.display.BlendMode;
+import flash.display.GradientType;
+import flash.display.Graphics;
+import flash.display.Sprite;
+import flash.events.Event;
+
+import mx.core.DPIClassification;
+import mx.core.UIComponent;
+import mx.core.mx_internal;
+import mx.events.EffectEvent;
+import mx.events.FlexEvent;
+import mx.utils.ColorUtil;
+
+import spark.components.ArrowDirection;
+import spark.components.Callout;
+import spark.components.ContentBackgroundAppearance;
+import spark.components.Group;
+import spark.core.SpriteVisualElement;
+import spark.effects.Fade;
+import spark.primitives.RectangularDropShadow;
+import spark.skins.android4.assets.CalloutContentBackground;
+import spark.skins.android4.supportClasses.CalloutArrow;
+import spark.skins.mobile.supportClasses.MobileSkin;
+
+use namespace mx_internal;
+
+/**
+ * The default skin class for the Spark Callout component in mobile
+ * applications.
+ *
+ * <p>The <code>contentGroup</code> lies above a <code>backgroundColor</code> fill
+ * which frames the <code>contentGroup</code>. The position and size of the frame
+ * adjust based on the host component <code>arrowDirection</code>, leaving
+ * space for the <code>arrow</code> to appear on the outside edge of the
+ * frame.</p>
+ *
+ * <p>The <code>arrow</code> skin part is not positioned by the skin. Instead,
+ * the Callout component positions the arrow relative to the owner in
+ * <code>updateSkinDisplayList()</code>. This method assumes that Callout skin
+ * and the <code>arrow</code> use the same coordinate space.</p>
+ *
+ * @see spark.components.Callout
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+public class CalloutSkin extends MobileSkin
+{
+ mx_internal static const BACKGROUND_GRADIENT_BRIGHTNESS_TOP:int = 15;
+
+ mx_internal static const BACKGROUND_GRADIENT_BRIGHTNESS_BOTTOM:int = -15;
+
+ //--------------------------------------------------------------------------
+ //
+ // Constructor
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * Constructor.
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ public function CalloutSkin()
+ {
+ super();
+
+ dropShadowAlpha = 0.7;
+ contentBackgroundInsetClass = spark.skins.android4.assets.CalloutContentBackground;
+
+ switch (applicationDPI)
+ {
+ case DPIClassification.DPI_640:
+ {
+
+ backgroundCornerRadius = 24;
+ backgroundGradientHeight = 440;
+ frameThickness = 12;
+ arrowWidth = 160;
+ arrowHeight = 80;
+ contentCornerRadius = 40;
+ dropShadowBlurX = 64;
+ dropShadowBlurY = 64;
+ dropShadowDistance = 12;
+ highlightWeight = 4;
+
+ break;
+ }
+ case DPIClassification.DPI_480:
+ {
+ backgroundCornerRadius = 16;
+ backgroundGradientHeight = 330;
+ frameThickness = 8;
+ arrowWidth = 120;
+ arrowHeight = 60;
+ contentCornerRadius = 28;
+ dropShadowBlurX = 48;
+ dropShadowBlurY = 48;
+ dropShadowDistance = 8;
+ highlightWeight = 2;
+
+ break;
+ }
+ case DPIClassification.DPI_320:
+ {
+
+ backgroundCornerRadius = 12;
+ backgroundGradientHeight = 220;
+ frameThickness = 6;
+ arrowWidth = 80;
+ arrowHeight = 40;
+ contentCornerRadius = 20;
+ dropShadowBlurX = 32;
+ dropShadowBlurY = 32;
+ dropShadowDistance = 6;
+ highlightWeight = 2;
+
+ break;
+ }
+ case DPIClassification.DPI_240:
+ {
+ backgroundCornerRadius = 8;
+ backgroundGradientHeight = 165;
+ frameThickness = 4;
+ arrowWidth = 60;
+ arrowHeight = 30;
+ contentCornerRadius = 14;
+ dropShadowBlurX = 24;
+ dropShadowBlurY = 24;
+ dropShadowDistance = 4;
+ highlightWeight = 1;
+
+ break;
+ }
+ case DPIClassification.DPI_120:
+ {
+ backgroundCornerRadius = 4;
+ backgroundGradientHeight = 83;
+ frameThickness = 2;
+ arrowWidth = 30;
+ arrowHeight = 15;
+ contentCornerRadius = 7;
+ dropShadowBlurX = 12;
+ dropShadowBlurY = 12;
+ dropShadowDistance = 2;
+ highlightWeight = 0.5;
+
+ break;
+ }
+ default:
+ {
+ // default DPI_160
+ backgroundCornerRadius = 6;
+ backgroundGradientHeight = 110;
+ frameThickness = 3;
+ arrowWidth = 40;
+ arrowHeight = 20;
+ contentCornerRadius = 10;
+ dropShadowBlurX = 16;
+ dropShadowBlurY = 16;
+ dropShadowDistance = 3;
+ highlightWeight = 1;
+
+ break;
+ }
+ }
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Variables
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @copy spark.skins.spark.ApplicationSkin#hostComponent
+ */
+ public var hostComponent:Callout;
+
+ /**
+ * Enables a RectangularDropShadow behind the <code>backgroundColor</code> frame.
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ protected var dropShadowVisible:Boolean = true;
+
+ /**
+ * Enables a vertical linear gradient in the <code>backgroundColor</code> frame. This
+ * gradient fill is drawn across both the arrow and the frame. By default,
+ * the gradient brightens the background color by 15% and darkens it by 60%.
+ *
+ * @default true
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ protected var useBackgroundGradient:Boolean = true;
+
+ /**
+ * Corner radius used for the <code>contentBackgroundColor</code> fill.
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ protected var contentCornerRadius:uint;
+
+ /**
+ * A class reference to an FXG class that is layered underneath the
+ * <code>contentGroup</code>. The instance of this class is sized to match the
+ * <code>contentGroup</code>.
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ protected var contentBackgroundInsetClass:Class;
+
+ /**
+ * Corner radius of the <code>backgroundColor</code> "frame".
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ protected var backgroundCornerRadius:Number;
+
+ /**
+ * The thickness of the <code>backgroundColor</code> "frame" that surrounds the
+ * <code>contentGroup</code>.
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ protected var frameThickness:Number;
+
+ /**
+ * Color of the border stroke around the <code>backgroundColor</code> "frame".
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ protected var borderColor:Number = -1; // not set
+
+ /**
+ * Thickness of the border stroke around the <code>backgroundColor</code>
+ * "frame".
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ protected var borderThickness:Number = -1 ; // marker that borderThickness was not set directly
+
+ /**
+ * Width of the arrow in vertical directions. This property also controls
+ * the height of the arrow in horizontal directions.
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ protected var arrowWidth:Number;
+
+ /**
+ * Height of the arrow in vertical directions. This property also controls
+ * the width of the arrow in horizontal directions.
+ *
+ * @langversion 3.0
+ * @playerversion AIR 3
+ * @productversion Flex 4.6
+ */
+ protected var arrowHeight:Number;
+
+ /**
+ * @private
+ * Instance of the contentBackgroundClass
+ */
+ mx_internal var contentBackgroundGraphic:SpriteVisualElement;
+
+ /**
+ * @private
+ * Tracks changes to the skin state to support the fade out tranisition
+ * when closed;
+ */
+ mx_internal var isOpen:Boolean;
+
+ private var backgroundGradientHeight:Number;
+
+ private var contentMask:Sprite;
+
+ private var backgroundFill:SpriteVisualElement;
+
+ private var dropShadow:RectangularDropShadow;
+
+ private var dropShadowBlurX:Number;
+
+ private var dropShadowBlurY:Number;
+
+ private var dropShadowDistance:Number;
+
+ private var dropShadowAlpha:Number;
+
+ private var fade:Fade;
+
+ private var highlightWeight:Number;
+
+ //--------------------------------------------------------------------------
+ //
+ // Skin parts
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @copy spark.components.SkinnableContainer#contentGroup
+ */
+ public var contentGroup:Group;
+
+ /**
+ * @copy spark.components.Callout#arrow
+ */
+ public var arrow:UIComponent;
+
+ /* helper private accessors */
+
+ /* returns borderThickness from style if member is -1, or borderThickness. Returns 0 if NaN */
+ mx_internal function get actualBorderThickness():Number
+ {
+ var border: Number = borderThickness != -1 ? borderThickness : getStyle('borderThickness');
+ return isNaN(border)? 0: border;
+ }
+
+ mx_internal function get actualBorderColor():uint
+ {
+ return borderColor != -1 ? borderColor: getStyle('borderColor');
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Overridden methods
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @private
+ */
+ override protected function createChildren():void
+ {
+ super.createChildren();
+
+ if (dropShadowVisible)
+ {
+ dropShadow = new RectangularDropShadow();
+ dropShadow.angle = 90;
+ dropShadow.distance = dropShadowDistance;
+ dropShadow.blurX = dropShadowBlurX;
+ dropShadow.blurY = dropShadowBlurY;
+ dropShadow.tlRadius = dropShadow.trRadius = dropShadow.blRadius =
+ dropShadow.brRadius = backgroundCornerRadius ;
+ dropShadow.mouseEnabled = false;
+ dropShadow.alpha = dropShadowAlpha;
+ addChild(dropShadow);
+ }
+
+ // background fill placed above the drop shadow
+ backgroundFill = new SpriteVisualElement();
+ addChild(backgroundFill);
+
+ // arrow
+ if (!arrow)
+ {
+ arrow = new CalloutArrow();
+ arrow.id = "arrow";
+ arrow.styleName = this;
+ addChild(arrow);
+ }
+
+ // contentGroup
+ if (!contentGroup)
+ {
+ contentGroup = new Group();
+ contentGroup.id = "contentGroup";
+ addChild(contentGroup);
+ }
+
+
+ }
+
+ /**
+ * @private
+ */
+ override protected function commitProperties():void
+ {
+ super.commitProperties();
+
+ // add or remove the contentBackgroundGraphic
+ var contentBackgroundAppearance:String = getStyle("contentBackgroundAppearance");
+
+ if (contentBackgroundAppearance == ContentBackgroundAppearance.INSET)
+ {
+ // create the contentBackgroundGraphic
+ if (!contentBackgroundGraphic && contentBackgroundInsetClass)
+ {
+ contentBackgroundGraphic = new contentBackgroundInsetClass() as SpriteVisualElement;
+
+ // with the current skin structure, contentBackgroundGraphic is
+ // always the last child
+ addChild(contentBackgroundGraphic);
+ }
+ }
+ else if (contentBackgroundGraphic)
+ {
+ // if already created, remove the graphic for "flat" and "none"
+ removeChild(contentBackgroundGraphic);
+ contentBackgroundGraphic = null;
+ }
+
+ // always invalidate to accomodate arrow direction changes
+ invalidateSize();
+ invalidateDisplayList();
+ }
+
+
+ /**
+ * @private
+ */
+ override protected function measure():void
+ {
+ super.measure();
+
+ var borderWeight:Number =actualBorderThickness;
+ var frameAdjustment:Number = (frameThickness + borderWeight) * 2;
+
+ var arrowMeasuredWidth:Number;
+ var arrowMeasuredHeight:Number;
+
+ // pad the arrow so that the edges are within the background corner radius
+ if (isArrowHorizontal)
+ {
+ arrowMeasuredWidth = arrowHeight;
+ arrowMeasuredHeight = arrowWidth + (backgroundCornerRadius * 2);
+ }
+ else if (isArrowVertical)
+ {
+ arrowMeasuredWidth = arrowWidth + (backgroundCornerRadius * 2);
+ arrowMeasuredHeight = arrowHeight;
+ }
+
+ // count the contentGroup size and frame size
+ measuredMinWidth = contentGroup.measuredMinWidth + frameAdjustment;
+ measuredMinHeight = contentGroup.measuredMinHeight + frameAdjustment;
+
+ measuredWidth = contentGroup.getPreferredBoundsWidth() + frameAdjustment;
+ measuredHeight = contentGroup.getPreferredBoundsHeight() + frameAdjustment;
+
+ // add the arrow size based on the arrowDirection
+ if (isArrowHorizontal)
+ {
+ measuredMinWidth += arrowMeasuredWidth;
+ measuredMinHeight = Math.max(measuredMinHeight, arrowMeasuredHeight);
+
+ measuredWidth += arrowMeasuredWidth;
+ measuredHeight = Math.max(measuredHeight, arrowMeasuredHeight);
+ }
+ else if (isArrowVertical)
+ {
+ measuredMinWidth += Math.max(measuredMinWidth, arrowMeasuredWidth);
+ measuredMinHeight += arrowMeasuredHeight;
+
+ measuredWidth = Math.max(measuredWidth, arrowMeasuredWidth);
+ measuredHeight += arrowMeasuredHeight;
+ }
+ }
+
+ /**
+ * @private
+ * SkinnaablePopUpContainer skins must dispatch a
+ * FlexEvent.STATE_CHANGE_COMPLETE event for the component to properly
+ * update the skin state.
+ */
+ override protected function commitCurrentState():void
+ {
+ super.commitCurrentState();
+
+ var isNormal:Boolean = (currentState == "normal");
+ var isDisabled:Boolean = (currentState == "disabled")
+
+ // play a fade out if the callout was previously open
+ if (!(isNormal || isDisabled) && isOpen)
+ {
+ if (!fade)
+ {
+ fade = new Fade();
+ fade.target = this;
+ fade.duration = 200;
+ fade.alphaTo = 0;
+ }
+
+ // BlendMode.LAYER while fading out
+ blendMode = BlendMode.LAYER;
+
+ // play a short fade effect
+ fade.addEventListener(EffectEvent.EFFECT_END, stateChangeComplete);
+ fade.play();
+
+ isOpen = false;
+ }
+ else
+ {
+ isOpen = isNormal || isDisabled;
+
+ // handle re-opening the Callout while fading out
+ if (fade && fade.isPlaying)
+ {
+ // Do not dispatch a state change complete.
+ // SkinnablePopUpContainer handles state interruptions.
+ fade.removeEventListener(EffectEvent.EFFECT_END, stateChangeComplete);
+ fade.stop();
+ }
+
+ if (isDisabled)
+ {
+ // BlendMode.LAYER to allow CalloutArrow BlendMode.ERASE
+ blendMode = BlendMode.LAYER;
+
+ alpha = 0.5;
+ }
+ else
+ {
+ // BlendMode.NORMAL for non-animated state transitions
+ blendMode = BlendMode.NORMAL;
+
+ if (isNormal)
+ alpha = 1;
+ else
+ alpha = 0;
+ }
+
+ stateChangeComplete();
+ }
+ }
+
+ /**
+ * @private
+ */
+ override protected function drawBackground(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ super.drawBackground(unscaledWidth, unscaledHeight);
+
+ var frameEllipseSize:Number = backgroundCornerRadius * 2;
+
+ // account for borderThickness center stroke alignment
+ var borderWeight:Number =actualBorderThickness;
+ var showBorder:Boolean = borderWeight > 0 ;
+
+
+ // contentBackgroundGraphic already accounts for the arrow position
+ // use it's positioning instead of recalculating based on unscaledWidth
+ // and unscaledHeight
+ var frameX:Number = Math.floor(contentGroup.getLayoutBoundsX() - frameThickness) - (borderWeight / 2);
+ var frameY:Number = Math.floor(contentGroup.getLayoutBoundsY() - frameThickness) - (borderWeight / 2);
+ var frameWidth:Number = contentGroup.getLayoutBoundsWidth() + (frameThickness * 2) + borderWeight;
+ var frameHeight:Number = contentGroup.getLayoutBoundsHeight() + (frameThickness * 2) + borderWeight;
+
+ var backgroundColor:Number = getStyle("primaryAccentColor");
+ var backgroundAlpha:Number = getStyle("backgroundAlpha");
+
+ var bgFill:Graphics = backgroundFill.graphics;
+ bgFill.clear();
+
+ if (showBorder)
+ bgFill.lineStyle(borderWeight, actualBorderColor, 1, true);
+
+ if (useBackgroundGradient)
+ {
+ // top color is brighter if arrowDirection == ArrowDirection.UP
+ var backgroundColorTop:Number = ColorUtil.adjustBrightness2(backgroundColor,
+ BACKGROUND_GRADIENT_BRIGHTNESS_TOP);
+ var backgroundColorBottom:Number = ColorUtil.adjustBrightness2(backgroundColor,
+ BACKGROUND_GRADIENT_BRIGHTNESS_BOTTOM);
+
+ // max gradient height = backgroundGradientHeight
+ colorMatrix.createGradientBox(unscaledWidth, backgroundGradientHeight,
+ Math.PI / 2, 0, 0);
+
+ bgFill.beginGradientFill(GradientType.LINEAR,
+ [backgroundColorTop, backgroundColorBottom],
+ [backgroundAlpha, backgroundAlpha],
+ [0, 255],
+ colorMatrix);
+ }
+ else
+ {
+ bgFill.beginFill(backgroundColor, backgroundAlpha);
+ }
+
+ bgFill.drawRoundRect(frameX, frameY, frameWidth,
+ frameHeight, frameEllipseSize, frameEllipseSize);
+ bgFill.endFill();
+
+ // draw content background styles
+ var contentBackgroundAppearance:String = getStyle("contentBackgroundAppearance");
+
+ if (contentBackgroundAppearance != ContentBackgroundAppearance.NONE)
+ {
+ var contentEllipseSize:Number = contentCornerRadius * 2;
+ var contentBackgroundAlpha:Number = getStyle("contentBackgroundAlpha");
+ var contentWidth:Number = contentGroup.getLayoutBoundsWidth();
+ var contentHeight:Number = contentGroup.getLayoutBoundsHeight();
+
+ // all appearance values except for "none" use a mask
+ if (!contentMask)
+ contentMask = new SpriteVisualElement();
+
+ contentGroup.mask = contentMask;
+
+ // draw contentMask in contentGroup coordinate space
+ var maskGraphics:Graphics = contentMask.graphics;
+ maskGraphics.clear();
+ maskGraphics.beginFill(0, 1);
+ maskGraphics.drawRoundRect(0, 0, contentWidth, contentHeight,
+ contentEllipseSize, contentEllipseSize);
+ maskGraphics.endFill();
+
+ // reset line style to none
+ if (showBorder)
+ bgFill.lineStyle(NaN);
+
+ // draw the contentBackgroundColor
+ bgFill.beginFill(getStyle("contentBackgroundColor"),
+ contentBackgroundAlpha);
+ bgFill.drawRoundRect(contentGroup.getLayoutBoundsX(),
+ contentGroup.getLayoutBoundsY(),
+ contentWidth, contentHeight, contentEllipseSize, contentEllipseSize);
+ bgFill.endFill();
+
+ if (contentBackgroundGraphic)
+ contentBackgroundGraphic.alpha = contentBackgroundAlpha;
+ }
+ else // if (contentBackgroundAppearance == CalloutContentBackgroundAppearance.NONE))
+ {
+ // remove the mask
+ if (contentMask)
+ {
+ contentGroup.mask = null;
+ contentMask = null;
+ }
+ }
+
+ // draw highlight in the callout when the arrow is hidden
+ if (useBackgroundGradient && !isArrowHorizontal && !isArrowVertical)
+ {
+ // highlight width spans the callout width minus the corner radius
+ var highlightWidth:Number = frameWidth - frameEllipseSize;
+ var highlightX:Number = frameX + backgroundCornerRadius;
+ var highlightOffset:Number = (highlightWeight * 1.5);
+
+ // straight line across the top
+ bgFill.lineStyle(highlightWeight, 0xFFFFFF, 0.2 * backgroundAlpha);
+ bgFill.moveTo(highlightX, highlightOffset);
+ bgFill.lineTo(highlightX + highlightWidth, highlightOffset);
+ }
+ }
+
+ /**
+ * @private
+ */
+ override protected function layoutContents(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ super.layoutContents(unscaledWidth, unscaledHeight);
+
+ // pad the arrow so that the edges are within the background corner radius
+ if (isArrowHorizontal)
+ {
+ arrow.width = arrowHeight;
+ arrow.height = arrowWidth + (backgroundCornerRadius * 2);
+ }
+ else if (isArrowVertical)
+ {
+ arrow.width = arrowWidth + (backgroundCornerRadius * 2);
+ arrow.height = arrowHeight;
+ }
+
+ setElementSize(backgroundFill, unscaledWidth, unscaledHeight);
+ setElementPosition(backgroundFill, 0, 0);
+
+ var frameX:Number = 0;
+ var frameY:Number = 0;
+ var frameWidth:Number = unscaledWidth;
+ var frameHeight:Number = unscaledHeight;
+
+ switch (hostComponent.arrowDirection)
+ {
+ case ArrowDirection.UP:
+ frameY = arrow.height;
+ frameHeight -= arrow.height;
+ break;
+ case ArrowDirection.DOWN:
+ frameHeight -= arrow.height;
+ break;
+ case ArrowDirection.LEFT:
+ frameX = arrow.width;
+ frameWidth -= arrow.width;
+ break;
+ case ArrowDirection.RIGHT:
+ frameWidth -= arrow.width;
+ break;
+ default:
+ // no arrow, content takes all available space
+ break;
+ }
+
+ if (dropShadow)
+ {
+ setElementSize(dropShadow, frameWidth, frameHeight);
+ setElementPosition(dropShadow, frameX, frameY);
+ }
+
+ // Show frameThickness by inset of contentGroup
+ var borderWeight:Number = actualBorderThickness;
+ var contentBackgroundAdjustment:Number = frameThickness + borderWeight;
+
+ var contentBackgroundX:Number = frameX + contentBackgroundAdjustment;
+ var contentBackgroundY:Number = frameY + contentBackgroundAdjustment;
+
+ contentBackgroundAdjustment = contentBackgroundAdjustment * 2;
+ var contentBackgroundWidth:Number = frameWidth - contentBackgroundAdjustment;
+ var contentBackgroundHeight:Number = frameHeight - contentBackgroundAdjustment;
+
+ if (contentBackgroundGraphic)
+ {
+ setElementSize(contentBackgroundGraphic, contentBackgroundWidth, contentBackgroundHeight);
+ setElementPosition(contentBackgroundGraphic, contentBackgroundX, contentBackgroundY);
+ }
+
+ setElementSize(contentGroup, contentBackgroundWidth, contentBackgroundHeight);
+ setElementPosition(contentGroup, contentBackgroundX, contentBackgroundY);
+
+ // mask position is in the contentGroup coordinate space
+ if (contentMask)
+ setElementSize(contentMask, contentBackgroundWidth, contentBackgroundHeight);
+ }
+
+ override public function styleChanged(styleProp:String):void
+ {
+ super.styleChanged(styleProp);
+
+ var allStyles:Boolean = !styleProp || styleProp == "styleName";
+
+ if (allStyles || (styleProp == "contentBackgroundAppearance"))
+ invalidateProperties();
+
+ if (allStyles || (styleProp == "backgroundAlpha"))
+ {
+ var backgroundAlpha:Number = getStyle("backgroundAlpha");
+
+ // Use BlendMode.LAYER to allow CalloutArrow to erase the dropShadow
+ // when the Callout background is transparent
+ blendMode = (backgroundAlpha < 1) ? BlendMode.LAYER : BlendMode.NORMAL;
+ }
+ }
+
+ /**
+ * @private
+ */
+ mx_internal function get isArrowHorizontal():Boolean
+ {
+ return (hostComponent.arrowDirection == ArrowDirection.LEFT
+ || hostComponent.arrowDirection == ArrowDirection.RIGHT);
+ }
+
+ /**
+ * @private
+ */
+ mx_internal function get isArrowVertical():Boolean
+ {
+ return (hostComponent.arrowDirection == ArrowDirection.UP
+ || hostComponent.arrowDirection == ArrowDirection.DOWN);
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Event handlers
+ //
+ //--------------------------------------------------------------------------
+
+ private function stateChangeComplete(event:Event=null):void
+ {
+ if (fade && event)
+ fade.removeEventListener(EffectEvent.EFFECT_END, stateChangeComplete);
+
+ // SkinnablePopUpContainer relies on state changes for open and close
+ dispatchEvent(new FlexEvent(FlexEvent.STATE_CHANGE_COMPLETE));
+ }
+}
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/flex-sdk/blob/3fd6027d/frameworks/projects/mobiletheme/src/spark/skins/ios7/CheckBoxSkin.as
----------------------------------------------------------------------
diff --git a/frameworks/projects/mobiletheme/src/spark/skins/ios7/CheckBoxSkin.as b/frameworks/projects/mobiletheme/src/spark/skins/ios7/CheckBoxSkin.as
new file mode 100644
index 0000000..f091205
--- /dev/null
+++ b/frameworks/projects/mobiletheme/src/spark/skins/ios7/CheckBoxSkin.as
@@ -0,0 +1,268 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+// 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.android4
+{
+ import flash.display.DisplayObject;
+
+ import mx.core.DPIClassification;
+
+ import spark.skins.android4.assets.CheckBox_up;
+ import spark.skins.mobile.supportClasses.SelectableButtonSkinBase;
+
+ /**
+ * ActionScript-based skin for CheckBox components in mobile applications.
+ *
+ * @see spark.components.CheckBox
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public class CheckBoxSkin extends SelectableButtonSkinBase
+ {
+ //--------------------------------------------------------------------------
+ //
+ // Class constants
+ //
+ //--------------------------------------------------------------------------
+
+ private static const exclusions:Array = ["labelDisplay", "labelDisplayShadow"];
+
+ //--------------------------------------------------------------------------
+ //
+ // Member variables
+ //
+ //--------------------------------------------------------------------------
+
+ protected var symbolOffsetX:Number;
+ protected var symbolOffsetY:Number;
+ protected var iconWidth:Number;
+ protected var iconHeight:Number;
+ protected var symbolWidth:Number;
+ protected var symbolHeight:Number;
+
+ //--------------------------------------------------------------------------
+ //
+ // Constructor
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * Constructor.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public function CheckBoxSkin()
+ {
+ super();
+
+ layoutPaddingLeft = 0;
+ layoutPaddingRight = 0;
+ layoutPaddingTop = 0;
+ layoutPaddingBottom = 0;
+
+ upIconClass = spark.skins.android4.assets.CheckBox_up;
+ upSelectedIconClass = spark.skins.android4.assets.CheckBox_upSelected;
+ downIconClass = spark.skins.android4.assets.CheckBox_down;
+ downSelectedIconClass = spark.skins.android4.assets.CheckBox_downSelected;
+ upSymbolIconClass = null;
+ upSymbolIconSelectedClass = spark.skins.android4.assets.CheckBox_upSymbolSelected;
+ downSymbolIconSelectedClass = spark.skins.android4.assets.CheckBox_downSymbolSelected;
+ downSymbolIconClass = null;
+
+ switch (applicationDPI)
+ {
+ case DPIClassification.DPI_640:
+ {
+
+ layoutGap = 16;
+ minWidth = 128;
+ minHeight = 128;
+ layoutBorderSize = 6;
+ iconWidth = 128;
+ iconHeight = 128;
+ symbolWidth = 64;
+ symbolHeight = 64;
+ symbolOffsetX = 32;
+ symbolOffsetY = 32;
+
+ break;
+ }
+ case DPIClassification.DPI_480:
+ {
+
+ layoutGap = 12;
+ minWidth = 96;
+ minHeight = 96;
+ layoutBorderSize = 4;
+ iconWidth = 96;
+ iconHeight = 96;
+ symbolWidth = 48;
+ symbolHeight = 48;
+ symbolOffsetX = 24;
+ symbolOffsetY = 24;
+
+ break;
+ }
+ case DPIClassification.DPI_320:
+ {
+
+ layoutGap = 8;
+ minWidth = 64;
+ minHeight = 64;
+ layoutBorderSize = 3;
+ iconWidth = 64;
+ iconHeight = 64;
+ symbolWidth = 32;
+ symbolHeight = 32;
+ symbolOffsetX = 16;
+ symbolOffsetY = 16;
+
+ break;
+ }
+ case DPIClassification.DPI_240:
+ {
+
+ layoutGap = 6;
+ minWidth = 48;
+ minHeight = 48;
+ layoutBorderSize = 2;
+ iconWidth = 48;
+ iconHeight = 48;
+ symbolWidth = 24;
+ symbolHeight = 24;
+ symbolOffsetX = 12;
+ symbolOffsetY = 12;
+
+ break;
+ }
+ case DPIClassification.DPI_120:
+ {
+
+ layoutGap = 3;
+ minWidth = 24;
+ minHeight = 24;
+ layoutBorderSize = 1;
+ iconWidth = 24;
+ iconHeight = 24;
+ symbolWidth = 12;
+ symbolHeight = 12;
+ symbolOffsetX = 6;
+ symbolOffsetY = 6;
+
+ break;
+ }
+ default:
+ {
+ // default DPI_160
+
+ layoutGap = 4;
+ minWidth = 32;
+ minHeight = 32;
+ layoutBorderSize = 2;
+ iconWidth = 32;
+ iconHeight = 32;
+ symbolWidth = 16;
+ symbolHeight = 16;
+ symbolOffsetX = 8;
+ symbolOffsetY = 8;
+
+
+ break;
+ }
+ }
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Overridden methods
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @private
+ * CheckBox <code>chromeColor</code> is drawn to match the FXG rectangle
+ * shape and position.
+ */
+ override protected function drawBackground(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ // super draws a transparent hit zone
+ super.drawBackground(unscaledWidth, unscaledHeight);
+
+ // get the size and position of iconDisplay
+ var currentIcon:DisplayObject = getIconDisplay();
+ var widthAdjustment:Number = layoutBorderSize * 2;
+
+ graphics.beginFill(getStyle("chromeColor"));
+ graphics.drawRoundRect(currentIcon.x + layoutBorderSize,
+ currentIcon.y + layoutBorderSize,
+ currentIcon.width - widthAdjustment,
+ currentIcon.height - widthAdjustment, layoutBorderSize, layoutBorderSize);
+ graphics.endFill();
+ }
+
+ /**
+ * List of IDs of items that should be excluded when rendering the focus ring.
+ * Only items of type DisplayObject or GraphicElement should be excluded. Items
+ * of other types are ignored.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ override protected function get focusSkinExclusions():Array
+ {
+ return exclusions;
+ }
+
+ override protected function commitCurrentState():void
+ {
+ super.commitCurrentState();
+ if(symbolIcon != null)
+ {
+ symbolIcon.width = symbolWidth;
+ symbolIcon.height = symbolHeight;
+ }
+ var iconDisplay:DisplayObject = getIconDisplay();
+ if(iconDisplay != null)
+ {
+ iconDisplay.width = iconWidth;
+ iconDisplay.height = iconHeight;
+ }
+ }
+
+ override protected function layoutContents(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ super.layoutContents(unscaledWidth, unscaledHeight);
+ // position the symbols to align with the background "icon"
+ if (symbolIcon)
+ {
+ var currentIcon:DisplayObject = getIconDisplay();
+ setElementPosition(symbolIcon, symbolOffsetX, symbolOffsetY);
+ }
+ }
+
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/flex-sdk/blob/3fd6027d/frameworks/projects/mobiletheme/src/spark/skins/ios7/HScrollBarSkin.as
----------------------------------------------------------------------
diff --git a/frameworks/projects/mobiletheme/src/spark/skins/ios7/HScrollBarSkin.as b/frameworks/projects/mobiletheme/src/spark/skins/ios7/HScrollBarSkin.as
new file mode 100644
index 0000000..1e71279
--- /dev/null
+++ b/frameworks/projects/mobiletheme/src/spark/skins/ios7/HScrollBarSkin.as
@@ -0,0 +1,205 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+// 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.android4
+{
+
+import mx.core.DPIClassification;
+import mx.core.mx_internal;
+
+import spark.components.Button;
+import spark.components.HScrollBar;
+import spark.skins.mobile.supportClasses.MobileSkin;
+
+use namespace mx_internal;
+
+/**
+ * ActionScript-based skin for HScrollBar components in mobile applications.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+public class HScrollBarSkin extends MobileSkin
+{
+ //--------------------------------------------------------------------------
+ //
+ // Variables
+ //
+ //--------------------------------------------------------------------------
+ /**
+ * Constructor.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public function HScrollBarSkin()
+ {
+ super();
+
+ minWidth = 20;
+ thumbSkinClass = HScrollBarThumbSkin;
+ var paddingBottom:int;
+ var paddingHorizontal:int;
+
+ // Depending on density set our measured height
+ switch (applicationDPI)
+ {
+ case DPIClassification.DPI_640:
+ {
+ minHeight = 24;
+ paddingBottom = HScrollBarThumbSkin.PADDING_BOTTOM_640DPI;
+ paddingHorizontal = HScrollBarThumbSkin.PADDING_HORIZONTAL_640DPI;
+ break;
+ }
+ case DPIClassification.DPI_480:
+ {
+ minHeight = 18;
+ paddingBottom = HScrollBarThumbSkin.PADDING_BOTTOM_480DPI;
+ paddingHorizontal = HScrollBarThumbSkin.PADDING_HORIZONTAL_480DPI;
+ break;
+ }
+ case DPIClassification.DPI_320:
+ {
+ minHeight = 12;
+ paddingBottom = HScrollBarThumbSkin.PADDING_BOTTOM_320DPI;
+ paddingHorizontal = HScrollBarThumbSkin.PADDING_HORIZONTAL_320DPI;
+ break;
+ }
+ case DPIClassification.DPI_240:
+ {
+ minHeight = 9;
+ paddingBottom = HScrollBarThumbSkin.PADDING_BOTTOM_240DPI;
+ paddingHorizontal = HScrollBarThumbSkin.PADDING_HORIZONTAL_240DPI;
+ break;
+ }
+ case DPIClassification.DPI_120:
+ {
+ minHeight = 5;
+ paddingBottom = HScrollBarThumbSkin.PADDING_BOTTOM_120DPI;
+ paddingHorizontal = HScrollBarThumbSkin.PADDING_HORIZONTAL_120DPI;
+ break;
+ }
+ default:
+ {
+ // default DPI_160
+ minHeight = 6;
+ paddingBottom = HScrollBarThumbSkin.PADDING_BOTTOM_DEFAULTDPI;
+ paddingHorizontal = HScrollBarThumbSkin.PADDING_HORIZONTAL_DEFAULTDPI;
+ break;
+ }
+ }
+
+ // The minimum width is set such that, at it's smallest size, the thumb appears
+ // as wide as it is high.
+ minThumbWidth = (minHeight - paddingBottom) + (paddingHorizontal * 2);
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Variables
+ //
+ //--------------------------------------------------------------------------
+ /**
+ * @copy spark.skins.spark.ApplicationSkin#hostComponent
+ */
+ public var hostComponent:HScrollBar;
+
+ /**
+ * Minimum width for the thumb
+ */
+ protected var minThumbWidth:Number;
+
+ /**
+ * Skin to use for the thumb Button skin part
+ */
+ protected var thumbSkinClass:Class;
+
+ //--------------------------------------------------------------------------
+ //
+ // Skin parts
+ //
+ //--------------------------------------------------------------------------
+ /**
+ * HScrollbar track skin part.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public var track:Button;
+
+ /**
+ * HScrollbar thumb skin part.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public var thumb:Button;
+
+
+ //--------------------------------------------------------------------------
+ //
+ // Overridden methods
+ //
+ //--------------------------------------------------------------------------
+ /**
+ * @private
+ */
+ override protected function createChildren():void
+ {
+ // Create our skin parts if necessary: track and thumb.
+ if (!track)
+ {
+ // We don't want a visible track so we set the skin to MobileSkin
+ track = new Button();
+ track.setStyle("skinClass", spark.skins.mobile.supportClasses.MobileSkin);
+ track.width = minWidth;
+ track.height = minHeight;
+ addChild(track);
+ }
+
+ if (!thumb)
+ {
+ thumb = new Button();
+ thumb.minWidth = minThumbWidth;
+ thumb.setStyle("skinClass", thumbSkinClass);
+ thumb.width = minHeight;
+ thumb.height = minHeight;
+ addChild(thumb);
+ }
+ }
+
+ /**
+ * @private
+ */
+ override protected function layoutContents(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ super.layoutContents(unscaledWidth, unscaledHeight);
+
+ setElementSize(track, unscaledWidth, unscaledHeight);
+ }
+}
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/flex-sdk/blob/3fd6027d/frameworks/projects/mobiletheme/src/spark/skins/ios7/HScrollBarThumbSkin.as
----------------------------------------------------------------------
diff --git a/frameworks/projects/mobiletheme/src/spark/skins/ios7/HScrollBarThumbSkin.as b/frameworks/projects/mobiletheme/src/spark/skins/ios7/HScrollBarThumbSkin.as
new file mode 100644
index 0000000..ed3a6b9
--- /dev/null
+++ b/frameworks/projects/mobiletheme/src/spark/skins/ios7/HScrollBarThumbSkin.as
@@ -0,0 +1,169 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+// 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.android4
+{
+
+import flash.display.CapsStyle;
+import flash.display.JointStyle;
+import flash.display.LineScaleMode;
+
+import mx.core.DPIClassification;
+import mx.core.mx_internal;
+
+import spark.components.Button;
+import spark.skins.mobile.supportClasses.MobileSkin;
+
+use namespace mx_internal;
+
+/**
+ * ActionScript-based skin for the HScrollBar thumb skin part in mobile applications.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+public class HScrollBarThumbSkin extends MobileSkin
+{
+ //--------------------------------------------------------------------------
+ //
+ // Class constants
+ //
+ //--------------------------------------------------------------------------
+
+ // These constants are also accessed from HScrollBarSkin
+ mx_internal static const PADDING_BOTTOM_640DPI:int = 10;
+ mx_internal static const PADDING_HORIZONTAL_640DPI:int = 8;
+ mx_internal static const PADDING_BOTTOM_480DPI:int = 8;
+ mx_internal static const PADDING_HORIZONTAL_480DPI:int = 6;
+ mx_internal static const PADDING_BOTTOM_320DPI:int = 5;
+ mx_internal static const PADDING_HORIZONTAL_320DPI:int = 4;
+ mx_internal static const PADDING_BOTTOM_240DPI:int = 4;
+ mx_internal static const PADDING_HORIZONTAL_240DPI:int = 3;
+ mx_internal static const PADDING_BOTTOM_120DPI:int = 2;
+ mx_internal static const PADDING_HORIZONTAL_120DPI:int = 2;
+ mx_internal static const PADDING_BOTTOM_DEFAULTDPI:int = 3;
+ mx_internal static const PADDING_HORIZONTAL_DEFAULTDPI:int = 2;
+
+ //--------------------------------------------------------------------------
+ //
+ // Constructor
+ //
+ //--------------------------------------------------------------------------
+ /**
+ * Constructor.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public function HScrollBarThumbSkin()
+ {
+ super();
+
+ // Depending on density set padding
+ switch (applicationDPI)
+ {
+ case DPIClassification.DPI_480:
+ {
+ paddingBottom = PADDING_BOTTOM_480DPI;
+ paddingHorizontal = PADDING_HORIZONTAL_480DPI;
+ break;
+ }
+ case DPIClassification.DPI_320:
+ {
+ paddingBottom = PADDING_BOTTOM_320DPI;
+ paddingHorizontal = PADDING_HORIZONTAL_320DPI;
+ break;
+ }
+ case DPIClassification.DPI_240:
+ {
+ paddingBottom = PADDING_BOTTOM_240DPI;
+ paddingHorizontal = PADDING_HORIZONTAL_240DPI;
+ break;
+ }
+ default:
+ {
+ paddingBottom = PADDING_BOTTOM_DEFAULTDPI;
+ paddingHorizontal = PADDING_HORIZONTAL_DEFAULTDPI;
+ break;
+ }
+ }
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Properties
+ //
+ //--------------------------------------------------------------------------
+ /**
+ * @copy spark.skins.spark.ApplicationSkin#hostComponent
+ */
+ public var hostComponent:Button;
+
+ //--------------------------------------------------------------------------
+ //
+ // Variables
+ //
+ //--------------------------------------------------------------------------
+ /**
+ * Padding from bottom.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var paddingBottom:int;
+
+ /**
+ * Horizontal padding from left and right.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var paddingHorizontal:int;
+
+
+ //--------------------------------------------------------------------------
+ //
+ // Overridden methods
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @private
+ */
+ override protected function drawBackground(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ super.drawBackground(unscaledWidth, unscaledHeight);
+
+ var thumbHeight:Number = unscaledHeight - paddingBottom;
+
+ graphics.beginFill(getStyle("thumbColor"), 1);
+ graphics.drawRect(paddingHorizontal + .5, 0.5, unscaledWidth - 2 * paddingHorizontal, thumbHeight);
+
+ graphics.endFill();
+ }
+}
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/flex-sdk/blob/3fd6027d/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderSkin.as
----------------------------------------------------------------------
diff --git a/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderSkin.as b/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderSkin.as
new file mode 100644
index 0000000..6f970f8
--- /dev/null
+++ b/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderSkin.as
@@ -0,0 +1,293 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+// 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.android4
+{
+ import flash.display.BlendMode;
+ import flash.display.DisplayObject;
+ import flash.events.Event;
+
+ import mx.core.ClassFactory;
+ import mx.core.IFactory;
+
+ import spark.components.Button;
+ import spark.components.HSlider;
+ import spark.skins.android4.assets.HSliderTrack_filled;
+ import spark.skins.mobile.supportClasses.HSliderDataTip;
+ import spark.skins.mobile.supportClasses.MobileSkin;
+
+ /**
+ * Android 4.x specific ActionScript-based skin for HSlider controls in mobile applications.
+ *
+ * <p>The base Flex implementation creates an HSlider with fixed height
+ * and variable width with a fixed-size thumb. As the height of the
+ * HSlider component increases, the vertical dimensions of the visible HSlider remain
+ * the same, and the HSlider stays vertically centered.</p>
+ *
+ * <p>The thumb and track implementations can be customized by subclassing
+ * this skin class and overriding the thumbSkinClass, trackSkinClass,
+ * and/or dataTipClass variables as necessary.</p>
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public class HSliderSkin extends MobileSkin
+ {
+ //--------------------------------------------------------------------------
+ //
+ // Constructor
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * Constructor.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ *
+ */
+ public function HSliderSkin()
+ {
+ super();
+
+ thumbSkinClass = spark.skins.android4.HSliderThumbSkin;
+ trackSkinClass = spark.skins.android4.HSliderTrackSkin;
+ filledTrackSkinClass = spark.skins.android4.assets.HSliderTrack_filled;
+ dataTipClass = spark.skins.mobile.supportClasses.HSliderDataTip;
+
+ blendMode = BlendMode.LAYER;
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Properties
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @copy spark.skins.spark.ApplicationSkin#hostComponent
+ */
+ private var _hostComponent:HSlider;
+
+ /**
+ * @copy spark.skins.spark.ApplicationSkin#hostComponent
+ */
+ public function get hostComponent():HSlider
+ {
+ return _hostComponent;
+ }
+
+ public function set hostComponent(value:HSlider):void
+ {
+ if (_hostComponent)
+ _hostComponent.removeEventListener(Event.CHANGE, thumbPositionChanged_handler);
+ _hostComponent = value;
+ if (_hostComponent)
+ _hostComponent.addEventListener(Event.CHANGE, thumbPositionChanged_handler);
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Skin parts
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * HSlider track skin part
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public var track:Button;
+
+ /**
+ * HSlider track skin part that
+ * depicts area that is filled
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public var filledTrack:DisplayObject;
+
+ /**
+ * HSlider thumb skin part
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public var thumb:Button;
+
+ /**
+ * HSlider dataTip class factory
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public var dataTip:IFactory;
+
+ //--------------------------------------------------------------------------
+ //
+ // Variables
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * Specifies the skin class that will be used for the HSlider thumb.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var thumbSkinClass:Class;
+
+ /**
+ * Specifies the skin class that will be used for the HSlider track.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var trackSkinClass:Class;
+ /**
+ * Specifies the skin class that will be used for the HSlider track's
+ * filled area.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var filledTrackSkinClass:Class;
+
+ /**
+ * Specifies the class that will be used for the HSlider datatip.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var dataTipClass:Class;
+
+ //--------------------------------------------------------------------------
+ //
+ // Overridden methods
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @private
+ */
+ override protected function commitCurrentState():void
+ {
+ if (currentState == "disabled")
+ alpha = 0.5;
+ else if (currentState == "normal")
+ alpha = 1;
+ }
+
+ /**
+ * @private
+ */
+ override protected function createChildren():void
+ {
+ // Create our skin parts: track and thumb
+ track = new Button();
+ track.setStyle("skinClass", trackSkinClass);
+ addChild(track);
+
+ filledTrack = new filledTrackSkinClass();
+ addChild(filledTrack);
+
+ thumb = new Button();
+ thumb.setStyle("skinClass", thumbSkinClass);
+ addChild(thumb);
+
+ // Set up the class factory for the dataTip
+ dataTip = new ClassFactory();
+ ClassFactory(dataTip).generator = dataTipClass;
+ }
+
+ /**
+ * @private
+ * The HSliderSkin width will be no less than the width of the thumb skin.
+ * The HSliderSkin height will be no less than the greater of the heights of
+ * the thumb and track skins.
+ */
+ override protected function measure():void
+ {
+ measuredWidth = track.getPreferredBoundsWidth();
+ measuredHeight = Math.max(track.getPreferredBoundsHeight(), thumb.getPreferredBoundsHeight());
+
+ measuredMinHeight = Math.max(track.getPreferredBoundsHeight(), thumb.getPreferredBoundsHeight());
+ measuredMinWidth = thumb.getPreferredBoundsWidth();
+ }
+
+ /**
+ * @private
+ */
+ override protected function layoutContents(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ super.layoutContents(unscaledWidth, unscaledHeight);
+
+ // minimum height is no smaller than the larger of the thumb or track
+ var calculatedSkinHeight:int = Math.max(Math.max(thumb.getPreferredBoundsHeight(), track.getPreferredBoundsHeight()),
+ unscaledHeight);
+
+ // minimum width is no smaller than the thumb
+ var calculatedSkinWidth:int = Math.max(thumb.getPreferredBoundsWidth(),
+ unscaledWidth);
+
+ // once we know the skin height, center the thumb and track
+ thumb.y = Math.max(Math.round((calculatedSkinHeight - thumb.getPreferredBoundsHeight()) / 2), 0);
+ var calculatedTrackY:int = Math.max(Math.round((calculatedSkinHeight - track.getPreferredBoundsHeight()) / 2), 0);
+
+ // size and position
+ setElementSize(thumb, thumb.getPreferredBoundsWidth(), thumb.getPreferredBoundsHeight()); // thumb does NOT scale
+ setElementSize(track, calculatedSkinWidth, track.getPreferredBoundsHeight()); // note track is NOT scaled vertically
+ setElementPosition(track, 0, calculatedTrackY);
+
+ //Set size and position of filled area based on thumb's current location
+ var filledTrackWidth:Number = thumb.getLayoutBoundsX();
+ setElementSize(filledTrack, filledTrackWidth, track.getPreferredBoundsHeight()); // note track is NOT scaled vertically
+ setElementPosition(filledTrack, track.x + HSliderTrackSkin(track.skin).visibleTrackOffset , calculatedTrackY);
+ }
+
+ private function thumbPositionChanged_handler(event:Event):void
+ {
+ //Just trigger a redraw so that the filled area of the track updates itself
+ invalidateDisplayList();
+ }
+
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/flex-sdk/blob/3fd6027d/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderThumbSkin.as
----------------------------------------------------------------------
diff --git a/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderThumbSkin.as b/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderThumbSkin.as
new file mode 100644
index 0000000..517ff93
--- /dev/null
+++ b/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderThumbSkin.as
@@ -0,0 +1,333 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+// 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.android4
+{
+import flash.display.DisplayObject;
+
+import mx.core.DPIClassification;
+
+import spark.components.Button;
+import spark.skins.android4.assets.HSliderThumb_normal;
+import spark.skins.mobile.supportClasses.MobileSkin;
+
+/**
+ * Android 4.x specific ActionScript-based skin for the HSlider thumb skin part in mobile applications.
+ *
+ * <p>Note that this particular implementation defines a hit zone which is larger than
+ * the visible thumb for better usability on mobile screens.</p>
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+public class HSliderThumbSkin extends MobileSkin
+{
+ //--------------------------------------------------------------------------
+ //
+ // Constructor
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * Constructor.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ *
+ */
+ public function HSliderThumbSkin()
+ {
+ super();
+
+ thumbNormalClass = spark.skins.android4.assets.HSliderThumb_normal;
+ thumbPressedClass = spark.skins.android4.assets.HSliderThumb_pressed;
+
+ // set the dimensions to use based on the screen density
+ switch (applicationDPI)
+ {
+ case DPIClassification.DPI_640:
+ {
+ thumbImageWidth = 116;
+ thumbImageHeight = 116;
+
+ hitZoneOffset = 20;
+ hitZoneSideLength = 160;
+
+ break;
+ }
+ case DPIClassification.DPI_480:
+ {
+ // Note provisional may need changes
+ thumbImageWidth = 88;
+ thumbImageHeight = 88;
+
+ hitZoneOffset = 20;
+ hitZoneSideLength = 130;
+
+ break;
+ }
+ case DPIClassification.DPI_320:
+ {
+ thumbImageWidth = 58;
+ thumbImageHeight = 58;
+
+ hitZoneOffset = 10;
+ hitZoneSideLength = 80;
+
+ break;
+ }
+ case DPIClassification.DPI_240:
+ {
+ thumbImageWidth = 44;
+ thumbImageHeight = 44;
+
+ hitZoneOffset = 10;
+ hitZoneSideLength = 65;
+
+ break;
+ }
+ case DPIClassification.DPI_120:
+ {
+ thumbImageWidth = 22;
+ thumbImageHeight = 22;
+
+ hitZoneOffset = 5;
+ hitZoneSideLength = 33;
+
+ break;
+ }
+ default:
+ {
+ // default DPI_160
+ thumbImageWidth = 29;
+ thumbImageHeight = 29;
+
+ hitZoneOffset = 5;
+ hitZoneSideLength = 40;
+
+ break;
+ }
+
+ }
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Properties
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @copy spark.skins.spark.ApplicationSkin#hostComponent
+ */
+ public var hostComponent:Button;
+
+ //--------------------------------------------------------------------------
+ //
+ // Variables
+ //
+ //--------------------------------------------------------------------------
+
+ // FXG thumb classes
+ /**
+ * Specifies the FXG class to use when the thumb is in the normal state
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var thumbNormalClass:Class;
+
+ /**
+ * Specifies the FXG class to use when the thumb is in the pressed state
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var thumbPressedClass:Class;
+
+ /**
+ * Specifies the DisplayObject to use when the thumb is in the normal state
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var thumbSkin_normal:DisplayObject;
+
+ /**
+ * Specifies the DisplayObject to use when the thumb is in the pressed state
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var thumbSkin_pressed:DisplayObject;
+
+ /**
+ * Specifies the current DisplayObject that should be shown
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var currentThumbSkin:DisplayObject;
+
+ /**
+ * Width of the overall thumb image
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var thumbImageWidth:int;
+
+ /**
+ * Height of the overall thumb image
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var thumbImageHeight:int;
+
+ /**
+ * Length of the sizes of the hitzone (assumed to be square)
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var hitZoneSideLength:int;
+
+ /**
+ * Distance between the left edge of the hitzone and the left edge
+ * of the thumb
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var hitZoneOffset:int;
+
+ /**
+ * @private
+ * Remember which state is currently being displayed
+ */
+ private var displayedState:String;
+
+ //--------------------------------------------------------------------------
+ //
+ // Overridden methods
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @private
+ */
+ override protected function commitCurrentState():void
+ {
+ if (currentState == "up")
+ {
+ // show the normal button
+ if (!thumbSkin_normal)
+ {
+ thumbSkin_normal = new thumbNormalClass();
+ addChild(thumbSkin_normal);
+ }
+ else
+ {
+ thumbSkin_normal.visible = true;
+ }
+ currentThumbSkin = thumbSkin_normal;
+
+ // hide the pressed button
+ if (thumbSkin_pressed)
+ thumbSkin_pressed.visible = false;
+ }
+ else if (currentState == "down")
+ {
+ // show the pressed button
+ if (!thumbSkin_pressed)
+ {
+ thumbSkin_pressed = new thumbPressedClass();
+ addChild(thumbSkin_pressed);
+ }
+ else
+ {
+ thumbSkin_pressed.visible = true;
+ }
+ currentThumbSkin = thumbSkin_pressed;
+
+ // hide the normal button
+ if (thumbSkin_normal)
+ thumbSkin_normal.visible = false;
+ }
+
+ displayedState = currentState;
+
+ invalidateDisplayList();
+ }
+
+ /**
+ * @private
+ */
+ override protected function measure():void
+ {
+ measuredWidth = thumbImageWidth;
+ measuredHeight = thumbImageHeight;
+ }
+
+ /**
+ * @private
+ */
+ override protected function layoutContents(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ super.layoutContents(unscaledWidth, unscaledHeight);
+
+ setElementSize(currentThumbSkin, unscaledWidth, unscaledHeight);
+ setElementPosition(currentThumbSkin, 0, 0)
+ }
+
+ /**
+ * @private
+ */
+ override protected function drawBackground(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ // put in a larger hit zone than the thumb
+ graphics.beginFill(0xffffff, 0);
+ graphics.drawRect(-hitZoneOffset, -hitZoneOffset, hitZoneSideLength, hitZoneSideLength);
+ graphics.endFill();
+ }
+}
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/flex-sdk/blob/3fd6027d/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderTrackSkin.as
----------------------------------------------------------------------
diff --git a/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderTrackSkin.as b/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderTrackSkin.as
new file mode 100644
index 0000000..57dc8f3
--- /dev/null
+++ b/frameworks/projects/mobiletheme/src/spark/skins/ios7/HSliderTrackSkin.as
@@ -0,0 +1,227 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+// 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.android4
+{
+ import flash.display.DisplayObject;
+
+ import mx.core.DPIClassification;
+
+ import spark.components.Button;
+ import spark.skins.android4.assets.HSliderTrack;
+ import spark.skins.mobile.supportClasses.MobileSkin;
+
+ /**
+ * ActionScript-based skin for the HSlider track skin part in mobile applications.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public class HSliderTrackSkin extends MobileSkin
+ {
+ //--------------------------------------------------------------------------
+ //
+ // Constructor
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * Constructor.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ *
+ */
+ public function HSliderTrackSkin()
+ {
+ super();
+
+ trackClass = spark.skins.android4.assets.HSliderTrack;
+
+ // set the right dimensions to use based on the screen density
+ switch (applicationDPI)
+ {
+ case DPIClassification.DPI_640:
+ {
+ trackWidth = 1200;
+ trackHeight = 8;
+
+ visibleTrackOffset = 48;
+
+ break;
+ }
+ case DPIClassification.DPI_480:
+ {
+ trackWidth = 900;
+ trackHeight = 6;
+
+ visibleTrackOffset = 38;
+
+ break;
+ }
+ case DPIClassification.DPI_320:
+ {
+ trackWidth = 600;
+ trackHeight = 4;
+
+ visibleTrackOffset = 24;
+
+ break;
+ }
+ case DPIClassification.DPI_240:
+ {
+ trackWidth = 450;
+ trackHeight = 3;
+
+ visibleTrackOffset = 18;
+
+ break;
+ }
+ case DPIClassification.DPI_120:
+ {
+ trackWidth = 225;
+ trackHeight = 2;
+
+ visibleTrackOffset = 9;
+
+ break;
+ }
+ default:
+ {
+ // default DPI_160
+ trackWidth = 300;
+ trackHeight = 2;
+
+ visibleTrackOffset = 12;
+
+ break;
+ }
+ }
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Properties
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @copy spark.skins.spark.ApplicationSkin#hostComponent
+ */
+ public var hostComponent:Button;
+
+ //--------------------------------------------------------------------------
+ //
+ // Variables
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * Specifies the FXG class to use for the track image
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var trackClass:Class;
+
+ /**
+ * Specifies the DisplayObject for the track image
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var trackSkin:DisplayObject;
+
+ /**
+ * Specifies the track image width
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var trackWidth:int;
+
+ /**
+ * Specifies the track image height
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ protected var trackHeight:int;
+
+ /**
+ * Specifies the offset from the left and right edge to where
+ * the visible track begins. This should match the offset in the FXG assets.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+ public var visibleTrackOffset:int;
+
+ //--------------------------------------------------------------------------
+ //
+ // Overridden methods
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @private
+ */
+ override protected function createChildren():void
+ {
+ trackSkin = new trackClass();
+ addChild(trackSkin);
+ }
+
+ /**
+ * @private
+ */
+ override protected function measure():void
+ {
+ measuredWidth = trackWidth;
+ measuredHeight = trackHeight;
+ }
+
+ /**
+ * @private
+ */
+ override protected function layoutContents(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ super.layoutContents(unscaledWidth, unscaledHeight);
+
+ var unscaledTrackWidth:int = unscaledWidth - (2 * visibleTrackOffset);
+ setElementSize(trackSkin, unscaledTrackWidth, unscaledHeight);
+ setElementPosition(trackSkin, visibleTrackOffset, 0);
+ }
+
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/flex-sdk/blob/3fd6027d/frameworks/projects/mobiletheme/src/spark/skins/ios7/RadioButtonSkin.as
----------------------------------------------------------------------
diff --git a/frameworks/projects/mobiletheme/src/spark/skins/ios7/RadioButtonSkin.as b/frameworks/projects/mobiletheme/src/spark/skins/ios7/RadioButtonSkin.as
new file mode 100644
index 0000000..fd74645
--- /dev/null
+++ b/frameworks/projects/mobiletheme/src/spark/skins/ios7/RadioButtonSkin.as
@@ -0,0 +1,253 @@
+////////////////////////////////////////////////////////////////////////////////
+//
+// 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.android4
+{
+
+import flash.display.DisplayObject;
+
+import mx.core.DPIClassification;
+
+import spark.skins.android4.assets.RadioButton_up;
+import spark.skins.mobile.supportClasses.SelectableButtonSkinBase;
+
+/**
+ * ActionScript-based skin for RadioButton controls in mobile applications.
+ *
+ * @see spark.components.RadioButton
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ */
+public class RadioButtonSkin extends SelectableButtonSkinBase
+{
+ //--------------------------------------------------------------------------
+ //
+ // Class constants
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @private
+ */
+ static private const exclusions:Array = ["labelDisplay", "labelDisplayShadow"];
+
+ //--------------------------------------------------------------------------
+ //
+ // Member variables
+ //
+ //--------------------------------------------------------------------------
+
+ protected var symbolOffsetX:Number;
+ protected var symbolOffsetY:Number;
+ protected var iconWidth:Number;
+ protected var iconHeight:Number;
+ protected var symbolWidth:Number;
+ protected var symbolHeight:Number;
+
+ //--------------------------------------------------------------------------
+ //
+ // Constructor
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * Constructor.
+ *
+ * @langversion 3.0
+ * @playerversion Flash 10
+ * @playerversion AIR 2.5
+ * @productversion Flex 4.5
+ *
+ */
+ public function RadioButtonSkin()
+ {
+ super();
+
+ layoutPaddingLeft = 0;
+ layoutPaddingRight = 0;
+ layoutPaddingTop = 0;
+ layoutPaddingBottom = 0;
+
+ upIconClass = spark.skins.android4.assets.RadioButton_up;
+ upSelectedIconClass = spark.skins.android4.assets.RadioButton_up;
+ downIconClass = spark.skins.android4.assets.RadioButton_down;
+ downSelectedIconClass = spark.skins.android4.assets.RadioButton_down;
+ upSymbolIconClass = null;
+ downSymbolIconClass = null;
+ upSymbolIconSelectedClass = spark.skins.android4.assets.RadioButton_upSymbolSelected;
+ downSymbolIconSelectedClass = spark.skins.android4.assets.RadioButton_downSymbolSelected;
+
+ switch (applicationDPI)
+ {
+ case DPIClassification.DPI_640:
+ {
+
+ layoutGap = 16;
+ minWidth = 128;
+ minHeight = 128;
+ iconWidth = 128;
+ iconHeight = 128;
+ symbolWidth = 44;
+ symbolHeight = 44;
+ symbolOffsetX = 44;
+ symbolOffsetY = 44;
+
+ break;
+ }
+ case DPIClassification.DPI_480:
+ {
+
+ layoutGap = 12;
+ minWidth = 96;
+ minHeight = 96;
+ iconWidth = 96;
+ iconHeight = 96;
+ symbolWidth = 33;
+ symbolHeight = 33;
+ symbolOffsetX = 33;
+ symbolOffsetY = 33;
+
+ break;
+ }
+ case DPIClassification.DPI_320:
+ {
+
+ layoutGap = 8;
+ minWidth = 64;
+ minHeight = 64;
+ iconWidth = 64;
+ iconHeight = 64;
+ symbolWidth = 22;
+ symbolHeight = 22;
+ symbolOffsetX = 22;
+ symbolOffsetY = 22;
+
+ break;
+ }
+ case DPIClassification.DPI_240:
+ {
+
+ layoutGap = 6;
+ minWidth = 48;
+ minHeight = 48;
+ iconWidth = 48;
+ iconHeight = 48;
+ symbolWidth = 16.5;
+ symbolHeight = 16.5;
+ symbolOffsetX = 16.5;
+ symbolOffsetY = 16.5;
+
+ break;
+ }
+ case DPIClassification.DPI_120:
+ {
+
+ layoutGap = 3;
+ minWidth = 24;
+ minHeight = 24;
+ iconWidth = 24;
+ iconHeight = 24;
+ symbolWidth = 8.25;
+ symbolHeight = 8.25;
+ symbolOffsetX = 8.25;
+ symbolOffsetY = 8.25;
+
+ break;
+ }
+ default:
+ {
+
+ layoutGap = 4;
+ minWidth = 32;
+ minHeight = 32;
+ iconWidth = 32;
+ iconHeight = 32;
+ symbolWidth = 11;
+ symbolHeight = 11;
+ symbolOffsetX = 11;
+ symbolOffsetY = 11;
+
+ break;
+ }
+ }
+ }
+
+ //--------------------------------------------------------------------------
+ //
+ // Overridden methods
+ //
+ //--------------------------------------------------------------------------
+
+ /**
+ * @private
+ * RadioButton <code>chromeColor</code> is drawn to match the FXG ellipse
+ * shape and position.
+ */
+ override protected function drawBackground(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ // super draws a transparent hit zone
+ super.drawBackground(unscaledWidth, unscaledHeight);
+
+ // get the size and position of iconDisplay
+ var currentIcon:DisplayObject = getIconDisplay();
+
+ graphics.beginFill(getStyle("chromeColor"));
+ graphics.drawEllipse(currentIcon.x + 1, currentIcon.y + 1, currentIcon.width - 2, currentIcon.height - 2);
+ graphics.endFill();
+ }
+
+ /**
+ * @private
+ */
+ override protected function get focusSkinExclusions():Array
+ {
+ return exclusions;
+ }
+
+ override protected function commitCurrentState():void
+ {
+ super.commitCurrentState();
+ if(symbolIcon != null)
+ {
+ symbolIcon.width = symbolWidth;
+ symbolIcon.height = symbolHeight;
+ }
+ var iconDisplay:DisplayObject = getIconDisplay();
+ if(iconDisplay != null)
+ {
+ iconDisplay.width = iconWidth;
+ iconDisplay.height = iconHeight;
+ }
+ }
+
+ override protected function layoutContents(unscaledWidth:Number, unscaledHeight:Number):void
+ {
+ super.layoutContents(unscaledWidth, unscaledHeight);
+ // position the symbols to align with the background "icon"
+ if (symbolIcon)
+ {
+ var currentIcon:DisplayObject = getIconDisplay();
+ setElementPosition(symbolIcon, symbolOffsetX, symbolOffsetY);
+ }
+ }
+}
+}
\ No newline at end of file