• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>

            loop_in_codes

            低調(diào)做技術(shù)__歡迎移步我的獨(dú)立博客 codemaro.com 微博 kevinlynx

            MMO游戲?qū)ο髮傩栽O(shè)計(jì)

            MMO游戲?qū)ο髮傩栽O(shè)計(jì)

            Author: Kevin Lynx
            Date: 5.2.2011

            一般的MMORPG中,游戲?qū)ο笾饕ü治锖屯婕摇_@兩類(lèi)對(duì)象在經(jīng)過(guò)游戲性方面的不斷“進(jìn)化”后,其屬性數(shù)量及與之相關(guān)的邏輯往往會(huì)變得很巨大。如何將這一塊做得既不損失效率,又能保證結(jié)構(gòu)的靈活、清晰、可維護(hù)?本文將提供一種簡(jiǎn)單的結(jié)構(gòu)。

            原始結(jié)構(gòu)

            最原始的結(jié)構(gòu),極有可能為這樣:

            Player:     +---------------+
                        | property-1    |
                        +---------------+
                        | property-2    |
                        +---------------+
                        |     ...       |
                        +---------------+
                        | operator-1    |
                        +---------------+
                        | operator-2    |
                        +---------------+
                        | ...           |
                        +---------------+
            

            也就是,一個(gè)對(duì)象為一個(gè)C++類(lèi),然后里面直接塞滿了各種屬性名,然后是針對(duì)這個(gè)屬性的邏輯操作(函數(shù))。其結(jié)果就是Player成為巨類(lèi)。針對(duì)這個(gè)情況,一直以來(lái)我覺(jué)得可以使用一種簡(jiǎn)單的方法來(lái)拆分這個(gè)類(lèi)。冠以官腔,稱(chēng)之為Entity-Component-based Desgin。產(chǎn)生這種想法和我的個(gè)人技術(shù)積累有一定關(guān)系,見(jiàn)下文。

            Policy-based Design

            Policy-based Design,基于決策的設(shè)計(jì)。這個(gè)概念來(lái)源于<Modern C++ Design>。雖然這本書(shū)講述的是針對(duì)C++模板的使用及設(shè)計(jì)技巧。但這種思想依然被我潛意識(shí)般地用在其他地方。Policy大致來(lái)說(shuō)就是一個(gè)小的組件(Component)。它努力不依賴(lài)于其他東西,它可能就是個(gè)簡(jiǎn)單的類(lèi),它擁有極少的數(shù)據(jù)結(jié)構(gòu),及針對(duì)這些數(shù)據(jù)的極少操作接口。舉例而言,玩家MP的自動(dòng)回復(fù)功能,就可封裝為一個(gè)Policy。將許多Policy組合起來(lái),就可完成一個(gè)復(fù)雜的功能。

            這種思想還可指導(dǎo)很多程序結(jié)構(gòu)方面的設(shè)計(jì)。例如在做功能的接口拆分時(shí),就將每個(gè)函數(shù)設(shè)計(jì)得足夠小,小到單純地完成一個(gè)功能。一個(gè)功能的入口函數(shù),就將之前實(shí)現(xiàn)的小函數(shù)全部組合起來(lái),然后共同完成功能點(diǎn)。

            當(dāng)然,<Modern C++ Design>里的Policy在表現(xiàn)形式上有所不同。但其核心思想相同,主要體現(xiàn)在 組合 特點(diǎn)上。

            Entity-Component-based Design

            Entity-Component-based Design按照google到的文章,嚴(yán)格來(lái)說(shuō)算是與OOP完全不同的軟件設(shè)計(jì)方法。不過(guò)在這里它將按照我的意思重新被解釋。

            如果說(shuō)Policy-based Design極大可能地影響著我們平時(shí)的細(xì)節(jié)編碼,那么Entity-Component則是直接對(duì)游戲?qū)ο蟮慕Y(jié)構(gòu)設(shè)計(jì)做直接的說(shuō)明。 一個(gè)游戲?qū)ο缶褪且粋€(gè)Entity。 Entity擁有很少的屬性,也許僅包含一個(gè)全局標(biāo)示的ID。 一個(gè)Component則是Entity的某個(gè)行為、或者說(shuō)某個(gè)組成部分。 其實(shí)說(shuō)白了,以玩家為例,一個(gè)玩家對(duì)象就是一個(gè)Entity,而一個(gè)MP的自動(dòng)回復(fù)功能就可被包裝為一個(gè)Component。這個(gè)Component可能包含若干與該功能相關(guān)的數(shù)據(jù),例如回復(fù)時(shí)間間隔,每次的回復(fù)量等。我們往玩家對(duì)象這個(gè)Entity添加各種Component,也就是給玩家添加各種邏輯功能。

            但是,Component之間可能會(huì)涉及到交互,玩家對(duì)象之外的模塊可能也會(huì)與玩家內(nèi)的某個(gè)Component交互。子功能點(diǎn)的拆分,不得不涉及到更多的膠水代碼,這也算一種代價(jià)。

            游戲?qū)ο髮傩栽O(shè)計(jì)

            這份屬性結(jié)構(gòu)設(shè)計(jì),基本就是參考了上面提到的設(shè)計(jì)思想。整個(gè)系統(tǒng)有如下組件:

            Entity:    +-------------------+
                       | property-table    |
                       +-------------------+
                       | component-table   |
                       +-------------------+
            Property:  +-------------------+
                       | observer-list     |
                       +-------------------+
            Component: +--------------------+
                       | logic-related data |
                       +--------------------+
                       | logic-related func |
                       +--------------------+
            

            意即,所有Entity都包含一個(gè)屬性表和組件表。這里的屬性表并非硬編碼的屬性數(shù)據(jù)成員集合,而是一個(gè)key-value形式的表。Property包含一個(gè)觀察者列表,其實(shí)就是一系列回調(diào)函數(shù),但是這些觀察者本質(zhì)上也是組件,后面會(huì)提到。Component正如上文描述,僅包含Component本身實(shí)現(xiàn)的功能所需要的數(shù)據(jù)和函數(shù)。整個(gè)結(jié)構(gòu)大致的代碼如下:

            class Entity {
            private:
                GUID id;
                std::map<std::string, IComponent*> components;
                std::map<std::string, Property*> properties;
            };
            class Property {
            private:
                std::string name;
                Value val;
                std::vector<IComponent*> observers;
            };
            class IComponent {
            public:
                virtual bool Operate (const Args &args) { return false; }
                virtual void OnNotify (const Property &property, const Args &args) {}
            protected:
                std::string name;
                Entity *entity;
            };
            

            屬性本身是抽象的,這完全是因?yàn)槲覀儗傩越y(tǒng)一地放在了一個(gè)表里。從而又導(dǎo)致屬性的值也需要繼續(xù)閱讀

            posted on 2011-05-02 19:19 Kevin Lynx 閱讀(7020) 評(píng)論(18)  編輯 收藏 引用 所屬分類(lèi): game develop模塊架構(gòu)

            評(píng)論

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-02 20:19 so

            MUD游戲編程里也有屬性集這樣的設(shè)計(jì)。靈活。不過(guò)訪問(wèn)速度上肯定沒(méi)有直接定死屬性來(lái)得快。  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-02 20:36 Kevin Lynx

            @so
            加了個(gè)“繼續(xù)閱讀”指向我那個(gè)獨(dú)立博客。- -| 你都要在這里留言。  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 10:33 lin_style

            有個(gè)問(wèn)題:是否代碼行數(shù)多、屬性多,就代表他的邏輯一定是復(fù)雜的?一定要拆分?  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 12:02 飯中淹

            你那個(gè)獨(dú)立博客在CHROME上會(huì)標(biāo)紅標(biāo)骷髏頭。

              回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 12:03 Kevin Lynx

            @lin_style
            基本上是。雖然邏輯不一定復(fù)雜,可能僅僅是大量功能的堆積。但其維護(hù)性肯定不好。回憶一下當(dāng)你剛接手熟悉一個(gè)項(xiàng)目代碼時(shí),看到一個(gè)巨類(lèi)時(shí)的感覺(jué)。  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 12:11 Kevin Lynx

            @飯中淹
            Linux下的chrome看沒(méi)有什么骷髏頭啊。。- -|  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 12:51 lin_style

            @Kevin Lynx
            如果能夠一遍就看懂“巨類(lèi)”,我可能覺(jué)得這種分類(lèi)方式是對(duì)的。比如人物屬性,人物本來(lái)就有這么多屬性啊。而且這些屬性放在一起,并沒(méi)有很復(fù)雜的讀取邏輯,即使有不同的功能拓展,那也是每個(gè)功能類(lèi)自己的模塊化問(wèn)題。你文中,"ClientUpdater" “HP”,從概念上都分成獨(dú)立的屬性模塊."ClientUpdater"有必要這么做,但是也可以看成一個(gè)功能模塊類(lèi)去維護(hù)它,況且它也是屬于游戲玩法類(lèi)的,放在屬性接口層也不一定合適。而"HP",是一個(gè)很清晰的概念,不需要專(zhuān)門(mén)的封裝它,即使有hP1~HP1000這么多屬性,也沒(méi)有帶來(lái)多高的復(fù)雜讀。如果僅是憑借自己的編程習(xí)慣去封裝,那這個(gè)過(guò)與不過(guò)的度怎么區(qū)分呢?  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 13:57 Kevin Lynx

            @lin_style
            復(fù)雜性和可維護(hù)性不僅體現(xiàn)在本項(xiàng)目,一般一個(gè)團(tuán)隊(duì)的下個(gè)項(xiàng)目就是在上個(gè)項(xiàng)目的基礎(chǔ)上改。所以希望把這些游戲相關(guān)的東西盡量獨(dú)立出來(lái)。理想情況下是到了下個(gè)項(xiàng)目可以直接通過(guò)移除一部分模塊添加一部分模塊即可。

            當(dāng)然,如你所說(shuō),確實(shí)存在度的把握問(wèn)題。我現(xiàn)在是打算把基礎(chǔ)屬性(例如坐標(biāo))寫(xiě)死,或者通過(guò)本文的機(jī)制在程序里添加;其他屬性(主要是戰(zhàn)斗屬性、什么中毒抗性啊、暴擊傷害比率啊)放在腳本或配置里擴(kuò)展。

            但是如果是做引擎,這些包裝則是必須的了。
            ps. 因?yàn)樵趫F(tuán)隊(duì)里某部分代碼可能會(huì)在時(shí)間線上由不同的人修改,盡早地提出一種明顯的規(guī)則,可以約束后面的人不至于隨意而為。如果一開(kāi)始就在Player類(lèi)里塞功能,早期可能沒(méi)問(wèn)題,不過(guò)隨著項(xiàng)目進(jìn)展,后面的人極有可能模仿前人的做法,最終就會(huì)導(dǎo)致不斷地在Player里加功能代碼。膨脹由此而來(lái)。  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 15:58 飯中淹

            接著我在那邊跟你說(shuō)的,我是不允許代碼和腳本碰數(shù)據(jù)對(duì)象的屬性的。

            屬性必須由對(duì)象設(shè)計(jì)器生成。這個(gè)對(duì)象設(shè)計(jì)器是在線的,也就是運(yùn)行時(shí)創(chuàng)建,更改的。

            映射也是,映射說(shuō)起來(lái)就是一種腳本,用來(lái)關(guān)聯(lián)對(duì)象之間的屬性的東西。


              回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 16:06 Kevin Lynx

            @飯中淹
            話說(shuō)你把你們的服務(wù)器整成全部配置驅(qū)動(dòng)的;而我們?cè)谙蛉磕_本驅(qū)動(dòng)靠近。  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 17:58 飯中淹

            @Kevin Lynx
            配置+腳本共同的
            每個(gè)都可以實(shí)時(shí)修改
            這樣該錯(cuò)誤,更新什么的,根本不用重啟了

            服務(wù)器本身的程序就是一堆底層的庫(kù)在那里

            然后就是支持這些數(shù)據(jù)對(duì)象和映射。

            數(shù)據(jù)對(duì)象雖然看起來(lái)很復(fù)雜,實(shí)際上是個(gè)簡(jiǎn)單功能的容器類(lèi),和封包的結(jié)構(gòu)很像。

            大部分的事情都是在映射里做的。而這些映射都是腳本的。


            腳本我準(zhǔn)備用quartz composer那種卡片式的,這樣可以用IPAD,GPAD,樂(lè)PAD等各種PAD,用3G卡在某個(gè)公園的角落里摸幾下就把服務(wù)器BUG給修改好了。





              回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 18:01 飯中淹

            @Kevin Lynx
            數(shù)據(jù)也腳本化,我感覺(jué)不合適。

            我是要提供可視化編輯工具給策劃,讓他們自己去設(shè)計(jì)數(shù)據(jù)對(duì)象。

            腳本這些粗活,就是服務(wù)器程序來(lái)做。

            所有工具都做成各種PAD可部署的,這樣就不用限制辦公地點(diǎn)和時(shí)間了。

            隨時(shí)隨地做事。

            有個(gè)好的點(diǎn)子可以立即應(yīng)用到實(shí)際的游戲服務(wù)中去。

              回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 18:05 Kevin Lynx

            @飯中淹
            我們這回策劃將編寫(xiě)大量腳本。瞬間在策劃組掀起了學(xué)習(xí)Lua的熱潮。整體架子的發(fā)展路線,和你說(shuō)的差不多。程序這邊僅提供底層功能實(shí)現(xiàn)。  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì)[未登錄](méi) 2011-05-03 18:15 楊粼波

            數(shù)據(jù)還是放到配置里面的好,比如csv,xml。
            放腳本里面可以,但是編輯性不好啊。  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 19:37 Kevin Lynx

            @楊粼波
            這倒提醒我了。還真是不方便編輯。  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-03 23:20 cui

            都是單線程的服務(wù)? 多線程的服務(wù)實(shí)時(shí)更新配置文件,需要加的互斥太多了  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2011-05-06 10:55

            @Kevin Lynx
            @飯中淹

            配置驅(qū)動(dòng)與腳本驅(qū)動(dòng),我更偏向配置驅(qū)動(dòng),腳本太靈活了,debug的難度很大,要求高,不宜開(kāi)放出去。配置驅(qū)動(dòng)配置死了點(diǎn),但是安全穩(wěn)定。寫(xiě)一個(gè)配置編輯器來(lái)控制錯(cuò)誤相對(duì)比較簡(jiǎn)單。

            贊同@飯中淹 “不允許代碼和腳本碰數(shù)據(jù)對(duì)象的屬性的”,不然實(shí)在是非常危險(xiǎn)。對(duì)于腳本,應(yīng)該再封裝一層api。  回復(fù)  更多評(píng)論   

            # re: MMO游戲?qū)ο髮傩栽O(shè)計(jì) 2012-02-08 17:41 阿飛

            拜讀中,繼續(xù)學(xué)習(xí)!  回復(fù)  更多評(píng)論   

            国产午夜福利精品久久| 国产成人精品综合久久久久| 一级做a爰片久久毛片16| 精品久久久久久无码中文野结衣| 伊人久久大香线蕉AV一区二区| 国产亚洲精品美女久久久| 久久精品国产福利国产琪琪| 久久亚洲中文字幕精品有坂深雪| 国产精品成人精品久久久| 精品无码久久久久国产动漫3d| 99久久国产免费福利| 蜜臀av性久久久久蜜臀aⅴ| 欧美午夜精品久久久久久浪潮| 69SEX久久精品国产麻豆| 色青青草原桃花久久综合| 久久青青草原综合伊人| 亚洲av日韩精品久久久久久a | 国色天香久久久久久久小说| 色噜噜狠狠先锋影音久久| 奇米影视7777久久精品| 欧美日韩久久中文字幕| 久久亚洲AV无码西西人体| 久久亚洲高清观看| 狠狠色婷婷综合天天久久丁香| 亚洲国产精品久久久天堂| 麻豆久久久9性大片| 久久亚洲色一区二区三区| 国产精品久久久天天影视香蕉 | 久久久久中文字幕| 久久亚洲精品无码AV红樱桃| 亚洲精品无码久久久久久| 久久精品国产男包| 久久精品青青草原伊人| 国产精品久久久久久久app| 亚洲а∨天堂久久精品9966| 香蕉久久永久视频| 奇米影视7777久久精品人人爽| 一级女性全黄久久生活片免费| 久久国产精品免费| 午夜精品久久久内射近拍高清| 狠狠色丁香久久婷婷综合图片|