zoukankan      html  css  js  c++  java
  • RenderSprite小记

    类型定义:

     1   /** @private */
     2         public static const IMAGE:int = 0x01;
     3         /** @private */
     4         public static const ALPHA:int = 0x02;  //透明度变化
     5         /** @private */
     6         public static const TRANSFORM:int = 0x04;  //位置、缩放、旋转等变化
     7         /** @private */
     8         public static const BLEND:int = 0x08;
     9         /** @private */
    10         public static const CANVAS:int = 0x10;   //设置cachas
    11         /** @private */
    12         public static const FILTERS:int = 0x20;
    13         /** @private */
    14         public static const MASK:int = 0x40;
    15         /** @private */
    16         public static const CLIP:int = 0x80;
    17         /** @private */
    18         public static const STYLE:int = 0x100;
    19         /** @private */
    20         public static const GRAPHICS:int = 0x200;
    21         /** @private */
    22         public static const CUSTOM:int = 0x400;   //自定义
    23         /** @private */
    24         public static const CHILDS:int = 0x800;  //子节点变化
    25         /** @private */
    26         public static const INIT:int = 0x11111;

    Laya定义了12中对sprite操作类型,以及默认初始化表示INIT。
    每种操作类型对应以为,可以通过或操作合并多种操作。

    1         /** @private */
    2         public static var renders:Array = [];    //长度为4096的数组,存放所有可能的操作合集。
    3         /** @private */   //默认RenderSprite  操作函数为空
    4         protected static var NORENDER:RenderSprite = /*[STATIC SAFE]*/ new RenderSprite(0, null);
    5         /** @private */   //下一个操作的RenderSprite
    6         public var _next:RenderSprite;
    7         /** @private */   //当前RenderSprite对应的操作
    8         public var _fun:Function;

    _fun是RenderSprite对Sprite的操作,一个RenderSprite对象只有一种操作。
    _next是指向下一个操作的RenderSprite。可能同时对Sprite进行多种操作,这些操作需要按照一定顺序依次执行,_next就指向了下一步要做的操作。默认指向NORENDER。
    renders是一个静态数组,长度为0x800 * 2 ,在初始化时,使用INIT操作的RenderSprite填满,当对sprite执行操作合集时,如 TRANSFORM | CHILDS,将新的RenderSprite填充,填充的位置为操作类型的按位或的结果,如 TRANSFORM | CHILDS = 0x804。填充的新的RenderSprite将先对Sprite进行TRANSFORM操作,再执行CHILDS操作。
    NORENDER是一个处理函数为空的RenderSprite,RenderSprite._next默认执行NORENDER。

    初始化

     1         public static function __init__():void {
     2             var i:int, len:int;
     3             var initRender:RenderSprite;
     4             initRender = RunDriver.createRenderSprite(INIT, null);       //创建INIT类型的RenderSprite    这里的RenderSprite为RenderSprite3D
     5             len = renders.length = CHILDS * 2;                                      //设置数组长度为0x800 * 2
     6             for (i = 0; i < len; i++)
     7                 renders[i] = initRender;                                                      //给数组填充默认值
     8 
     9             renders[0] = RunDriver.createRenderSprite(0, null);            //0号位默认为空操作RenderSprite
    10 
    11             function _initSame(value:Array, o:RenderSprite):void {
    12                 var n:int = 0;
    13                 for (var i:int = 0; i < value.length; i++) {
    14                     n |= value[i];
    15                     renders[n] = o;
    16                 }
    17             }
    18             //填充数组部分位置
    19             _initSame([IMAGE, GRAPHICS, TRANSFORM, ALPHA], new RenderSprite(IMAGE, null));
    20             //IMAGE | GRAPHICS   和 IMAGE | TRANSFORM | GRAPHICS  有对应的处理函数
    21             renders[IMAGE | GRAPHICS] = RunDriver.createRenderSprite(IMAGE | GRAPHICS, null);
    22 
    23             renders[IMAGE | TRANSFORM | GRAPHICS] = new RenderSprite(IMAGE | TRANSFORM | GRAPHICS, null);
    24         }

    执行流程

    • sprite在设置scale,filters,cacheas,skew,graphic等属性或者修改父节点子节点时会改变其_renderType属性,将_renderType的对应位置设置为0或1。以scaleX为例:
     1   public function set scaleX(value:Number):void {
     2    var style:Style = getStyle();
     3    if (style._tf.scaleX !== value) {
     4     style.setScaleX(value);
     5     _tfChanged = true;
     6     conchModel && conchModel.scale(value, style._tf.scaleY);
     7     _renderType |= RenderSprite.TRANSFORM;      //与RenderSprite.TRANSFORM或操作,将对应标志位设置为1
     8     var p:Sprite = _parent as Sprite;
     9     if (p && p._repaint === 0) {
    10      p._repaint = 1;
    11      p.parentRepaint();
    12     }
    13    }
    14   }
    • 当进入渲染帧时,每一个Sprite会用自己的_renderType在RenderSprite._renders数组中找到对应操作的RenderSprite对象。并执行RenderSprite对象的_func方法。
     1   /**
     2    * 更新、呈现显示对象。由系统调用。
     3    * @param context 渲染的上下文引用。
     4    * @param x X轴坐标。
     5    * @param y Y轴坐标。
     6    */
     7   public function render(context:RenderContext, x:Number, y:Number):void {
     8    Stat.spriteCount++;
     9    RenderSprite.renders[_renderType]._fun(this, context, x + _x, y + _y);  //this 是sprite对象,_renderType作为renders数组的索引
    10    _repaint = 0;
    11   }
    • 初始化时,绝大多数的_renders数组都是指向操作类型为INIT的RenderSprite。当执行INIT的RenderSprite对象时会生成一个renderType对应的唯一的RenderSprite对象,这个对象包含着对一个Sprite的操作队列。
    private static function _initRenderFun(sprite:Sprite, context:RenderContext, x:Number, y:Number):void {
     var type:int = sprite._renderType;
     var r:RenderSprite = renders[type] = _getTypeRender(type);    //将新生成的RenderSprite放到type的索引位置,下次调用时,不需要再初始化。
    //生成完RenderSprite后,执行操作函数。
     r._fun(sprite, context, x, y);
    }
    // type为当前帧Sprite的renderType
      private static function _getTypeRender(type:int):RenderSprite {
       var rst:RenderSprite = null;
       var tType:int = CHILDS;   //0x800  操作的最后一种类型
       while (tType > 1) {
        if (tType & type)      //为每一个类型为1的类型创建一个RenderSprite,并将上一个RenderSprite设置为自己的next
         rst = RunDriver.createRenderSprite(tType, rst);
        tType = tType >> 1;
       }
       return rst;
      }

    由于是从高位到低位去取交集,类型小的RenderSprite会优先执行,类型大的会在_next中,当前一个操作执行完成后,再执行,这就保证了各个操作的执行顺序。

    其他

    • RenderSprite就是对Sprite渲染的工具合集,不持有对Sprite的引用。
    • 大部分RenderSprite对象为RenderSprite3D的实例。
    • 一个类型的RenderSprite只会初始化一次,下次再调用时,可以直接执行对应操作。
    • IMAGE | GRAPHICS 和 IMAGE | TRANSFORM | GRAPHICS 当做一个整体处理,有独立的处理函数。
  • 相关阅读:
    70.BOM
    69.捕获错误try catch
    68.键盘事件
    523. Continuous Subarray Sum
    901. Online Stock Span
    547. Friend Circles
    162. Find Peak Element
    1008. Construct Binary Search Tree from Preorder Traversal
    889. Construct Binary Tree from Preorder and Postorder Traversal
    106. Construct Binary Tree from Inorder and Postorder Traversal
  • 原文地址:https://www.cnblogs.com/chiguozi/p/9508578.html
Copyright © 2011-2022 走看看