Note that there are some explanatory texts on larger screens.

plurals
  1. POHow to drag images / objects within Canvas after zooming / scaling them?
    primarykey
    data
    text
    <p>Following is my Complete code. Which is edited as per this link <a href="https://stackoverflow.com/questions/18333936/how-to-drag-images-objects-within-canvas/18342255#18342255">How to drag images / objects within Canvas?</a>.</p> <p><strong>Requirement :</strong></p> <p>Basically what I am doing is, First I am drawing SVG file on canvas with drawSvg with the help of canvg.</p> <p>On this file I am plotting images(green1.png and orange1.png) through JSON which is present in markers.js.</p> <p><strong>Scenario 1:</strong></p> <p>If I pan without Zooming/scaling then able to drag those images(green1.png, orange1.png) and able to pan canvas properly.</p> <p>But If I zoom after panning then images are not translating on proper position because of panX and panY points. But panX and panY are point we want for panning.</p> <p><strong>Scenario 2:</strong> :</p> <p>If I scale/zoom first and then if I pan then images(orange1.png, green1.png) are changing their position and not able to drag images (orange1.png, green1.png).</p> <p><strong>What can be done in these scenarios?</strong></p> <p>HTML Code :</p> <pre><code>&lt;!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"&gt; &lt;html xmlns="http://www.w3.org/1999/xhtml" lang="en" xml:lang="en"&gt; &lt;head&gt; &lt;script src="http://code.jquery.com/jquery-1.10.1.min.js"&gt;&lt;/script&gt; &lt;style&gt; canvas { border:1px solid #000 } .tooltip{ *position:fixed; position:absolute; *background:#ff7; background:green; border:1px solid #000; padding:7px; font-family:sans-serif; font-size:12px; } .tooltip2 { *position:fixed; position:absolute; background:pink; border:1px solid #000; padding:7px; font-family:sans-serif; font-size:12px; } &lt;/style&gt; &lt;/head&gt; &lt;body&gt; &lt;script src="http://canvg.googlecode.com/svn/trunk/rgbcolor.js"&gt;&lt;/script&gt; &lt;script src="http://canvg.googlecode.com/svn/trunk/StackBlur.js"&gt;&lt;/script&gt; &lt;script src="http://canvg.googlecode.com/svn/trunk/canvg.js"&gt;&lt;/script&gt; &lt;canvas id="myCanvas" width="800" height="700" style="border: 1px solid;margin-top: 10px;"&gt;&lt;/canvas&gt; &lt;div id="buttonWrapper"&gt; &lt;input type="button" id="plus" value="+"&gt; &lt;input type="button" id="minus" value="-"&gt; &lt;input type="button" id="original_size" value="100%"&gt; &lt;/div&gt; &lt;script src="/static/js/markers.js"&gt;&lt;/script&gt; &lt;script src="/static/js/draw.js"&gt;&lt;/script&gt; &lt;/body&gt; &lt;/html&gt; </code></pre> <p>draw.js:</p> <pre><code>var dataJSON = data || []; var dataJSON2 = data2 || []; window.onload = function(){ //$(function(){ var canvas=document.getElementById("myCanvas"); var ctx=canvas.getContext("2d"); var canvasOffset=$("#myCanvas").offset(); var offsetX=canvasOffset.left; var offsetY=canvasOffset.top; var lastX=0; var lastY=0; var panX=0; var panY=0; var dragging=[]; var dragging2=[]; var isDown=false; function loadImages(sources, callback){ var images = {}; var loadImages = 0; var numImages = 0; //get num of sources for(var i in sources){ numImages++; } for(var i in sources){ images[i] = new Image(); images[i].onload = function(){ if(++loadImages &gt;= numImages){ callback(images); } }; images[i].src = sources[i]; } } var sources = {orange : '/static/images/orange1.png', green : '/static/images/green1.png'}; // load the tiger image var svgfiles = ["/static/images/awesome_tiger.svg"]; /*var tiger=new Image(); tiger.onload=function(){ draw(); } tiger.src="tiger.png";*/ function draw(scaleValue){ ctx.clearRect(0,0,canvas.width,canvas.height); ctx.save(); ctx.drawSvg(svgfiles[0],panX,panY,400*scaleValue, 400*scaleValue); //ctx.drawImage(tiger,panX,panY,tiger.width,tiger.height); //ctx.scale(scaleValue, scaleValue); loadImages(sources, function(images){ ctx.scale(scaleValue, scaleValue); for(var i = 0, pos; pos = dataJSON[i]; i++) { ctx.drawImage(images.orange, parseInt(parseInt(pos.x) + parseInt(panX)), parseInt(parseInt(pos.y) + parseInt(panY)), 20/scaleValue, 20/scaleValue); } for(var i = 0, pos; pos = dataJSON2[i]; i++) { ctx.drawImage(images.green, parseInt(parseInt(pos.x) + parseInt(panX)), parseInt(parseInt(pos.y) + parseInt(panY)), 20/scaleValue, 20/scaleValue); } ctx.restore(); }); }; var scaleValue = 1; var scaleMultiplier = 0.8; draw(scaleValue); var startDragOffset = {}; var mouseDown = false; // add button event listeners document.getElementById("plus").addEventListener("click", function(){ scaleValue /= scaleMultiplier; //checkboxZoomPan(); draw(scaleValue); }, false); document.getElementById("minus").addEventListener("click", function(){ scaleValue *= scaleMultiplier; //checkboxZoomPan(); draw(scaleValue); }, false); document.getElementById("original_size").addEventListener("click", function(){ scaleValue = 1; //checkboxZoomPan(); draw(scaleValue); }, false); // create an array of any "hit" colored-images function imagesHitTests(x,y){ // adjust for panning x-=panX; y-=panY; // create var to hold any hits var hits=[]; // hit-test each image // add hits to hits[] loadImages(sources, function(images){ for(var i = 0, pos; pos = dataJSON[i]; i++) { if(x &gt;= parseInt(pos.x * scaleValue) &amp;&amp; x &lt;= parseInt((pos.x * scaleValue) + 20) &amp;&amp; y &gt;= parseInt(pos.y * scaleValue) &amp;&amp; y &lt;= parseInt((pos.y * scaleValue) + 20)){ hits.push(i); } } }); return(hits); } function imagesHitTests2(x,y){ // adjust for panning //x-=panX; //x = parseInt(x) - parseInt(panX); // y-=panY; x-=panX; y-=panY; // create var to hold any hits var hits2=[]; // hit-test each image // add hits to hits[] loadImages(sources, function(images){ for(var i = 0, pos; pos = dataJSON2[i]; i++) { //if(x &gt; pos.x &amp;&amp; x &lt; parseInt(parseInt(pos.x) + parseInt(20)) &amp;&amp; y &gt; pos.y &amp;&amp; y &lt; parseInt(parseInt(pos.y) + parseInt(20))){ if(x &gt;= parseInt(pos.x * scaleValue) &amp;&amp; x &lt;= parseInt((pos.x * scaleValue) + 20) &amp;&amp; y &gt;= parseInt(pos.y * scaleValue) &amp;&amp; y &lt;= parseInt((pos.y * scaleValue) + 20)){ hits2.push(i); } } }); return(hits2); } function handleMouseDown(e){ // get mouse coordinates mouseX=parseInt(e.clientX-offsetX); mouseY=parseInt(e.clientY-offsetY); // set the starting drag position lastX=mouseX; lastY=mouseY; // test if we're over any of the images dragging=imagesHitTests(mouseX,mouseY); dragging2=imagesHitTests2(mouseX,mouseY); // set the dragging flag isDown=true; } function handleMouseUp(e){ // clear the dragging flag isDown=false; } function handleMouseMove(e){ // if we're not dragging, exit if(!isDown){ return; } //get mouse coordinates mouseX=parseInt(e.clientX-offsetX); mouseY=parseInt(e.clientY-offsetY); // calc how much the mouse has moved since we were last here var dx=mouseX-lastX; var dy=mouseY-lastY; // set the lastXY for next time we're here lastX=mouseX; lastY=mouseY; // handle drags/pans if(dragging.length&gt;0){ // we're dragging images // move all affected images by how much the mouse has moved for(var i = 0, pos; pos = dataJSON[dragging[i]]; i++) { pos.x = parseInt(pos.x) + parseInt(dx); pos.y = parseInt(pos.y) + parseInt(dy); } } else if(dragging2.length&gt;0){ for(var i = 0, pos1; pos1 = dataJSON2[dragging2[i]]; i++) { pos1.x = parseInt(pos1.x) + parseInt(dx); pos1.y = parseInt(pos1.y) + parseInt(dy); } } else{ // we're panning the tiger // set the panXY by how much the mouse has moved panX+=dx; panY+=dy; } draw(scaleValue); } // use jQuery to handle mouse events $("#myCanvas").mousedown(function(e){handleMouseDown(e);}); $("#myCanvas").mousemove(function(e){handleMouseMove(e);}); $("#myCanvas").mouseup(function(e){handleMouseUp(e);}); // }); // end $(function(){}); } </code></pre> <p>markers.js:</p> <pre><code>data = [ { "id" :["first"], "x": ["195"], "y": ["150"], "tooltiptxt": ["Region 1"] }, { "id" :["second"], "x": ["255"], "y": ["180"], "tooltiptxt": ["Region 2"] }, { "id" :["third"], "x": ["200"], "y": ["240"], "tooltiptxt": ["Region 3"] } ]; data2 = [ { "id" :["first2"], "x": ["225"], "y": ["150"], "tooltiptxt": ["Region 21"] }, { "id" :["second2"], "x": ["275"], "y": ["180"], "tooltiptxt": ["Region 22"] }, { "id" :["third3"], "x": ["300"], "y": ["240"], "tooltiptxt": ["Region 23"] } ]; </code></pre>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload