スティックポイントを使用したズームイン/ズームアウトは、Figma などのデザインツールやビルダーツールでよく見られる使用例です。このブログでは、JavaScript、HTML、CSS でそれを処理するための基本的なアルゴリズムを紹介します。
デモンストレーション
1.コンテナとスケーラブルなアイテムを作成します
<div id="app"> <div class="parent"> <div class="scalable-child"></div> </div> </div>
.scalable-child { width: 300px; height: 300px; position: relative; top: 0; left: 0; pointer-events: none; transform-origin: left top; background-image: url('https://cdn4.vectorstock.com/i/1000x1000/17/58/caro-pattern-background-vector-2261758.jpg'); background-size: contain; } .parent { position: relative; background-color: white; width: 100vw; height: 100vh; }
この例では、クラス「scalable-child」を持つスケーラブルなアイテムとして div を使用し、そのコンテナーはクラス「parent」を持つ div です。
一部のプロパティについてはご注意ください:
上、左: 0 がデフォルトの位置です
ポインタ イベント: なし。親にイベントを追加するため、ポインタ イベント !== なしの場合、アルゴリズムは失敗します。
Transform-origin: 左上、位置を計算するための座標原点を作成します
2.ホイールイベントリスナーを追加
const parent = document.querySelector('.parent'); const child = document.querySelector('.scalable-child');
parent.addEventListener('wheel', wheelEventHandler, { passive: false, capture: true, });
WheelEvent を使用して、ズームイン、ズームアウト、および子の移動を処理します
注: この例はトラックパッドのみを示しています。 (Ctrl +、Ctr -) などのホットキーやマウスのイベントも処理する必要があります。
let left = 0; let top = 0; let scale = 1; const wheelEventHandler = (e) => { e.preventDefault(); // Handle zoom with touch pad and hot key. const isZooming = e.ctrlKey || e.metaKey; let newValues = {}; if (isZooming) { newValues = calculateOnZooming(e, scale, left, top); } else { newValues = calculateOnMoving(e, scale, left, top); } left = newValues.newLeft; top = newValues.newTop; scale = newValues.newScale; Object.assign(child.style, { transform: `scale(${scale})`, left: `${left}px`, top: `${top}px`, }); };
まず、子要素がズームまたは移動しているかどうかを確認するための isZooming 変数があります。
次に、子要素の新しい位置とスケールを計算します。 left、top、scale は温度変数として使用されます。
そして、次は 2 つの計算関数にアルゴリズムを集中させます:
3.ズーム時に計算
const calculateOnZooming = (e, oldScale, oldLeft, oldTop) => { let newScale = oldScale - e.deltaY * oldScale * 0.01; newScale = Math.max(newScale, 0.1); const newLeft = oldLeft - (e.offsetX - oldLeft) * (newScale / scale - 1); const newTop = oldTop - (e.offsetY - oldTop) * (newScale / scale - 1); return { newScale, newLeft, newTop, }; };
ズームすると、wheelEvent はスケール比として deltaY を返し、それを使用して newScale を計算できます
デルタY> 0 =>ズームアウト
デルタY
0 =>ズームイン
newLeft 変数と newTop 変数の計算方法をさらに理解するために、以下の画像を見てみましょう:
子はスケール比からスケール' 比にスケールされ、点 A は A' に進みます。
detalX = x’ - x
= x * (スケール’ / スケール) - x
= x * (スケール’ / スケール - 1)
詳細Y = y’ - y
= y * (スケール’ / スケール) - y
= y * (スケール’ / スケール - 1)
newLeft = left - detalX
4.移動計算
const calculateOnMoving = (e, oldScale, oldLeft, oldTop) => { return { newLeft: oldLeft - e.deltaX * 2, newTop: oldTop - e.deltaY * 2, newScale: oldScale, }; };
移動イベントでは、newLeft と newTop の値のみを計算する必要があります。また、各デルタ値を *2 して速度も向上させます。
私たちが対処する必要があるのはこれだけです。お役に立てば幸いです。ご覧いただきありがとうございます!
以上がキャンバス内のスティッキーポイントをズームインまたはズームアウトするの詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。