将来を見据えたウェブ・アプリケーションの構築:The Codestのエキスパート・チームによる洞察
The Codestが、最先端技術を駆使してスケーラブルでインタラクティブなウェブアプリケーションを作成し、あらゆるプラットフォームでシームレスなユーザー体験を提供することにどのように秀でているかをご覧ください。The Codestの専門知識がどのようにデジタルトランスフォーメーションとビジネス...
新しいウェブサイトを作るときに私たちを混乱させたもののひとつが、ページのさまざまな場所で見ることができるモーフィング・ウェーブでした。私たちは、大きな労力をかけずに正しい方法で実装する方法について多くのアイデアを持っていました。しかし、ほとんどの解決策は時間がかかり、既存のライブラリよりも高速なものをゼロから構築する必要がありました。
私たちはまず、SVGオブジェクトをさまざまなライブラリでアニメーションさせることから始めました。1ページに3つのオブジェクトを表示したかったので、結果はそれほど満足のいくものではありませんでした。1つのSVGオブジェクトのすべてのパスを短時間で更新しなければならず、ページ全体がカタツムリのように遅くなってしまったのです。ドキュメントに純粋なSVGを挿入するソリューションは却下せざるを得ませんでした。その結果、他の2つのソリューションから選択することになりました。
について ビデオ
要素が2番目の選択肢だった。私たちは2つの問題からスタートした:
- .mp4や.webmのような最も一般的なビデオフォーマットでは適用できません、
- 動画はスケーラブルではないので、これは本当に問題だった。
私たちはこの解決策を後回しにしておくことにした。「他に何も見つからなければ、これを選ぶ」。
最後の選択肢は キャンバス
と WebGL
レンダリング。レンダリングのメカニズムをすべて自分たちで設計しなければならなかったからだ。というのも、私たちが持っているモルフィックウェーブはカスタムのものだったからです。
ゼロから始めよう。この波を作るために使わなければならない素材は何だったのだろう?アイデアは、すべての波が1×1の大きさのSVGファイルで、その周囲に特定のパスが配置されているというものだった。このSVGのアニメーションは、このファイルに対するいくつかのステートによって構築されました。つまり、すべてのアニメーションは、シェイプを動かす段階を含む一連のファイルとして表現されていたのだ。
すべてのパスは、特定の値が特定の順序で配置された配列の一種にすぎない。この配列内の特定の位置でそれらの値を変更すると、特定の部分の形状が変化する。次の例でこれを単純化することができる:
状態1: [1, 50, 25, 40, 100]
状態2: [0, 75, -20, 5, 120]
状態3: [5, 0, -100, 80, 90]
つまり、私たちがレンダリングしたい形状は、5つの要素を持つ配列で構成され、特定の時間内にリニア・イージングによって変化すると仮定できる。アニメーションが最後のステージを終えると、最初のステージに戻り、無限アニメーションのような印象を与える。
しかし......待てよ、上で紹介した配列とはいったい何なのか?先にも述べたように、それは特定の形状を表示する役割を担うパスである。すべてのマジックは d
プロパティを持つ。このプロパティは図形を描画するための「コマンド」の集合を含み、各コマンドは一種の引数を持っている。上記の配列は、これらのコマンドに付けられた全ての値(引数)からなる。
これらの "ステートファイル "の違いは、特定のコマンドの値だけで、コマンドの順番は同じだった。つまり、すべてのマジックは、すべての値を取得し、それらをアニメーション化することだった。
上の段落で、オブジェクトをアニメーションさせる唯一の魔法は、シェイプのすべてのステージ間のトランジションを作成することだと述べました。問題は、キャンバスでそれを行う方法です。
一緒に仕事をした誰もが持っていた機能 キャンバス
知っておくべきことは リクエストアニメーションフレーム.初めてこれを見る人は、まずこれを読むことから始めるべきだと心から思う。さて、この関数で私たちが注目しているのは、引数の-である。 DOMHighResTimeStamp
.とても恐ろしく見えるが、実際にはそれほど難しくはない。最初のレンダリングからの経過時間のタイムスタンプであると言える。
でも、これで何ができるんだろう?として リクエストアニメーションフレーム
関数を再帰的に呼び出せば、その呼び出しの間の時間差にアクセスできる。ここで科学的な話をしよう!⚛️ (ロケット・サイエンスではないかもしれないが...まだ)
物理学では、距離のデルタは時間のデルタに速度を掛けたものに等しいと教えられる。私たちの場合、特定の時間内に終点に到達したいので、速度は一定である。では、上記の状態でどのように表現できるか見てみよう:
これらの状態を1000ミリ秒で遷移させたいので、速度値は次のようになるとしよう:
delta: [ -1, 25, -45, -35, 20].
速度:[-1/1000、25/1000、-45/1000、-35/1000、20/1000]。
上の速度は、ミリ秒ごとに-1/1000ずつ値を増やしていくことを示している。そして、ここが我々の リクエストアニメーションフレーム
と時間デルタ。増加させたい特定の位置の値は、時間デルタにその位置の速度を掛けたものである。もうひとつ、問題なく達成するためには、その値を制限することで、目指す状態を超えないようにすることである。
トランジションが終了したら、また別のトランジションを呼び出す。実装はそれほど難しくないように思えるが、次のようなルールがある。 ソフトウェア開発 というのも、すでに実装されていることに時間を費やしたくないからだ。そこで 小さな図書館 このようなトランジションを無理のない方法で生み出すことができる。
こうして私たちは、まるで生き物のような波のアニメーションを作り上げた。
ご覧の通り、The Codestブランドのウェーブは1つのアニメーションフィギュアではない。同じ形でありながら、大きさや位置が異なる多くの図形で構成されています。このステップでは、このような方法で複製する方法を簡単に見ていきます。
キャンバスのコンテキストでは、次のことができる。 縮尺図面領域 (ここで "k "はスケーリング係数で、デフォルトでは "1 "に設定されている)、 キャンバスを翻訳するこれは描画領域のアンカーポイントを変更するようなものだ。また、これらのメソッドを使って、これらの状態の間をジャンプすることもできる: セーブ そして リストア.
これらのメソッドによって、「修正ゼロ」の状態を保存し、適切に拡大縮小され、平行移動されたキャンバスで、ループ内の特定の数の波をレンダリングすることができる。この後すぐに、保存した状態に戻ることができる。以上、フィギュアのクローニングについてだった。羊のクローンを作るよりずっと簡単だろう?
パフォーマンスの問題で、候補のひとつを却下したと申し上げました。キャンバスを使用するオプションはかなり高速ですが、さらに最適化できないとは誰も言っていません。まず、ブラウザのビューポートの外にあるときの図形の遷移についてはあまり気にしないという事実から始めましょう。
もうひとつ、プログラマーが大好きだったブラウザAPIがある。 交差点オブザーバー.これにより、ページの特定の要素を追跡し、それらの要素がビューポートから現れたり消えたりしたときに呼び出されるイベントを処理できるようになります。今現在、私たちはとても簡単な状況を持っています - 可視性の状態を作成し、IntersectionObserverイベントハンドラによってそれを変更し、単純に特定の形状に対してレンダリングシステムをオン/オフにしましょう。そして......パフォーマンスが大幅に向上した!ビューポートに表示されているものだけをレンダリングしているのです。
物事を実行する方法を選ぶのは、しばしば難しい選択である。特に、利用可能な選択肢が同じような長所と短所を持っているように見える場合はなおさらだ。正しい選択をするための鍵は、それぞれの選択肢を分析し、メリットが少ないと思われるものを除外することだ。あるソリューションは他のソリューションよりも時間がかかるが、最適化しやすかったり、カスタマイズしやすかったりする。
毎分のように新しいJSライブラリが登場していますが、それらでは解決できないこともあります。だからこそ、すべてのフロントエンドエンジニアは(彼らだけでなく)ブラウザのAPIを知り、技術的なニュースにアンテナを張り、時には「このライブラリの実装をこうしたらどうなるだろう」と考えてみるべきなのです。ブラウザに関する知識が増えれば、本当に素晴らしいものを作ることができ、使用するツールについて適切な判断を下せるようになり、自分たちの仕事に自信を持てるようになります。 コード.
続きを読む
– Ruby 3.0.Rubyとあまり知られていないプライバシー管理方法
– 黙って金を受け取れ #1:製品開発プロセスにおける隠れたコストと真の俊敏性
– CTOの課題 - ソフトウェア製品のスケールアップと成長