以下C++相關(guān)的都廢了藕坯,老板終于決定廢掉原來(lái)的服務(wù)器用C#重寫了
-
Web Socket與C++ 原生Socket通信實(shí)現(xiàn)
MDZZ
Web Socket的C++實(shí)現(xiàn)采用開源庫(kù)Web Socket++(還有一個(gè)beast.websocket,蛋四這個(gè)的參考資料比較少)
這個(gè)庫(kù)基于Boost.asio,需要先配置boost,配置過(guò)程中的error:
Error:c4996 unsafe ,
無(wú)法解析的外部符號(hào) "class boost::system::error_categorye
-D_SCL_SECURE_NO_WARNINGS: Properties->C/C++->Command Line->add option復(fù)制
無(wú)法解析的xxx__imp__ntohs@4 referenced in function xxx: #pragma comment(lib,"WS2_32.lib")
to_string is not a member of std:
MinGW官網(wǎng)上那個(gè)getMinGW安裝的g++(5.3.0)對(duì)于c++11中的一部分在源碼中沒(méi)有實(shí)現(xiàn)夕凝,win上可以使用MinGW-w64的安裝包柠偶,除了獲取新版本的g++外,還可以選擇x86_64,即64位g++程序胎署,目前版本為4.5吆录,g++版本更新到 6.2.0
Websocket++提供了多種config,其中config::core僅需要stl,編譯環(huán)境僅依賴C++11琼牧,蛋四沒(méi)有什么文檔恢筝,好像是沒(méi)有實(shí)現(xiàn)網(wǎng)絡(luò)功能,總之不會(huì)用巨坊,大多采用config::asio滋恬,這套方案直接實(shí)現(xiàn)了網(wǎng)絡(luò)功能,蛋四需要boost::asio抱究,也就是需要先編一份boost出來(lái)
整個(gè)流程有兩種思路:
1.h5客戶端連接到AgentServer轉(zhuǎn)發(fā)服務(wù)器,在轉(zhuǎn)發(fā)服務(wù)器上維護(hù)客戶端列表带斑,Agent和Tcp服務(wù)器之間保持一個(gè)socket連接鼓寺,轉(zhuǎn)發(fā)服務(wù)器將每條消息標(biāo)識(shí)來(lái)源ID轉(zhuǎn)發(fā)給TcpSrv,TcpSrv處理之后標(biāo)識(shí)接收者ID發(fā)送給Agent勋磕,由Agent再發(fā)送給對(duì)應(yīng)的客戶端
2.client連接到Agent之后Agent發(fā)起一個(gè)到Tcp的連接,客戶端列表要存兩份,Agent這里要存一個(gè)tcpClient-wsClient的map
打算先用第一種
原生Socket
先插個(gè)書簽
所謂的事件綁定和回調(diào)品腹,本質(zhì)還是一個(gè)(獨(dú)立線程中)while(true)嵌套for循環(huán)姻灶,每一次循環(huán)依次檢查每一個(gè)連接上recv是否大于0來(lái)判斷是否收到來(lái)自某個(gè)連接的數(shù)據(jù)
OVER
-
關(guān)于自動(dòng)重連
- 自動(dòng)重連主要是基于客戶端發(fā)起的(網(wǎng)絡(luò)不穩(wěn)定,斷網(wǎng)之類的)
- 因?yàn)橥瓿啥丝趯?duì)斷網(wǎng)的檢測(cè)(特別是ios端)存在延遲赶站,很多時(shí)候需要客戶端和服務(wù)器之間互發(fā)心跳包以確保連接
- 為了保證用戶體驗(yàn)幔虏,客戶端盡量采用靜默自動(dòng)重連(可以轉(zhuǎn)菊花但盡量少?gòu)椏颍?/li>
- tcp的connect建立是很快的,如果connect之后立刻開始收發(fā)數(shù)據(jù)贝椿,網(wǎng)絡(luò)極度不穩(wěn)定的話可能會(huì)丟包想括?,解決方案是讓網(wǎng)絡(luò)線程connect之后休眠一小段時(shí)間.
- 每一次重連(重啟網(wǎng)絡(luò)線程)之間應(yīng)該有個(gè)間隔時(shí)間(比如2s)烙博,期間客戶端轉(zhuǎn)菊花瑟蜈,但上一次連接(失斞萄贰)2s后才會(huì)嘗試再次連接,因?yàn)樵诰W(wǎng)絡(luò)不穩(wěn)定的情況下(比如剛剛打開wifi開關(guān))即使連100次也是很快就全部失敗了
- 注意客戶端重連函數(shù)可能由不同的定時(shí)器觸發(fā)(連接失敗或是心跳包之類的)铺根,因此標(biāo)志是否正在重連是很有必要的宪躯,如果執(zhí)行重連函數(shù)的時(shí)候正在重連,一定不能再次執(zhí)行重連位迂,否則會(huì)造成無(wú)限連接失敗進(jìn)而卡死(ui都會(huì)死的那種)
客戶端部分使用Cocos Creator
JS腳本之類的
js里函數(shù)和變量本質(zhì)上是一樣的,聲明都是var something = somethingElse
js中沒(méi)有類和命名空間的概念,在creator中
var MyClass=cc.Class({ //使用這樣的方式來(lái)定義一個(gè)類访雪,在cc.Class“命名空間”下
ctor:function(){} //構(gòu)造函數(shù),new的時(shí)候調(diào)用
})
var a=new MyClass(); //調(diào)用ctor
cc.Class({
extends:cc.Component, //組件腳本繼承自cc.Component
properties:{}, //這里竟然支持get/set方法可怕
onLoad:function{}, //組件的初始化函數(shù)囤官,類似于Unity腳本周期中的Awake冬阳?和Unity里一樣,組件的初始化不要用new
start:function(){}, //onLoad之后調(diào)用,Unity start()函數(shù)
update:function{} //update函數(shù)党饮,貼心的是新建腳本這個(gè)函數(shù)默認(rèn)是被注釋掉的肝陪,畢竟事件響應(yīng)的實(shí)現(xiàn)方式比update里一串分支優(yōu)雅的多
})
layaBox?
- 刪除腳本文件除了src里刪掉,bin/js里也要手動(dòng)刪除刑顺,還有bin/index.html里的js加載
- pivot是以像素為單位的氯窍,默認(rèn)0,0即左上角
- 另一個(gè)anchor是0~1的范圍,但只適用于UI組件
- sprite.cacheAsBitmap = true; 將多個(gè)對(duì)象緩存為靜態(tài)圖像蹲堂,這樣繪制一大堆東西只有一個(gè)drawcall狼讨?(看文檔好像并不是
- loader.load([asset path],Handler.create(this,func,[args]) 給資源加載添加完成回調(diào),如果加載失敗會(huì)在控制臺(tái)輸出
- 注意由IDE搭建的UI類或是UI擴(kuò)展類的初始化要放在加載完成的回調(diào)函數(shù)里,否則會(huì)產(chǎn)生找不到資源的錯(cuò)誤(因?yàn)楸淮虻搅藞D集里柒竞,res下并沒(méi)有直接的對(duì)應(yīng)路徑)
- 資源路徑的根目錄是bin政供,也就是說(shuō)加載路徑是"res/xxx/xxx.xx"
- asset path可以是數(shù)組形式,加載一堆圖集
- stage/gameObject.on/off([eventType],[caller],[function])來(lái)啟用/關(guān)閉事件捕獲
- Laya.Tween.to/from,緩動(dòng)屬性(組),還可以添加補(bǔ)間樣式朽基、回調(diào)和延遲執(zhí)行時(shí)間,好屌哦
- Laya.timer.loop/once 定時(shí)器布隔,timer.clear 停止執(zhí)行
- Laya.Stat是那個(gè)顯示幀率之類的狀態(tài)框...
-
UI層級(jí)面板優(yōu)化
Unity有合并batch的概念,相鄰的UI組件紋理如果使用同一圖集可以一起渲染稼虎,Layer也有這種用法衅檀,而且更直觀誒,用顏色標(biāo)記不同圖集,調(diào)整標(biāo)記顏色相同的組件到一起霎俩,如圖
- F12發(fā)布UI項(xiàng)目哀军,圖片放在asset目錄的子目錄下
TypeScript
import [name =] namespace;js里是var name = namespace;
變量聲明及初始化 var name:Type = new Type(args);
類函數(shù)聲明 funName(args):return type{},不需要加關(guān)鍵字function