Skip to content

Instantly share code, notes, and snippets.

@tpodhraski
Created September 13, 2012 21:11
Show Gist options
  • Save tpodhraski/3717680 to your computer and use it in GitHub Desktop.
Save tpodhraski/3717680 to your computer and use it in GitHub Desktop.
AutosizeLayout
package FoxholeYAML
{
import flash.geom.Point;
import flash.utils.Dictionary;
import org.josht.starling.foxhole.layout.ILayout;
import org.josht.starling.foxhole.layout.LayoutBoundsResult;
import org.josht.starling.foxhole.layout.ViewPortBounds;
import org.osflash.signals.ISignal;
import org.osflash.signals.Signal;
import starling.display.DisplayObject;
public class AutosizeLayout implements ILayout
{
public static const AUTORESIZE_FLOW_HORIZONTAL:String = "horizontal";
public static const AUTORESIZE_FLOW_VERTICAL:String = "vertical";
protected var _onLayoutChange:Signal = new Signal(ILayout);
private var _componentSettings:Dictionary;
private var _paddingTop:Number;
private var _paddingBottom:Number;
private var _paddingLeft:Number;
private var _paddingRight:Number;
private var _gap:Number;
private var _flow:String;
public function AutosizeLayout()
{
_paddingTop = 0;
_paddingBottom = 0;
_paddingLeft = 0;
_paddingRight = 0;
_gap = 0;
_flow = AUTORESIZE_FLOW_HORIZONTAL;
_componentSettings = new Dictionary(true);
}
public function setComponentAutosizeSettings(component:DisplayObject, settings:AutosizeSettings):void
{
var record:AutosizeRecord = new AutosizeRecord();
record.autosizeSettings = settings;
record.originalX = component.x;
record.originalY = component.y;
record.originalWidth = component.width;
record.originalHeight = component.height;
_componentSettings[component] = record;
}
/**
* Using the item dimensions, calculates a scroll position that will
* ensure that the item at a given index will be visible within the
* specified bounds.
*/
public function getScrollPositionForIndex(index:int, items:Vector.<DisplayObject>, x:Number, y:Number, width:Number, height:Number, result:Point = null):Point
{
return new Point(items[index].x, items[index].y);
}
/**
* @inheritDoc
*/
public function get onLayoutChange():ISignal
{
return _onLayoutChange;
}
/**
* @inheritDoc
*/
public function layout(items:Vector.<DisplayObject>, viewPortBounds:ViewPortBounds = null, result:LayoutBoundsResult = null):LayoutBoundsResult
{
if (!viewPortBounds) {
return result;
}
var nonResizableWidth:Number = 0;
var nonResizableHeight:Number = 0;
var relative:Number = 0;
var getItemInfo:Function = function(anItem:DisplayObject):AutosizeRecord
{
var resultRecord:AutosizeRecord = _componentSettings[item];
if (resultRecord == null)
{
_componentSettings[anItem] = resultRecord = new AutosizeRecord();
resultRecord.originalX = anItem.x;
resultRecord.originalY = anItem.y;
resultRecord.originalWidth = anItem.width;
resultRecord.originalHeight = anItem.height;
resultRecord.autosizeSettings = new AutosizeSettings();
}
return resultRecord;
}
var itemAutoresize:AutosizeRecord;
var item:DisplayObject;
for each(item in items)
{
itemAutoresize = getItemInfo(item);
if (itemAutoresize.autosizeSettings.resizable)
{
relative += itemAutoresize.autosizeSettings.relativeSize;
}
else
{
nonResizableWidth += itemAutoresize.originalWidth;
nonResizableHeight += itemAutoresize.originalHeight;
}
}
var remainingWidth:Number = viewPortBounds.explicitWidth - nonResizableWidth - _paddingLeft - _paddingRight;
var remainingHeight:Number = viewPortBounds.explicitHeight - nonResizableHeight - _paddingTop - _paddingBottom;
var perRelativeWidth:Number = relative == 0 ? 0 : remainingWidth / relative;
var perRelativeHeight:Number = relative == 0 ? 0 : remainingHeight / relative;
var currentX:Number = _paddingLeft;
var currentY:Number = _paddingTop;
for each(item in items)
{
itemAutoresize = getItemInfo(item);
item.x = currentX;
item.y = currentY;
if (itemAutoresize.autosizeSettings.resizable)
{
if (_flow == AUTORESIZE_FLOW_HORIZONTAL)
{
item.width = itemAutoresize.autosizeSettings.relativeSize * perRelativeWidth;
}
else
{
item.height = itemAutoresize.autosizeSettings.relativeSize * perRelativeHeight;
}
}
else
{
// should not resize.
}
if (_flow == AUTORESIZE_FLOW_HORIZONTAL)
{
currentX += item.width + _gap;
item.height = viewPortBounds.explicitHeight;
}
else
{
currentY += item.height + _gap;
item.width = viewPortBounds.explicitWidth;
}
}
return result;
}
}
}
package FoxholeYAML
{
internal class AutosizeRecord
{
public var autosizeSettings:AutosizeSettings;
public var originalX:Number;
public var originalY:Number;
public var originalWidth:Number;
public var originalHeight:Number;
}
}
package FoxholeYAML
{
public class AutosizeSettings
{
public var resizable:Boolean;
public var relativeSize:int;
public function AutosizeSettings(resizable:Boolean = true, relativeSize:int = 1)
{
this.resizable = resizable;
this.relativeSize = relativeSize;
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment