簡體   English   中英

AngularJS 1.3頁面不會在IE8中加載

[英]AngularJS 1.3 page won't load in IE8

作為一個有角色的用戶,我對這個問題的標題感到不寒而栗,因為IE8是邪惡的化身,應該像狂犬病一樣被放下。

話雖這么說,我想知道是否有其他人遇到過在IE8中加載Angular 1.3的問題,並且在加載之前頁面中斷並且只報告錯誤: Object Expected在使用isArray()函數的if條件下出現。 (isArray()也可以在Angular 1.2中找到,所以它讓我感到困惑,它在那里工作但在1.3中沒有

為了讓每個人都理解我的理由,我的公司最近采取了不再支持IE8進行新開發的步驟。 但是我們的新UI只需要在初始登錄頁面上支持IE8,這樣用戶仍然可以訪問支持IE8的舊軟件。 我希望我可以使用1.3,只是為着陸頁寫下小調整,直到它也從IE8下面出來。

首要問題:是否可以將Angular 1.3與IE8一起使用,或者在我們完全刪除IE8支持之前,我是否會被迫使用1.2?

有一種方法,雖然它有點粗糙。 下面是您需要在角度之前加載的代碼,您的應用程序可能會運行。 這是墊片/填充物的集合,大部分來自Mozilla Developer Network。

請注意,這只允許AngularJS運行,它不會更新IE8的JS運行時。 所以像somePromise.catch(...)這樣的東西不起作用,你必須寫somePromise["catch"](...)

if (!Array.prototype.indexOf) {
    Array.prototype.indexOf = function(searchElement) {
        if (this.length === 0) {
            return -1;
        }
        var n = 0;
        if (arguments.length > 1) {
            n = Number(arguments[1]);
            if (isNaN(n)) {
                n = 0;
            } else if (n !== 0 && n !== Infinity && n !== -Infinity) {
                n = (n > 0 || -1) * Math.floor(Math.abs(n));
            }
        }
        if (n >= this.length) {
            return -1;
        }
        var k = n >= 0 ? n : Math.max(this.length - Math.abs(n), 0);
        while (k < this.length) {
            if (k in this && this[k] === searchElement) {
                return k;
            }
            ++k;
        }
        return -1;
    };
}

if (!Array.prototype.filter) {
    Array.prototype.filter = function(fun/*, thisArg*/) {
        if (this === undefined || this === null) {
            throw new TypeError();
        }

        var t = Object(this);
        var len = t.length >>> 0;
        if (typeof fun !== 'function') {
            throw new TypeError();
        }

        var res = [];
        var thisArg = arguments.length >= 2 ? arguments[1] : void 0;
        for (var i = 0; i < len; i++) {
            if (i in t) {
                var val = t[i];
                if (fun.call(thisArg, val, i, t)) {
                    res.push(val);
                }
            }
        }
        return res;
    };
}

if (!Array.isArray) {
    Array.isArray = function(arg) {
        return Object.prototype.toString.call(arg) === '[object Array]';
    };
}

if (!Array.prototype.every) {
    Array.prototype.every = function(callbackfn, thisArg) {
        'use strict';
        var T, k;
        if (this == null) {
            throw new TypeError('this is null or not defined');
        }
        var O = Object(this);
        var len = O.length >>> 0;
        if (typeof callbackfn !== 'function') {
            throw new TypeError();
        }
        if (arguments.length > 1) {
            T = thisArg;
        }
        k = 0;
        while (k < len) {

            var kValue;

            if (k in O) {
                kValue = O[k];
                var testResult = callbackfn.call(T, kValue, k, O);
                if (!testResult) {
                    return false;
                }
            }
            k++;
        }
        return true;
    };
}

if (!Object.create) {
    Object.create = (function() {
        var Object = function() {};
        return function (prototype) {
            if (arguments.length > 1) {
                throw new Error('Second argument not supported');
            }
            if (typeof prototype != 'object') {
                throw new TypeError('Argument must be an object');
            }
            Object.prototype = prototype;
            var result = new Object();
            Object.prototype = null;
            return result;
        };
    })();
}

if (!Array.prototype.forEach) {
    Array.prototype.forEach = function(fun /*, thisArg */) {
        if (this === void 0 || this === null)
            throw new TypeError();

        var t = Object(this);
        var len = t.length >>> 0;
        if (typeof fun !== "function")
            throw new TypeError();

        var thisArg = arguments.length >= 2 ? arguments[1] : void 0;
        for (var i = 0; i < len; ++i) {
            if (i in t)
                fun.call(thisArg, t[i], i, t);
        }
    };
}

if (!String.prototype.trim) {
    String.prototype.trim = function() {
        return this.replace(/^\s+|\s+$/gm, '');
    };
}

(function() {
    //$http uses onload instead of onreadystatechange. Need shimming as IE8 doesn't have onload.
    if (new XMLHttpRequest().onload === undefined) {
        var orig = XMLHttpRequest.prototype.send;
        XMLHttpRequest.prototype.send = function() {
            var self = this;
            if (!this.onreadystatechange && this.onload) {
                this.onreadystatechange = function() {
                    if (self.readyState === 4) {
                        self.onload();
                    }
                };
            }
            orig.apply(self, arguments);
        };
    }
})();

if (!Date.now) {
    Date.now = function() {
        return new Date().getTime();
    };
}

if (!Function.prototype.bind) {
    Function.prototype.bind = function(oThis) {
        if (typeof this !== "function") {
            throw new TypeError("Function.prototype.bind - what is trying to be bound is not callable");
        }
        var aArgs = Array.prototype.slice.call(arguments, 1),
            fToBind = this,
            fNOP = function() {
            },
            fBound = function() {
                return fToBind.apply(this instanceof fNOP && oThis
                        ? this
                        : oThis,
                    aArgs.concat(Array.prototype.slice.call(arguments)));
            };

        fNOP.prototype = this.prototype;
        fBound.prototype = new fNOP();

        return fBound;
    };
}

if (!Object.keys) {
    Object.keys = function(object) {
        var keys = [];
        for (var o in object) {
            if (object.hasOwnProperty(o)) {
                keys.push(o);
            }
        }
        return keys;
    };
}

if (!Object.getPrototypeOf) {
    Object.getPrototypeOf = function(object) {
        return object.__proto__ || object.constructor.prototype;
    };
}

如果你有angular-bootstrap,你還需要“修補”angular.min.js文件,因為angular-boostrap使用{in: someCondition} ,但由於舊的JS運行時, in關鍵字是保留的,並且會在代碼生成。

查找: var e=(b?"s":'((l&&l.hasOwnProperty("'+a+'"))?l:s)')+"."+a;

替換: var e=(b?"s":'((l&&l.hasOwnProperty("'+a+'"))?l:s)')+"['"+a+"']";

根據對問題的評論和Zenorbi的回答,Angular 1.3不再能夠在IE8中正確加載。 它從未被設計為繼續在IE8中工作,所以這不應該是一個驚喜。

我實際上想出了一個簡單的解決方法,它會使任何IE8用戶的頁面加載時間稍微慢一些,這對我來說是可以接受的。

使用此代碼,我可以簡單地加載1.3,如果任何IE8用戶加載頁面,它將直接加載角度1.2,只需覆蓋任何重復的代碼:

<script type="text/javascript" src="target/libraries/angular.min.js"></script>
<!--[if lt IE 9]>
<script type="text/javascript" src="target/libraries/angular-1.2.min.js"></script>
<![endif]-->
<script type="text/javascript" src="target/libraries/angular-route.min.js"></script>
<!--[if lt IE 9]>
<script type="text/javascript" src="target/libraries/angular-route-1.2.min.js"></script>
<![endif]-->

注意 :這通常是一種可怕的做法。 如果我們正在努力支持IE8用戶,我會選擇Zenorbi的答案,因為它允許你只加載一個版本的角度。

根據SamHuckabyZenorbi的答案,我想出了一個可接受的解決方案,這是他們的想法和見解的結合,這篇文章如果Internet Explorer那么做其他事情(如何...)Phil Nash

     <!--[if !IE]>-->
        <script src="/ui/resources/webjars/angularjs/1.4.0/angular.js"></script>
        <script src="/ui/resources/webjars/angularjs/1.4.0/angular-route.js"></script>
    <!--<![endif]-->

    <!--[if gt IE 8]>
        <script src="/ui/resources/webjars/angularjs/1.4.0/angular.js"></script>
        <script src="/ui/resources/webjars/angularjs/1.4.0/angular-route.js"></script>
    <![endif]-->

    <!--[if lt IE 9]>
        <script type="text/javascript" src="/ui/resources/lib/angularjs/1.2.28/angular.js"></script>
        <script type="text/javascript" src="/ui/resources/lib/angularjs/1.2.28/angular-route.js"></script>
    <![endif]-->

        <script type="text/javascript" src="webjars/es5-shim/4.0.6/es5-shim.js"></script>
        <script type="text/javascript" src="webjars/es6-shim/0.20.2/es6-shim.js"></script>

<!--[if !IE]>-->...<!--<![endif]--> - 條件評論將由IE評估,但其中的腳本將不會被IE加載並且將會被所有其他瀏覽器加載

<!--[if gt IE 8]>...<![endif]--> - 條件評論將由IE評估,如果大於IE 8,腳本將被加載

<!--[if lt IE 9]>...<![endif]--> - 條件評論將由IE評估,如果小於IE 9,將加載腳本。

es5-shimes6-shim都應該從IE8條件注釋塊中刪除並由所有瀏覽器檢查(並且它不是昂貴的操作)因為我最近發現SafariString.prototype.startsWith()問題

是的,我們在第一個和第二個條件注釋中有一些代碼重復(並且它不能以不同的方式解決)但是我們沒有加載任何不需要的腳本 ,我們可以在這里關閉我們的任務。

來自Angular Developer Guide遷移文檔

注意:AngularJS 1.3正在放棄對IE8的支持。 在我們的博客上閱讀更多相關信息。 AngularJS 1.2將繼續支持IE8,但核心團隊並不打算花時間解決IE8或更早版本的特定問題。

Github用戶@fergaldoyle 維護一個包含shiming / polyfill和其他補丁策略的repo ,以保持兼容性。

這可能是許多解決方案提供商的可行策略

我嘗試了L0lander的答案(這是我首選的答案),但是當使用較舊的角度版本時,其他腳本會抱怨,並且最終無法正常工作。 所以,我檢查了我的網站的統計數據,0.2%只使用IE8或更低,我不會讓自己頭疼這么小的人群,所以我只是添加了一條消息,要求IE8或更低版本的用戶升級。

body標簽之后將以下代碼添加到您的所有頁面:

<!--[if lt IE 9]>
    <div style="text-align: center; font-size: 22px; padding: 20px; background-color: #d14c4c; color: #f3e3e3;">Your version of Internet Explorer is too old for this site to function properly.<br>Please <a href="https://www.google.com/search?q=update+internet+explorer" target="_blank" style="text-decoration: underline; color: #76c880">click here</a> to upgrade to a newer version.</div>
<![endif]-->

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM