LUA --熱更新

--什麼是熱更新? git

遊戲客戶端啓動時,主動請求服務端檢查版本號,並更新資源到本地. 服務器

應用場景: 函數

狀況一:遊戲客戶端已經發布了,但忽然發現有個比較嚴重的bug須要修復。這時須要更新遊戲的代碼(Lua代碼)。 this

狀況二:情人節到了,須要搞個活動,在遊戲中營造一個節日氛圍。這時,須要更新遊戲資源或增長一些功能。 url


好處:不須要從新打包和提交應用到市場等待審覈. spa

-- 熱更新流程-->遊戲啓動-->檢查版本 .net

    -->有版本更新-->初始化下載路徑 代理

                        -->設置搜索目錄路徑(優先搜索下載目錄資源code

                        -->下載更新zip包-->解壓zip包-->進入遊戲 orm

    -->沒有版本更新-->進入遊戲

--cocos2dx 已經封裝好了AssetsManager,主要用於熱更新。

-----------------------------------------------------------------------------------------------  昨天沒完成的東西,今天 繼續補。唉,東西貴在堅持,本人是也是剛學cocos2dx,對於一個實習來講,有點時間寫東西,我以爲是件很祝福的東西,也但願能經過文章來交更多的朋友,無論你來至哪一個地球。(友人A:有完沒完,說好的熱更新呢。)好吧,廢話很少說,友人A 是我心裏的一個角色,你們請無視。(友人A: .......)

-- 關於AssetsManager資產管理類,主要是用來更新資源的,(友人A:..老兄說一下這個AssetsManager..都有些什麼方法..),那接下來的說一下API。


virtual bool checkUpdate()
檢測是否有版本更新
virtual void update();
下載更新的資源包並解壓到下載路徑
void setDelegate();
設置下載回調
void setConnectionTimeout(unsigned int timeout);
鏈接超時

(友人A:...喂喂,只給這些有個球用啊..)

好吧,咱們來看一下實戰吧。

這個例程是用的是Cocos2dx 上的helloworld修改的,定義一個updateLayer類,如下是頭文件。

#include "cocos2d.h"
USING_NS_CC;
#include "cocos-ext.h"
USING_NS_CC_EXT;
#include "AssetsManager/AssetsManager.h"

// 熱更新實現示例
class UpdateLayer:public CCLayer, public AssetsManagerDelegateProtocol
{
public:
	static CCScene* scene(){
		CCScene* scene = CCScene::create();
		scene->addChild(UpdateLayer::create());
		return scene;
	};
	static UpdateLayer* create(){
		UpdateLayer* pLayer = new UpdateLayer;
		if (pLayer && pLayer->init())
		{
			pLayer->autorelease();
			return pLayer;
		}
		delete pLayer;
		return NULL;
	};
	// 初始化
	bool init();
    
	// 下載回調函數
	virtual void onError(cocos2d::extension::AssetsManager::ErrorCode errorCode);
	virtual void onProgress(int percent);
	virtual void onSuccess();
    
	// 菜單回調函數
	void reset(CCObject* pSender);		// 重置版本
	void getClientVersion(CCObject* pSender);	// 獲取當前客戶端版本號
	void checkUpdate(CCObject* pSender);      // 檢查是否有版本更新
	void update(CCObject* pSender);		// 更新版本
	void enterScene(CCObject* pSender);	// 進入場景,若是未更新屏幕中間會顯示歎號的圖片,更新後會顯示另外一張圖片
protected:
	// 初始化下載目錄
	void initDownloadDir();
	// 刪除目錄
	void deleteDir(std::string dir);
private:
	CCLabelTTF* m_label;
	std::string m_downloadDir;
	AssetsManager* getAssetsManager();
};



如下是C++文件 :
#include "UpdateLayer.h"
#include "HelloWorldScene.h"

#if (CC_TARGET_PLATFORM != CC_PLATFORM_WIN32)
#include <dirent.h>
#include <sys/stat.h>
#endif

bool UpdateLayer::init(){
	if (CCLayer::init())
	{
		
		// 設置資源包下載目錄
		m_downloadDir = CCFileUtils::sharedFileUtils()->getWritablePath();
		m_downloadDir += "download";
        
		// 設置代理
		getAssetsManager()->setDelegate(this);
        
		// 添加資源包下載路徑到搜索路徑,優先搜索更新的資源
		std::vector<std::string> searchPaths = CCFileUtils::sharedFileUtils()->getSearchPaths();
		searchPaths.insert(searchPaths.begin(), m_downloadDir);
		CCFileUtils::sharedFileUtils()->setSearchPaths(searchPaths);
		
		// 提示
		m_label = CCLabelTTF::create("", "Arial", 18);
		m_label->setAnchorPoint(ccp(1,0.5));
		m_label->setPosition(ccp(465,20));
		addChild(m_label);
        
		// 菜單
		CCMenu* menu = CCMenu::create();
		menu->setPosition(CCPointZero);
		addChild(menu);
        
		CCSize visibleSize = CCDirector::sharedDirector()->getVisibleSize();
        
		// 重置
		CCMenuItemFont* itemReset = CCMenuItemFont::create("reset",this,menu_selector(UpdateLayer::reset));
		itemReset->setPosition(ccp(visibleSize.width/2, 50));
		menu->addChild(itemReset);
		// 獲取當前版本號
		CCMenuItemFont* itemGetClientVersion = CCMenuItemFont::create("getClientVersion",this,menu_selector(UpdateLayer::getClientVersion));
		itemGetClientVersion->setPosition(ccp(visibleSize.width/2, 100));
		menu->addChild(itemGetClientVersion);
		// 獲取服務器最新版本
		CCMenuItemFont* itemGetServerVersion = CCMenuItemFont::create("checkUpdate",this,menu_selector(UpdateLayer::checkUpdate));
		itemGetServerVersion->setPosition(ccp(visibleSize.width/2, 150));
		menu->addChild(itemGetServerVersion);
		// 更新版本
		CCMenuItemFont* itemUpdateVersion = CCMenuItemFont::create("updateVersion",this,menu_selector(UpdateLayer::update));
		itemUpdateVersion->setPosition(ccp(visibleSize.width/2, 200));
		menu->addChild(itemUpdateVersion);
		// 進入場景
		CCMenuItemFont* itemEnterScene = CCMenuItemFont::create("enterScene",this,menu_selector(UpdateLayer::enterScene));
		itemEnterScene->setPosition(ccp(visibleSize.width/2, 250));
		menu->addChild(itemEnterScene);
		return true;
	}
	return false;
}


AssetsManager* UpdateLayer::getAssetsManager(){
	static AssetsManager* s_assetsManager = NULL;
    
	if (s_assetsManager ==NULL)
	{
		s_assetsManager = new AssetsManager("https://coding.net/u/linchaolong/p/Cocos2d-x_HotUpdate/git/raw/master/test.zip",  //下載資源包的url
                                            "https://coding.net/u/linchaolong/p/Cocos2d-x_HotUpdate/git/raw/master/version", // 獲取服務端版本號的url
                                            m_downloadDir.c_str()); // 資源保存路徑
		s_assetsManager->setDelegate(this);//callBack
		s_assetsManager->setConnectionTimeout(3);
	}
	CCLOG("save path : %s",s_assetsManager->getStoragePath());
	return s_assetsManager;
}

void UpdateLayer::initDownloadDir(){
    
	// 若是下載目錄不存在,則建立下載目錄
#if (CC_TARGET_PLATFORM != CC_PLATFORM_WIN32)
	DIR *pDir = NULL;
    
	pDir = opendir (m_downloadDir.c_str());
	if (! pDir)
	{
		mkdir(m_downloadDir.c_str(), S_IRWXU | S_IRWXG | S_IRWXO);
	}
#else
	if ((GetFileAttributesA(m_downloadDir.c_str())) == INVALID_FILE_ATTRIBUTES)
	{
		CreateDirectoryA(m_downloadDir.c_str(), 0);
	}
#endif
}

void UpdateLayer::deleteDir(std::string dir){
	// Remove downloaded files
#if (CC_TARGET_PLATFORM != CC_PLATFORM_WIN32)
	std::string command = "rm -r ";
	// Path may include space.
	command += "\"" + dir + "\"";
	system(command.c_str());
#else
	std::string command = "rd /s /q ";
	// Path may include space.
	command += "\"" + dir + "\"";
	system(command.c_str());
#endif
}

void UpdateLayer::onError(cocos2d::extension::AssetsManager::ErrorCode errorCode){
	switch (errorCode)
	{
        case cocos2d::extension::AssetsManager::kCreateFile:
            CCLOG("error : create file failure");
            m_label->setString("error : create file failure");
            break;
        case cocos2d::extension::AssetsManager::kNetwork:
            CCLOG("error : no network");
            m_label->setString("error : no network");
            break;
        case cocos2d::extension::AssetsManager::kNoNewVersion:
            CCLOG("error : no new version");
            m_label->setString("error : no new version");
            break;
        case cocos2d::extension::AssetsManager::kUncompress:
            CCLOG("error : uncompress file error");
            m_label->setString("error : uncompress file error");
            break;
        default:
            break;
	}
}

void UpdateLayer::onProgress(int percent){
	char progress[80];
	memset( progress, '\0', sizeof(progress) );
	snprintf(progress, sizeof(progress), "hotupdate downloading %d%%", percent);
	CCLOG("percent=%d %s",percent,progress);
	m_label->setString(progress);
}

void UpdateLayer::onSuccess(){
	CCLOG("download success.");
	m_label->setString("download success.");
}

void UpdateLayer::update(CCObject* pSender){
	// 初始化下載目錄
	initDownloadDir();
	// 下載更新包
	getAssetsManager()->update();
}

void UpdateLayer::reset(CCObject* pSender){
	if ("" != m_downloadDir)
	{
		// 刪除下載目錄
		deleteDir(m_downloadDir);
	}
	// 刪除版本號
	getAssetsManager()->deleteVersion();
}

void  UpdateLayer::getClientVersion(CCObject* pSender){
	CCString* msg = CCString::createWithFormat("current client version : %s", getAssetsManager()->getVersion().c_str());
	CCLOG("%s",msg->getCString());
	m_label->setString(msg->getCString());
}

void UpdateLayer::checkUpdate(CCObject* pSender){
	if (getAssetsManager()->checkUpdate())
	{
		CCLOG("has new version");
		m_label->setString("has new version");
	}else{
		CCLOG("has not new version");
		m_label->setString("has not new version");
	}
}

void UpdateLayer::enterScene(CCObject* pSender){
	CCDirector::sharedDirector()->replaceScene(HelloWorld::scene());
}



在hellowrold 跳轉場景時,就跳到一個updateLayer場景。

(友人A:.....嗯,不對,好像在哪見過,時間也不過,也在不是上班,你吖的在寫東西,你老闆知道嗎)

........我想說Duang...不過確實這東西的出處:http://blog.csdn.net/linchaolong/article/details/42321767

不過我想說的,Fuck the regulation,有時候不要過本身太大的壓力,人就要活得自在點好,也不過幾十年,還要有不明白的,能夠給我留言。

(友人A:......)

相關文章
相關標籤/搜索