私は、Hot DotのWeb開発者であるFedor furikuretsu Ananievです。今日は、JS視差アプリケーションを非常に高速にしたい人のための簡単なヒントを紹介します。
ストーリーは、新しいサイトhotdot.proのメインページを作成して得られた経験に基づいています。 このページは複数のスライドに分割され、各スライドはブラウザウィンドウのサイズを引き継ぎます。 各スライドには、浮遊視差レイヤーがある場合とない場合があります。 ページの背景も視差レイヤーの法則に従って移動します。
すべてはJSで始まります
私が解決したい最初の明らかな問題はスクリプトです。
「なぜ解決したいのですか?」
スクリプトは、視差モデル内のレイヤーの位置を変更し、DOMを変更します。 多かれ少なかれ印象的なアプリケーションには多くのレイヤーがあります。 また、目の前のコードが1つのレイヤーをレンダリングするためのコードに近いほど、1秒あたりにブラウザーによって呼び出される回数が多くなり、速度を上げたいと思うようになります。
例:
視差に5つのスライドがあり、平均して各スライドに3つのレイヤーがあり、最小許容映画周波数25 FPSで視差を更新すると、1つのレイヤーのレンダリングを担当するコードが呼び出されます
5×3×25 = 375回/秒。
この種の数学は、一般的に使用されるコードの場所ですべての操作を追跡する動機を与えます。
コンテナ内のフローティングレイヤーの2Dモデルは長い間テストされており、高校生にとって難しくはないため、この記事では省略します。 ただし、注目に値するのは、経験則がレイヤーに適用されることです。
レイヤーの位置を更新するには、2つの操作で十分です。
- 特定のレイヤーに固有の特定の定数係数に、親内部での変位を乗算する
- 最初の操作の結果を、このレイヤーに固有の一定の初期位置に追加します。
-なぜこのルールが私たちにとって重要なのですか?
そのおかげで、レイヤーXの幅、親のレイヤーXの位置、ビューアーの位置、および親の幅からビューアーの位置を変更するたびに、レイヤーXの位置を構築する必要がありません。 5つ以上の操作の代わりに、上記の2つだけを実行すれば十分です。 レイヤーを初期化するときに、レイヤーXに固有の係数と初期変位を選択するだけです。
あなたの心の状態については、別の経験則が適用されます:
1秒あたり5回+ 375回ではなく2つの操作を実行すると、
気分が良くなります。
ブラウザは友人のフリーランサーよりも速く描画しますが、それでも十分に速くありません
ブラウザーの開発の世界に長い間やってこなかったオプティマイザーである場合、私たちにとっての発見は、たとえ画面から外れていても描画要素が存在することです。
3Dエンジンの古典的な手法に慣れている私たちは、画面外のすべてがレンダリングキューから何らかの形で最適に削除されると考えるかもしれません。 しかし、それは削除されません。
結果:
Xの時点で画面に表示されない要素を非表示にする(つまり、css-rules display:noneを強制する)機会がある場合は、あらゆる方法でこれを実行してください。
視差の場合、要素はスライドであり、幸いなことに、 「画面の外側にある」プロパティの定義は非常に簡単です。
ビデオカード
- Webkitおよびgeckoブラウザーでは、leftの代わりに
translate3d
を使用して絶対間隔のレイヤーの動きを調整すると、即座にパフォーマンスが向上します。 - Operaでは、2次元バージョンのみが使用可能です
translate
。 私の場合、その使用によるパフォーマンスの向上は疑わしいものでした。 - Internet Explorerは、従来の左を使用してレイヤーをオフセットする場合、他のすべてのブラウザーを完全に実行します。 興味深いことに、私の場合、
translate3d
を使用するとパフォーマンスが低下しました。
また、
translate
に切り替えると、座標またはオフセットをパーセントで指定する機能が失われることも十分に認識しています。 場合によっては、この制限がかなり痛いことに注意してください。
障害者
DOMの非常に小さな変更(ルートよりもリーフに近いノードを含む)によって、画面上のすべてのものやすべてのものが非常に高価に再描画されることを知ることは非常に貴重です。
-これは実際に私にとって何を意味しますか?
ページ上でユーザーをスライドさせる過程で、無害な小さなアニメーションを遠くの隠れたスライドで再生する場合、ブラウザはページの再構築とその後の再描画のプロセスを開始します。 アニメーションが一歩進むたびに起動します。 そして、これはユーザーがページをスクロールする時点であり、プロセッサはすでに大量のレイヤーをすばやく移動するために最善を尽くしています。 たとえば、jQueryのステップ周波数は13ミリ秒です。 自分自身を締める :それは痛いでしょう。
-ユーザーがページをスライドしている間に少なくとも何かを変更することは可能ですか?
はい 要素の位置を変更するには、大きな費用をかけなくてもかまいません。そのような変更は再描画を引き起こさず、要素の再構成のみを引き起こすためです。 再構成は非常に迅速に行われ、レイヤーの再描画を必要とせず、ビデオカード上で完全に行うことができます。これは私たちにとって間違いなくメリットです。
ただし、レイヤーを移動すると、パフォーマンスを監視するとDOMを変更する機能が終了します。
美しい解決策:
ユーザーがページ内を移動している間は、すべてのアニメーションを無効にします。 そのため、プロセッサの非常に高価なアニメーションは、ユーザーがどこにも移動せず、視差が静的な場合にのみ再生されます。 ユーザーが移動すると、プロセッサーは視差レイヤーの移動のみに集中します。
統計
スタジオページの2つのバージョンのChromeの統計を見てみましょう:最適化を無効および有効にします。 寛大にしましょう。最初のバージョンでは最適化されたJSをオフにしません。非常に小さな描画最適化を残します。
テストは簡単でした。 私は急いでではなく、左から右にサイトを運転しました。 しかし、したがって、テストは2番目のバージョンでも非常に残酷でした。
最初に何が見えますか? 最初のチャート全体が緑色で塗りつぶされます。 非常に、非常に多くのフレームを描画および再描画します。 中央処理装置で行われるブラウザーの膨大な作業と、ユーザーにとって非常に不快な感覚。
2番目のグラフでは、緑は何倍も少なくなっています。 より多くの空の灰色の長方形。 これは最初のチャートにありますが、それほど高くはありません。 彼らはどういう意味ですか? 2番目のケースでは、非常に多くのフレームで、ブラウザがその処理に非常に迅速に対応するため、ほとんどの場合、フレームに割り当てられた何かを行うことができます。 最初のケースでは、ブラウザに息をする時間がほとんどありません。
ブラウザーが作業に多くの時間を費やしているときの2番目のグラフの高色の列のまれなケースは、スライドの可視性を切り替える必要があり、2つのスライド間で前後にスライドするときに驚くべきパフォーマンスに支払う代償です。
フレームレートの大きな違いを見てみましょう: 最初のチャートでブラウザが毎秒30フレーム以上をめったに与えない場合、2番目のチャートで毎秒30フレーム未満を生成することはめったにありません。
これは素晴らしい結果です。
私たちが調べたテクニックは、多くの作業と考えを要しました。
しかし、彼らは文字通りブレーキの沼地から私たちを生産的なウェブアプリケーションの領域に引き込みました。
私の作品があなたのプロジェクトに役立つことを願っており、私たちのスタジオの開発にご関心をお寄せいただきありがとうございます。
頑張って