国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專欄INFORMATION COLUMN

erget源碼分析(1):入口文件分析

Rainie / 2006人閱讀

摘要:是一個(gè)靜態(tài)類,調(diào)用方法來初始化各項(xiàng)支持信息。小結(jié)通過和這兩個(gè)靜態(tài)類初始化了項(xiàng)目運(yùn)行的環(huán)境參數(shù),然后創(chuàng)建了屏幕適配器根據(jù)不同的適配策略調(diào)整。下一篇源碼分析全局哈?;惡腿之惒胶瘮?shù)對(duì)象接口

egret的github地址是https://github.com/egret-labs...,大家自己git clone到本地。

一.路口html文件

用ergetWing新建一個(gè)工程,打開根目錄下的index.html,這個(gè)就是項(xiàng)目的入口文件,我們看下其中裝載游戲內(nèi)容的DIV容器

   

這里是官方的配置說明,因?yàn)槲覀兒竺娣治鲈创a會(huì)用到,大家可以先粗略看一下

data-entry-class=”Main” 設(shè)置項(xiàng)目的入口文件,表示項(xiàng)目的入口類,默認(rèn)為Main,如果需要自定義的話需要在項(xiàng)目中先創(chuàng)建類,然后在這里配置類的名字。
data-orientation=”auto” 設(shè)置旋轉(zhuǎn)模式。
data-scale-mode=”showAll” 設(shè)置縮放模式。
data-frame-rate=”30” 這里是運(yùn)行的幀率。
data-content-width=”480” 和 data-content-height=”800” 用來設(shè)置舞臺(tái)的設(shè)計(jì)寬和高
data-show-paint-rect=”false” 設(shè)置顯示臟矩形的重繪區(qū)域。
data-multi-fingered=”2” 設(shè)置多指觸摸
data-show-fps=”false” data-show-log=”false” 這里設(shè)置顯示幀率和log,只有在調(diào)試時(shí)會(huì)顯示,發(fā)布的版本會(huì)去掉。
data-log-filter=”” 設(shè)置一個(gè)正則表達(dá)式過濾條件,日志文本匹配這個(gè)正則表達(dá)式的時(shí)候才顯示這條日志。如 data-log-filter="^egret" 表示僅顯示以 egret 開頭的日志。
data-show-fps-style=”x:0,y:0,size:30,textColor:0x00c200,bgAlpha:0.9” 這里設(shè)置fps面板的樣式。目前支持默認(rèn)的這幾種設(shè)置,修改其值即可,比如修改面板位置可以設(shè)置x和y,改變大小可以設(shè)置size,改變文字顏色textColor,改變背景面板的透明度bgAlpha。

頁面打開后會(huì)立即執(zhí)行egret.runEgret(),這幾個(gè)參數(shù)后面會(huì)詳細(xì)講,我們先理解erget的運(yùn)行流程。

EgretWeb.ts入口腳本

我們?cè)谠创a項(xiàng)目中搜索runEgret可以看到分別在
src/egret/native/EgretNative.ts
src/egret/player/EgretEntry.ts
src/egret/web/EgretWeb.ts中被定義。
這是egret的一個(gè)基本的結(jié)構(gòu),EgretEntry.ts定義了接口,而EgretNative.ts和EgretWeb.ts分別定義在原生平臺(tái)和web平臺(tái)上的實(shí)現(xiàn)。我們先按照web部分的思路進(jìn)行分析。

1.初始化環(huán)境參數(shù)
    let isRunning: boolean = false;

    /**
     * @private
     * 網(wǎng)頁加載完成,實(shí)例化頁面中定義的Egret標(biāo)簽
     */
    function runEgret(options?: runEgretOptions): void {
        if (isRunning) {
            return;
        }
        isRunning = true;
        if (!options) {
            options = {};
        }
        Html5Capatibility._audioType = options.audioType;
        Html5Capatibility.$init();
        //......
   }

首先看runEntry函數(shù)的前面幾行,這里利用一個(gè)閉包和isRunning,還有if語句來防止重復(fù)運(yùn)行游戲。這里的isRunning這個(gè)變量明顯只被runEntry函數(shù)使用,所以不把它定義為成員私有屬性而是定義成一個(gè)變量。Html5Capatibility是一個(gè)靜態(tài)類,調(diào)用$init()方法來初始化html5各項(xiàng)支持信息。

public static $init(): void {
    let ua: string = navigator.userAgent.toLowerCase();
    Html5Capatibility.ua = ua;
    egret.Capabilities.$isMobile = (ua.indexOf("mobile") != -1 || ua.indexOf("android") != -1);
    //......
}

我們稍微來看一下$init()方法,這里還調(diào)用了一個(gè)全局靜態(tài)類Capabilities,這個(gè)類在src/egret/system/Capabilities.ts下,主要是存儲(chǔ)當(dāng)前運(yùn)行的設(shè)備(PC/IOS/Android)信息、平臺(tái)信息(web/native)、渲染模式、引擎版本和客戶端尺寸。
我們可以看出,在web平臺(tái)關(guān)于運(yùn)行環(huán)境的各項(xiàng)信息從Capabilities獲得,HTML5的接口支持從Html5Capatibility獲得。

2.配置渲染
 // WebGL上下文參數(shù)自定義
function runEgret(options?: runEgretOptions): void {
        if (options.renderMode == "webgl") {
            // WebGL抗鋸齒默認(rèn)關(guān)閉,提升PC及某些平臺(tái)性能
            let antialias = options.antialias;
            WebGLRenderContext.antialias = !!antialias;
            // WebGLRenderContext.antialias = (typeof antialias == undefined) ? true : antialias;
        }
    sys.CanvasRenderBuffer = web.CanvasRenderBuffer;
    setRenderMode(options.renderMode);
    ......
}

這里有個(gè)小技巧就是利用兩個(gè)!來轉(zhuǎn)型,因?yàn)閛ptions.antialias可能是false、true、undefined中的一個(gè),如果是false或者true,兩個(gè)!!相當(dāng)于沒有作用,如果是undefined就被轉(zhuǎn)換成false。

    /**
     * 設(shè)置渲染模式。"auto","webgl","canvas"
     * @param renderMode
     */
    function setRenderMode(renderMode: string): void {
        //......
        if (renderMode == "webgl" && WebGLUtils.checkCanUseWebGL()) {
            sys.RenderBuffer = web.WebGLRenderBuffer;
            sys.systemRenderer = new WebGLRenderer();
            sys.canvasRenderer = new CanvasRenderer();
            sys.customHitTestBuffer = new WebGLRenderBuffer(3, 3);
            sys.canvasHitTestBuffer = new CanvasRenderBuffer(3, 3);
            Capabilities.$renderMode = "webgl";
        }
        else {
            sys.RenderBuffer = web.CanvasRenderBuffer;
            sys.systemRenderer = new CanvasRenderer();
            sys.canvasRenderer = sys.systemRenderer;
            sys.customHitTestBuffer = new CanvasRenderBuffer(3, 3);
            sys.canvasHitTestBuffer = sys.customHitTestBuffer;
            Capabilities.$renderMode = "canvas";
        }
        //......
    }

我們簡(jiǎn)單來看一下setRenderMode方法,如果用戶把renderMode設(shè)置為webGL并且瀏覽器支持webGL就使用webGL否則使用canvas,WebGLUtils.checkCanUseWebGL()這個(gè)方法大家可以自己去看一下,同樣使用了兩個(gè)!!的技巧,關(guān)于webGL的使用大家可以看這里初識(shí) WebGL

3.分辨率配置
function runEgret(options?: runEgretOptions): void {
        //......
        let canvasScaleFactor;
        if (options.canvasScaleFactor) {
            canvasScaleFactor = options.canvasScaleFactor;
        }
        else if(options.calculateCanvasScaleFactor) {
            canvasScaleFactor = options.calculateCanvasScaleFactor(sys.canvasHitTestBuffer.context);
        }
        else {
            //based on : https://github.com/jondavidjohn/hidpi-canvas-polyfill
            let context = sys.canvasHitTestBuffer.context;
            let backingStore = context.backingStorePixelRatio ||
                context.webkitBackingStorePixelRatio ||
                context.mozBackingStorePixelRatio ||
                context.msBackingStorePixelRatio ||
                context.oBackingStorePixelRatio ||
                context.backingStorePixelRatio || 1;
            canvasScaleFactor = (window.devicePixelRatio || 1) / backingStore;
        }
        sys.DisplayList.$canvasScaleFactor = canvasScaleFactor;
        //......
}

如果用戶配置了縮放比例就使用它,配置了計(jì)算縮放比例的方法就調(diào)用它,否則計(jì)算當(dāng)前瀏覽器支持的最大精度的縮放比例。

4.執(zhí)行系統(tǒng)定時(shí)器
function runEgret(options?: runEgretOptions): void {
    //......
    let ticker = egret.ticker;
    startTicker(ticker);
    //......
}
        

egret.sys.$ticker是egret.SystemTicker類的單例對(duì)象,首先對(duì)它調(diào)用了startTicker方法:

function startTicker(ticker:egret.sys.SystemTicker):void {
    var requestAnimationFrame =
        window["requestAnimationFrame"] ||
        window["webkitRequestAnimationFrame"] ||
        window["mozRequestAnimationFrame"] ||
        window["oRequestAnimationFrame"] ||
        window["msRequestAnimationFrame"];
    if (!requestAnimationFrame) {
        requestAnimationFrame = function (callback) {
            return window.setTimeout(callback, 1000 / 60);
        };
    }
    requestAnimationFrame.call(window, onTick);
    function onTick():void {
        ticker.update();
        requestAnimationFrame.call(window, onTick)
    }
}

這里同樣是判讀瀏覽器是否存在requestAnimationFrame的API,存在則使用之,否則使用setTimeout方法,這里onTicker使用了延遲遞歸調(diào)用,實(shí)現(xiàn)每隔一段時(shí)間就調(diào)用一次ticker.update()方法,這里使用call方法確保調(diào)用該方法對(duì)象是全局window對(duì)象,避開js中this的坑。

5.屏幕適配和播放器的創(chuàng)建
function runEgret(options?: runEgretOptions): void {
    //......
    if (options.screenAdapter) {
            egret.sys.screenAdapter = options.screenAdapter;
        }
        else if (!egret.sys.screenAdapter) {
            egret.sys.screenAdapter = new egret.sys.DefaultScreenAdapter();
        }

        let list = document.querySelectorAll(".egret-player");
        let length = list.length;
        for (let i = 0; i < length; i++) {
            let container = list[i];
            let player = new WebPlayer(container, options);
            container["egret-player"] = player;
            //webgl模式關(guān)閉臟矩形
            if (Capabilities.$renderMode == "webgl") {
                player.stage.dirtyRegionPolicy = DirtyRegionPolicy.OFF;
            }
        }
        if (Capabilities.$renderMode == "webgl") {
            egret.sys.DisplayList.prototype.setDirtyRegionPolicy = function () { };
        }

        window.addEventListener("resize", function () {
            if (isNaN(resizeTimer)) {
                resizeTimer = window.setTimeout(doResize, 300);
            }
        });
    //......
   
}
//......
    let resizeTimer: number = NaN;

    function doResize() {
        resizeTimer = NaN;

        egret.updateAllScreens();

        if (customContext) {
            customContext.onResize(context);
        }
    }

接下來使用document.querySelectorAll()方法取得所有擁有"egret-player"的CSS class的DOM對(duì)象。就是我們一開始在index.html的body里看到的那個(gè)div標(biāo)簽。
遍歷這些DOM對(duì)象,為每一個(gè)創(chuàng)建一個(gè)egret.WebPlayer對(duì)象,并賦值給DOM的"egret-player"屬性(這是個(gè)自定義屬性)。

這里還有一個(gè)值得注意的對(duì)方是resizeTimer,每當(dāng)瀏覽器尺寸變化先進(jìn)行一個(gè)判斷,如果不存在重繪定時(shí)器(也就是resizeTimer為NaN),就啟動(dòng)一個(gè)定時(shí)器,在300毫秒后重新獲取瀏覽器尺寸重新繪制,并把resizeTimer賦值為NaN表示這個(gè)定時(shí)器關(guān)閉了。這么做,是因?yàn)樵赑C端,我們修改瀏覽器尺寸是一個(gè)延續(xù)動(dòng)作,也就是鼠標(biāo)持續(xù)移動(dòng)改變窗口尺寸,定義一個(gè)300毫秒的定時(shí)器延時(shí)重繪是防止過多的重繪請(qǐng)求占用資源。

小結(jié)

runEgret通過Html5Capatibility和Capatibilities這兩個(gè)靜態(tài)類初始化了項(xiàng)目運(yùn)行的環(huán)境參數(shù),然后創(chuàng)建了屏幕適配器egret.sys.screenAdapter根據(jù)不同的適配策略調(diào)整。然后通過監(jiān)聽winodw對(duì)象的resize事件監(jiān)聽客戶端尺寸變化(包括旋轉(zhuǎn)設(shè)備,改變?yōu)g覽器窗口尺寸等)。最主要的事情是調(diào)用創(chuàng)建一個(gè)定時(shí)器無限地調(diào)用egret.sys.$ticker的update()方法進(jìn)行全局的數(shù)據(jù)更新和視圖渲染。那么整個(gè)游戲引擎大概的啟用流程到這里就結(jié)束了。

下一篇:erget源碼分析(2):全局哈?;惡腿之惒胶瘮?shù)對(duì)象接口

文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請(qǐng)注明本文地址:http://specialneedsforspecialkids.com/yun/89710.html

相關(guān)文章

  • erget源碼分析(2):全局哈?;惡腿之惒胶瘮?shù)對(duì)象接口

    摘要:異步函數(shù)對(duì)象接口,包含和兩個(gè)成員方法。哈希計(jì)數(shù)在整個(gè)的源碼中都沒有找到和方法的調(diào)用,這兩個(gè)方法的具體作用是在原生中實(shí)現(xiàn)類式繼承和私有屬性一類的功能。 文件結(jié)構(gòu) utils/HashObject.ts文件:showImg(https://segmentfault.com/img/bVZpuq?w=642&h=472); 首先解釋一下文件結(jié)構(gòu)圖 __extends方法 通過原型對(duì)象模擬類...

    godlong_X 評(píng)論0 收藏0
  • erget源碼分析(3):生命周期

    摘要:概述下面我們來分析一下中的生命周期。定義了監(jiān)聽生命周期的類,這個(gè)三個(gè)成員方法分別執(zhí)行暫停繼續(xù)和刷新。方法作為橋梁,接收到具體的類型的函數(shù),創(chuàng)建的一個(gè)實(shí)例作為參數(shù)調(diào)用它。函數(shù)做了兩件事情暫停應(yīng)用程序,暫停背景音樂和音效的播放。 概述 下面我們來分析一下erget中的生命周期。 src/egret/player/SystemTicker.ts: export namespace li...

    Hydrogen 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

最新活動(dòng)
閱讀需要支付1元查看
<