行走于手机游戏与APP之间的图形学人
参考文献:(原创不易,尊重原创产权,如需转载,请注明出处)
http://baike.baidu.com/view/1006503.htm?fr=aladdin
http://bbs.csdn.net/topics/360265271
http://www.cnblogs.com/helloandroid/articles/2948081.html
http://www.apihome.cn/api/android/GLSurfaceView.html
http://blog.sina.com.cn/s/blog_69887cd70100jxmu.html
http://www.jb51.net/article/40018.htm
http://www.cnblogs.com/qlee/archive/2011/05/16/2048026.html(vector的reserve和resize)
http://blog.csdn.net/liguangzhenghi/article/details/8185751(Android中获取应用程序(包)的信息-----PackageManager的使用)
http://blog.csdn.net/dinglin_87/article/details/7471406(AndroidManifest.xml中的meta-data属性介绍)
http://blog.csdn.net/stevenhu_223/article/details/18360397(Android中的软引用(SoftRefrerence)和弱引用(WeakReference))
http://blog.sina.com.cn/s/blog_637607ec01015y8y.html(SensorEventListener)
站在Android App开发者角度 分析template project之proj.android
Comment | Cocos2dxActivity | Cocos2dxHelperListener | Cocos2dxGLSurfaceView | Cocos2dxTextInputWraper | Cocos2dxRenderer | Cocos2dxEditText |

1、深入阅读org.cocos2dx.cpp.AppActivity

主Activity“AppActivity”是继承自Cocos2dxActivity

Cocos2dxActivity是继承自Activity、并实现了Cocos2dxHelperListener接口的抽象类

抽象类:不允许实例化的类,用关键字abstract修饰,如果一个类中含有abstract方法,那么这个类必须使用abstract来修饰。反之,abstract类中却可以没有abstract方法。不能有抽象构造函数或抽象静态方法。Abstract类的子类为它们父类中的所有抽象方法提供实现,否则它们也是抽象类。取而代之,在子类中实现该方法。虽然不能创建abstract类的实例,然而可以创建一个变量,其类型是一个抽象类,并让它指向具体子类的一个实例。

Cocos2dxHelperListener接口是定义了三个public函数(showDialog、showEditTextDialog、runOnGLThread)的public static interface

public static interface:接口必须要具体类实现才有意义,所以必须是public;接口中的数据对所有实现类只有一份,所以是static,即单例

Cocos2dxActivity类主要定义了如下变量:

1.1.1、private final static String TAG = Cocos2dxActivity.class.getSimpleName();(该变量用于打log的时候起到标示的作用。)

getSimpleName()返回源代码中给出的底层类的简称。

1.1.2、private Cocos2dxGLSurfaceView mGLSurfaceView;

Cocos2dxGLSurfaceView是继承自GLSurfaceView的类

GLSurfaceView是OpenGL绘制所在的容器。为了能在Android应用中使用OpenGLES绘画,必须创建一个view作为容器。而最直接的方式就是从GLSurfaceView派生一个类。使用GLSurfaceView几乎是整合OpenGLES到你的应用的唯一方式。对于一个全屏或近全屏的graphicsview,它是最好的选择。如果只是在某个小部分显示OpenGLES图形则可以考虑TextureView。当然如果你比较变态,你完全可以使用SurfaceView创建一个OpenGLES view。GLSurfaceView中其实不需要做太多工作,实际的绘制任务都在GLSurfaceView.Renderer中了。所以GLSurfaceView中的代码也非常少,你甚至可以直接使用GLSurfaceView,但是,然而,别这样做。因为你需要扩展这个类来响应触摸事件。

Cocos2dxGLSurfaceView类主要定义了如下变量:

1.2.1、private static Handler sHandler;

Handler在Android中主要是负责发送和处理消息。它的主要用途大致是下面两个:1)按计划发送消息或执行某个Runnanble;2)从其他线程中发送来的消息放入消息队列中,避免线程冲突(常见于更新UI线程)

1.2.2、private static Cocos2dxGLSurfaceView mCocos2dxGLSurfaceView;

1.2.3、private static Cocos2dxTextInputWraper sCocos2dxTextInputWraper;

Cocos2dxTextInputWraper是实现了TextWatcher接口和OnEditorActionListener接口的类

Cocos2dxTextInputWraper类主要定义了如下变量:

1.3.1、private final Cocos2dxGLSurfaceView mCocos2dxGLSurfaceView;

Cocos2dxTextInputWraper类主要使用了如下函数:

1.3.2、构造函数:public Cocos2dxTextInputWraper(final Cocos2dxGLSurfaceView pCocos2dxGLSurfaceView) 将输入参数定义赋值给内部变量

1.2.4、private Cocos2dxRenderer mCocos2dxRenderer;

Cocos2dxRenderer是实现了GLSurfaceView.Renderer接口的类

实际的绘图动作都是在GLSurfaceView.Renderer里面发生的

Cocos2dxRenderer类主要使用了如下函数:

1.4.1、public void onSurfaceCreated(final GL10 pGL10, final EGLConfig pEGLConfig)

作用:

通过jni调用native层的Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeInit函数。获取(或者创建)单例s_SharedDirector(Director的子类,Ref的孙子类),获取(或者创建)单例Configuration对象(Ref的子类),实例化了2个scence(Node的子类,Ref的孙子类)变量_runningScene和_nextScene(实例化了一个Camera(Node的子类、Ref的孙子类),创建了一个新的event),实例化Node类的一个变量_notificationNode,使用vector的reserve给_scenesStack预留15个空位,初始化变量accumDt、_frameRate、_FPSLabel、_drawnBatchesLabel、_drawnVerticesLabel、_totalFrames、_frames、_lastUpdate(时间结构体)、_paused、_purgeDirectorInNextLoop、_winSizeInPoints、_openGLView、_contentScaleFactor,实例化了一个Scheduler,实例化了一个ActionManager,并将ActionManager使用scheduleUpdate与Scheduler关联上。实例化了一个EventDispatcher(Ref的子类),实例化了4个EventCustom(Event的子类、Ref的孙子类),实例化之后将其成员变量_userData 设置为当前Director;实例化一个TextureCache(Ref的子类);初始化Matrix,如果_modelViewMatrixStack、_projectionMatrixStack、_textureMatrixStack不为空,就先进行pop,然后将将单位矩阵压入;实例化一个Renderer;实例化一个Console(Ref的子类)。由于新创建的glview为空,所以创建一个新的glview为GLViewImpl(GLView的子类,Ref的孙子类)的一个实例,并将其initWithFullScreen和加入autorelease pool。将_designResolutionSize和_screenSize根据传入的宽和高设置好,并根据get出来的windows的宽和高以及framebuffer的宽和高以及是否为retina屏,设置window size。将glview通过setOpenGLView设置为director的glview。然后开始run(调用真正的cocos2dx开发者的入口函数AppDelegate::applicationDidFinishLaunching()),开始显示fps,设置fps的默认值,创建一个scene,创建一个layer,然后将layer加入scene,将scene加入scenestack,设置动画延迟。

调用Director类的getInstance函数,创建(或者获取)s_SharedDirector单例,创建的时候调用祖父类Ref的构造函数,父类Director的构造函数,DisplayLinkDirector的构造函数,将如下变量进行了初始化:_referenceCount(1),单例uObjectCount变量 = 0;_luaID = 0;_ID = ++单例uObjectCount变量;_luaID = 0,_scriptObject = nullptr,然后调用了s_SharedDirector的父类Director的init函数。

调用Configuration类的getInstance函数,实例化一个Configuration对象,调用了父类Ref的构造函数将如下变量设置为初始值:_referenceCount(1);_luaID = 0;_ID = ++单例uObjectCount变量;_scriptObject = nullptr;然后在Configuration的构造函数中等将如下变量设置为初始值:maxTextureSize(0)、maxModelviewStackDepth(0)、supportsPVRTC(false)、supportsETC1(false)、supportsS3TC(false)、supportsATITC(false)、supportsATITC(false)、supportsNPOT(false)、supportsBGRA8888(false)、supportsDiscardFramebuffer(false)、supportsShareableVAO(false)、maxSamplesAllowed(0)、maxTextureUnits(0)、glExtensions(nullptr)。然后在Configuration类的init函数中,定义了一些key_value对:"cocos2d.x.version"->"cocos2d-x 3.3beta0";"cocos2d.x.compiled_with_profiler"->false;"cocos2d.x.compiled_with_gl_state_cache"->true;"cocos2d.x.build_type"->?

将如下变量设置成默认值:_oldAnimationInterval = _animationInterval = 1.0 / kDefaultFPS;_displayStats->false;projection->3d;_projection(初始化为单位矩阵mat4) = Projection::_3D;pixel_format->rgba8888;单例Texture2D::PixelFormat g_defaultAlphaPixelFormat变量=Texture2D::PixelFormat::RGBA8888;pvr_alpha_premultipled->false;单例_PVRHaveAlphaPremultiplied变量=false;

场景类的实例_runningScene、_nextScene=nullptr,调用场景类祖父类Ref的构造函数将如下变量设置为初始值:_referenceCount(1); _luaID = 0;_ID = ++单例uObjectCount变量;_scriptObject = nullptr;调用父类Node的构造函数将如下变量赋予初始值:_rotationX(0.0f);_rotationY(0.0f);_rotationZ_X(0.0f);_rotationZ_Y(0.0f);_scaleX(1.0f);_scaleY(1.0f);_scaleZ(1.0f);_positionZ(0.0f);_position(Vec2::ZERO);_skewX(0.0f);_skewY(0.0f);_anchorPointInPoints(Vec2::ZERO)=(0,0);_anchorPoint(Vec2::ZERO);_contentSize(Size::ZERO)=(0,0);_useAdditionalTransform(false);_transformDirty(true);_inverseDirty(true);_transformUpdated(true);_localZOrder(0);_globalZOrder(0);_parent(nullptr);_tag(Node::INVALID_TAG)=-1;_userData(nullptr);_userObject(nullptr);_glProgramState(nullptr);orderOfArrival(0);_running(false);_visible(true);_ignoreAnchorPointForPosition(false);_reorderChildDirty(false);_isTransitionFinished(false);_updateScriptHandler(0);_componentContainer(nullptr);_physicsBody(nullptr);_physicsScaleStartX(1.0f);_physicsScaleStartY(1.0f);_displayedOpacity(255);_realOpacity(255);_displayedColor(Color3B::WHITE)=(255, 255, 255);_realColor(Color3B::WHITE);_cascadeColorEnabled(false);_cascadeOpacityEnabled(false);_usingNormalizedPosition(false);_normalizedPositionDirty(false);_name("");_hashOfName(0);_cameraMask(1);获取s_SharedDirector单例,将director的ActionManager、Scheduler、EventDispatcher进行retain,retain就是将_referenceCount+1;创建(或者获取)ScriptEngineManager单例,获得默认的ScriptEngineProtocol,_scriptType = engine = kScriptTypeNone;_transform = _inverse = _additionalTransform = Mat4::IDENTITY(单位矩阵)。场景类的构造函数:_physicsWorld=nullptr;_ignoreAnchorPointForPosition = true;_anchorPoint = Vec2(0.5f, 0.5f);_anchorPointInPoints = Vec2(_contentSize.width * 0.5, _contentSize.height * 0.5);_transformUpdated = _transformDirty = _inverseDirty = true。创建一个新的Camera,调用祖父类Ref的构造函数、父类Node的构造函数以及Camera的构造函数,设置如下几个值:_cameraFlag(1);_scene(nullptr);_viewProjectionDirty(true)。调用Camera的initDefault函数,从Directore得到size=_winSizeInPoints,然后得到zeye=_winSizeInPoints.height / 1.1566f;使用initPerspective初始化camera(?),并将camera加入Ref的autorelease pool,并将camera进行addChild。定义_event = Director::getInstance()->getEventDispatcher()->addCustomEventListener(Director::EVENT_PROJECTION_CHANGED, std::bind(&Scene::onProjectionChanged, this, std::placeholders::_1));并对_event进行remain

将如下变量设置成默认值:_oldAnimationInterval = _animationInterval = 1.0 / kDefaultFPS;_displayStats->false;projection->3d;_projection(初始化为单位矩阵mat4) = Projection::_3D;pixel_format->rgba8888;单例Texture2D::PixelFormat g_defaultAlphaPixelFormat变量=Texture2D::PixelFormat::RGBA8888;pvr_alpha_premultipled->false;单例_PVRHaveAlphaPremultiplied变量=false;

Scheduler的实例_scheduler,调用Scheduler的构造函数,将如下变量设置为初始值:_timeScale(1.0f);_updatesNegList(nullptr);_updates0List(nullptr);_updatesPosList(nullptr);_hashForUpdates(nullptr);_hashForTimers(nullptr);_currentTarget(nullptr);_currentTargetSalvaged(false);_updateHashLocked(false);_scriptHandlerEntries(20);使用vector的reserve给_functionsToPerform预留30个空位

schedule函数是帧回调函数,默认是每帧结束的时候调用一次这个函数(游戏的主要逻辑在这里触发,比如碰撞检测),回调函数的格式是:无返回参数、输入参数为float。如:schedule(schedule_selector(MainScene::update))

ActionManager的实例_actionManager,调用父类Ref的构造函数_referenceCount(1); _luaID = 0;_ID = ++单例uObjectCount变量;_scriptObject = nullptr;调用ActionManager的构造函数_targets(nullptr);_currentTarget(nullptr);_currentTargetSalvaged(false)

EventDispatcher的实例_eventDispatcher,调用父类Ref的构造函数_referenceCount(1); _luaID = 0;_ID = ++单例uObjectCount变量;_scriptObject = nullptr

EventCustom的实例_eventAfterDraw、_eventAfterVisit、_eventAfterUpdate、_eventProjectionChanged,调用祖父类Ref的构造函数_referenceCount(1); _luaID = 0;_ID = ++单例uObjectCount变量;_scriptObject = nullptr;调用父类的构造函数_type(输入参数);_isStopped(false);_currentTarget(nullptr)。

TextureCache的实例_textureCache,调用父类Ref的构造函数_referenceCount(1); _luaID = 0;_ID = ++单例uObjectCount变量;_scriptObject = nullptr;调用TextureCache的构造函数:TextureCache;_asyncStructQueue(nullptr);_imageInfoQueue(nullptr);_needQuit(false);_asyncRefCount(0)。

Renderer的实例_renderer,调用Renderer的构造函数_lastMaterialID(0);_lastBatchedMeshCommand(nullptr);_filledVertex(0);_filledIndex(0);_glViewAssigned(false);_isRendering(false);_cacheTextureListener(nullptr),实例化了一个GroupCommandManager(Ref的子类),调用父类Ref的构造函数_referenceCount(1); _luaID = 0;_ID = ++单例uObjectCount变量;_scriptObject = nullptr;将DEFAULT_RENDER_QUEUE push到_commandGroupStack;将defaultRenderQueue push_back到_renderGroups;给_batchedCommands预留BATCH_QUADCOMMAND_RESEVER_SIZE个位置。

Console的实例_console,父类Ref的构造函数_referenceCount(1); _luaID = 0;_ID = ++单例uObjectCount变量;_scriptObject = nullptr;调用Console的构造函数:_listenfd(-1);_running(false);_endThread(false);_sendDebugStrings(false)。

GLViewImpl的实例ret,祖父类Ref的构造函数_referenceCount(1); _luaID = 0;_ID = ++单例uObjectCount变量;_scriptObject = nullptr;调用父类GLView的构造函数:_scaleX(1.0f);_scaleY(1.0f);_resolutionPolicy(ResolutionPolicy::UNKNOWN);调用GLViewImpl的构造函数:初始化三个extension:glGenVertexArraysOES、glBindVertexArrayOES、glDeleteVertexArraysOES

director的setOpenGLView函数是:如果当前的glview并非刚创建的这个glview,就将之前的glview release,然后设置成当前的glview,并进行retain。获取到单例Configuration对象(Ref的子类),并根据GPU信息(GLversion、extension等),把对应的参数使用Vector Dict的形式设置好,并根据是否是debug模式设置debug log,将_winSizeInPoints设置为_designResolutionSize,创建StatsLabel,将texture的g_defaultAlphaPixelFormat设置为Texture2D::PixelFormat::RGBA4444,实例化Image,使用固定值进行初始化,实例化一个texture,使用生成的图片进行初始化,加入_textures,起名为cc_fps_images,retain后加入autorelease pool,在android或者windows平台下,还需要将texture和图片加入VolatileTextureMgr。实例化三个LabelAtlas(AtlasNode、LabelProtocol的子类,Node、TextureProtocol的孙子类,BlendProtocol的重孙类)的对象,将其加入autorelease pool,retain,设置_ignoreContentScaleFactor为true,并进行初始化,初始化后,根据传入的string对应的进行设置,并设置contentsize。设置setScale,可以进行尺寸更新。将texture的g_defaultAlphaPixelFormat设置回去为Texture2D::PixelFormat::RGBA8888,给label设置position。设置Blend参数、关闭depthtest、设置viewport、设置单位阵、设置矩阵和LookAt、设置clearColor。初始化initGLView,开启时间调度机_eventDispatcher

LabelAtlas的实例化,调用爷爷类Node的构造函数,以及父类AtlasNode的构造函数,_itemsPerRow(0),_itemsPerColumn(0),_itemWidth(0),_itemHeight(0),_textureAtlas(nullptr),isOpacityModifyRGB(false),_quadsToDraw(0),_uniformColor(0),_ignoreContentScaleFactor(false)。

LabelAtlas的初始化initWithString(传入string,texture,宽、高、startCharMap)。调用AtlasNode的initWithTexture函数(传入texture,宽、高、string长度),设置宽、高、颜色、不透明度、blend方法,实例化一个TextureAtlas(Ref的子类),调用Ref的构造函数,调用TextureAtlas的构造函数_indices(nullptr),_dirty(false),_texture(nullptr),_quads(nullptr),_rendererRecreatedListener(nullptr)。使用initWithTexture(传入texture、string长度)初始化这个texture,把texture retain,设置_quads和_indices,设置VAO和VBO,获取program。

onSurfaceCreated() :在开始渲染的时候被调用,无论什么时候OpenGL ES 渲染不得不重新被创建。(渲染是典型的丢失并重新创建当活动被暂停或恢复。)该方法一个创建长生命周期OpenGL资源(如材质)的好地方。

c++中的auto用来声明自动变量,是存储类型标识符,表明变量(自动)具有本地范围,块范围的变量声明(如for循环体内的变量声明)默认为auto存储类型。大多普通声明方式声明的变量都是auto变量,他们不需要明确指定auto关键字,默认就是auto的了。auto变量在离开作用域是会变程序自动释放,不会发生内存溢出情况(除了包含指针的类)。

c++中的using namespace std包含标准库中的一切,使用了该语句,就好像它们被声明为全局变量一样。但这又会带来了一个新问题。无数原有的C++代码都依赖于使用了多年的伪标准库中的功能,他们都是在全局空间下的。所以就有了等等这样的头文件,一个是为了兼容以前的C++代码,一个是为了支持新的标准。

c++中的static形容的变量为单例。

c++中的在A里面加friend class B;使得B类可以访问A类里面的protected和private的成员函数或成员变量,因此,可以在B里面使用a.x来访问A类的私有成员int x;如果没有这句,这段代码编译不过的。但注意一点,在A里面声明了这句,只能让B类内部访问A类的保护或私有成员,反之A类不能访问B类保护或私有成员

c++中如果编译器是支持nullptr的话,那么应该直接使用nullptr来替代NULL的宏定义。正常使用过程中他们是完全等价的。因为NULL就被直接定义为一个整型0。在大多数情况下这并不会产生什么问题,但是万一有重载或者模板推导的时候,编译器就无法给出正确结果了。

c++中new(std::nothrow) 顾名思义,即不抛出异常,当new一个对象失败时,默认设置该对象为NULL,这样可以方便的通过if(p == NULL) 来判断new操作是否成功。建议在c++代码中,凡是涉及到new操作,都采用new(std::nothrow),然后if(p==NULL)的方式进行判断

c++中mutable也是为了突破const的限制而设置的。被mutable修饰的变量,将永远处于可变的状态,即使在一个const函数中。

vector 的reserve增加了vector的capacity,但是它的size没有改变!reserve是容器预留空间,但在空间内不真正创建元素对象,所以在没有添加新的对象之前,不能引用容器内的元素。加入新的元素时,要调用push_back()/insert()函数。而resize改变了vector的capacity同时也增加了它的size!resize是改变容器的大小,且在创建对象,因此,调用这个函数之后,就可以引用容器内的对象了,因此当加入新的元素时,用operator[]操作符,或者用迭代器来引用元素对象。此时再调用push_back()函数,是加在这个新的空间后面的。

System.nanoTime()获取当前时间,纳米级

1.4.2、public void onSurfaceChanged(final GL10 pGL10, final int pWidth, final int pHeight)

onSurfaceChanged():该方法在surface大小改变时被调用。这是设置你opengl视图端的好地方。如果相机是固定的,不会围着场景移动,你也可以在这里设置你的相机。

1.4.3、public void onDrawFrame(final GL10 gl)

作用:

在这个函数中加入了延迟动画时间的限制,在限制之内的话会直接通过jni层调用native层的Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeRender。然后调用drawScene函数,首先根据delay时间判断是否需要skip一帧frame,如果没有暂停,更新_scheduler(根据优先级)和_eventDispatcher,clear color和depth,设置矩阵,clear状态,设置camera,设置矩阵,进行绘制,然后swapbuffer,最后clear

onDrawFrame():每帧的时候该方法都会被调用,这个用于画场景是可靠的。你完全可以通过调用glClear方法开清楚帧缓存,接着通过其他的opengl ES来调用画当前的场景。

1.4.4、public void handleOnResume()

1.4.5、public void handleOnPause()

1.2.5、private Cocos2dxEditText mCocos2dxEditText;

Cocos2dxEditText是继承自EditText的类

Cocos2dxGLSurfaceView类主要使用了如下函数:

1.2.6、构造函数调用父类构造函数,并调用initView函数

1.2.7、protected void initView()设置GL version,SurfaceView等变量以及消息处理方法

setEGLContextClientVersion(2)当使用OpenGLES 2.0时,必须在GLSurfaceView构造器中调用该函数,它说明了你将要使用2.0版的API

setFocusableInTouchMode(true)确保能接收到触屏事件

1.2.8、public void onResume()调用父类的onResume,设置render模式,使用线程通信控制render线程resume

setRenderMode(RENDERMODE_CONTINUOUSLY):The renderer is called continuously to re-render the scene

queueEvent(Runnable)方法就是一种相对简单的操作。由于渲染器在独立的渲染线程里,你应该使用Java的跨线程机制跟渲染器通讯。由于GLSurfaceView是多线程操作,所以需要一些特殊的处理。如果在UI线程里调用渲染器的方法,很容易收到“call to OpenGL ES API with no current context”的警告,典型的误区就是在键盘或鼠标事件方法里直接调用opengl es的API,因为UI事件和渲染绘制在不同的线程里。更甚者,这种情况下调用glDeleteBuffers这种释放资源的方法,可能引起程序的崩溃,因为UI线程想释放它,渲染线程却要使用它。

1.2.9、public void onPause()设置render模式,使用线程通信控制render线程pause

setRenderMode(RENDERMODE_WHEN_DIRTY):The renderer only renders when the surface is created, or when requestRender() is called.停止持续渲染当调用GLSurfaceView.requestRender()时,程序再渲染屏幕。

1.1.3、private Cocos2dxHandler mHandler;

1.1.4、private static Cocos2dxActivity sContext = null;

1.1.5、private Cocos2dxVideoHelper mVideoHelper = null;

1.1.6、private Cocos2dxWebViewHelper mWebViewHelper = null;

Cocos2dxActivity类主要使用了如下函数:

1.1.7、protected void onCreate(final Bundle savedInstanceState)

作用:

protected void onLoadNativeLibraries():load jni层包进来的一个native lib,叫做libcocos2dcpp.so

getPackageManager()方法获得已安装的应用程序信息

public abstract ApplicationInfo getApplicationInfo(String packageName, int flags);参数:packagename:包名,flags:该ApplicationInfo是此flags标记,通常可以直接赋予常数0即可;功能:返回该ApplicationInfo对象

ApplicationInfo.metaData获取AndroidManifest.xml中的MetaData标签值返回Bundle

实例化Cocos2dxHandler,在Cocos2dxHandler的构造函数中使用弱引用的方式,将该对象的成员变量mActivity定义为一个Cocos2dxActivity的实例

SoftReference:软引用-->当虚拟机内存不足时,将会回收它指向的对象;需要获取对象时,可以调用get方法。WeakReference:弱引用-->随时可能会被垃圾回收器回收,不一定要等到虚拟机内存不足时才强制回收。要获取对象时,同样可以调用get方法。WeakReference一般用来防止内存泄漏,要保证内存被虚拟机回收,SoftReference多用作来实现缓存机制(cache);

调用Cocos2dxHelper的init函数,定义了Cocos2dxHelper的成员变量sCocos2dxHelperListener为sCocos2dxHelperListener的实现类的实例化activity,sPackageName为包名,sFileDirectory为activity的绝对路径,nativeSetApkPath为通过ApplicationInfo的sourceDir来获得目前版本的apk绝对路径。

实例化了一个实现SensorEventListener接口的Cocos2dxAccelerometer,从系统服务中获得传感器管理器,使用SensorMannager调用getDefaultSensor(Sensor.TYPE_ACCELEROMETER)方法拿到加速重力感应的Sensor对象,获取屏幕介质信息,并获取屏幕的方向

SensorEventListener要监视原始的传感器数据,你需要实现两个通过SensorEventListener接口暴露的回调方法:onAccuracyChanged()和onSensorChanged()。Android系统在任何发生下列事情的时候都会调用这两个方法:传感器精度的改变,系统会调用onAccuracyChanged()方法,它提供了你要引用的发生精度变化的Sensor对象。传感器报告新的值,系统会调用onSensorChanged()方法,它提供了一个SensorEvent对象。SensorEvent对象包含了有关新的传感器数据的信息,包括:数据的精度、产生数据的传感器、产生数据时的时间戳、以及传感器记录的新的数据。

实例化了一个Cocos2dxMusic对象,初始化左声道、右声道、背景音乐、播放状态

实例化了一个Cocos2dxSound对象,初始化左声道、右声道、背景音乐、播放状态

调用Cocos2dxHelper的nativeSetContext函数,传入activity和activity的AssetManager,将java层的AssetManager传入native层

getGLContextAttrs()通过jni调用native层的Java_org_cocos2dx_lib_Cocos2dxActivity_getGLContextAttrs,初始化app,使用8888248初始化GLContext,然后将这个attribute get出来传回去

this.init()设置content size,设置visibleSize,设置可见的起点(左下角),创建关闭按钮并设置位置,创建菜单把关闭按钮放入菜单并设置位置,把菜单加入,创建标签设置位置,并把标签加入,创建helloword图片设置位置,并把图片加入

实例化了一个Cocos2dxVideoHelper对象

实例化了一个Cocos2dxWebViewHelper对象

Copyright © 沪ICP备14044869号-1