starling 笔记

------------------------------------------------------------------

这里的舞台是flash原生舞台,不是starling舞台

// register other event handlers
stage.addEventListener(Event.ENTER_FRAME, onEnterFrame, false, 0, true);
stage.addEventListener(KeyboardEvent.KEY_DOWN, onKey, false, 0, true);
stage.addEventListener(KeyboardEvent.KEY_UP, onKey, false, 0, true);
stage.addEventListener(Event.RESIZE, onResize, false, 0, true);
stage.addEventListener(Event.MOUSE_LEAVE, onMouseLeave, false, 0, true);


starling onEnterFrame

1.通过方法调度事件..传入的参数是两帧之间的时间
调用了mTouchProcessor的advanceTime
调用了mStage的advanceTime
调用了mJuggler的advanceTime

2.render 按照viewport缩放舞台自适应..等.


display object 的EnterFrame事件

1.当向displayobject增加事件的时候,如果是enterFrame事件,则会向starling舞台把该display添加到..mEnterFrameListeners数组中
//enterFrame只能被添加一次
if (type == Event.ENTER_FRAME && !hasEventListener(type))
{
addEventListener(Event.ADDED_TO_STAGE, addEnterFrameListenerToStage); =====> Starling.current.stage.addEnterFrameListener(this);
addEventListener(Event.REMOVED_FROM_STAGE, removeEnterFrameListenerFromStage);
if (this.stage) addEnterFrameListenerToStage(); //如果已经添加到了舞台上,则不会触发ADDED_TO_STAGE事件,这里则手动添加
}

2.starling舞台,会在每帧的时候.调用advanceTime方法.循环所有listeners..广播事件


-------------------------------------------------------
<h2>contentScaleFactor</h2>

Starling.current 实例化的Starling

mViewPort.width

mViewPort

mPreviousViewPort 早先的viewport

mClippedViewPort 原生的舞台viewport 和 mViewPort的 交集区域

mSupportHighResolutions 支持搞分辨率

mNativeStageContentScaleFactor,原生舞台缩放因子.

----------------------------------------------------------------------------

缩放比例
(mViewPort.width * mNativeStageContentScaleFactor) / mStage.stageWidth;

updateViewPort中...如果支持高资源而且原生的stage有contentsScaleFactor则..设置原生缩放银子
<pre>
if (mSupportHighResolutions && "contentsScaleFactor" in mNativeStage)
mNativeStageContentScaleFactor = mNativeStage["contentsScaleFactor"]; //要设置 支持高分辨率 和 原生舞台的contentsScaleFactor
else
mNativeStageContentScaleFactor = 1.0;
</pre>

------------------------------------------------------------------------

//一个空纹理..然后向里面上传数据

public static function empty(width:Number, height:Number, premultipliedAlpha:Boolean=true,
mipMapping:Boolean=true, optimizeForRenderToTexture:Boolean=false,
scale:Number=-1, format:String="bgra"):Texture
{
if (scale <= 0) scale = Starling.contentScaleFactor; //如没有在Starling中进行特殊设置..默认为1

var actualWidth:int, actualHeight:int;
var nativeTexture:flash.display3D.textures.TextureBase;
var context:Context3D = Starling.context;

if (context == null) throw new MissingContextError();

var origWidth:int = width * scale; //原始宽度
var origHeight:int = height * scale; //原始高度
var potWidth:int = getNextPowerOfTwo(origWidth); //获取该宽度最接近的偶数幂
var potHeight:int = getNextPowerOfTwo(origHeight); //获取该高度最接近的偶数幂
var isPot:Boolean = (origWidth == potWidth && origHeight == potHeight); //是否扩充
var useRectTexture:Boolean = !isPot && !mipMapping && //是否使用了矩形原理,如果扩充了..而且不使用mip..而且...剩下两个不知道 ...
Starling.current.profile != "baselineConstrained" &&
"createRectangleTexture" in context && format.indexOf("compressed") == -1;

if (useRectTexture)
{
actualWidth = origWidth;
actualHeight = origHeight;

// Rectangle Textures are supported beginning with AIR 3.8. By calling the new
// methods only through those lookups, we stay compatible with older SDKs.
nativeTexture = context["createRectangleTexture"](
actualWidth, actualHeight, format, optimizeForRenderToTexture);
}
else //基本上都是这个
{
actualWidth = potWidth;
actualHeight = potHeight;

nativeTexture = context.createTexture(actualWidth, actualHeight, format,
optimizeForRenderToTexture);
}

var concreteTexture:ConcreteTexture = new ConcreteTexture(nativeTexture, format, //通过原生纹理.创建了concreteTexture
actualWidth, actualHeight, mipMapping, premultipliedAlpha,
optimizeForRenderToTexture, scale);

concreteTexture.onRestore = concreteTexture.clear;

if (isPot || useRectTexture) //没有扩充或者使用了矩形纹理
return concreteTexture;
else
return new SubTexture(concreteTexture, new Rectangle(0, 0, width, height), true);
}

trace(!isPot,!mipMapping,Starling.current.profile != "baselineConstrained",
"createRectangleTexture" in context,format.indexOf("compressed") == -1);


false true false false true //经过 处理过的图片
true false false false true //未经过处理过的图片


//纹理的流程
/**
* 1.都是通过empty方法.建立一个空的纹理然后在bitmapData方法中.上传bitmap数据
* 2.在empty方法中会 将bitmap的width和height..扩充到2的幂数倍上
* 3.在empty方法中会 用实例化ConcreteTexture封装了Stage3D纹理对象的ConcreteTexture,用于存储纹理属性。
* 4.如果没有扩充幂数倍.或者使用了矩形纹理,则返回的是ConcreteTexture对象.
* 5.因为扩充后的大小和原始大小不一样..所以需要使用SubTexture对象.通过原始大小的rect操作纹理坐标截取原始大小的纹理..返回正常的纹理
*/


/**
* 纹理缩放主要来自两个地方..纹理是针对当前舞台的...所以要把纹理缩放到当前舞台需要的大小..即素材制作为原始素材的2倍,读取纹理的时候缩放成舞台需要的纹理大小即
* 除以2.然后starling会根据viewport将舞台进行缩放..达到高清的效果
*
* 1. Starling.contentScaleFactor
* 2.从外部传入的scale参数.....
*/

trace(texture.width,texture.nativeWidth,texture.scale);
trace(texture.height,texture.nativeHeight,texture.scale);


------------------------------------------------------------------------------------
关于starling内置的缩放模式
starling的viewport获取算法:
RectangleUtil的fit方法:

var stageWidth:int = 320;
var stageHeight:int = 480;

//获取根据showall等缩放模式返回的viewport大小..会改变x,y的值,以及缩放其中的一边...达到最合适的舞台大小
var viewPort:Rectangle = RectangleUtil.fit(
new Rectangle(0, 0, stageWidth, stageHeight),
new Rectangle(0, 0, stage.fullScreenWidth, stage.fullScreenHeight),
ScaleMode.SHOW_ALL, iOS);

mStarling = new Starling(Game, stage, viewPort);
mStarling.stage.stageWidth = stageWidth; // <- same size on all devices!
mStarling.stage.stageHeight = stageHeight; // <- same size on all devices!


在舞台的呈现的时候...会向viewport对舞台进行整体缩放.

所以只要根据stagewidth和stageheight..制作素材即可.

舞台(starling的stage)的大小决定了在该视口中显示的坐标系统的大小。(举个栗子:我用小米,屏幕分辨率是854*480.我设定statling的stage为400*400,那么手机屏幕上显示出来的其实是400*400像素的图像,只不过放大拉伸了,同理我设定starling的stage为1000*1000,虽然小米屏幕只有854*480像素,但它显示的是1000*1000的图像,图像被缩小了。)

------------------------------
关于dispaly的width和height

宽和高的获取..并不是直接返回属性width和height..而是,通过getBounds方法返回一个rect的width和height属性.

getBounds(mParent, sHelperRect) helerect为一个空的rect

quad
会根据其内部的mVertexData.的右下角点.设置sHelperPoint
mVertexData.getPosition(3, sHelperPoint);
最后根据缩放和pivotX和pivotY.返回一个新的矩形.

containers
首先矩阵进行计算,然后每一个子元件的每个顶点都和该矩阵相乘...他获取的是当前容器内部元素的宽和高...所以直接设置宽和高无效..
this._container = new Sprite();
this.addChild(this._container);
this._container.y = headBg.height;

this._container.width= 640;

trace(this._container.width);//该处是0


避免重复调用width和height
获取宽度和高度属性是一个昂贵的性能开销,特别是对于Sprite容器(首先矩阵进行计算,然后每一个子元件的每个顶点都和该矩阵相乘)。
出于这个原因,请避免重复访问它们,比如在一个循环里面。在某些情况下,使用一个恒定的值来代替它们更有意义。

--------------------------------
TextureSmoothing
image 默认 BILINEAR 双线性过滤。创建像素间的平滑过渡。
QuadBatch xxx
RenderTexture 若persistent===true 则其TmHelperImage的smooting为extureSmoothing.NONE

----------------------------------
纹理集
mTextureRegions

mTextureRegions 是个Dictionary 保存该纹理的region,索引是name,
mTextureFrames 是个Dictionary 保存该纹理的frame,索引是name 纹理框..是什么?

xml中每个子纹理.定义了以下属性
name
x,y,widht,height ---------------------------region
frameX,frameY,frameWidth,frameHeight---------frame


上面三个参数..通过addRegion方法..
mTextureRegions[name] = region;
mTextureFrames[name] = frame;


-------------------------------------------

assetManager

enqueue :
将一个或一组素材加入到队列中;只有在成功调用了"loadQueue"方法后这些资源才可用。
这个方法可以接受下面这些类型:
1.使用字符串定义的URL,链接到一个本地或远程网络上的资源。支持类型: png, jpg, atf, mp3, fnt, xml (纹理图集).
2.File类的实例 (只有AIR应用适用) 指定的一个目录或一个文件.如果是目录,则会自动扫描该目录下所有支持的文件类型。
3.包含静态成员结合Embed方式内嵌素材的类.

getName方法中:
对象的名称会自动提取:比如一个文件名称是"image.png",那么会自动将素材命名为"image"。
如果是通过类的嵌入素材方式,那么变量名称就会使用嵌入时那个名称。
一个例外是纹理图集:他们将具备相同的名称(实际引用的那个纹理名称)。

enqueueWithName: 将资源推入到mRawAssets数组中..并返回资源名称

---------
loadQueue

addSound(name, asset as Sound); 将加载的声音..保存在mSounds里
addTexture(name,texture) 将纹理存储在mTextures
addObject() 将json加载到mObject中
addByteArray(name, bytes); 将bytes 保存到mByteArrays
addXml(name:String, xml:XML) 如果是普通的xml保存到mXmls
addTextureAtlas rootNode == "TextureAtlas"的xml会被处理然后把纹理集保存到mAtlases...注意如果mTextures有同名纹理.则会从mTextures中删除
rootNode == "font" 会被TextField.registerBitmapFont注册.

getTexture 如果mTextures中有纹理..则会返回..没有的话,则查找纹理集.否则返回null
-------------------------------------------------------------------

juggler 当你创建了一个自定义juggler,那么你必须在每一帧上调用“advanceTime”方法.即在Main类的enterFrame方法中执行这个juggler的advancerTime方法

Starling在初始化的时候会默认生成一个juggler事例。并在每一帧的时候调用该实例的advanceTime函数

add 向mObjects中添加实现了IAnimatable接口的对象..即该对象要有advanceTime方法..例如movieClip .并添加了.Event.REMOVE_FROM_JUGGLER事件

advanceTime 会在每帧的时候循环调用mObjects中的object的advaneTime方法... 即每帧..

remove 可以直接使用该方法从juggler中移除..或者触发Event.REMOVE_FROM_JUGGLER事件

removeTweens...一般补间动画完成后,会自动删除!!如果手动移除用这个,触发Event.REMOVE_FROM_JUGGLER事件,会播放nextTween

purge() 移除所有对象

delayCall 延迟调用函数 实例化了一个DelayedCall,并添加到juggler中.

tween
在指定的时间内,用一个补间动画(tween)去"运动"一个对象。在内部,这个方法使用一个tween的实例(从缓存池中获取的),然后添加到juggler里面。 这个方法是一个快捷机制,用来方便的创建一个tween并且使用它。 设置'properties'属性,可以用键值对的方式来定义tween和动画对象。这里是一个示例片段: juggler.tween(object, 2.0, { transition: Transitions.EASE_IN_OUT, delay: 20, // -> tween.delay = 20 x: 50 // -> tween.animate("x", 50) });

Tween

补间一旦完成,他们会从juggler中被自动删除

sTweenPool juggler第一次添加tween后..会始终至少在sTweenPool中保存一个空的tween.

Transitions (过渡)类包含了一些静态方法,来定义缓动相关的函数。这些函数被用在Tween类执行动画的时候。用在tween中.默认为linear

------------------------------------------------------------------
hitest 返回舞台坐标系某个点下方的最顶层的显示对象,如果没有找到任何对象,则返回null。

测试点是否在该displayobject上.如果在则返回该对象,不在则返回null;

舞台触发touch事件---> TouchProcessor的processTouches事件--->使用hittest查找 target...然后触发touch事件

转载于:https://my.oschina.net/zhepama/blog/265026

猜你喜欢

转载自blog.csdn.net/weixin_33834679/article/details/91927349