日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程语言 > c/c++ >内容正文

c/c++

cocos2dx之lua项目开发中MVC框架的简单应用

發(fā)布時(shí)間:2023/12/31 c/c++ 20 豆豆
生活随笔 收集整理的這篇文章主要介紹了 cocos2dx之lua项目开发中MVC框架的简单应用 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
****************************************************************************

時(shí)間:2015-03-31

作者:Sharing_Li

轉(zhuǎn)載注明出處:http://blog.csdn.net/sharing_li/article/details/44658317

****************************************************************************

?

???????近期的游戲項(xiàng)目中使用了lua腳本來開發(fā),項(xiàng)目中用到了MVC框架,近期有朋友問我怎么弄。在這里簡單分享一下思路和一些開發(fā)中的技巧。?

?????? 先簡單說說MVC,即Model View Controller。Model(模型),一般負(fù)責(zé)數(shù)據(jù)的處理。View(視圖)。一般負(fù)責(zé)界面的顯示。Controller(控制器),一般負(fù)責(zé)前端的邏輯處理。拿一款手機(jī)游戲來說,界面UI的顯示、布局等就是View負(fù)責(zé);點(diǎn)擊了button,手勢的滑動(dòng)等操作由Controller來處理;游戲中須要的數(shù)據(jù)資源就交給Model。?

????? ?接下來,看看在游戲開發(fā)中怎么用,這里用Lua(環(huán)境使用cocos code ide)給大家說說。

?????? 先來看看項(xiàng)目的文件夾結(jié)構(gòu):

??????? 當(dāng)中cocos、Controller、Model、View這個(gè)不用多說,Event里面保存的全局消息類型,Managers是用于管理游戲中的東東的。比方管理資源,管理各種場景切換。層的切換等等。Utilities提供一些工具類,比方字符串的處理等。大家也能夠依據(jù)自己的需求來定制目錄,比方定義一個(gè)NetCenter目錄,專門用于處理網(wǎng)絡(luò)的。

本樣例中沒實(shí)用到數(shù)據(jù)操作和工具類。所以這兩個(gè)目錄為空。

??????? 我們以游戲的執(zhí)行流程為線索來展開說明。

??????? 執(zhí)行項(xiàng)目。進(jìn)入到main.lua文件,來看看main函數(shù):

?

local function main()collectgarbage("collect")-- avoid memory leakcollectgarbage("setpause", 100)collectgarbage("setstepmul", 5000)-- initialize directorlocal director = cc.Director:getInstance()--turn on display FPSdirector:setDisplayStats(true)--set FPS. the default value is 1.0/60 if you don't call thisdirector:setAnimationInterval(1.0 / 60)cc.Director:getInstance():getOpenGLView():setDesignResolutionSize(320, 480, 1)--create scene local scene = require("GameScene")local gameScene = scene:startGame()end

?

??????? 我們最后調(diào)用了GameScene類中的startGame函數(shù),來看看GameScene這個(gè)類:

require("Managers.SceneManager") require("Managers.LayerManager")local GameScene = class("GameScene") local scene = nilfunction GameScene:startGame()--初始化scene = cc.Scene:create()if cc.Director:getInstance():getRunningScene() thencc.Director:getInstance():replaceScene(scene)elsecc.Director:getInstance():runWithScene(scene)endSceneManager:initLayer(scene)self:enterGame() endfunction GameScene:enterGame()LayerManager:getInstance():gotoLayerByType(LAYER_TYPE_MAIN) endreturn GameScene

?????? 在startGame函數(shù)中,我們創(chuàng)建了一個(gè)空?qǐng)鼍啊H缓笳{(diào)用SceneManager場景管理器來初始化場景。最后調(diào)用enterGame函數(shù)正式進(jìn)入游戲主界面,當(dāng)中enterGame函數(shù)中又有一個(gè)LayerManager層管理器。

我們來看看這兩個(gè)管理器是怎樣工作的。先看看SceneManager:

--場景管理器 SceneManager = {}--背景層 bgLayer = nil --游戲?qū)?gameLayer = nil --彈窗層 panelLayer = nilfunction SceneManager:initLayer(scene)bgLayer = cc.Layer:create()scene:addChild(bgLayer)gameLayer = cc.Layer:create()scene:addChild(gameLayer)panelLayer = cc.Layer:create()scene:addChild(panelLayer) end

?????? 非常easy,按順序初始化了三個(gè)空Layer。再來看看LayerManager管理器:

--Layer管理器 LayerManager = {}LAYER_TYPE_MAIN = "LAYER_TYPE_MAIN"local curLayer = nilfunction LayerManager:new(o)o = o or {}setmetatable(o,self)self.__index = selfreturn o endfunction LayerManager:getInstance()if self.instance == nil thenself.instance = self:new()endreturn self.instance endfunction LayerManager:gotoLayerByType(type)if curLayer ~= nil thencurLayer:destroy()endif type == "LAYER_TYPE_MAIN" thenlocal layer = require("Controller.MainLayerController"):create()curLayer = layerend end

??????? 看看gotoLayerByType這個(gè)函數(shù),首先切換層的時(shí)候。看看當(dāng)前層是否為空。不為空就刪掉。然后依據(jù)傳遞過來的參數(shù)來推斷要切換到哪個(gè)層。這里出現(xiàn)MVC中的Controller部分,看看是什么情況。這里調(diào)用了類MainLayerController中的create函數(shù):

function MainLayerC:create()local layer = MainLayerC:new()return layer endfunction MainLayerC:ctor()self:createUI()--創(chuàng)建界面self:addBtnEventListener()--加入button監(jiān)聽 endfunction MainLayerC:createUI()local layer = require("View.MainLayerView")self.mainLayer = layer:createUI()gameLayer:addChild(self.mainLayer) end

?????? 這里我們又發(fā)現(xiàn)了MVC中的View,在createUI函數(shù)中,我們調(diào)用了類MainLayerView的createUI函數(shù),并將其加入到場景的游戲?qū)又小N覀儊砜纯碝ainLayerView這個(gè)類。

local eventDispatcher = cc.Director:getInstance():getEventDispatcher()local MainLayerV = class("MainLayerView",function()return cc.Layer:create() end)function MainLayerV:createUI()local mainLayer = MainLayerV:new()return mainLayer endfunction MainLayerV:ctor()self:initUI() endfunction MainLayerV:initUI()local winSize = cc.Director:getInstance():getWinSize()self.bg = cc.Sprite:create(ResManager.main_bg)self.bg:setPosition(winSize.width / 2,winSize.height / 2)self:addChild(self.bg)local function menuCallback(tag,menuItem)local event = cc.EventCustom:new(EVENT_CLICK_MENU_MAIN)event._usedata = tageventDispatcher:dispatchEvent(event)endself.btnItem1 = cc.MenuItemImage:create(ResManager.main_btn1,ResManager.main_btn1,ResManager.main_btn1)self.btnItem1:setPosition(winSize.width / 2,winSize.height / 3)self.btnItem1:setTag(1)self.btnItem1:registerScriptTapHandler(menuCallback)self.btnItem2 = cc.MenuItemImage:create(ResManager.main_btn2,ResManager.main_btn2)self.btnItem2:setPosition(winSize.width / 2,winSize.height / 2)self.btnItem2:setTag(2)self.btnItem2:registerScriptTapHandler(menuCallback)self.btnItem3 = cc.MenuItemImage:create(ResManager.main_btn3,ResManager.main_btn3)self.btnItem3:setPosition(winSize.width / 2,winSize.height / 3 * 2)self.btnItem3:setTag(3)self.btnItem3:registerScriptTapHandler(menuCallback)--創(chuàng)建菜單self.menu = cc.Menu:create(self.btnItem1,self.btnItem2,self.btnItem3)self.menu:setPosition(0,0)self:addChild(self.menu) endreturn MainLayerV


??????? 能夠看到,我們在主界面中加入了一張背景圖和三個(gè)button。我們是通過資源管理器ResManager來管理游戲中的素材的。ResManager文件非常easy:

--資源管理器 ResManager = {}--主界面 ResManager.main_bg = "bg_big.png" ResManager.main_btn1 = "cell.png" ResManager.main_btn2 = "cell2.png" ResManager.main_btn3 = "cell3.png"

?????? 這樣做的優(yōu)點(diǎn)是,假設(shè)圖片改了名字或者換了路徑等。僅僅須要在這里改一次就能夠了。

?????? 能夠看到我們給三個(gè)button注冊了響應(yīng)函數(shù)menuCallback,在這個(gè)函數(shù)中。就是MVC中的V和C之間的“溝通”了。

我們定義了一個(gè)自己定義事件EVENT_CLICK_MENU_MAIN,并給這個(gè)事件加入了一個(gè)附帶參數(shù)_usedata,這個(gè)參數(shù)保存的是三個(gè)button的tag。然后將這個(gè)事件發(fā)送給他的監(jiān)聽者。這里大家應(yīng)該明確了,我們在相應(yīng)的Controller中注冊了EVENT_CLICK_MENU_MAIN的監(jiān)聽,但有這個(gè)事件發(fā)過來時(shí)。我們就響應(yīng)。依據(jù)事件攜帶的參數(shù)_usedata,我們就知道了在View中。玩家點(diǎn)擊了哪個(gè)button。這樣做的優(yōu)點(diǎn)是,保證了每一個(gè)界面僅僅有一個(gè)消息。我們僅僅須要依據(jù)這個(gè)消息攜帶的附加參數(shù)來推斷詳細(xì)的事件,從而降低了消息個(gè)數(shù),這樣有助于游戲的效率。另外,我們在響應(yīng)這個(gè)消息的時(shí)候,也會(huì)做一定的優(yōu)化,來看看類MainLayerController的響應(yīng)函數(shù):

function MainLayerC:addBtnEventListener()--button事件處理local function eventBtnListener(event)local eventNum = event._usedatalocal switch = {[1] = function()print("Btn one")end,[2] = function()print("Btn two")end,[3] = function()print("Btn three")end}switch[eventNum]()end--注冊事件處理self._eventBtnListener = cc.EventListenerCustom:create(EVENT_CLICK_MENU_MAIN,eventBtnListener)eventDispatcher:addEventListenerWithSceneGraphPriority(self._eventBtnListener,self.mainLayer) end

??????? 能夠看到實(shí)際情況,我們并不須要對(duì)傳遞過來的參數(shù)進(jìn)行推斷,而是定義了一個(gè)函數(shù)數(shù)組。直接依據(jù)下標(biāo)來調(diào)用相應(yīng)的消息響應(yīng)。之后繼續(xù)通過各種管理器來對(duì)游戲內(nèi)容進(jìn)行變化,方式和MainLayerController和MainLayerView差點(diǎn)兒相同。

??????? 到這里,MVC應(yīng)用的簡介就結(jié)束啦。免費(fèi)下載代碼












本文轉(zhuǎn)自mfrbuaa博客園博客,原文鏈接:http://www.cnblogs.com/mfrbuaa/p/5125274.html,如需轉(zhuǎn)載請(qǐng)自行聯(lián)系原作者


總結(jié)

以上是生活随笔為你收集整理的cocos2dx之lua项目开发中MVC框架的简单应用的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。