2011-12-06 10 views
2

Creating an HTML 5 canvas painting applicationに基づいて、私はHTML5キャンバスペインティングアプリケーションを作成しました。それは正常に動作しますが、各オブジェクトを作成した後、オブジェクトをドラッグするだけです。 Working demoHTML5キャンバスペインティングアプリケーションのドラッグ&ドロップの実装方法は?

数字のドラッグアンドドロップの実装方法は?

答えて

2

のソースコードと

チェックアウトは、彼らのデモあなたが自分でアンドゥ/リドゥを処理する必要がありますlibに「生」としてラファエルを使用している場合。 graphiti libにはUndo/Redo Stackがあり、SVG、PNG、JSONのエクスポートをサポートしています...

さらにVisoのようなコネクタやポートがあります。

http://www.draw2d.org/graphiti/jsdoc/#!/example

挨拶

3

ユーザーがキャンバスをクリックすると、座標を確認し(オブジェクトの座標と比較して)、オブジェクト上にあるかどうかを確認する必要があります。例えば。ポイント(でもマウスダウンのために例えば座標)は、このメソッドの円内にあるかどうかをテストすることができます:

function (pt) { 
    return Math.pow(pt.x - point.x,2) + Math.pow(pt.y - point.y,2) < 
                  Math.pow(radius,2); 
}; 

をマウスダウンがオブジェクト上にある場合は、あなたがオブジェクトを変更する必要がどのようにマウスに従って座標移動される。

<!DOCTYPE html> 
<html> 
<head> 
<script> 
window.onload = function() { 
    drawCircle(circle); 
    element = document.getElementById('canvas'); 
    element.addEventListener('mousedown', startDragging, false); 
    element.addEventListener('mousemove', drag, false); 
    element.addEventListener('mouseup', stopDragging, false); 
    element.addEventListener('mouseout', stopDragging, false); 
} 

function mouseX(e) { 
return e.clientX - element.offsetLeft; 
} 

function mouseY(e) { 
return e.clientY - element.offsetTop; 
} 

var Point = function (x, y) { 
    this.x = x; 
    this.y = y; 
    return this; 
} 

var Circle = function (point, radius) { 
    this.point = point; 
    this.radius = radius; 
    this.isInside = function (pt) { 
     return Math.pow(pt.x - point.x, 2) + Math.pow(pt.y - point.y, 2) < 
                  Math.pow(radius, 2); 
    }; 
    return this; 
} 

function startDragging(e) { 
    var p = new Point(e.offsetX, e.offsetY); 
    if(circle.isInside(p)) { 
     deltaCenter = new Point(p.x - circle.point.x, p.y - circle.point.y); 
    } 
} 

function drag(e) { 
    if(deltaCenter != null) { 
     circle.point.x = (mouseX(e) - deltaCenter.x); 
     circle.point.y = (mouseY(e) - deltaCenter.y); 
     drawCircle(circle); 
    } 
} 

function stopDragging(e) { 
    deltaCenter = null; 
} 

function drawCircle(circle) { 
    var canvas = document.getElementById('canvas'); 
    var ctx = canvas.getContext('2d'); 
    ctx.clearRect(0, 0, canvas.width, canvas.height); 
    ctx.beginPath(); 
    ctx.arc(circle.point.x, circle.point.y, circle.radius, 0, Math.PI*2, true); 
    ctx.fill(); 
} 

var circle = new Circle(new Point(30, 40), 25); 
var deltaCenter = null; 
var element; 

</script> 
</head> 
<body> 
<canvas id="canvas" width="400" height="300"></canvas> 
</body> 
</html> 

は、私がこれを行う簡単な方法はないと思うjsFiddle

+0

こんにちはジョナス..返事に感謝し、どのような形状の座標を取得しますか? – ramesh

+0

@rajeeesh:あなたは自分でそれを保存する必要があります。 – Jonas

+0

こんにちは、これは私が画像を追加するために使用している関数です...どのようにcoordingtesを保存するには? this.mouseup = function(ev){ if(tool.started){ tool.mousemove(ev); var x = ev._x-28; var y = ev._y-28; var imageObj = new Image(); imageObj.onload = function(){ var p = context.drawImage(imageObj、x、y); };imageObj.src = "test.png"; tool.started = false; img_update(); } }; – ramesh

1

上でそれを試してみてください。ここで

は、あなたが円をドラッグすることができる。例えば、あります。

もしあなたが単に行を扱っているのであれば、私のアプローチは、作成されたすべての行、開始座標、終了座標、およびある種のz-インデックスを追跡することです。ユーザーがドラッグ操作(マウスをクリック)を開始すると、その点が線の近くにあるかどうかを確認してから、オブジェクトを更新し、マウスが移動したときにキャンバスを再描画する必要があります。

How can I tell if a point belongs to a certain line?

あなたがが複雑なオブジェクトを扱っている場合、これは多くの複雑になります。ポイントがパス内にあるかどうかを確認するソリューションを見つける必要があります。

1

HTML5キャンバスに描画されたオブジェクトは、ピクセルに変換されて忘れられます。それらのプロパティーを調整したり、キャンバスを更新してその効果を見ることはできません。キャンバスにはこれらのピクセルが設定されているので、基本的にキャンバス全体(または少なくとも一部)をプロパティを調整するときに再描画する必要があります。

代わりに、このアプリケーションではSVGを考慮する必要があります.SVG要素はDOMに保存され、プロパティが更新されるとブラウザは変更を反映するようにグラフィックを更新します。

キャンバスを使用する必要がある場合は、マウスヒット、オブジェクトプロパティ、および再描画を処理するためのかなりのコードを書く必要があります。

+0

こんにちはジェームズはあなたの返事に感謝し、サンプルやチュートリアルはありますか?アプリケーションを再コーディングする必要がありますか、それとも私の要件に合わせてアップグレードできますか? ありがとうございました – ramesh

+1

私の頭の上から私はその種のものの例やチュートリアルとのリンクを知らない。 Paper.jsやKineticJSのような、キャンバスの周りのベクトルグラフィックラッパーで、読書を開始するのに適したライブラリがあります。あなたはどちらかの方法で何らかのコードを書かなければならないと思いますが、ライブラリを使用している場合は多分そうではないかもしれません。 SVGは大きな変更になり、独自のベクトルグラフィックスコードを書くことも大きな変更になります。 –

+1

Srikanthが指摘しているように、Raphael.jsはベクトルグラフィックスライブラリでもありますが、SVGを使用し、バックエンドとしてはキャンバスを使用していません。 –

3

同様の効果がJoint.jShttp://www.jointjs.com/)とRaphaël.jsのhttp://raphaeljs.com/)を用いて達成することができます。

Raphaelで作成した図形は、DOM要素と同様にアクセスでき、属性を使用して操作できます。素晴らしいフレームワークです。

Joint.jsはシェイプの接続に役立ちます。彼らにはダイアグラムライブラリもあり、ERD、Statemachineおよびいくつかの一般的な図の作成に役立ちます。最も重要な点は、ダイアグラム要素を拡張して独自のカスタム要素を作成できることです。その顎は落ち着いて冷静です。http://www.jointjs.com/demos

関連する問題