数十行のjsを使用してクールなキャンバスインタラクティブ効果を実現する方法を教えます

数十行のjsを使用してクールなキャンバスインタラクティブ効果を実現する方法を教えます

さっそく、レンダリングをご覧ください。

この記事のサンプルコードは、Franksという外国人のYouTubeの教育ビデオからコピーしたものです。彼はキャンバスに関するビデオもたくさん公開しており、学ぶ価値は十分にあります。私はキャンバスにあまり詳しくないので、マスターに従ってコードを入力して学習ノートを作りました。また、この記事の例のページ構造は非常に単純(htmlにはキャンバスのみを含む)であるため、次のコード部分は投稿しません。結局のところ、jsが主役です。

1. 円を描く

まずは静的な円を描いてみましょう。いくつかの API を理解するだけで十分です。MDN に詳しい説明があります。ここでは詳しく説明しません。js コードを見てみましょう。

定数キャンバス = document.querySelector('#canvas');
const ctx = canvas.getContext('2d');
キャンバスの幅 = ウィンドウの内側の幅;
キャンバスの高さ = ウィンドウの内側の高さ;
関数drawCircle() {
 ctx.beginPath();
 ctx.fillStyle = '青';
 ctx.arc(10, 10, 10, 0, Math.PI * 2);
 ctx.fill();
 ctx.closePath();
}
円を描画します。

これで半径10pxの円が描画されました。キャンバスを使ったことがない人でも短時間で描画できます。とても簡単ですね。次はこれをベースにアニメーションを追加してみましょう。

2. マウスで動かした円

ここで、円をマウスで動かしたい場合は、キャンバス上でマウス操作イベントをバインドする必要があります。ここでは、mousemove/click イベントに焦点を当てます。マウスが動くと、円の座標も変化するため、円の座標を更新する必要があります。アニメーションについては、requestAnimationFrame によって実現されます。コードはもう少しです。

定数マウス = {};
キャンバス.addEventListener('mousemove', (e) => {
 マウスx = ex;
 マウスのyキーを押します。
});
キャンバス.addEventListener('クリック', (e) => {
 マウスx = ex;
 マウスのyキーを押します。
});
キャンバス.addEventListener('マウスアウト', () => {
 mouse.x = mouse.y = 未定義;
});
関数drawCircle() {
 ctx.beginPath();
 ctx.fillStyle = '青';
 ctx.arc(mouse.x, mouse.y, 10, 0, Math.PI * 2);
 ctx.fill();
 ctx.closePath();
}
関数アニメーション() {
 ctx.clearRect(0, 0, キャンバス.幅, キャンバス.高さ);
 円を描画します。
 アニメーションフレームをリクエストします(アニメーション化します);
}
アニメーション化();

効果は以下の通り。マウスでボールを動かすことができます。とても簡単です。

animate 関数で ctx.clearRect をコメント アウトすると、効果は次のようになります。

3. マウスでドラッグした粒子

パーティクルは、位置、サイズ、速度が異なる多数の円です。マウス イベント オブジェクト情報に基づいてパーティクルを初期化できます。

定数マウス = {};
// マウスをクリックまたは移動したときに新しいパーティクルオブジェクトを配列に追加します。 function addNewParticles(e) {
 マウスx = ex;
 マウスのyキーを押します。
 配列.apply(null, { 長さ: 2 }).forEach(() => {
  パーティクルを新しいパーティクル()にプッシュします。
 });
}
キャンバスにEventListenerを追加します('mousemove'、新しいパーティクルを追加します);
キャンバスにEventListenerを追加します('click'、新しいパーティクルを追加します);
const 粒子配列 = [];
クラス粒子{
 コンストラクタ() {
  マウスをダブルクリックします。
  マウスのy座標を計算
  this.size = Math.random() * 5 + 1;
  this.speedX = Math.random() * 3 - 1.5; // -1.5 ~ 1.5 で、負の数の場合は左に移動し、正の数の場合は右に移動します。speedY についても同様です。 this.speedY = Math.random() * 3 - 1.5;
 }
 アップデート() {
  this.size -= 0.1; // 円の半径が徐々に減少します this.x += this.speedX; // 円の座標を更新します this.y += this.speedY;
 }
 描く() {
  ctx.beginPath();
  ctx.fillStyle = '#fff';
  ctx.arc(this.x, this.y, this.size, 0, Math.PI * 2);
  ctx.fill();
  ctx.closePath();
 }
}
関数handleParticles() {
 (i = 0 とします; i < particlesArray.length; i++) {
  パーティクルアレイ[i]を更新します。
  パーティクルアレイ[i].draw();
  if (particlesArray[i].size <= 0.3) { // 半径が小さすぎる粒子を削除します。particlesArray.splice(i, 1);
   私 - ;
  }
 }
}
関数アニメーション() {
 パーティクルを処理します。
 アニメーションフレームをリクエストします(アニメーション化します);
}
アニメーション化();

これで、記事の冒頭の最初のアニメーション効果を実現できました。ここでは主に、パーティクルの更新と描画をカプセル化するために Particle クラスを追加し、条件に応じて小さなパーティクルを削除しました。ここはまだ非常にシンプルで、コードは数十行しかありませんが、効果は良好です。

4. カラーグラデーション粒子

色のグラデーションを実現するために、ビデオ作成者は HSL カラー モデルを使用しました。私たちがよく知っている RGB モードと比較すると、色は変数で制御できるため、非常に便利です。3 番目のコード スニペットに基づいて少し変更するだけです。

let hue = 0; // 色相......
クラス粒子{
 ......
 描く() {
  ctx.beginPath();
  ctx.fillStyle = `hsl(${hue}, 100%, 50%)`;
  ctx.arc(this.x, this.y, this.size, 0, Math.PI * 2);
  ctx.fill();
  ctx.closePath();
 }
}
関数handleParticles() {
 ......
}
関数アニメーション() {
    色相++;
    パーティクルを処理します。
    アニメーションフレームをリクエストします(アニメーション化します);
 
}
アニメーション化();

色相値を動的に設定し、円の塗りつぶしスタイルを変更することで、色のグラデーションを持つパーティクルを作成できます。効果は、冒頭の 2 番目のアニメーションに示されているとおりです。
上記に基づいて、次のように変更するなど、新しいトリックを実行することもできます。

関数アニメーション() {
 // ctx.clearRect(0, 0, キャンバス.幅, キャンバス.高さ);
 ctx.fillStyle = 'rgba(0, 0, 0, 0.2)';
 ctx.fillRect(0, 0, キャンバスの幅、キャンバスの高さ);
 色相++;
 パーティクルを処理します。
 アニメーションフレームをリクエストします(アニメーション化します);
}

これで、パーティクルにトレーリング効果が追加されました。これは、記事の冒頭にある 3 番目のアニメーションです。ここでは、キャンバス全体の透明度を重ねて、前のペイント効果をフェードさせ、最終的に非表示にします。視覚的な観点からは、グラデーションのトレーリング効果です。これまでのところ、効果はますます面白くなってきていますが、コードはまだほとんどありません。

5. 連結粒子

最後に、記事の冒頭にある 4 番目のアニメーション効果である粒子を接続する必要があります。前のアニメーションに基づいて、2 つの円の間に直線を描くことができます。もちろん、2 つの円の中心間の距離を取得してから描画する必要があります。これには、handleParticles 関数の変更が含まれ、残りは変更されません。

関数handleParticles() {
 (i = 0 とします; i < particlesArray.length; i++) {
  パーティクルアレイ[i]を更新します。
  パーティクルアレイ[i].draw();
  // 現在の粒子から始めて、次の粒子を走査し、対応する距離を 1 つずつ計算します。for (let j = i + 1; j < particlesArray.length; j++) {
   定数dx = 粒子配列[i].x - 粒子配列[j].x;
   定数dy = particlesArray[i].y - particlesArray[j].y;
   const distance = Math.sqrt(dx * dx + dy * dy); // 中学校の知識if (distance < 100) { // 距離が大きすぎて破棄できません。そうしないと視覚効果が悪くなります// 直線を描画しますctx.beginPath();
    ctx.strokeStyle = `hsl(${hue}, 100%, 50%)`;
    ctx.moveTo(粒子配列[i].x、粒子配列[i].y);
    ctx.lineTo(粒子配列[j].x、粒子配列[j].y);
    ctx.stroke();
    ctx.closePath();
   }
  }
  (粒子配列[i].サイズ<= 0.3)の場合{
   粒子配列.splice(i, 1);
   私 - ;
  }
 }
}

ループを追加して直線を描くことで効果が実現し、見た目も非常に良くなりました。ここまでは、基本的に作者の手順に従いました。コード量は多くありませんが、効果は非常に良好です。さらに重要なのは、キャンバスを学習する熱意が再燃したことです。

要約する

数十行の js を使用してクールなキャンバス インタラクティブ効果を実現する方法を説明した記事はこれで終わりです。js を使用してキャンバス インタラクティブ効果を実現する方法に関する関連コンテンツの詳細については、123WORDPRESS.COM の以前の記事を検索するか、次の関連記事を引き続き参照してください。今後も 123WORDPRESS.COM を応援していただければ幸いです。

以下もご興味があるかもしれません:
  • 画像の断片化と再編成のアニメーション効果を実現する JavaScript+html5 キャンバス
  • js キャンバスで星空の背景効果を実現
  • 流星効果を実現する JavaScript キャンバス
  • js キャンバスはランダムなパーティクル効果を実現します

<<:  Kubernetesでポッドを作成する方法

>>:  ウェブページの最も基本的なコード

推薦する

JS で async と await を使用する方法

目次1. 非同期2. 待つ: 3. 包括的なアプリケーション1. 非同期async 、非同期コードが...

Vue ベースの円形スクロールリスト機能を実装する

注: 親コンテナーに高さと :data='Array' および overfolw:h...

Docker Compose で環境変数を参照する方法の例

プロジェクトでは、さまざまな条件や使用シナリオを制御するために、docker-compose.yml...

Node.js における path.join() の利点の分析

文字列連結ではなく path.join() メソッドを使用する必要があるのはなぜか疑問に思うかもしれ...

XHTML と CSS によるオブジェクト指向プログラミング

<br />XHTML と CSS がオブジェクト指向だったらよかったのに。 。太陽は北...

優れたウェブワイヤーフレーム設計・制作ツール13選を紹介

プロジェクトの作業を開始するときは、ワイヤーフレームを使用してアイデアをスケッチすることが重要です。...

証明書を使用してリモート Docker サーバーに接続する方法

目次1. スクリプトを使用してDockerのTLSを暗号化する2. Dockerの設定を変更してリモ...

HTML フォーム_PowerNode Java アカデミー

1. フォーム1. フォームの役割HTML フォームは、さまざまな種類のユーザー入力を受け取り、ユー...

CSS の読み込みによってブロックが発生しますか?

おそらく誰もが js の実行によって DOM ツリーの解析とレンダリングがブロックされることを知って...

モバイルデバイスで 1 ピクセルの境界線の問題を解決するいくつかの方法 (5 つの方法)

この記事では、モバイルデバイス上の 1 ピクセルの境界線の問題を解決する 5 つの方法を紹介します。...

Vmwareでディスクを追加する方法:ディスクを拡張する

この記事では、ディスクを追加または拡張して、Vmare で有効にする方法について説明します。シナリオ...

CentOS での samba フォルダ共有サーバー構成の詳細な説明

1. はじめに最近、CentOS での開発には多くの不便があることがわかりました。Windows/M...

高性能ウェブサイトの最適化ガイド

パフォーマンスの黄金律:エンドユーザーの応答時間のわずか 10% ~ 20% が HTML ドキュメ...

CentOS7 に YUM 経由で MySQL 5.7 をインストールする詳細な手順

1. インストールパッケージを保存する場所に移動しますcd /home/lnmp 2. MySQL ...