function class(classname, super)
local superType = type(super)
local cls --如果父类既不是函数也不是table则说明父类为空
if superType ~= "function" and superType ~= "table" then
superType = nil
super = nil
end --如果父类的类型是函数或者是C对象
if superType == "function" or (super and super.__ctype == 1) then
-- inherited from native C++ Object
cls = {} --如果父类是表则复制成员并且设置这个类的继承信息
--如果是函数类型则设置构造方法并且设置ctor函数
if superType == "table" then
-- copy fields from super
for k,v in pairs(super) do cls[k] = v end
cls.__create = super.__create
cls.super = super
else
cls.__create = super
cls.ctor = function() end
end --设置类型的名称
cls.__cname = classname
cls.__ctype = 1 --定义该类型的创建实例的函数为基类的构造函数后复制到子类实例
--并且调用子数的ctor方法
function cls.new(...)
local instance = cls.__create(...)
-- copy fields from class to native object
for k,v in pairs(cls) do instance[k] = v end
instance.class = cls
instance:ctor(...)
return instance
end else
--如果是继承自普通的lua表,则设置一下原型,并且构造实例后也会调用ctor方法
-- inherited from Lua Object
if super then
cls = {}
setmetatable(cls, {__index = super})
cls.super = super
else
cls = {ctor = function() end}
end cls.__cname = classname
cls.__ctype = 2 -- lua
cls.__index = cls function cls.new(...)
local instance = setmetatable({}, cls)
instance.class = cls
instance:ctor(...)
return instance
end
end return cls end

  

class函数有两个参数,一个是className, 一个是super。这里的super可以是一个table,也可以是一个函数,但不能是userdata。而这个table又分为两种,一种是映射c++相应的类的派生类,一种是纯lua object。下面就根据这几种情况进行讨论。
	1、当基类是function时。
	如函数为 function test() return cc.CCScene:create() end。在定义派生类SceneA时,将此函数作为参数传入class(name, super)。那么返回的新类实际上就是一个Table,且此table中有两个属性,super = test, __create = test。当我们用这个新类构造对象时,调用SceneA.new();然后new又调用前面的test函数,而test函数返回的是一个userData。所以自定义的派生类实际上是一个Table,而由此派生类实例化出的对象实际上是一个UserData。(注意,lua中Table与UserData不一样)。到这里为止,我们就可以用SceneA.new()来构造对象了,但遗憾的是,这里构造的对象不具有SceneExtend属性(quick封装的几个常用函数)。那么如何解决这个问题呢?只需要改写test函数如下:function test() local scene = cc.CCScene:create()  return SceneExtend.extend(scene) end。这样无疑增加了代码量,但庆幸的是,quick为我们封装了这两步操作,所以我们可以直接用如下函数 function test() return display.newScene() end.
	总结:当我们要继承CCNode,CCScene这种C++类时,用function作为基类。
	2、当基类是table,且type == 1 (这里的type=1表示该基类是c++类的派生类,如①中定义的SceneA)时。
	__create = super.__create, super 中的其他属性,则用for循环全部拷贝到派生类中。
	总结:当我们继承CCNode这种C++类的派生类时(如SceneA),直接用派生类SceneA来作为基类)
	3、当基类是table,且是普通的lua对象时(type = nil),直接用这个对象做基类。

	从上面的new函数可以看到,在实例化对象时,都调用了instance:ctor(...)。所以我们在定义类时,一般要加上该构造函数,若没有,则实际调用的是基类的构造函数。(注意上面的第③中情况,class函数已经为我们添加了ctor函数。)

cocos2dx-lua class解析的更多相关文章

  1. cocos2d-x lua绑定解析

    花了几天时间看了下cocos2d-x lua绑定那块,总算是基本搞明白了,下面分三部分解析lua绑定: 一.lua绑定主要用到的底层函数 lua绑定其本质就是有一个公用的lua_Stack来进行C和L ...

  2. RichLabel基于Cocos2dx+Lua v3.x

    RichLabel 简介 RichLabel基于Cocos2dx+Lua v3.x解析字符串方面使用了labelparser,它可以将一定格式的字符串,转换为lua中的表结构扩展标签极其简单,只需添加 ...

  3. Cocos2d-x Lua 阅读Csv文件,使用数据更方便

    在我的书或出售之前,我的源代码,有Csvshadow文件. 也许这是偏见.我与工作将是最长的轮廓Csv,所以,我会帮助不大喜欢它的游戏. Csv文件,非常格式easy,也就是说,一个数据线,字段之间用 ...

  4. cocos2dx lua 3.10 使用cjson

    本篇介绍如何在lua中使用cjson对数据进行json的encode与decode,首先简单介绍下cjson: Lua CJSON 是 Lua 语言提供高性能的 JSON 解析器和编码器,其性能比纯 ...

  5. cocos2d-x lua 中使用protobuf并对http进行处理

    cocos2d-x lua 中使用protobuf并对http进行处理 本文介绍 cocos2d-x lua 中使用http 和 基于cocos2d-x 对lua http的封装(部分ok) 本博客链 ...

  6. cocos2d-x + Lua接入iOS原生SDK的实现方案[转]

    相信很多朋友在使用cocos2d-x+lua开发游戏时都遇到过接入iOS原生SDK的问题,比如常见的接应用内支付SDK,广告SDK或是一些社交平台SDK等等,我也没少接过这类SDK.这篇文章主要是对我 ...

  7. Cocos2dx lua 3D实例代码

    用cocoside 创建一个项目 cocos2dx lua 项目即可 ,然后替换掉gamescene 就可以,具体效果还有函数的参数,相信大家一看就明白.简单说下ide 创建的 cocos lua 项 ...

  8. cocos2dx lua 绑定之二:手动绑定自定义类中的函数

    cococs2dx 3.13.1 + vs2013 + win10 1.首先按照<cocos2dx lua 绑定之一:自动绑定自定义类>绑定Student类 2.在Student类中增加一 ...

  9. lua标签解析器

    lua 标签解析器 概述 一个类xml标签解析函数,将标签解析成Lua中的表结构它可以用来解析简单xml结构,可以作为RichLabel控件的字符串解析组件(其实它现在就是这么用的;-)) 原理 使用 ...

  10. cocos2d-x lua table数据存储

    cocos2d-x lua table数据存储 version: cocos2d-x 3.6 1. 将table转为json http://blog.csdn.net/songcf_faith/art ...

随机推荐

  1. ASP.NET 对类进行XML序列化和反序列化

    1 序列化方法 public void SerializeObject<T>(string Xmlname,T t) { XmlSerializer ser = new XmlSerial ...

  2. iOS获取真机沙盒文件、获取真机本地数据

    有时我们需要对真机内的数据进行分析,那么如何获取沙盒所有数据文件呢? 1.设备连接到电脑,打开xcode 2.打开window-devices 3.打开后,选择设备名,选择app,导出数据 4.最后拿 ...

  3. iOS transform解决连续多次旋转缩放,实现图片旋转缩放效果

    一.需求 实现imageView的缩放旋转效果,一般有两种方式: 1.底层加scrollview,利用scrollview的属性实现.(推荐这种,这是我比较后发现的,手势做缩放旋转会有点弊端) 2.利 ...

  4. Swift3 根据秒数获取视频时长(转换成00:00:00时间格式)以及将时长转换成秒

    直接代码了: /// 秒转换成00:00:00格式 /// /// - Parameter secounds: <#secounds description#> /// - Returns ...

  5. 常用Raspberry Pi周边传感器的使用教程(转)

    转:http://bbs.xiaomi.cn/thread-7797152-1-1.html 在Raspberry Pi 的使用和开发过程中,你可能时常需要一些硬件和传感器等来支持你的开发工作,例如, ...

  6. 【备份】使用mysqldump 实现rename database name(mysql数据库改名称)

    需求:将jxl_credit改名为jxl_test;输入:jxl_credit输出: jxl_test; 实现方式:1).新建jxl_test,2).备份jxl_credit到本地,3).然后将备份数 ...

  7. ubuntu 连接windows远程桌面 &&rdesktop 退出全屏模式

    参考:http://www.asgone.net/ubuntu-connect-windows-remote-desktop/ 呵呵,使用上了ubuntu,怎么接连上我的服务器的远程桌面呢,找了找帮助 ...

  8. 树莓派进阶之路 (024) - windows远程桌面连接树莓派通过xrdp服务(转)

    本文转载:http://www.cnblogs.com/edgexie/p/6527992.html 在网上看到很多关于windows远程桌面连接树莓派的教程.我也按照教程试过了,遇到了几个坑.特意记 ...

  9. 进阶之路(中级篇) - 017 有关于Arduino 驱动舵机及相关问题

    /********************************* 代码功能:通过串口控制电机 使用函数: Serial.available(); //判断串口是否接收到数据 Serial.prin ...

  10. ROS学习(四)—— 创建ROS Package

    一.caktin Package的组成 1.必须含有 package.xml文件,提供有关程序包的元信息 2.必须含有一个catkin版本的 CmakeLists.txt文件,如果是一个catkin元 ...