描画内容を追跡するために、描画アプリケーション、コンピュータ支援設計システム (CAD システム)、ゲームなどの多くのアプリケーションは、現在表示されているオブジェクトのリストを保持しています。通常、これらのアプリケーションでは、ユーザーが現在画面に表示されているオブジェクトを操作できます。たとえば、CAD アプリケーションでは、設計内の要素を選択、移動、ズームなどできます。
・「HTML5 Canvasコアテクノロジー」
Canvas での实现拖拽
同様です。Canvas は、 点(x, y)
isPointInPath(x, y)
という API を提供します。パス内にある場合は true を返します。したがって、次のようなアイデアが考えられます。
各パスを記述できる数组
を保持し、 ispointInPath(x, y)
使用して、クリックされた位置が特定のパス内にあるかどうかを判断し、このパス内にある場合は、このパスを選択し、操作 (移動、ズームなど) を実行します。 、グラフィックを描画します
この記事では、 多边形拖拽为例进行说明
。デモは次のとおりです (インプリントの背後にある理由は、画面録画ソフトウェアです:Japanese_ogre:)。
コードペンが開きます
デモでポリゴンを描画する方法は以前にまとめたので、ここでは詳しく説明しません: Ghost:: Canvas のポリゴン描画
アイデアの説明以下の図は、大まかな説明と疑似コードを示しています。このアイデアは難しくありませんが、いくつかの詳細に対処する必要があります。
コード構造はここにリストされ、そのアイデアは CodePen にマークされています。
この記事ではドラッグに重点を置いているため、描画部分の説明は少なくなります。
//ポリゴンパスの描画関数 functiondrawPolygonPath//ポリゴンクラス定義 class Polygon{ ...}//クリックイベントに従ってキャンバス内の位置を返す function positoinInCanvas//2 点間の直線距離を取得 function getDistance//開始段階では、ドラッグを記録します オブジェクトのドラッグ Canvas.onmousedown//フェーズのドラッグ、パスの描画、ストローク Canvas.onmousemove//フェーズの終了、オブジェクトのドラッグ位置の更新 Canvas.onmouseup重要な部分の説明
次に、コードの主要な部分と詳細の処理を開始します。
ドラッグ オブジェクトの配列を維持する方法プログラムの初期化中に、polygonArray 配列を定義します。
ポリゴン配列 = []
新しいポリゴンが描画されるたびに、メンテナンスのために新しいポリゴン オブジェクトが配列にプッシュされます。
const Polygon = new Polygon(mouseStart.get('x'),mouseStart.get('y'),sideNum,radius);polygonArray.push(polygon);//レコード パス オブジェクト
以降のクリック操作では、対応する情報に基づいてクリック位置が経路上にあるかどうかを判断する必要がある。
クリック時にドラッグするオブジェクトを選択する方法まず、クリックされたときにcanvas中
対応する位置を取得します。私のコードでは、 mouseStart
使用してx
とy
次に、 polygonArray
内のpolygon
を走査し、走査中にpolygon.createPath()
を呼び出し、クリックされた位置にパスがあるかどうかをisPointInPath()
使用して判断します。存在する場合は、 draggingPolygon = polygon
関数が終了します。
const pos = PositionInCanvas(e, CanvasLeft, CanvasTop);//キャンバス内のピクセル位置を取得する//マウスの開始点を記録する smouseStart.set('x', pos.x);mouseStart.set('y', pos. y);...for (ポリゴンをポリゴン配列にする) {polygon.createPath(); (ctx.isPointInPath(mouseStart.get('x'),mouseStart.get('y'))) { ドラッグポリゴン = ポリゴン } }ドラッグ時の計算
この部分を十分に理解する必要があります。この段階では、 mousemove
段階にあり、関数が非常に頻繁にトリガーされるため、2 つのconsole.log(draggingPolygon)
とデモのコードに基づいてデバッグすることをお勧めします。
言葉でわかりやすく表現するように努めます
まず、 move
時のmouseStart
からの距離を計算します。これはdiffとして記録されます。x軸にoffsetX
、y軸にoffsetY
があります。
const pos = PositionInCanvas(e, CanvasLeft, CanvasTop), diff = new Map([ ['offsetX', pos.x - MouseStart.get('x')], ['offsetY', pos.y - MouseStart.get( 'y')] ]);
次に、現在のドラッグ オブジェクトのcenterX
とcenterY
を記録し、temp として記録します。
tempCenterX = ドラッグポリゴン.センターX、テンポセンターY = ドラッグポリゴン.センターY; とします。
これは理解するのが難しい点です。なぜ記録する必要があるのでしょうか。後で使用しますので、読み続けてください。
diff
のオフセットに従って、draggingPolygon の新しい中心位置を設定します。
ドラッグポリゴン.センターX += diff.get('オフセットX'); ドラッグポリゴン.センターY += ディフ.get('オフセットY');
次に、キャンバスをクリアして、新しいパスとストロークを描画します。
ctx.clearRect(0, 0, Canvas.width, Canvas.height);for (polygonArray のポリゴンにする) {drawPolygonPath(polygon.sideNum, Polygon.radius, Polygon.centerX, Polygon.centerY, ctx); );}
最後に、前述のtempCenterX
とtempCenterY
が使用されます。
ドラッグポリゴン.センターX = 一時センターX; ドラッグポリゴン.センターY = 一時センターY;
なぜこれを行う必要があるのでしょうか?
ドラッグは基于多边形的原位置
、この時点で回復がないと漂移
発生するため、 mousemove
ステージは不能确定函数的最终位置
。効果は次のとおりです。
私が明確にしていなかった場合は、コードを変更してデバッグすることを皆さんにお勧めします。
ドラッグ後の処理ドラッグが完了すると、 mouseup
段階になります。この時点で、dragginPolygon の最終位置を決定し、それを更新し、最後に在没有拖拽多边形情况下,鼠标在画布上移动触发对应代码
除外するために null に設定します。 在没有拖拽多边形情况下,鼠标在画布上移动触发对应代码
const pos = PositionInCanvas(e, CanvasLeft, CanvasTop), offsetMap = new Map([ ['offsetX', pos.x - MouseStart.get('x')], ['offsetY', pos.y - MouseStart.get( 'y')] ]); ドラッグポリゴン.centerX += offsetMap.get('offsetX'); offsetMap.get('offsetY'); ドラッグポリゴン = null;結論
実際、この機能の実装は難しくありません。概念を理解することが重要です。現在表示されているオブジェクトのリストを保持し、isPointInPath で判断することで追跡が実現されます。
最後に、皆さんの交流と学習を歓迎します
参考文献「HTML5 Canvasコアテクノロジー」
以上がこの記事の全内容です。皆様の学習のお役に立てれば幸いです。また、VeVb Wulin Network をご支援いただければ幸いです。