ZoulouX

Starling Virtual List Test on iOS

May 10th, 2012
125
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. Compilation in ipa-ad-hoc :
  2.  
  3. FPS for iOS :
  4. - iPhone 3GS            : from 5 to 60, average 7
  5. - iPhone 4S retina      : from 7 to 60, average 10
  6. - iPad 1            : from 1 to 60, average 1
  7. - iPad 3 non retina         : from 5 to 60, average 10
  8.  
  9. /**
  10.  * The main class
  11.  */
  12. package fr.babostesting.examples.stage3d.starling.virtual
  13. {
  14.     import flash.display.Sprite;
  15.     import flash.display.StageAlign;
  16.     import flash.display.StageQuality;
  17.     import flash.display.StageScaleMode;
  18.     import flash.events.Event;
  19.     import flash.geom.Rectangle;
  20.     import flash.utils.setTimeout;
  21.     import starling.core.Starling;
  22.    
  23.     /**
  24.      * @author ZoulouX
  25.      */
  26.     public class StarlingVirtualListTest extends Sprite
  27.     {
  28.         protected var _starling:Starling;
  29.        
  30.         public function StarlingVirtualListTest ()
  31.         {
  32.             if (stage != null)
  33.                 init();
  34.             else
  35.                 addEventListener(Event.ADDED_TO_STAGE, init);
  36.         }
  37.        
  38.         private function init (event:Event = null):void
  39.         {
  40.             removeEventListener(Event.ADDED_TO_STAGE, init);
  41.            
  42.             stage.align = StageAlign.TOP_LEFT;
  43.             stage.scaleMode = StageScaleMode.NO_SCALE;
  44.             stage.quality = StageQuality.LOW;
  45.             stage.autoOrients = false;
  46.            
  47.             stage.addEventListener(Event.RESIZE, stageResizedHandler);
  48.            
  49.             setTimeout(startUI, 1);
  50.         }
  51.        
  52.         protected function stageResizedHandler (event:Event):void
  53.         {
  54.             if (_starling != null)
  55.             {
  56.                 _starling.viewPort = new Rectangle(0, 0, stage.stageWidth, stage.stageHeight);
  57.                
  58.                 _starling.stage.stageWidth = stage.stageWidth;
  59.                 _starling.stage.stageHeight = stage.stageHeight;
  60.             }
  61.         }
  62.        
  63.         protected function startUI ():void
  64.         {
  65.             _starling = new Starling(ListBaseClass, stage);
  66.            
  67.             _starling.showStats = true;
  68.            
  69.             _starling.antiAliasing = 0;
  70.            
  71.             _starling.start();
  72.         }
  73.     }
  74. }
  75.  
  76.  
  77.  
  78. /**
  79.  * The starling main class. Get touch events and generate lines.
  80.  */
  81. package fr.babostesting.examples.stage3d.starling.virtual
  82. {
  83.     import com.greensock.easing.Back;
  84.     import com.greensock.easing.Strong;
  85.     import com.greensock.TweenMax;
  86.     import flash.geom.Point;
  87.     import flash.net.URLLoader;
  88.     import flash.net.URLRequest;
  89.     import fr.babos.graphic.tools.BitmapCache;
  90.     import fr.babos.utils.ArrayUtils;
  91.     import starling.display.Sprite;
  92.     import starling.events.Event;
  93.     import starling.events.Touch;
  94.     import starling.events.TouchEvent;
  95.     import starling.events.TouchPhase;
  96.    
  97.     /**
  98.      * @author ZoulouX
  99.      */
  100.     public class ListBaseClass extends Sprite
  101.     {
  102.         protected var _container:Sprite;
  103.        
  104.         protected var _elements:Array;
  105.         protected var _twitterData:Object;
  106.         protected var _currentPosition:Point;
  107.         protected var _delta:Number = 0;
  108.        
  109.         protected var _totalElementToShow:int;
  110.         protected var _bitmapCache:BitmapCache;
  111.        
  112.         public function ListBaseClass ()
  113.         {
  114.             addEventListener(Event.ADDED_TO_STAGE, init);
  115.         }
  116.        
  117.         protected function init (event:Event):void
  118.         {
  119.             _totalElementToShow = 160;
  120.            
  121.             var serviceURL:String = "http://search.twitter.com/search.json?q=as3&rpp=" + _totalElementToShow.toString(10) + "&include_entities=true&result_type=mixed";
  122.            
  123.             var urlLoader:URLLoader = new URLLoader(new URLRequest(serviceURL));
  124.             urlLoader.addEventListener("complete", dataLoadedHandler);
  125.             trace("loading");
  126.         }
  127.        
  128.         public function dataLoadedHandler (event:Object):void
  129.         {
  130.             (event.currentTarget as URLLoader).removeEventListener("complete", dataLoadedHandler);
  131.            
  132.             trace("loaded");
  133.            
  134.             _twitterData = JSON.parse((event.currentTarget as URLLoader).data);
  135.            
  136.             if (_twitterData["results"] != null)
  137.                 _twitterData = _twitterData.results;
  138.            
  139.             _totalElementToShow = _twitterData.length;
  140.            
  141.             _bitmapCache = new BitmapCache();
  142.            
  143.             _elements = [];
  144.            
  145.             _container = new Sprite();
  146.            
  147.             addChild(_container);
  148.            
  149.             addEventListener(Event.ENTER_FRAME, enterFrameHandler);
  150.             addEventListener(TouchEvent.TOUCH, touchEventHandler);
  151.         }
  152.        
  153.         protected function touchEventHandler (event:TouchEvent):void
  154.         {
  155.             var touch:Touch = event.getTouch(stage);
  156.             var location:Point = touch.getLocation(stage);
  157.            
  158.             var minPosition:int = 0;
  159.             var maxPosition:int = - (_totalElementToShow) * 100 + stage.stageHeight;
  160.            
  161.             if (touch.phase == TouchPhase.BEGAN)
  162.             {
  163.                 _currentPosition = location.clone();
  164.                
  165.                 TweenMax.killTweensOf(_container);
  166.                
  167.                 _delta = 0;
  168.             }
  169.             else if (touch.phase == TouchPhase.MOVED)
  170.             {
  171.                 _delta = location.y - _currentPosition.y;
  172.                
  173.                 if (_container.y > minPosition || _container.y < maxPosition)
  174.                 {
  175.                     _delta /= 2;
  176.                 }
  177.                
  178.                 _container.y = int(_container.y + _delta - .5);
  179.                 //_container.y += _delta;
  180.                
  181.                 _currentPosition = location.clone();
  182.             }
  183.             else if (touch.phase == TouchPhase.ENDED)
  184.             {
  185.                 if (_delta != 0)
  186.                 {
  187.                     trace(_delta);
  188.                    
  189.                     var destination:Number = _container.y + _delta * 6;
  190.                    
  191.                     var ease:Function = Strong.easeOut;
  192.                    
  193.                     if (destination > minPosition)
  194.                     {
  195.                         destination = minPosition;
  196.                        
  197.                         if (_container.y < minPosition)
  198.                             ease = Back.easeOut;
  199.                     }
  200.                     else if (destination < maxPosition)
  201.                     {
  202.                         destination = maxPosition;
  203.                        
  204.                         if (_container.y > maxPosition)
  205.                             ease = Back.easeOut;
  206.                     }
  207.                    
  208.                     TweenMax.to(_container, .8, {
  209.                         roundProps: ["y"],
  210.                         y: destination,
  211.                         ease: ease
  212.                     });
  213.                 }
  214.             }
  215.         }
  216.        
  217.         protected function enterFrameHandler (event:Event):void
  218.         {
  219.             updateElements();
  220.         }
  221.        
  222.         protected function updateElements ():void
  223.         {
  224.             var start:int = int(- _container.y / 100) - 1;
  225.             var end:int = start + Math.ceil(stage.stageHeight / 100) + 1;
  226.            
  227.             //trace(">", start, "/", end);
  228.            
  229.             var i:int = start;
  230.             var element:LineElement;
  231.            
  232.             for each (element in _elements)
  233.             {
  234.                 if (element.index < start || element.index > end)
  235.                 {
  236.                     trace("DELETE", element.index);
  237.                    
  238.                     _elements = ArrayUtils.deleteElement(_elements, element);
  239.                    
  240.                     element.removeFromParent(true);
  241.                 }
  242.             }
  243.            
  244.             while (i <= end)
  245.             {
  246.                 element = null;
  247.                
  248.                 for each (var currentElement:LineElement in _elements)
  249.                 {
  250.                     if (currentElement.index == i)
  251.                     {
  252.                         element = currentElement;
  253.                         break;
  254.                     }
  255.                 }
  256.                
  257.                 if (element == null)
  258.                 {
  259.                     element = needElementAt(i);
  260.                    
  261.                     if (element != null)
  262.                     {
  263.                         trace("ADD ELEMENT", i);
  264.                        
  265.                         _elements.push(element);
  266.                        
  267.                         element.index = i;
  268.                        
  269.                         element.y = i * 100;
  270.                        
  271.                         _container.addChild(element);
  272.                     }
  273.                 }
  274.                
  275.                 i ++;
  276.             }
  277.         }
  278.        
  279.         protected function needElementAt (pAt:int):LineElement
  280.         {
  281.             var item:Object
  282.            
  283.             if (pAt in _twitterData)
  284.             {
  285.                 item = {
  286.                     avatar: _twitterData[pAt].profile_image_url,
  287.                     username: _twitterData[pAt].from_user_name,
  288.                     text: _twitterData[pAt].text
  289.                 };
  290.             }
  291.            
  292.             return new LineElement(item, _bitmapCache);
  293.         }
  294.     }
  295. }
  296.  
  297.  
  298.  
  299.  
  300.  
  301. /**
  302.  * The class for one line in the virtual list
  303.  */
  304. package fr.babostesting.examples.stage3d.starling.virtual
  305. {
  306.     import com.greensock.TweenMax;
  307.     import flash.display.BitmapData;
  308.     import flash.text.TextFormatAlign;
  309.     import fr.babos.graphic.tools.BitmapCache;
  310.     import starling.display.Image;
  311.     import starling.display.Quad;
  312.     import starling.display.Sprite;
  313.     import starling.events.Event;
  314.     import starling.text.TextField;
  315.     import starling.textures.Texture;
  316.     import starling.textures.TextureSmoothing;
  317.    
  318.     /**
  319.      * @author ZoulouX
  320.      */
  321.     public class LineElement extends Sprite
  322.     {
  323.         protected static var __backgroundTexture        :Texture;
  324.        
  325.        
  326.         protected var _item                             :Object;
  327.        
  328.         protected var _background                       :Image;
  329.        
  330.         protected var _image                            :Image;
  331.        
  332.         protected var _title                            :TextField;
  333.        
  334.         protected var _text                             :TextField;
  335.        
  336.         protected var _backImage                        :Quad;
  337.        
  338.         protected var _bitmapCache                      :BitmapCache;
  339.        
  340.        
  341.         public var index                                :int;
  342.        
  343.        
  344.         public function LineElement (pData:Object, pBitmapCache:BitmapCache)
  345.         {
  346.             _item = pData;
  347.             _bitmapCache = pBitmapCache;
  348.            
  349.             addEventListener(Event.ADDED_TO_STAGE, addedToStageHandler);
  350.         }
  351.        
  352.         protected function addedToStageHandler (event:Event):void
  353.         {
  354.             // Générer l'image de fond des cases
  355.             if (__backgroundTexture == null)
  356.             {
  357.                 var backgroundBitmapData:BitmapData = new BitmapData(2, 100, false, 0xFFFFFFFF);
  358.                 backgroundBitmapData.setPixel(0, 99, 0xCCCCCC);
  359.                 backgroundBitmapData.setPixel(1, 99, 0xCCCCCC);
  360.                
  361.                 __backgroundTexture = Texture.fromBitmapData(backgroundBitmapData);
  362.                 __backgroundTexture.repeat = true;
  363.             }
  364.            
  365.             // Le fond de la case
  366.             _background = new Image(__backgroundTexture);
  367.             _background.smoothing = TextureSmoothing.NONE;
  368.            
  369.             _background.width = stage.stageWidth;
  370.             _background.height = 100;
  371.            
  372.             addChild(_background);
  373.            
  374.             if (_item != null)
  375.             {
  376.                 // Le fond de l'avatar
  377.                 _backImage = new Quad(80, 80);
  378.                
  379.                 _backImage.setVertexColor(0, 0xDDDDDD);
  380.                 _backImage.setVertexColor(1, 0xDDDDDD);
  381.                 _backImage.setVertexColor(2, 0x999999);
  382.                 _backImage.setVertexColor(3, 0x999999);
  383.                
  384.                 _backImage.width = 80;
  385.                 _backImage.height = 80;
  386.                
  387.                 _backImage.x = 10;
  388.                 _backImage.y = 10;
  389.                
  390.                 addChild(_backImage);
  391.                
  392.                 _bitmapCache.load(_item.avatar, avatarSuccessHandler);
  393.                
  394.                 // Le titre
  395.                 _title = new TextField(stage.stageWidth - 120, 20, _item.username, "Verdana", 11, 0x666666);
  396.                 _title.hAlign = TextFormatAlign.LEFT;
  397.                 _title.vAlign = "top";
  398.                
  399.                 _title.x = 102;
  400.                 _title.y = 12;
  401.                
  402.                 addChild(_title);
  403.                
  404.                 // Le contenu
  405.                 _text = new TextField(stage.stageWidth - 120, 70, _item.text);
  406.                 _text.hAlign = TextFormatAlign.LEFT;
  407.                 _text.vAlign = "top";
  408.                
  409.                 _text.x = 102;
  410.                 _text.y = 30;
  411.                
  412.                 addChild(_text);
  413.             }
  414.         }
  415.        
  416.         protected function avatarSuccessHandler (pBitmapData:BitmapData, pFromCache:Boolean):void
  417.         {
  418.             if (_backImage == null)
  419.                 return;
  420.            
  421.             _image = new Image(Texture.fromBitmapData(pBitmapData));
  422.             //_image.smoothing = TextureSmoothing.NONE;
  423.            
  424.             _image.width = 80;
  425.             _image.height = 80;
  426.            
  427.             _image.x = 10;
  428.             _image.y = 10;
  429.            
  430.             addChild(_image);
  431.            
  432.             _image.texture = Texture.fromBitmapData(pBitmapData);
  433.            
  434.             TweenMax.from(_image, pFromCache ? 0 : .25, {
  435.                 alpha: 0,
  436.                 onComplete: _backImage.removeFromParent,
  437.                 onCompleteParams: [true]
  438.             });
  439.         }
  440.     }
  441. }
Advertisement
Add Comment
Please, Sign In to add comment