diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..316ccfa
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,23 @@
+.DS_Store
+Thumbs.db
+*.swc
+*.stackdump
+._*
+*.local.properties
+*.p12
+out/
+output/
+third-party/
+signing/
+.actionScriptProperties
+.flexLibProperties
+.project
+.settings/
+bin-debug/
+bin-release/
+html-template/
+.metadata/
+*.iml
+.idea/
+archive/
+*.lnk
\ No newline at end of file
diff --git a/LICENSE.md b/LICENSE.md
new file mode 100644
index 0000000..53027d0
--- /dev/null
+++ b/LICENSE.md
@@ -0,0 +1,29 @@
+Simplified BSD License
+======================
+
+Copyright 2012-2015 Bowler Hat LLC. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without modification,
+are permitted provided that the following conditions are met:
+
+1. Redistributions of source code must retain the above copyright notice, this
+ list of conditions and the following disclaimer.
+
+2. Redistributions in binary form must reproduce the above copyright notice,
+ this list of conditions and the following disclaimer in the documentation
+ and/or other materials provided with the distribution.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
+ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
+ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+The views and conclusions contained in the software and documentation are those
+of the authors and should not be interpreted as representing official policies,
+either expressed or implied, of the copyright holders.
\ No newline at end of file
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..c6b4bcb
--- /dev/null
+++ b/README.md
@@ -0,0 +1,32 @@
+# Feathers UI 3.0.0-prerelease [![Build Status](https://travis-ci.org/BowlerHatLLC/feathers.svg?branch=master)](https://travis-ci.org/BowlerHatLLC/feathers)
+
+---
+
+**Warning:** This is a pre-release version of Feathers UI. It may contain bugs or unfinished features. It is not recommended for production apps because it is considered potentially *unstable*. Use at your own risk. To download a stable build, visit the [Feathers website](http://feathersui.com/).
+
+---
+
+Say hello to [Feathers UI](http://feathersui.com/), a library of light-weight, skinnable, and extensible UI controls for mobile and desktop. The components run on [Starling Framework](http://starling-framework.org/) and the [Adobe Flash runtimes](http://gaming.adobe.com/technologies/) — offering blazing fast GPU powered graphics to create a smooth and responsive experience. Build completely standalone, native applications on iOS, Android, Windows, and Mac OS X, or target Adobe Flash Player in desktop browsers. Created by [Josh Tynjala](http://twitter.com/joshtynjala) from Bowler Hat LLC, Feathers UI is free and open source.
+
+## Quick Links
+
+* [Website](http://feathersui.com/)
+* [Help](http://feathersui.com/help/)
+* [API Reference](http://feathersui.com/api-reference/)
+* [Discussion Forum](http://forum.starling-framework.org/forum/feathers)
+* [Github Project](https://github.com/BowlerHatLLC/feathers)
+
+### News and Updates
+
+* [Like on Facebook](https://facebook.com/feathersui)
+* [Follow on Twitter](https://twitter.com/feathersui)
+* [Find on Google+](https://www.google.com/+feathersui)
+
+## Minimum Requirements
+
+* Adobe AIR or Adobe Flash Player 19.0
+* [Starling Framework 2.0](http://forum.starling-framework.org/topic/preview-starling-20)
+
+## Downloads
+
+To download the latest stable version of Feathers UI, visit [feathersui.com](http://feathersui.com/).
\ No newline at end of file
diff --git a/RELEASENOTES.md b/RELEASENOTES.md
new file mode 100644
index 0000000..beb2536
--- /dev/null
+++ b/RELEASENOTES.md
@@ -0,0 +1,5 @@
+# feathers-compat Release Notes
+
+## 1.0.0-prerelease - In Development
+
+* Initial release
diff --git a/build.properties b/build.properties
new file mode 100644
index 0000000..1cc029b
--- /dev/null
+++ b/build.properties
@@ -0,0 +1,25 @@
+feathers.root = ${basedir}/../feathers
+
+#this folder should contain the contents of starling.zip/starling/src
+starling.root = ${feathers.root}/third-party/starling
+
+#this folder should contain the SWC files for flexunit, as described here:
+#https://github.com/Gamua/Starling-Framework/blob/v1.7/tests/README.md
+#additionally, it should contain the JAR files for the flexunit ant tasks
+flexunit.root = ${feathers.root}/third-party/flexunit
+
+source.root = ${basedir}/source
+api.root = ${feathers.root}/documentation/api-reference
+test.root = ${basedir}/test
+
+output.path = ${basedir}/output
+dependency.output = ${output.path}/dependencies
+swc.output = ${output.path}/swc
+api.output = ${output.path}/api-reference
+source.output = ${output.path}/source
+
+swf.version = 30
+
+feathers.compat.version = 1.0.0-prerelease
+
+footer.text = Feathers | feathers-compat
\ No newline at end of file
diff --git a/build.xml b/build.xml
new file mode 100644
index 0000000..11cfa86
--- /dev/null
+++ b/build.xml
@@ -0,0 +1,143 @@
+
+
Note: This class is no longer recommended as a base + * class for themes. See Custom + * Feathers themes for complete details.
+ * + *In the example below, the buttonInitializer()
function
+ * will be called when a Button
is added to the display list,
+ * and no values are specified in its styleNameList
that match
+ * other initializers:
You can specify a value in the button's styleNameList
to
+ * call a different initializer for a button. You might do this to apply
+ * different skins for some buttons:
The callToActionButtonInitializer()
function will be called
+ * when a Button
with the Button.ALTERNATE_STYLE_NAME_CALL_TO_ACTION
+ * value is added to its styleNameList
:
Initializers are not called for subclasses. If a Check
is
+ * added to the display list (Check
extends
+ * Button
), the buttonInitializer()
function will
+ * not be called. This important restriction allows subclasses to have
+ * different skins.
You can target a specific subclass with the same initializer function + * without adding it for all subclasses:
+ * + *In this case, Button
and Check
will trigger
+ * the buttonInitializer()
function, but Radio
+ * (another subclass of Button
) will not.
You can target a class and all of its subclasses, using a different + * function. This is recommended only when you are absolutely sure that + * no subclasses will need a separate initializer.
+ * + *In this case, Button
, Check
, Radio
+ * and every other subclass of Button
(including any subclasses
+ * that you create yourself) will trigger the buttonInitializer()
+ * function.
In the following example, the required base class is changed:
+ * + *DisplayListWatcher
.
+ *
+ * In the following example, children are not processed recursively:
+ * + *DisplayListWatcher
is extended for a
+ * theme, it should also dispose textures and other assets.
+ */
+ public function dispose():void
+ {
+ if(this.root)
+ {
+ this.root.removeEventListener(Event.ADDED, addedHandler);
+ this.root = null;
+ }
+ if(this._excludedObjects)
+ {
+ this._excludedObjects.length = 0;
+ this._excludedObjects = null;
+ }
+ for(var key:Object in this.initializedObjects)
+ {
+ delete this.initializedObjects[key];
+ }
+ for(key in this._initializerNameTypeMap)
+ {
+ delete this._initializerNameTypeMap[key];
+ }
+ for(key in this._initializerNoNameTypeMap)
+ {
+ delete this._initializerNoNameTypeMap[key];
+ }
+ for(key in this._initializerSuperTypeMap)
+ {
+ delete this._initializerSuperTypeMap[key];
+ }
+ this._initializerSuperTypes.length = 0;
+ }
+
+ /**
+ * Excludes a display object, and all if its children (if any) from
+ * being watched.
+ */
+ public function exclude(target:DisplayObject):void
+ {
+ if(!this._excludedObjects)
+ {
+ this._excludedObjects = new In the following example, we check if a display object is excluded:
+ * + *DisplayListWatcher
+ * is created.
+ *
+ * If the object has already been initialized, it won't be + * initialized again. However, it's children may be initialized, if they + * haven't been initialized yet.
+ */ + public function initializeObject(target:DisplayObject):void + { + var targetAsRequiredBaseClass:DisplayObject = DisplayObject(target as requiredBaseClass); + if(targetAsRequiredBaseClass) + { + var isInitialized:Boolean = this._initializeOnce && this.initializedObjects[targetAsRequiredBaseClass]; + if(!isInitialized) + { + if(this.isExcluded(target)) + { + return; + } + + if(this._initializeOnce) + { + this.initializedObjects[targetAsRequiredBaseClass] = true; + } + this.processAllInitializers(target); + } + } + + if(this.processRecursively) + { + var targetAsContainer:DisplayObjectContainer = target as DisplayObjectContainer; + if(targetAsContainer) + { + var childCount:int = targetAsContainer.numChildren; + for(var i:int = 0; i < childCount; i++) + { + var child:DisplayObject = targetAsContainer.getChildAt(i); + this.initializeObject(child); + } + } + } + } + + /** + * @private + */ + protected function processAllInitializers(target:DisplayObject):void + { + var superTypeCount:int = this._initializerSuperTypes.length; + for(var i:int = 0; i < superTypeCount; i++) + { + var type:Class = this._initializerSuperTypes[i]; + if(target is type) + { + this.applyAllStylesForTypeFromMaps(target, type, this._initializerSuperTypeMap); + } + } + type = Class(Object(target).constructor); + this.applyAllStylesForTypeFromMaps(target, type, this._initializerNoNameTypeMap, this._initializerNameTypeMap); + } + + /** + * @private + */ + protected function applyAllStylesForTypeFromMaps(target:DisplayObject, type:Class, map:Dictionary, nameMap:Dictionary = null):void + { + var initializer:Function; + var hasNameInitializer:Boolean = false; + if(target is IFeathersControl && nameMap) + { + var nameTable:Object = nameMap[type]; + if(nameTable) + { + var uiControl:IFeathersControl = IFeathersControl(target); + var styleNameList:TokenList = uiControl.styleNameList; + var nameCount:int = styleNameList.length; + for(var i:int = 0; i < nameCount; i++) + { + var name:String = styleNameList.item(i); + initializer = nameTable[name] as Function; + if(initializer != null) + { + hasNameInitializer = true; + initializer(target); + } + } + } + } + if(hasNameInitializer) + { + return; + } + + initializer = map[type] as Function; + if(initializer != null) + { + initializer(target); + } + } + + /** + * @private + */ + protected function addedHandler(event:Event):void + { + this.initializeObject(event.target as DisplayObject); + } + } +} \ No newline at end of file diff --git a/source/feathers/skins/ImageStateValueSelector.as b/source/feathers/skins/ImageStateValueSelector.as new file mode 100644 index 0000000..29a3d14 --- /dev/null +++ b/source/feathers/skins/ImageStateValueSelector.as @@ -0,0 +1,97 @@ +/* +feathers-compat +Copyright 2012-2016 Bowler Hat LLC. All Rights Reserved. + +This program is free software. You can redistribute and/or modify it in +accordance with the terms of the accompanying license agreement. +*/ +package feathers.skins +{ + import starling.display.Image; + import starling.textures.Texture; + + /** + * Values for each state are Texture instances, and the manager attempts to + * reuse the existing Image instance that is passed in to getValueForState() + * as the old value by swapping the texture. + */ + public class ImageStateValueSelector extends StateWithToggleValueSelector + { + /** + * Constructor. + */ + public function ImageStateValueSelector() + { + } + + /** + * @private + */ + protected var _imageProperties:Object; + + /** + * Optional properties to set on the Image instance. + * + * @see http://doc.starling-framework.org/core/starling/display/Image.html starling.display.Image + */ + public function get imageProperties():Object + { + if(!this._imageProperties) + { + this._imageProperties = {}; + } + return this._imageProperties; + } + + /** + * @private + */ + public function set imageProperties(value:Object):void + { + this._imageProperties = value; + } + + /** + * @private + */ + override public function setValueForState(value:Object, state:Object, isSelected:Boolean = false):void + { + if(!(value is Texture)) + { + throw new ArgumentError("Value for state must be a Texture instance."); + } + super.setValueForState(value, state, isSelected); + } + + /** + * @private + */ + override public function updateValue(target:Object, state:Object, oldValue:Object = null):Object + { + var texture:Texture = super.updateValue(target, state) as Texture; + if(!texture) + { + return null; + } + + if(oldValue is Image) + { + var image:Image = Image(oldValue); + image.texture = texture; + image.readjustSize(); + } + else + { + image = new Image(texture); + } + + for(var propertyName:String in this._imageProperties) + { + var propertyValue:Object = this._imageProperties[propertyName]; + image[propertyName] = propertyValue; + } + + return image; + } + } +} diff --git a/source/feathers/skins/Scale9ImageStateValueSelector.as b/source/feathers/skins/Scale9ImageStateValueSelector.as new file mode 100644 index 0000000..44cdaba --- /dev/null +++ b/source/feathers/skins/Scale9ImageStateValueSelector.as @@ -0,0 +1,102 @@ +/* +feathers-compat +Copyright 2012-2016 Bowler Hat LLC. All Rights Reserved. + +This program is free software. You can redistribute and/or modify it in +accordance with the terms of the accompanying license agreement. +*/ +package feathers.skins +{ + import feathers.textures.Scale9Textures; + + import starling.display.Image; + + /** + * Values for each state are Scale9Textures instances, and the manager + * attempts to reuse the existing starling.display.Image instance that is + * passed in to getValueForState() as the old value by swapping the + * textures and scale9Grid. + */ + public class Scale9ImageStateValueSelector extends StateWithToggleValueSelector + { + /** + * Constructor. + */ + public function Scale9ImageStateValueSelector() + { + } + + /** + * @private + */ + protected var _imageProperties:Object; + + /** + * Optional properties to set on the Scale9Image instance. + * + * @see feathers.display.Scale9Image + */ + public function get imageProperties():Object + { + if(!this._imageProperties) + { + this._imageProperties = {}; + } + return this._imageProperties; + } + + /** + * @private + */ + public function set imageProperties(value:Object):void + { + this._imageProperties = value; + } + + /** + * @private + */ + override public function setValueForState(value:Object, state:Object, isSelected:Boolean = false):void + { + if(!(value is Scale9Textures)) + { + throw new ArgumentError("Value for state must be a Scale9Textures instance."); + } + super.setValueForState(value, state, isSelected); + } + + /** + * @private + */ + override public function updateValue(target:Object, state:Object, oldValue:Object = null):Object + { + var textures:Scale9Textures = super.updateValue(target, state) as Scale9Textures; + if(!textures) + { + return null; + } + + if(oldValue is Image) + { + var image:Image = Image(oldValue); + image.texture = textures.texture; + image.scale9Grid = textures.scale9Grid; + image.readjustSize(); + } + else + { + image = new Image(textures.texture); + image.scale9Grid = textures.scale9Grid; + image.tileGrid = null; + } + + for(var propertyName:String in this._imageProperties) + { + var propertyValue:Object = this._imageProperties[propertyName]; + image[propertyName] = propertyValue; + } + + return image; + } + } +} diff --git a/source/feathers/skins/SmartDisplayObjectStateValueSelector.as b/source/feathers/skins/SmartDisplayObjectStateValueSelector.as new file mode 100644 index 0000000..449c338 --- /dev/null +++ b/source/feathers/skins/SmartDisplayObjectStateValueSelector.as @@ -0,0 +1,241 @@ +/* +feathers-compat +Copyright 2012-2016 Bowler Hat LLC. All Rights Reserved. + +This program is free software. You can redistribute and/or modify it in +accordance with the terms of the accompanying license agreement. +*/ +package feathers.skins +{ + import feathers.textures.Scale3Textures; + import feathers.textures.Scale9Textures; + + import flash.utils.Dictionary; + + import starling.display.DisplayObject; + import starling.display.Image; + import starling.display.Quad; + import starling.textures.ConcreteTexture; + import starling.textures.SubTexture; + import starling.textures.Texture; + + /** + * Values for each state are textures or colors, and the manager attempts to + * reuse the existing display object that is passed in to getValueForState() + * as the old value, if possible. Supports Image and Texture, Scale3Image + * and Scale3Textures, Scale9Image and Scale9Textures, or Quad and uint + * (color) value. + * + *Additional value type handlers may be added, or the default type + * handlers may be replaced.
+ */ + public class SmartDisplayObjectStateValueSelector extends StateWithToggleValueSelector + { + /** + * The value type handler for typestarling.textures.Texture
.
+ *
+ * @see http://doc.starling-framework.org/core/starling/textures/Texture.html starling.display.Texture
+ */
+ public static function textureValueTypeHandler(value:Texture, oldDisplayObject:DisplayObject = null):DisplayObject
+ {
+ var displayObject:Image;
+ if(oldDisplayObject && Object(oldDisplayObject).constructor === Image)
+ {
+ displayObject = Image(oldDisplayObject);
+ displayObject.texture = value;
+ displayObject.scale9Grid = null;
+ displayObject.tileGrid = null;
+ displayObject.readjustSize();
+ }
+ if(!displayObject)
+ {
+ displayObject = new Image(value);
+ }
+ return displayObject;
+ }
+
+ /**
+ * The value type handler for type feathers.textures.Scale3Textures
.
+ *
+ * @see feathers.textures.Scale3Textures
+ */
+ public static function scale3TextureValueTypeHandler(value:Scale3Textures, oldDisplayObject:DisplayObject = null):DisplayObject
+ {
+ var displayObject:Image;
+ if(oldDisplayObject && Object(oldDisplayObject).constructor === Image)
+ {
+ displayObject = Image(oldDisplayObject);
+ displayObject.texture = value.texture;
+ displayObject.scale9Grid = value.scale9Grid;
+ displayObject.tileGrid = null;
+ }
+ if(!displayObject)
+ {
+ displayObject = new Image(value.texture);
+ displayObject.scale9Grid = value.scale9Grid;
+ }
+ return displayObject;
+ }
+
+ /**
+ * The value type handler for type feathers.textures.Scale9Textures
.
+ *
+ * @see feathers.textures.Scale9Textures
+ */
+ public static function scale9TextureValueTypeHandler(value:Scale9Textures, oldDisplayObject:DisplayObject = null):DisplayObject
+ {
+ var displayObject:Image;
+ if(oldDisplayObject && Object(oldDisplayObject).constructor === Image)
+ {
+ displayObject = Image(oldDisplayObject);
+ displayObject.texture = value.texture;
+ displayObject.scale9Grid = value.scale9Grid;
+ displayObject.tileGrid = null;
+ }
+ if(!displayObject)
+ {
+ displayObject = new Image(value.texture);
+ displayObject.scale9Grid = value.scale9Grid;
+ }
+ return displayObject;
+ }
+
+ /**
+ * The value type handler for type uint
(a color to display
+ * by a quad).
+ *
+ * @see http://doc.starling-framework.org/core/starling/display/Quad.html starling.display.Quad
+ */
+ public static function uintValueTypeHandler(value:uint, oldDisplayObject:DisplayObject = null):DisplayObject
+ {
+ var displayObject:Quad;
+ if(oldDisplayObject && Object(oldDisplayObject).constructor === Quad)
+ {
+ displayObject = Quad(oldDisplayObject);
+ }
+ if(!displayObject)
+ {
+ displayObject = new Quad(1, 1, value);
+ }
+ displayObject.color = value;
+ return displayObject;
+ }
+
+ /**
+ * Constructor.
+ */
+ public function SmartDisplayObjectStateValueSelector()
+ {
+ this.setValueTypeHandler(Scale9Textures, scale9TextureValueTypeHandler);
+ this.setValueTypeHandler(Scale3Textures, scale3TextureValueTypeHandler);
+ //the constructor property of a uint is actually Number.
+ this.setValueTypeHandler(Number, uintValueTypeHandler);
+ }
+
+ /**
+ * @private
+ */
+ protected var _displayObjectProperties:Object;
+
+ /**
+ * Optional properties to set on the display object instance.
+ */
+ public function get displayObjectProperties():Object
+ {
+ if(!this._displayObjectProperties)
+ {
+ this._displayObjectProperties = {};
+ }
+ return this._displayObjectProperties;
+ }
+
+ /**
+ * @private
+ */
+ public function set displayObjectProperties(value:Object):void
+ {
+ this._displayObjectProperties = value;
+ }
+
+ /**
+ * @private
+ */
+ protected var _handlers:Dictionary = new Dictionary(true);
+
+ /**
+ * @private
+ */
+ override public function updateValue(target:Object, state:Object, oldValue:Object = null):Object
+ {
+ var value:Object = super.updateValue(target, state);
+ if(value === null)
+ {
+ return null;
+ }
+
+ var typeHandler:Function = this.valueToValueTypeHandler(value);
+ if(typeHandler != null)
+ {
+ var displayObject:DisplayObject = typeHandler(value, oldValue);
+ }
+ else
+ {
+ throw new ArgumentError("Invalid value: ", value);
+ }
+
+ for(var propertyName:String in this._displayObjectProperties)
+ {
+ var propertyValue:Object = this._displayObjectProperties[propertyName];
+ displayObject[propertyName] = propertyValue;
+ }
+
+ return displayObject;
+ }
+
+ /**
+ * Sets a function to handle updating a value of a specific type. The
+ * function must have the following signature:
+ *
+ * function(value:Object, oldDisplayObject:DisplayObject = null):DisplayObject+ * + *
The oldDisplayObject
is optional, and it may be of
+ * a type that is different than what the function will return. If the
+ * types do not match, the function should create a new object instead
+ * of reusing the old display object.
Scale3Image
.
+ *
+ * @see feathers.display.Scale3Image
+ */
+ public final class Scale3Textures
+ {
+ /**
+ * @private
+ */
+ private static const SECOND_REGION_ERROR:String = "The size of the second region must be greater than zero.";
+
+ /**
+ * @private
+ */
+ private static const SUM_X_REGIONS_ERROR:String = "The combined height of the first and second regions must be less than or equal to the width of the texture.";
+
+ /**
+ * @private
+ */
+ private static const SUM_Y_REGIONS_ERROR:String = "The combined width of the first and second regions must be less than or equal to the height of the texture.";
+
+ /**
+ * If the direction is horizontal, the layout will start on the left and continue to the right.
+ */
+ public static const DIRECTION_HORIZONTAL:String = "horizontal";
+
+ /**
+ * If the direction is vertical, the layout will start on the top and continue to the bottom.
+ */
+ public static const DIRECTION_VERTICAL:String = "vertical";
+
+ /**
+ * Constructor.
+ *
+ * @param texture A Starling Texture to slice up into three regions. It is recommended to turn of mip-maps for best rendering results.
+ * @param firstRegionSize The size, in pixels, of the first of the three regions. This value should be based on the original texture dimensions, with no adjustments for scale factor.
+ * @param secondRegionSize The size, in pixels, of the second of the three regions. This value should be based on the original texture dimensions, with no adjustments for scale factor.
+ * @param direction Indicates if the regions should be positioned horizontally or vertically.
+ */
+ public function Scale3Textures(texture:Texture, firstRegionSize:Number, secondRegionSize:Number, direction:String = DIRECTION_HORIZONTAL)
+ {
+ if(secondRegionSize <= 0)
+ {
+ throw new ArgumentError(SECOND_REGION_ERROR);
+ }
+ var sumRegions:Number = firstRegionSize + secondRegionSize;
+ if(direction === DIRECTION_HORIZONTAL)
+ {
+ if(sumRegions > texture.frameWidth)
+ {
+ throw new ArgumentError(SUM_X_REGIONS_ERROR);
+ }
+ }
+ else if(sumRegions > texture.frameHeight) //vertical
+ {
+ throw new ArgumentError(SUM_Y_REGIONS_ERROR);
+ }
+ this._texture = texture;
+ this._direction = direction;
+ this._firstRegionSize = firstRegionSize;
+ this._secondRegionSize = secondRegionSize;
+ if(this._direction === DIRECTION_HORIZONTAL)
+ {
+ this._scale9Grid = new Rectangle(firstRegionSize, 0, secondRegionSize, texture.frameHeight);
+ }
+ else
+ {
+ this._scale9Grid = new Rectangle(0, firstRegionSize, texture.frameWidth, secondRegionSize);
+ }
+ }
+
+ /**
+ * @private
+ */
+ private var _texture:Texture;
+
+ /**
+ * The original texture.
+ */
+ public function get texture():Texture
+ {
+ return this._texture;
+ }
+
+ /**
+ * @private
+ */
+ private var _scale9Grid:Rectangle;
+
+ /**
+ * The scale9Grid created from the regions.
+ */
+ public function get scale9Grid():Rectangle
+ {
+ return this._scale9Grid;
+ }
+
+ /**
+ * @private
+ */
+ private var _firstRegionSize:Number;
+
+ /**
+ * The size of the first region, in pixels.
+ */
+ public function get firstRegionSize():Number
+ {
+ return this._firstRegionSize;
+ }
+
+ /**
+ * @private
+ */
+ private var _secondRegionSize:Number;
+
+ /**
+ * The size of the second region, in pixels.
+ */
+ public function get secondRegionSize():Number
+ {
+ return this._secondRegionSize;
+ }
+
+ /**
+ * @private
+ */
+ private var _direction:String;
+
+ /**
+ * The direction of the sub-texture layout.
+ *
+ * @default Scale3Textures.DIRECTION_HORIZONTAL
+ *
+ * @see #DIRECTION_HORIZONTAL
+ * @see #DIRECTION_VERTICAL
+ */
+ public function get direction():String
+ {
+ return this._direction;
+ }
+ }
+}
diff --git a/source/feathers/textures/Scale9Textures.as b/source/feathers/textures/Scale9Textures.as
new file mode 100644
index 0000000..00b6273
--- /dev/null
+++ b/source/feathers/textures/Scale9Textures.as
@@ -0,0 +1,96 @@
+/*
+feathers-compat
+Copyright 2016 Bowler Hat LLC. All Rights Reserved.
+
+This program is free software. You can redistribute and/or modify it in
+accordance with the terms of the accompanying license agreement.
+*/
+package feathers.textures
+{
+ import flash.geom.Rectangle;
+
+ import starling.textures.Texture;
+
+ /**
+ * Slices a Starling Texture into nine regions to be used by Scale9Image
.
+ *
+ * @see feathers.display.Scale9Image
+ */
+ public final class Scale9Textures
+ {
+ /**
+ * @private
+ */
+ private static const ZERO_WIDTH_ERROR:String = "The width of the scale9Grid must be greater than zero.";
+
+ /**
+ * @private
+ */
+ private static const ZERO_HEIGHT_ERROR:String = "The height of the scale9Grid must be greater than zero.";
+
+ /**
+ * @private
+ */
+ private static const SUM_X_REGIONS_ERROR:String = "The sum of the x and width properties of the scale9Grid must be less than or equal to the width of the texture.";
+
+ /**
+ * @private
+ */
+ private static const SUM_Y_REGIONS_ERROR:String = "The sum of the y and height properties of the scale9Grid must be less than or equal to the height of the texture.";
+
+ /**
+ * Constructor.
+ *
+ * @param texture A Starling Texture to slice up into nine regions. It is recommended to turn of mip-maps for best rendering results.
+ * @param scale9Grid The rectangle defining the region in the horizontal center and vertical middle, with other regions being calculated automatically. This value should be based on the original texture dimensions, with no adjustments for scale factor.
+ */
+ public function Scale9Textures(texture:Texture, scale9Grid:Rectangle)
+ {
+ if(scale9Grid.width <= 0)
+ {
+ throw new ArgumentError(ZERO_WIDTH_ERROR);
+ }
+ if(scale9Grid.height <= 0)
+ {
+ throw new ArgumentError(ZERO_HEIGHT_ERROR);
+ }
+ if((scale9Grid.x + scale9Grid.width) > texture.frameWidth)
+ {
+ throw new ArgumentError(SUM_X_REGIONS_ERROR);
+ }
+ if((scale9Grid.y + scale9Grid.height) > texture.frameHeight)
+ {
+ throw new ArgumentError(SUM_Y_REGIONS_ERROR);
+ }
+ this._texture = texture;
+ this._scale9Grid = scale9Grid;
+ }
+
+ /**
+ * @private
+ */
+ private var _texture:Texture;
+
+ /**
+ * The original texture.
+ */
+ public function get texture():Texture
+ {
+ return this._texture;
+ }
+
+ /**
+ * @private
+ */
+ private var _scale9Grid:Rectangle;
+
+ /**
+ * The grid representing the nine sub-regions of the texture.
+ */
+ public function get scale9Grid():Rectangle
+ {
+ return this._scale9Grid;
+ }
+ }
+}
+
diff --git a/test/source/TestFeathersCompat.as b/test/source/TestFeathersCompat.as
new file mode 100644
index 0000000..67120ed
--- /dev/null
+++ b/test/source/TestFeathersCompat.as
@@ -0,0 +1,75 @@
+package
+{
+ import feathers.compat.tests.ImageStateValueSelectorTests;
+ import feathers.compat.tests.Scale3TexturesTests;
+ import feathers.compat.tests.Scale9ImageStateValueSelectorTests;
+ import feathers.compat.tests.SmartDisplayObjectStateValueSelectorTests;
+ import feathers.compat.tests.StateValueSelectorTests;
+ import feathers.compat.tests.StateWithToggleValueSelectorTests;
+
+ import flash.display.Sprite;
+ import flash.display.StageAlign;
+ import flash.display.StageScaleMode;
+ import flash.events.Event;
+ import flash.system.System;
+
+ import org.flexunit.internals.TraceListener;
+ import org.flexunit.listeners.CIListener;
+ import org.flexunit.runner.FlexUnitCore;
+
+ import starling.core.Starling;
+ import starling.display.Sprite;
+ import starling.events.Event;
+
+ [SWF(width="960",height="640",frameRate="60",backgroundColor="#4a4137")]
+ public class TestFeathersCompat extends flash.display.Sprite
+ {
+ public static var starlingRoot:starling.display.Sprite;
+
+ public function TestFeathersCompat()
+ {
+ if(this.stage)
+ {
+ this.stage.align = StageAlign.TOP_LEFT;
+ this.stage.scaleMode = StageScaleMode.NO_SCALE;
+ }
+
+ this.loaderInfo.addEventListener(flash.events.Event.COMPLETE, loaderInfo_completeHandler);
+ }
+
+ private var _starling:Starling;
+ private var _flexunit:FlexUnitCore;
+
+ private function loaderInfo_completeHandler(event:flash.events.Event):void
+ {
+ Starling.multitouchEnabled = true;
+ this._starling = new Starling(starling.display.Sprite, this.stage);
+ this._starling.addEventListener(starling.events.Event.ROOT_CREATED, starling_rootCreatedHandler);
+ this._starling.start();
+ }
+
+ private function starling_rootCreatedHandler(event:starling.events.Event):void
+ {
+ starlingRoot = starling.display.Sprite(this._starling.root);
+ this._flexunit = new FlexUnitCore();
+ this._flexunit.addListener(new TraceListener());
+ this._flexunit.addListener(new CIListener());
+ this._flexunit.addEventListener(FlexUnitCore.TESTS_COMPLETE, flexunit_testsCompleteHandler);
+ this._flexunit.run(
+ [
+ Scale3TexturesTests,
+ StateValueSelectorTests,
+ StateWithToggleValueSelectorTests,
+ SmartDisplayObjectStateValueSelectorTests,
+ Scale9ImageStateValueSelectorTests,
+ ImageStateValueSelectorTests,
+ ]);
+ }
+
+ private function flexunit_testsCompleteHandler(event:flash.events.Event):void
+ {
+ System.exit(0);
+ }
+
+ }
+}
\ No newline at end of file
diff --git a/test/source/feathers/compat/tests/ImageStateValueSelectorTests.as b/test/source/feathers/compat/tests/ImageStateValueSelectorTests.as
new file mode 100644
index 0000000..17f1ff2
--- /dev/null
+++ b/test/source/feathers/compat/tests/ImageStateValueSelectorTests.as
@@ -0,0 +1,55 @@
+package feathers.compat.tests
+{
+ import feathers.skins.ImageStateValueSelector;
+ import feathers.skins.SmartDisplayObjectStateValueSelector;
+ import feathers.textures.Scale3Textures;
+ import feathers.textures.Scale9Textures;
+
+ import flash.geom.Rectangle;
+
+ import org.flexunit.Assert;
+
+ import starling.display.Image;
+ import starling.display.Quad;
+ import starling.textures.Texture;
+
+ public class ImageStateValueSelectorTests
+ {
+ private static const STATE_ONE:String = "stateOne";
+ private static const STATE_TWO:String = "stateTwo";
+
+ private var _valueSelector:ImageStateValueSelector;
+
+ [Before]
+ public function prepare():void
+ {
+ this._valueSelector = new ImageStateValueSelector();
+ }
+
+ [After]
+ public function cleanup():void
+ {
+ this._valueSelector = null;
+ }
+
+ [Test]
+ public function testTexture():void
+ {
+ var defaultTexture:Texture = Texture.fromColor(20, 20);
+ var stateOneTexture:Texture = Texture.fromColor(30, 30);
+
+ this._valueSelector.defaultValue = defaultTexture;
+ this._valueSelector.setValueForState(stateOneTexture, STATE_ONE);
+
+ var result:Image = Image(this._valueSelector.updateValue({}, STATE_ONE, null));
+ Assert.assertStrictlyEquals("ImageStateValueSelector did not set correct texture on Image from Texture using setValueForState()", result.texture, stateOneTexture);
+
+ var secondResult:Image = Image(this._valueSelector.updateValue({}, STATE_TWO, result));
+ Assert.assertStrictlyEquals("ImageStateValueSelector did not reuse Image for different Texture", result, secondResult);
+ Assert.assertStrictlyEquals("ImageStateValueSelector did not set correct texture on Image from Texture using defaultValue", secondResult.texture, defaultTexture);
+
+ defaultTexture.dispose();
+ stateOneTexture.dispose();
+ }
+ }
+}
diff --git a/test/source/feathers/compat/tests/Scale3TexturesTests.as b/test/source/feathers/compat/tests/Scale3TexturesTests.as
new file mode 100644
index 0000000..4a89cb3
--- /dev/null
+++ b/test/source/feathers/compat/tests/Scale3TexturesTests.as
@@ -0,0 +1,44 @@
+package feathers.compat.tests
+{
+ import feathers.textures.Scale3Textures;
+
+ import flash.geom.Rectangle;
+
+ import org.flexunit.Assert;
+
+ import starling.textures.Texture;
+
+ public class Scale3TexturesTests
+ {
+ private var _scale3Textures:Scale3Textures;
+
+ [Before]
+ public function prepare():void
+ {
+ }
+
+ [After]
+ public function cleanup():void
+ {
+ if(this._scale3Textures.texture)
+ {
+ this._scale3Textures.texture.dispose();
+ }
+ this._scale3Textures = null;
+ }
+
+ [Test]
+ public function testHorizontalScale9Grid():void
+ {
+ this._scale3Textures = new Scale3Textures(Texture.fromColor(20, 40), 5, 10, Scale3Textures.DIRECTION_HORIZONTAL);
+ Assert.assertTrue("Scale3Textures scale9Grid not correct when direction is horizontal", this._scale3Textures.scale9Grid.equals(new Rectangle(5, 0, 10, 40)));
+ }
+
+ [Test]
+ public function testVerticalScale9Grid():void
+ {
+ this._scale3Textures = new Scale3Textures(Texture.fromColor(20, 40), 5, 10, Scale3Textures.DIRECTION_VERTICAL);
+ Assert.assertTrue("Scale3Textures scale9Grid not correct when direction is vertical", this._scale3Textures.scale9Grid.equals(new Rectangle(0, 5, 20, 10)));
+ }
+ }
+}
diff --git a/test/source/feathers/compat/tests/Scale9ImageStateValueSelectorTests.as b/test/source/feathers/compat/tests/Scale9ImageStateValueSelectorTests.as
new file mode 100644
index 0000000..61c7a6e
--- /dev/null
+++ b/test/source/feathers/compat/tests/Scale9ImageStateValueSelectorTests.as
@@ -0,0 +1,54 @@
+package feathers.compat.tests
+{
+ import feathers.skins.Scale9ImageStateValueSelector;
+ import feathers.textures.Scale9Textures;
+
+ import flash.geom.Rectangle;
+
+ import org.flexunit.Assert;
+
+ import starling.display.Image;
+ import starling.textures.Texture;
+
+ public class Scale9ImageStateValueSelectorTests
+ {
+ private static const STATE_ONE:String = "stateOne";
+ private static const STATE_TWO:String = "stateTwo";
+
+ private var _valueSelector:Scale9ImageStateValueSelector;
+
+ [Before]
+ public function prepare():void
+ {
+ this._valueSelector = new Scale9ImageStateValueSelector();
+ }
+
+ [After]
+ public function cleanup():void
+ {
+ this._valueSelector = null;
+ }
+
+ [Test]
+ public function testScale9Textures():void
+ {
+ var defaultTextures:Scale9Textures = new Scale9Textures(Texture.fromColor(20, 20), new Rectangle(5, 5, 10, 10));
+ var stateOneTextures:Scale9Textures = new Scale9Textures(Texture.fromColor(30, 30), new Rectangle(6, 6, 18, 18));
+
+ this._valueSelector.defaultValue = defaultTextures;
+ this._valueSelector.setValueForState(stateOneTextures, STATE_ONE);
+
+ var result:Image = Image(this._valueSelector.updateValue({}, STATE_ONE, null));
+ Assert.assertStrictlyEquals("Scale9ImageStateValueSelector did not set correct texture on Image from Scale9Textures using setValueForState()", result.texture, stateOneTextures.texture);
+ Assert.assertTrue("Scale9ImageStateValueSelector did not set correct scale9Grid on Image from Scale9Textures using setValueForState()", result.scale9Grid.equals(stateOneTextures.scale9Grid));
+
+ var secondResult:Image = Image(this._valueSelector.updateValue({}, STATE_TWO, result));
+ Assert.assertStrictlyEquals("Scale9ImageStateValueSelector did not reuse Image for different Scale9Textures", result, secondResult);
+ Assert.assertStrictlyEquals("Scale9ImageStateValueSelector did not set correct texture on Image from Scale9Textures using defaultValue", secondResult.texture, defaultTextures.texture);
+ Assert.assertTrue("Scale9ImageStateValueSelector did not set correct scale9Grid on Image from Scale9Textures using defaultValue", secondResult.scale9Grid.equals(defaultTextures.scale9Grid));
+
+ defaultTextures.texture.dispose();
+ stateOneTextures.texture.dispose();
+ }
+ }
+}
diff --git a/test/source/feathers/compat/tests/SmartDisplayObjectStateValueSelectorTests.as b/test/source/feathers/compat/tests/SmartDisplayObjectStateValueSelectorTests.as
new file mode 100644
index 0000000..a5886dd
--- /dev/null
+++ b/test/source/feathers/compat/tests/SmartDisplayObjectStateValueSelectorTests.as
@@ -0,0 +1,115 @@
+package feathers.compat.tests
+{
+ import feathers.skins.SmartDisplayObjectStateValueSelector;
+ import feathers.textures.Scale3Textures;
+ import feathers.textures.Scale9Textures;
+
+ import flash.geom.Rectangle;
+
+ import org.flexunit.Assert;
+
+ import starling.display.Image;
+ import starling.display.Quad;
+ import starling.textures.Texture;
+
+ public class SmartDisplayObjectStateValueSelectorTests
+ {
+ private static const STATE_ONE:String = "stateOne";
+ private static const STATE_TWO:String = "stateTwo";
+
+ private var _valueSelector:SmartDisplayObjectStateValueSelector;
+
+ [Before]
+ public function prepare():void
+ {
+ this._valueSelector = new SmartDisplayObjectStateValueSelector();
+ }
+
+ [After]
+ public function cleanup():void
+ {
+ this._valueSelector = null;
+ }
+
+ [Test]
+ public function testColor():void
+ {
+ var defaultColor:uint = 0xff0000;
+ var stateOneColor:uint = 0x0000ff;
+
+ this._valueSelector.defaultValue = defaultColor;
+ this._valueSelector.setValueForState(stateOneColor, STATE_ONE);
+
+ var result:Quad = Quad(this._valueSelector.updateValue({}, STATE_ONE, null));
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not set correct color on Quad from uint using setValueForState()", result.color, stateOneColor);
+
+ var secondResult:Quad = Quad(this._valueSelector.updateValue({}, STATE_TWO, result));
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not reuse Quad for different color", result, secondResult);
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not set correct color on Quad from uint using defaultValue", secondResult.color, defaultColor);
+ }
+
+ [Test]
+ public function testTexture():void
+ {
+ var defaultTexture:Texture = Texture.fromColor(20, 20);
+ var stateOneTexture:Texture = Texture.fromColor(30, 30);
+
+ this._valueSelector.defaultValue = defaultTexture;
+ this._valueSelector.setValueForState(stateOneTexture, STATE_ONE);
+
+ var result:Image = Image(this._valueSelector.updateValue({}, STATE_ONE, null));
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not set correct texture on Image from Texture using setValueForState()", result.texture, stateOneTexture);
+
+ var secondResult:Image = Image(this._valueSelector.updateValue({}, STATE_TWO, result));
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not reuse Image for different Texture", result, secondResult);
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not set correct texture on Image from Texture using defaultValue", secondResult.texture, defaultTexture);
+
+ defaultTexture.dispose();
+ stateOneTexture.dispose();
+ }
+
+ [Test]
+ public function testScale3Textures():void
+ {
+ var defaultTextures:Scale3Textures = new Scale3Textures(Texture.fromColor(20, 20), 5, 10, Scale3Textures.DIRECTION_HORIZONTAL);
+ var stateOneTextures:Scale3Textures = new Scale3Textures(Texture.fromColor(30, 30), 6, 18, Scale3Textures.DIRECTION_HORIZONTAL);
+
+ this._valueSelector.defaultValue = defaultTextures;
+ this._valueSelector.setValueForState(stateOneTextures, STATE_ONE);
+
+ var result:Image = Image(this._valueSelector.updateValue({}, STATE_ONE, null));
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not set correct texture on Image from Scale3Textures using setValueForState()", result.texture, stateOneTextures.texture);
+ Assert.assertTrue("SmartDisplayObjectStateValueSelector did not set correct scale9Grid on Image from Scale3Textures using setValueForState()", result.scale9Grid.equals(stateOneTextures.scale9Grid));
+
+ var secondResult:Image = Image(this._valueSelector.updateValue({}, STATE_TWO, result));
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not reuse Image for different Scale9Textures", result, secondResult);
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not set correct texture on Image from Scale3Textures using defaultValue", secondResult.texture, defaultTextures.texture);
+ Assert.assertTrue("SmartDisplayObjectStateValueSelector did not set correct scale9Grid on Image from Scale3Textures using defaultValue", secondResult.scale9Grid.equals(defaultTextures.scale9Grid));
+
+ defaultTextures.texture.dispose();
+ stateOneTextures.texture.dispose();
+ }
+
+ [Test]
+ public function testScale9Textures():void
+ {
+ var defaultTextures:Scale9Textures = new Scale9Textures(Texture.fromColor(20, 20), new Rectangle(5, 5, 10, 10));
+ var stateOneTextures:Scale9Textures = new Scale9Textures(Texture.fromColor(30, 30), new Rectangle(6, 6, 18, 18));
+
+ this._valueSelector.defaultValue = defaultTextures;
+ this._valueSelector.setValueForState(stateOneTextures, STATE_ONE);
+
+ var result:Image = Image(this._valueSelector.updateValue({}, STATE_ONE, null));
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not set correct texture on Image from Scale9Textures using setValueForState()", result.texture, stateOneTextures.texture);
+ Assert.assertTrue("SmartDisplayObjectStateValueSelector did not set correct scale9Grid on Image from Scale9Textures using setValueForState()", result.scale9Grid.equals(stateOneTextures.scale9Grid));
+
+ var secondResult:Image = Image(this._valueSelector.updateValue({}, STATE_TWO, result));
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not reuse Image for different Scale9Textures", result, secondResult);
+ Assert.assertStrictlyEquals("SmartDisplayObjectStateValueSelector did not set correct texture on Image from Scale9Textures using defaultValue", secondResult.texture, defaultTextures.texture);
+ Assert.assertTrue("SmartDisplayObjectStateValueSelector did not set correct scale9Grid on Image from Scale9Textures using defaultValue", secondResult.scale9Grid.equals(defaultTextures.scale9Grid));
+
+ defaultTextures.texture.dispose();
+ stateOneTextures.texture.dispose();
+ }
+ }
+}
diff --git a/test/source/feathers/compat/tests/StateValueSelectorTests.as b/test/source/feathers/compat/tests/StateValueSelectorTests.as
new file mode 100644
index 0000000..beb24f4
--- /dev/null
+++ b/test/source/feathers/compat/tests/StateValueSelectorTests.as
@@ -0,0 +1,43 @@
+package feathers.compat.tests
+{
+ import feathers.skins.StateValueSelector;
+
+ import org.flexunit.Assert;
+
+ public class StateValueSelectorTests
+ {
+ private static const STATE_ONE:String = "stateOne";
+ private static const STATE_TWO:String = "stateTwo";
+
+ private var _valueSelector:StateValueSelector;
+
+ [Before]
+ public function prepare():void
+ {
+ this._valueSelector = new StateValueSelector();
+ }
+
+ [After]
+ public function cleanup():void
+ {
+ this._valueSelector = null;
+ }
+
+ [Test]
+ public function testUpdateValue():void
+ {
+ var defaultValue:String = "Hello World";
+ var stateOneValue:Number = 12;
+
+ this._valueSelector.defaultValue = defaultValue;
+ this._valueSelector.setValueForState(stateOneValue, STATE_ONE);
+
+ var result:Object = this._valueSelector.updateValue({}, STATE_ONE, null);
+ Assert.assertStrictlyEquals("StateValueSelector did not return correct value for setValueForState()", result, stateOneValue);
+
+ var secondResult:Object = this._valueSelector.updateValue({}, STATE_TWO, result);
+ Assert.assertFalse("StateValueSelector incorrectly reused result", result === secondResult);
+ Assert.assertStrictlyEquals("StateValueSelector did not return correct value for defaultValue", secondResult, defaultValue);
+ }
+ }
+}
diff --git a/test/source/feathers/compat/tests/StateWithToggleValueSelectorTests.as b/test/source/feathers/compat/tests/StateWithToggleValueSelectorTests.as
new file mode 100644
index 0000000..8fe7be9
--- /dev/null
+++ b/test/source/feathers/compat/tests/StateWithToggleValueSelectorTests.as
@@ -0,0 +1,43 @@
+package feathers.compat.tests
+{
+ import feathers.skins.StateWithToggleValueSelector;
+
+ import org.flexunit.Assert;
+
+ public class StateWithToggleValueSelectorTests
+ {
+ private static const STATE_ONE:String = "stateOne";
+ private static const STATE_TWO:String = "stateTwo";
+
+ private var _valueSelector:StateWithToggleValueSelector;
+
+ [Before]
+ public function prepare():void
+ {
+ this._valueSelector = new StateWithToggleValueSelector();
+ }
+
+ [After]
+ public function cleanup():void
+ {
+ this._valueSelector = null;
+ }
+
+ [Test]
+ public function testUpdateValue():void
+ {
+ var defaultValue:String = "Hello World";
+ var stateOneValue:Number = 12;
+
+ this._valueSelector.defaultValue = defaultValue;
+ this._valueSelector.setValueForState(stateOneValue, STATE_ONE);
+
+ var result:Object = this._valueSelector.updateValue({}, STATE_ONE, null);
+ Assert.assertStrictlyEquals("StateWithToggleValueSelector did not return correct value for setValueForState()", result, stateOneValue);
+
+ var secondResult:Object = this._valueSelector.updateValue({}, STATE_TWO, result);
+ Assert.assertFalse("StateWithToggleValueSelector incorrectly reused result", result === secondResult);
+ Assert.assertStrictlyEquals("StateWithToggleValueSelector did not return correct value for defaultValue", secondResult, defaultValue);
+ }
+ }
+}