zoukankan      html  css  js  c++  java
  • 解析cocos2d-lua项目中的Hello World

    创建完cocos2d-x的lua项目后。打开项目的Resources目录,找到hello.lua。cocos2d-x的lua项目的測试样例主要就是由这个脚本文件运行的。

    require "AudioEngine" --引入声音引擎文件
    
    -- for CCLuaEngine traceback
    function __G__TRACKBACK__(msg)
        print("----------------------------------------")
        print("LUA ERROR: " .. tostring(msg) .. "
    ")--打印错误信息
        print(debug.traceback())--输出当前运行的traceback信息
        print("----------------------------------------")
    end
    --主函数
    local function main()
        -- avoid memory leak
        -- 避免内存泄露
        --操作垃圾收集器
        collectgarbage("setpause", 100)
        collectgarbage("setstepmul", 5000)
        --定义日志输出函数
        local cclog = function(...)
            print(string.format(...))
        end
        --引入hello2脚本
        require "hello2"
        --调用hello2脚本中的myadd函数
        cclog("result is " .. myadd(3, 5))
    
        ---------------
        --获取屏幕的可视化大小
        local visibleSize = CCDirector:sharedDirector():getVisibleSize()
        --获取可视区域的起点坐标
        local origin = CCDirector:sharedDirector():getVisibleOrigin()
    
        -- add the moving dog
        --创建一个可移动的小狗
        local function creatDog()
            local frameWidth = 105
            local frameHeight = 95
    
            -- create dog animate
            --加入小狗的贴图到内存中
            local textureDog = CCTextureCache:sharedTextureCache():addImage("dog.png")
            --创建截取第一个小狗的精灵帧的矩形
            local rect = CCRectMake(0, 0, frameWidth, frameHeight)
            --创建一个小狗的精灵帧
            local frame0 = CCSpriteFrame:createWithTexture(textureDog, rect)
            --创建截取第二个小狗的精灵帧的矩形
            rect = CCRectMake(frameWidth, 0, frameWidth, frameHeight)
            --创建一个第二个小狗的精灵帧
            local frame1 = CCSpriteFrame:createWithTexture(textureDog, rect)
    
            --以小狗的第一个精灵帧创建一个小狗精灵
            local spriteDog = CCSprite:createWithSpriteFrame(frame0)
            --自己定义一个bool值的属性,标记为false
            spriteDog.isPaused = false
            --设置小狗的位置在 x:0, y:屏幕高度*0.75 处
            spriteDog:setPosition(origin.x, origin.y + visibleSize.height / 4 * 3)
            --创建一个用于存储精灵帧的数组
            local animFrames = CCArray:create()
            --把上面的两个精灵帧加入到数组中
            animFrames:addObject(frame0)
            animFrames:addObject(frame1)
            --以0.5秒的切换速度方式创建一个动画描写叙述
            local animation = CCAnimation:createWithSpriteFrames(animFrames, 0.5)
            --依据上面的动画描写叙述创建一个动画
            local animate = CCAnimate:create(animation);
            --运行该动画
            spriteDog:runAction(CCRepeatForever:create(animate))
    
            -- moving dog at every frame
            --小狗每帧都在移动
            local function tick()
                if spriteDog.isPaused then return end--假设暂停,则返回,不移动
                local x, y = spriteDog:getPosition()--获取小狗的当前位置
                if x > origin.x + visibleSize.width then--假设小狗的移到屏幕外面
                    x = origin.x--重置小狗的位置
                else
                    x = x + 1--每帧往右移动一个像素
                end
                --刷新小狗的最新位置
                spriteDog:setPositionX(x)
            end
            --运行定时器
            CCDirector:sharedDirector():getScheduler():scheduleScriptFunc(tick, 0, false)
            --返回创建的小狗
            return spriteDog
        end
    
        -- create farm
        --创建农田
        local function createLayerFarm()
            --创建一个农场层
            local layerFarm = CCLayer:create()
    
            -- add in farm background
            --创建一个背景精灵
            local bg = CCSprite:create("farm.jpg")
            --设置背景精灵的位置
            bg:setPosition(origin.x + visibleSize.width / 2 + 80, origin.y + visibleSize.height / 2)
            --把背景精灵加入到农场层中
            layerFarm:addChild(bg)
    
            -- add land sprite
            --创建农场精灵
            for i = 0, 3 do
                for j = 0, 1 do
                    local spriteLand = CCSprite:create("land.png")
                    spriteLand:setPosition(200 + j * 180 - i % 2 * 90, 10 + i * 95 / 2)
                    layerFarm:addChild(spriteLand)
                end
            end
    
            -- add crop
            --创建农作物
            local frameCrop = CCSpriteFrame:create("crop.png", CCRectMake(0, 0, 105, 95))
            for i = 0, 3 do
                for j = 0, 1 do
                    local spriteCrop = CCSprite:createWithSpriteFrame(frameCrop);
                    spriteCrop:setPosition(10 + 200 + j * 180 - i % 2 * 90, 30 + 10 + i * 95 / 2)
                    layerFarm:addChild(spriteCrop)
                end
            end
    
            -- add moving dog
            --创建一个会移动的小狗
            local spriteDog = creatDog()
            --将小狗加入到农场层中
            layerFarm:addChild(spriteDog)
    
            -- handing touch events
            --初始化触摸点
            local touchBeginPoint = nil
            --開始点击触摸屏
            local function onTouchBegan(x, y)
                --输出点击位置
                cclog("onTouchBegan: %0.2f, %0.2f", x, y)
                --将点击位置赋给触摸点
                touchBeginPoint = {x = x, y = y}
                --点击时小狗暂停移动
                spriteDog.isPaused = true
                -- CCTOUCHBEGAN event must return true
                return true
            end
            --滑动触摸屏
            local function onTouchMoved(x, y)
                --输出滑动位置
                cclog("onTouchMoved: %0.2f, %0.2f", x, y)
                --假设触摸点不为空
                if touchBeginPoint then
                    --获取农场层的当前位置
                    local cx, cy = layerFarm:getPosition()
                    --移动农场层
                    layerFarm:setPosition(cx + x - touchBeginPoint.x,
                                          cy + y - touchBeginPoint.y)
                    --将滑动的位置赋给触摸点
                    touchBeginPoint = {x = x, y = y}
                end
            end
            --离开触摸屏
            local function onTouchEnded(x, y)
                --输出离开屏幕时的位置
                cclog("onTouchEnded: %0.2f, %0.2f", x, y)
                --删除触摸点
                touchBeginPoint = nil
                --小狗又一次移动
                spriteDog.isPaused = false
            end
            --处理触摸状态
            local function onTouch(eventType, x, y)
                if eventType == "began" then   --点击屏幕状态
                    return onTouchBegan(x, y)
                elseif eventType == "moved" then --滑动屏幕状态
                    return onTouchMoved(x, y)
                else  --离开屏幕状态
                    return onTouchEnded(x, y) 
                end
            end
            --注冊触摸事件
            layerFarm:registerScriptTouchHandler(onTouch)
            --开启触摸
            layerFarm:setTouchEnabled(true)
            --返回农场层
            return layerFarm
        end
    
    
        -- create menu
        --创建菜单
        local function createLayerMenu()
            --创建一个菜单层
            local layerMenu = CCLayer:create()
            --定义三个变量
            local menuPopup, menuTools, effectID
            --运行菜单项的回调函数
            local function menuCallbackClosePopup()
                -- stop test sound effect
                --停止音效的播放
                AudioEngine.stopEffect(effectID)
                --隐藏菜单
                menuPopup:setVisible(false)
            end
            --运行菜单项的回调函数
            local function menuCallbackOpenPopup()
                -- loop test sound effect
                --获取播放音效的路径
                local effectPath = CCFileUtils:sharedFileUtils():fullPathForFilename("effect1.wav")
                --播放音效
                effectID = AudioEngine.playEffect(effectPath)
                --显示菜单
                menuPopup:setVisible(true)
            end
    
            -- add a popup menu
            --创建一个菜单项
            local menuPopupItem = CCMenuItemImage:create("menu2.png", "menu2.png")
            --设置菜单项位置
            menuPopupItem:setPosition(0, 0)
            --设置运行该菜单项所相应的回调函数
            menuPopupItem:registerScriptTapHandler(menuCallbackClosePopup)
            --创建一个菜单
            menuPopup = CCMenu:createWithItem(menuPopupItem)
            --设置菜单位置
            menuPopup:setPosition(origin.x + visibleSize.width / 2, origin.y + visibleSize.height / 2)
            --隐藏菜单
            menuPopup:setVisible(false)
            --将该菜单加入到菜单层
            layerMenu:addChild(menuPopup)
    
            -- add the left-bottom "tools" menu to invoke menuPopup
            --创建一个菜单项
            local menuToolsItem = CCMenuItemImage:create("menu1.png", "menu1.png")
            --设置菜单项位置
            menuToolsItem:setPosition(0, 0)
            --设置运行该菜单项所相应的回调函数
            menuToolsItem:registerScriptTapHandler(menuCallbackOpenPopup)
            --创建一个菜单
            menuTools = CCMenu:createWithItem(menuToolsItem)
            --设置菜单位置
            local itemWidth = menuToolsItem:getContentSize().width
            local itemHeight = menuToolsItem:getContentSize().height
            menuTools:setPosition(origin.x + itemWidth/2, origin.y + itemHeight/2)
            --将该菜单加入到菜单层
            layerMenu:addChild(menuTools)
            --返回菜单层
            return layerMenu
        end
    
        -- play background music, preload effect
    
        -- uncomment below for the BlackBerry version
        -- local bgMusicPath = CCFileUtils:sharedFileUtils():fullPathForFilename("background.ogg")
        --获取背景音乐的文件路径
        local bgMusicPath = CCFileUtils:sharedFileUtils():fullPathForFilename("background.mp3")
        --播放背景音乐
        AudioEngine.playMusic(bgMusicPath, true)
        --获取音效的文件路径
        local effectPath = CCFileUtils:sharedFileUtils():fullPathForFilename("effect1.wav")
        --将音效缓存到内存中
        AudioEngine.preloadEffect(effectPath)
    
        -- run
        --创建一个场景
        local sceneGame = CCScene:create()
        --将农村层加入到该场景中
        sceneGame:addChild(createLayerFarm())
        --将菜单层加入到该场景中
        sceneGame:addChild(createLayerMenu())
        --运行该场景
        CCDirector:sharedDirector():runWithScene(sceneGame)
    end
    --保护模式下调用主函数,并制定错误处理函数句柄__G__TRACKBACK__
    xpcall(main, __G__TRACKBACK__)
    

    而这个脚本是在AppDelegate.cpp中被运行的。里面初始化了cocos2d-x解析lua的引擎。

    bool AppDelegate::applicationDidFinishLaunching()
    {
        // initialize director
        CCDirector *pDirector = CCDirector::sharedDirector();
        pDirector->setOpenGLView(CCEGLView::sharedOpenGLView());
    
        // turn on display FPS
        pDirector->setDisplayStats(true);
    
        // set FPS. the default value is 1.0/60 if you don't call this
        pDirector->setAnimationInterval(1.0 / 60);
    
        // register lua engine
    	//初始化lua脚本引擎
        CCLuaEngine* pEngine = CCLuaEngine::defaultEngine();
    	//将lua脚本引擎加入到脚本引擎管理器中
        CCScriptEngineManager::sharedManager()->setScriptEngine(pEngine);
    	//取得lua的全局指针,全部的lua函数都须要使用这个指针来做为參数进行调用。  
        CCLuaStack *pStack = pEngine->getLuaStack();
    	//获取lua_State
        lua_State *tolua_s = pStack->getLuaState();
    	//开放扩展函数给lua调用
        tolua_extensions_ccb_open(tolua_s);
    	//假设是ios、android、win32平台则开放WebSocket类给lua调用
    #if (CC_TARGET_PLATFORM == CC_PLATFORM_IOS || CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID || CC_TARGET_PLATFORM == CC_PLATFORM_WIN32)
        pStack = pEngine->getLuaStack();
        tolua_s = pStack->getLuaState();
        tolua_web_socket_open(tolua_s);
    #endif
        
    #if (CC_TARGET_PLATFORM == CC_PLATFORM_BLACKBERRY)//黑莓平台,不清楚
        CCFileUtils::sharedFileUtils()->addSearchPath("script");
    #endif
    	//获取待运行的脚本路径
        std::string path = CCFileUtils::sharedFileUtils()->fullPathForFilename("hello.lua");
    	//运行脚本
        pEngine->executeScriptFile(path.c_str());
    
        return true;
    }

    当中CCLuaEngine是继承自CCScriptEngineProtocl,这个协议定义了lua引擎的功能,当中CCScriptEngineManager用来管理当期的脚本文件(眼下没发现这个管理类有什么用)。

    void CCScriptEngineManager::setScriptEngine(CCScriptEngineProtocol *pScriptEngine)
    {
        removeScriptEngine();//移除上一个的脚本引擎
        m_pScriptEngine = pScriptEngine;//将当前的脚本引擎赋给m_pScriptEngine
    }
    
    void CCScriptEngineManager::removeScriptEngine(void)
    {
        if (m_pScriptEngine)//假设脚本引擎的实例存在,则delete掉
        {
            delete m_pScriptEngine;
            m_pScriptEngine = NULL;
        }
    }


  • 相关阅读:
    Java 第十一届 蓝桥杯 省模拟赛 梅花桩
    Java 第十一届 蓝桥杯 省模拟赛 梅花桩
    Java 第十一届 蓝桥杯 省模拟赛 梅花桩
    Java 第十一届 蓝桥杯 省模拟赛 元音字母辅音字母的数量
    Java 第十一届 蓝桥杯 省模拟赛 元音字母辅音字母的数量
    Java 第十一届 蓝桥杯 省模拟赛 元音字母辅音字母的数量
    Java 第十一届 蓝桥杯 省模拟赛 最大的元素距离
    Java 第十一届 蓝桥杯 省模拟赛 递增序列
    Java 第十一届 蓝桥杯 省模拟赛 递增序列
    Java 第十一届 蓝桥杯 省模拟赛 最大的元素距离
  • 原文地址:https://www.cnblogs.com/gavanwanggw/p/6859969.html
Copyright © 2011-2022 走看看