--[[ btn 控件本身对象 ended 事件类型(放开)对应的回调函数 began 事件类型(按下)对应的回调函数 moved 事件类型(移动)对应的回调函数 canceled 事件类型(取消)对应的回调函数 ]] functioncc.exports.setButtonFunction(btn, ended, began, moved, canceled) btn:addTouchEventListener(function(sender, eventType) if eventType == ccui.TouchEventType.began then if began then began(sender) end elseif eventType == ccui.TouchEventType.ended then if ended then ended(sender) end elseif eventType == ccui.TouchEventType.moved then if moved then moved(sender) end elseif eventType == ccui.TouchEventType.canceled then if canceled then canceled(sender) end end end) end
functionViewBase:ctor(app, name) self:enableNodeEvents() self.app_ = app self.name_ = name
-- 检查子类中是否设置RESOURCE_FILENAME属性,并得到他的value值 local res = rawget(self.class, "RESOURCE_FILENAME") if res then --加载csb文件 self:createResourceNode(res) end --检查子类中是否设置RESOURCE_BINDING属性,并得到他的value值 local binding = rawget(self.class, "RESOURCE_BINDING") if res and binding then --获取控件的实例 self:createResourceBinding(binding) end --判断子类有没有重写onCreate方法,有,调用子类的onCreate方法 ifself.onCreate thenself:onCreate() end end
functionViewBase:getApp() returnself.app_ end
functionViewBase:getName() returnself.name_ end
functionViewBase:getResourceNode() returnself.resourceNode_ end --[[ *加载csb文件的方法 *resourceFilename 文件名称(带后缀名) ]] functionViewBase:createResourceNode(resourceFilename) --判断是否已经加载过csb文件 ifself.resourceNode_ then --移除自己 self.resourceNode_:removeSelf() --设置为nil self.resourceNode_ = nil end --通过CSLoader加载csb文件,得到一个节点 self.resourceNode_ = cc.CSLoader:createNode(resourceFilename) assert(self.resourceNode_, string.format("ViewBase:createResourceNode() - load resouce node from file \"%s\" failed", resourceFilename)) --将节点添加到该父节点(场景,层)中 self:addChild(self.resourceNode_) end --[[ *绑定控件 *binding 在ViewBase子类中设置的RESOURCE_BINDING(规则模板(表)) ]] functionViewBase:createResourceBinding(binding) assert(self.resourceNode_, "ViewBase:createResourceBinding() - not load resource node") --遍历规则表 for nodeName, nodeBinding inpairs(binding) do --节点通过名称直接获取子控件实例 --这里就是我上面说的问题所在了,这里是直接通过根节点获取控件,往往,根节点的子节点是容器,而不是控件,所以这里会得不到控件 local node = self.resourceNode_:getChildByName(nodeName) --如果设置变量名不为nil if nodeBinding.varname then --则将node赋值类nodeBinding.varname变量 self[nodeBinding.varname] = node end --遍历规则表中的事件 --nodeBinding.events or {}这个表达式相当于三目运算 nodeBinding.events~=nil?nodeBinding.events:{} for _, event inipairs(nodeBinding.events or {}) do --原生这里只支持touch事件,如果有别的需求可自行添加 if event.event == "touch"then --给控件设置onTouch事件并设置回调函数。 node:onTouch(handler(self, self[event.method])) end end end end --[[ *跳转场景(翻译:展示场景) *transition 衔接动画 *time 衔接动画播放时间 *more 动画类型 ]] functionViewBase:showWithScene(transition, time, more) self:setVisible(true) local scene = display.newScene(self.name_) scene:addChild(self) display.runScene(scene, transition, time, more) returnself end
--新增一个dom树表,用于存储dom树各个节点 ViewBase.dom = {} --[[ *递归遍历整个场景树中的容器和控件,将容器和控件存入dom表中 *rootNode 节点类型 ]] localfunctionrecursionChlidNOde(rootNode) local children = rootNode:getChildren() for _,childNOde inipairs(children or {}) do local name =childNOde:getName() print("name ",name) ViewBase.dom[name]=childNOde recursionChlidNOde(childNOde) end
end functionViewBase:createResourceBinding(binding) assert(self.resourceNode_, "ViewBase:createResourceBinding() - not load resource node") recursionChlidNOde(self.resourceNode_) for bindWidgetName, ruleTable inpairs(binding) do for widgetName,node inpairs(ViewBase.dom) do print(widgetName,tolua.type(node)) if ruleTable.varname and widgetName==bindWidgetName then self[ruleTable.varname] = node for _, event inipairs(ruleTable.events or {}) do if event.event == "touch"then node:onTouch(handler(self, self[event.method])) end end end end