LoginSignup
41
42

More than 1 year has passed since last update.

with IE(JavaScriptのIE11対応)

Last updated at Posted at 2020-09-26

はじめに

政府や行政サイトの「IE縛り」に代表されるように、IE汚染国である日本で仕事としてJavaScriptを書く場合、IEと共存するしなければならない場合が多いです。
with コロナならぬwith IEです。

IE生活様式

  • Transpile
  • Bundle
  • Polyfill

TranspileとBundle は、ES5の書き方で1つのファイルに書いていれば不要です。
エンジニアが不便を我慢すれば必要ない工程ではありますが、そんな我慢はしたくありません。
コロナで言えばマスク、消毒、手洗い、うがい、密を避ける、換気のような個人でできる対策に当たると思います。

Polyfillは、もともとIE11が対応していない機能に対応させるもので、コロナでいえば治療薬ともいえるものだと思いますが、薬なのでリスクもあります。

コロナと違って、みんなでIEやめる合意が取れればIE対応せずに済む世界になるんですが。
河野大臣、ハンコ、書面、FAXに続いて、IE対応不要もお願いします。

JavaScriptをIE11対応する

webpackとBabelのインストール

terminal
npm install -D webpack webpack-cli babel-loader @babel/core @babel/preset-env 
パッケージ 内容
webpack webpack本体
webpack-cli webpackのコマンドラインツール
babel-loader webpackでBabelを使えるようにする
@babel/core Babel本体
@babel/preset-env 指定したブラウザ環境で動作するように変換するプラグイン

設定ファイルの準備

package.jsonの編集

package.jsonにビルドコマンドを追加します。

package.json
{
 "scripts": {
   "dev": "webpack --mode development",
   "build": "webpack --mode production"
  }
}

webpack.config.jsの作成

プロジェクトルートにwebpackの設定ファイルのwebpack.config.jsを作成します。
babelでtargetsを指定しないとbabel/preset-envがbrowserslistとの連携を行なってくれるので指定しません。

webpack.config.js
module.exports = {
  module: {
    rules: [
      {
        test: /\.js$/,
        use: [
          {
            loader: "babel-loader"
          }
        ]
      }
    ]
  }
};

.babelrc

プロジェクトルートにBabelの設定ファイルの.babelrcファイルを作成します。
※webpack.config.js内に記述することもできます。

.babelrc
{
  "presets": ["@babel/preset-env"]
}

.browserslistrc

プロジェクトルートに対象ブラウザを指定する.browserslistrcファイルを作成します。

.browserslistrc
ie 11

.browserslistrcで対象ブラウザを指定する

Transpile

TranspileするJavaScriptの準備

src/index.js
window.addEventListener("load", () => {
  alert("InternetExplorer");
});

Transpile後のJavaScriptを読み込むHTMLの準備

dist/index.html
<!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Document</title>
</head>
<body>
  <script src="main.js"></script>
</body>
</html>

ビルド

terminal
npm run build

動作確認

IE11でdist/index.htmlを開いて、JavaScriptが実行できているか確認します。

polyfillの追加

APIがサポートされていないなど、構文の変換だけでは対応できない機能への対応を行うpolyfillを追加できるようにします。

core-jsのインストール

terminal
npm install -S core-js

.babelrcの変更

.babelrc
{
  "presets": [
    [
      "@babel/preset-env",
      {
        "useBuiltIns": "usage",
        "corejs": {
          "version": 3,
          "proposals": false  
        }
      }
    ]
  ]
}

Polyfillを追加するJavaScriptの準備

src/index.js
alert(Array.from("InternetExplorer"));

ビルド

terminal
npm run build

動作確認

IE11でdist/index.htmlを開いて、JavaScriptが実行できているか確認します。

regenerator-runtime

必要に応じてregenerator-runtimeを使用します。
(ビルド時にCan't resolve 'regenerator-runtime/runtime'が表示されたとき)

regenerator-runtimeのインストール
terminal
npm i -S regenerator
regenerator-runtimeのインポート
JavaScript
import  regeneratorRuntime  from  "regenerator-runtime" ;

//もしくは
//import  "regenerator-runtime / runtime.js" ;

TypeScriptをIE11対応する

webpackとTypeScriptのインストール

terminal
npm install -D webpack webpack-cli typescript ts-loader 

table:パッケージ

パッケージ 内容
webpack webpack本体
webpack-cli webpackのコマンドラインツール
typescript TypeScript本体
ts-loader webpackでTypeScriptを読み込む

設定ファイルの準備

package.jsonの編集

package.jsonにビルドコマンドを追加します。

package.json
{
  "scripts": {
    "dev": "webpack --mode development",
    "build": "webpack --mode production"
},

tsconfig.jsonの作成

tsconfigでは.browserslistrcが使えないので、targetでJavaScriptのバージョンを指定します。

tsconfig.json
{
  "compilerOptions": {
    "target": "ES5",
    "lib": ["dom", "ES5","ScriptHost"]
  }
}
target lib省略時に暗黙的に指定されているもの
ES5 DOM,ES5,ScriptHost
ES6 lib: DOM,ES6,DOM.Iterable,ScriptHost

※この時点ではlibの記述は不要ですが、後でlibを追加するので先にデフォルトのlibを記述しています。

webpack.config.jsの作成

webpack.config.js
module.exports = {
  module: {
    rules: [
      {
        test: /\.ts$/,
        loader: 'ts-loader'
      }
    ]
  },
  resolve: {
    extensions: ['.ts', '.js']
  }
}

Transpile

TranspileするJavaScriptの準備

アロー関数のコードをIEで実行できるように変換

src/index.ts
window.addEventListener("load", () => {
  alert("InternetExplorer");
});

Transpile後のJavaScriptを読み込むHTMLの準備

dist/index.html
<!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Document</title>
</head>
<body>
  <script src="main.js"></script>
</body>
</html>

ビルド

terminal
npm run build

IE11での動作確認

IE11でdist/index.htmlを開いて、JavaScriptが実行できているか確認します。

polyfillの追加

APIがサポートされていないなど、構文の変換だけでは対応できない機能への対応を行うpolyfillを追加できるようにします。

core-jsのインストール

terminal
npm install -S core-js

動作確認用のコードの準備

src/index.js
import "core-js";

alert(Array.from("InternetExplorer"));

tsconfig.jsonの変更

libに追加します。

tsconfig.json
{
  "compilerOptions": {
    "target": "ES5",
      "lib": ["dom", "ES5","ScriptHost","ES2015.Core"]
  }
}

今回はlibに"ES2015.Core"を追加しましたが、コードによって追加する内容は変わります。

libの値
  • es5
  • es6
  • es2015
  • es7
  • es2016
  • es2017
  • es2018
  • es2019
  • es2020
  • esnext
  • dom
  • dom.iterable
  • webworker
  • webworker.importscripts
  • scripthost
  • es2015.core
  • es2015.collection
  • es2015.generator
  • es2015.iterable
  • es2015.promise
  • es2015.proxy
  • es2015.reflect
  • es2015.symbol
  • es2015.symbol.wellknown
  • es2016.array.includees2017.object
  • es2017.sharedmemory
  • es2017.string
  • es2017.intl
  • es2017.typedarrays
  • es2018.asyncgenerator
  • es2018.asynciterable
  • es2018.intl
  • es2018.promise
  • es2018.regexp
  • es2019.array
  • es2019.object
  • es2019.string
  • es2019.symbol
  • es2020.bigint
  • es2020.promise
  • es2020.string
  • es2020.symbol.wellknown
  • es2020.intl
  • esnext.array
  • esnext.symbol
  • esnext.asynciterable
  • esnext.intl
  • esnext.bigint
  • esnext.string
  • esnext.promise

ビルド

terminal
npm run build

動作確認

IE11でdist/index.htmlを開いて、JavaScriptが実行できているか確認します。

regenerator-runtime

必要に応じてregenerator-runtimeを使用します。
(ビルド時にCan't resolve 'regenerator-runtime/runtime'が表示されたとき)

regenerator-runtimeのインストール
terminal
npm i -S regenerator
regenerator-runtimeのインポート
JavaScript
import  regeneratorRuntime  from  "regenerator-runtime" ;

//もしくは
//import  "regenerator-runtime / runtime.js" ;

環境を作らずにIE11対応する

あまり手をかけずにIE11対応をします。

Babel

https://babeljs.io/
https://babeljs.io/repl

アクセスしたブラウザ用にTranspileできるようですが、肝心のIE11が非対応のようです・・・・。

Polyfill

TranspileもBundleも不要で、Polyfillだけ使いたい場合はダウンロードしてきてHTMLから読み込めば使えるようになります。

例:intersectionObserver(https://github.com/w3c/IntersectionObserver/tree/master/polyfill)

index.html
<script src="intersection-observer.js"></script>

polyfill.io

https://polyfill.io/v3/
JavaScriptのPolyfillを配信しているサービスです。
※当然ですが、外部から読み込むので、polyfill.ioで障害が発生してしまったらPolyfillは無効になります。

下記URLで必要な機能を検索して、そのPolyfillを使えるURLを取得できます。
https://polyfill.io/v3/url-builder/

index.html
//ES2019の全polyfill取得
<script src="https://polyfill.io/v3/polyfill.min.js?features=es2019"></script>

//fetch機能だけのpolyfillを取得
<script src="https://polyfill.io/v3/polyfill.min.js?features=fetch"></script>
41
42
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
41
42