কোনও ক্যানভাস উপাদানটিতে ক্লিক ইভেন্ট হ্যান্ডলার যুক্ত করার সহজ উপায় কী যা ক্লিকের x এবং y স্থানাঙ্ক ফেরত দেবে (ক্যানভাস উপাদানটির সাথে সম্পর্কিত)?
কোনও লিগ্যাসি ব্রাউজারের সামঞ্জস্যতা প্রয়োজন নেই, সাফারি, অপেরা এবং ফায়ারফক্স করবে।
কোনও ক্যানভাস উপাদানটিতে ক্লিক ইভেন্ট হ্যান্ডলার যুক্ত করার সহজ উপায় কী যা ক্লিকের x এবং y স্থানাঙ্ক ফেরত দেবে (ক্যানভাস উপাদানটির সাথে সম্পর্কিত)?
কোনও লিগ্যাসি ব্রাউজারের সামঞ্জস্যতা প্রয়োজন নেই, সাফারি, অপেরা এবং ফায়ারফক্স করবে।
উত্তর:
2018 সম্পাদনা করুন: এই উত্তরটি বেশ পুরানো এবং এটি বর্তমান ব্রাউজারগুলিতে clientXএবং clientYবৈশিষ্ট্যগুলির কাজ হিসাবে পুরানো ব্রাউজারগুলির জন্য চেকগুলি ব্যবহার করে যা আর প্রয়োজন হয় না । আপনি আরও সহজ এবং সাম্প্রতিক সমাধানের জন্য প্যাট্রিক্স উত্তরটি পরীক্ষা করতে চাইতে পারেন ।
আসল উত্তর:
একটি নিবন্ধে বর্ণিত হিসাবে আমি পরে খুঁজে পেয়েছি তবে এটি আর নেই:
var x;
var y;
if (e.pageX || e.pageY) {
x = e.pageX;
y = e.pageY;
}
else {
x = e.clientX + document.body.scrollLeft + document.documentElement.scrollLeft;
y = e.clientY + document.body.scrollTop + document.documentElement.scrollTop;
}
x -= gCanvasElement.offsetLeft;
y -= gCanvasElement.offsetTop;
আমার জন্য পুরোপুরি সূক্ষ্ম কাজ।
আপনি যদি সরলতা পছন্দ করেন তবে তবুও ক্রস ব্রাউজার কার্যকারিতা চান তবে আমার কাছে এই সমাধানটি সবচেয়ে ভাল কাজ করেছে। এটি @ অ্যালডেকাইনের সমাধানের সরলিকরণ যা jQuery ছাড়াই ।
function getCursorPosition(canvas, event) {
const rect = canvas.getBoundingClientRect()
const x = event.clientX - rect.left
const y = event.clientY - rect.top
console.log("x: " + x + " y: " + y)
}
const canvas = document.querySelector('canvas')
canvas.addEventListener('mousedown', function(e) {
getCursorPosition(canvas, e)
})
getBoundingClientRectভিউ বন্দরের তুলনায় অবস্থানগুলি ফেরত দেবে? তখন আমার অনুমানটি ভুল ছিল was আমি কখনই এটি পরীক্ষা করে দেখিনি যেহেতু এটি আমার পক্ষে কখনও সমস্যা ছিল না, এবং আমি দয়া করে অন্য পাঠকদেরকে দেখলাম এমন একটি সম্ভাব্য সমস্যা সম্পর্কে সতর্ক করতে চেয়েছিলাম, তবে আপনার স্পষ্টতার জন্য আপনাকে ধন্যবাদ।
var canvas = document.getElementById('canvasID'); canvas.addEventListener("mousedown", function (e) { getCursorPosition(canvas, e);});
আপডেট (5/5/16): পিতৃস্থানীয়দের উত্তর পরিবর্তে ব্যবহার করা উচিত, কারণ এটি উভয়ই সহজ এবং আরও নির্ভরযোগ্য।
যেহেতু ক্যানভাস সর্বদা পুরো পৃষ্ঠার তুলনায় স্টাইল করা হয় না, তাই canvas.offsetLeft/Topআপনার প্রয়োজনীয় জিনিসটি সর্বদা ফিরে আসে না। এটি তার অফসেট প্যারেন্ট এলিমেন্টের তুলনায় অফসেট হওয়া পিক্সেলের সংখ্যা ফিরিয়ে দেবে, যা স্টাইল প্রয়োগ divকরে ক্যানভাস যুক্ত উপাদানগুলির মতো কিছু হতে পারে position: relative। এটির জন্য অ্যাকাউন্ট করতে আপনার offsetParentনিজের ক্যানভাস উপাদান দিয়ে শুরু করে s এর চেইনটি দিয়ে লুপ করতে হবে । এই কোডটি আমার পক্ষে নিখুঁতভাবে কাজ করে, ফায়ারফক্স এবং সাফারিতে পরীক্ষিত তবে সবার জন্য কাজ করা উচিত।
function relMouseCoords(event){
var totalOffsetX = 0;
var totalOffsetY = 0;
var canvasX = 0;
var canvasY = 0;
var currentElement = this;
do{
totalOffsetX += currentElement.offsetLeft - currentElement.scrollLeft;
totalOffsetY += currentElement.offsetTop - currentElement.scrollTop;
}
while(currentElement = currentElement.offsetParent)
canvasX = event.pageX - totalOffsetX;
canvasY = event.pageY - totalOffsetY;
return {x:canvasX, y:canvasY}
}
HTMLCanvasElement.prototype.relMouseCoords = relMouseCoords;
শেষ লাইনটি ক্যানভাস উপাদানের সাথে মাউস স্থানাঙ্ক পাওয়ার জন্য জিনিসগুলিকে সুবিধাজনক করে তুলেছে। দরকারী স্থানাঙ্কগুলি পাওয়ার জন্য যা প্রয়োজন তা হ'ল
coords = canvas.relMouseCoords(event);
canvasX = coords.x;
canvasY = coords.y;
event.offsetXএবং event.offsetYবৈশিষ্ট্য, তাই আমি যুক্ত করে আপনার সমাধানটি পরিবর্তন করেছি if (event.offsetX !== undefined && event.offsetY !== undefined) { return {x:event.offsetX, y:event.offsetY}; }। দেখে মনে হচ্ছে এটি কাজ করে।
event.offsetXএবং event.offsetYযা IE9 কাজ করে। ফায়ারফক্সের জন্য (পরীক্ষিত ডাব্লু / ভি 13) আপনি event.layerXএবং ব্যবহার করতে পারেন event.layerY।
canvasX = event.pageX - totalOffsetX - document.body.scrollLeft; canvasY = event.pageY - totalOffsetY - document.body.scrollTop;
আধুনিক ব্রাউজারটি এখন আপনার জন্য এটি পরিচালনা করে। ক্লিক হ্যান্ডলার থেকে ইভেন্টটি পেরিয়ে ক্রোম, আইই 9 এবং ফায়ারফক্স এইভাবে অফসেটএক্স / ওয়াই সমর্থন করে।
function getRelativeCoords(event) {
return { x: event.offsetX, y: event.offsetY };
}
বেশিরভাগ আধুনিক ব্রাউজারগুলি লেয়ারএক্স / ওয়াই সমর্থন করে, তবে ক্রোম এবং আইই ফায়ারফক্সে লেয়ারএক্স / ওয়াই এবং অফসেটএক্স / ওয়াই সমতুল্য পাতায় মার্জিন, প্যাডিং সহ পৃষ্ঠায় ক্লিকের নিখুঁত অফসেটের জন্য লেয়ারএক্স / ওয়াই ব্যবহার করে তবে অফসেট করা হয়নি এর আগে উপস্থিত ছিল না। সুতরাং, সামান্য পুরানো ব্রাউজারগুলির সাথে সামঞ্জস্যের জন্য, আপনি এটি ব্যবহার করতে পারেন:
function getRelativeCoords(event) {
return { x: event.offsetX || event.layerX, y: event.offsetY || event.layerY };
}
তাজা মতে QuirksmodeclientX এবং clientYপদ্ধতি সমস্ত প্রধান ব্রাউজারে সমর্থিত। সুতরাং, এটি এখানে যায় - ভাল, কার্যকরী কোড যা স্ক্রোলবারগুলির সাথে কোনও পৃষ্ঠায় একটি স্ক্রোলিং ডিভিতে কাজ করে:
function getCursorPosition(canvas, event) {
var x, y;
canoffset = $(canvas).offset();
x = event.clientX + document.body.scrollLeft + document.documentElement.scrollLeft - Math.floor(canoffset.left);
y = event.clientY + document.body.scrollTop + document.documentElement.scrollTop - Math.floor(canoffset.top) + 1;
return [x,y];
}
এই প্রয়োজন jQuery এর জন্য $(canvas).offset()।
আমি একটি সম্পূর্ণ ডিমেস্টেরেশন তৈরি করেছি যা প্রতিটি ব্রাউজারে এই সমস্যার সমাধানের সম্পূর্ণ উত্স কোড সহ কাজ করে: জাভাস্ক্রিপ্টে ক্যানভাসে মাউসের ক্লিকের সমন্বয়কারী । ডেমো চেষ্টা করার জন্য, কোডটি অনুলিপি করুন এবং এটি একটি পাঠ্য সম্পাদকের মধ্যে আটকান। তারপরে এটিকে উদাহরণ। Html হিসাবে সংরক্ষণ করুন এবং শেষ পর্যন্ত একটি ব্রাউজার দিয়ে ফাইলটি খুলুন।
ভেরিয়েবল (%) প্রস্থ সহ ক্যানভ্যাসগুলির জন্য রায়ান আর্তেকোনার জবাবটিতে এখানে একটি ছোট্ট পরিবর্তন রয়েছে :
HTMLCanvasElement.prototype.relMouseCoords = function (event) {
var totalOffsetX = 0;
var totalOffsetY = 0;
var canvasX = 0;
var canvasY = 0;
var currentElement = this;
do {
totalOffsetX += currentElement.offsetLeft;
totalOffsetY += currentElement.offsetTop;
}
while (currentElement = currentElement.offsetParent)
canvasX = event.pageX - totalOffsetX;
canvasY = event.pageY - totalOffsetY;
// Fix for variable canvas width
canvasX = Math.round( canvasX * (this.width / this.offsetWidth) );
canvasY = Math.round( canvasY * (this.height / this.offsetHeight) );
return {x:canvasX, y:canvasY}
}
সমন্বয় রূপান্তর করার সময় সতর্ক থাকুন; ক্লিক ইভেন্টে একাধিক নন-ক্রস-ব্রাউজারের মান ফিরে এসেছে। ব্রাউজার উইন্ডোটি স্ক্রোল করা থাকলে (ফায়ারফক্স 3.5 এবং Chrome 3.0 এ যাচাই করা হয়েছে) ক্লায়েন্টএক্স এবং ক্লায়েন্টওয়াই একা ব্যবহার করা যথেষ্ট নয়।
এই quirks মোড নিবন্ধটি আরও সঠিক ফাংশন সরবরাহ করে যা ডকুমেন্টের মূল সাথে সম্পর্কিত ক্লিক স্থানাঙ্ক গণনা করতে ডকুমেন্ট.body.scrolLeft এবং ক্লায়েন্টওয়্যারের সাথে পেজএক্স বা পেজওয়াই বা ক্লায়েন্টএক্সের সংমিশ্রণ ব্যবহার করতে পারে।
আপডেট: অতিরিক্তভাবে, অফসেট লেফট এবং অফসেটটপ উপাদানটির প্যাডযুক্ত আকারের সাথে সম্পর্কিত, অভ্যন্তরের আকার নয়। প্যাডিং সহ একটি ক্যানভাস: শৈলী প্রয়োগ করা হয়েছে এটির সামগ্রীর অঞ্চলের উপরের-বামটিকে অফসেট লেফট হিসাবে প্রতিবেদন করবে না। এই সমস্যার বিভিন্ন সমাধান রয়েছে; সবচেয়ে সহজ হতে পারে ক্যানভাসে সমস্ত বর্ডার, প্যাডিং ইত্যাদি স্টাইলগুলি সাফ করা এবং পরিবর্তে ক্যানভাসযুক্ত বাক্সে এগুলি প্রয়োগ করা।
আমি নিশ্চিত নই যে এই সমস্ত উত্তরের মূল বিষয়টি যা পিতামাতার উপাদানগুলির মধ্য দিয়ে লুপ করে দেয় এবং সমস্ত ধরণের অদ্ভুত স্টাফ করে ।
HTMLElement.getBoundingClientRectপদ্ধতি কোনো উপাদান প্রকৃত পর্দা অবস্থান হ্যান্ডেল করতে ডিজাইন করা হয়েছে। এর মধ্যে স্ক্রোলিং অন্তর্ভুক্ত রয়েছে, সুতরাং এর মতো জিনিসগুলির scrollTopপ্রয়োজন হয় না:
(এমডিএন থেকে) সীমাবদ্ধ আয়তক্ষেত্রটি গণনা করার সময়ভিউপোর্ট অঞ্চল (বা অন্য কোনও স্ক্রোলযোগ্য উপাদান )দিয়ে স্ক্রলিংয়ের পরিমাণটি বিবেচনায় নেওয়া হয়
খুব সহজ পদ্ধতির ইতিমধ্যে এখানে পোস্ট করা হয়েছে। যতক্ষণ কোনও বুনো সিএসএসের বিধি জড়িত না হয় এটি সঠিক ।
চিত্রের পিক্সেলের প্রস্থ এটির সিএসএস প্রস্থের সাথে মিলে না গেলে, আপনাকে পিক্সেল মানগুলিতে কিছু অনুপাত প্রয়োগ করতে হবে:
/* Returns pixel coordinates according to the pixel that's under the mouse cursor**/
HTMLCanvasElement.prototype.relativeCoords = function(event) {
var x,y;
//This is the current screen rectangle of canvas
var rect = this.getBoundingClientRect();
var top = rect.top;
var bottom = rect.bottom;
var left = rect.left;
var right = rect.right;
//Recalculate mouse offsets to relative offsets
x = event.clientX - left;
y = event.clientY - top;
//Also recalculate offsets of canvas is stretched
var width = right - left;
//I use this to reduce number of calculations for images that have normal size
if(this.width!=width) {
var height = bottom - top;
//changes coordinates by ratio
x = x*(this.width/width);
y = y*(this.height/height);
}
//Return as an array
return [x,y];
}
যতক্ষণ না ক্যানভাসের কোনও সীমানা নেই, এটি প্রসারিত চিত্রগুলির জন্য কাজ করে (জেএসফিডাল) ।
ক্যানভাসের ঘন সীমানা থাকলে জিনিসগুলি কিছুটা জটিল হয়ে যায় । আক্ষরিকভাবে আপনাকে সীমানাটি আয়তক্ষেত্র থেকে বিয়োগ করতে হবে। এটি .getComputesStyle ব্যবহার করে করা যেতে পারে । এই উত্তর প্রক্রিয়া বর্ণনা করে ।
ফাংশনটি তখন কিছুটা বড় হয়:
/* Returns pixel coordinates according to the pixel that's under the mouse cursor**/
HTMLCanvasElement.prototype.relativeCoords = function(event) {
var x,y;
//This is the current screen rectangle of canvas
var rect = this.getBoundingClientRect();
var top = rect.top;
var bottom = rect.bottom;
var left = rect.left;
var right = rect.right;
//Subtract border size
// Get computed style
var styling=getComputedStyle(this,null);
// Turn the border widths in integers
var topBorder=parseInt(styling.getPropertyValue('border-top-width'),10);
var rightBorder=parseInt(styling.getPropertyValue('border-right-width'),10);
var bottomBorder=parseInt(styling.getPropertyValue('border-bottom-width'),10);
var leftBorder=parseInt(styling.getPropertyValue('border-left-width'),10);
//Subtract border from rectangle
left+=leftBorder;
right-=rightBorder;
top+=topBorder;
bottom-=bottomBorder;
//Proceed as usual
...
}
আমি এই চূড়ান্ত ফাংশনকে বিভ্রান্ত করবে এমন কোনও কিছুই ভাবতে পারি না। জেএসফিডেলে নিজেকে দেখুন ।
আপনি নেটিভ পরিবর্তন পছন্দ না হয় prototypeগুলি শুধু ফাংশন পরিবর্তন এবং সঙ্গে এটি কল (canvas, event)(এবং কোনো প্রতিস্থাপন thisসঙ্গে canvas)।
এখানে একটি খুব সুন্দর টিউটোরিয়াল-
http://www.html5canvastutorials.com/advanced/html5-canvas-mouse-coordinates/
<canvas id="myCanvas" width="578" height="200"></canvas>
<script>
function writeMessage(canvas, message) {
var context = canvas.getContext('2d');
context.clearRect(0, 0, canvas.width, canvas.height);
context.font = '18pt Calibri';
context.fillStyle = 'black';
context.fillText(message, 10, 25);
}
function getMousePos(canvas, evt) {
var rect = canvas.getBoundingClientRect();
return {
x: evt.clientX - rect.left,
y: evt.clientY - rect.top
};
}
var canvas = document.getElementById('myCanvas');
var context = canvas.getContext('2d');
canvas.addEventListener('mousemove', function(evt) {
var mousePos = getMousePos(canvas, evt);
var message = 'Mouse position: ' + mousePos.x + ',' + mousePos.y;
writeMessage(canvas, message);
}, false);
আশাকরি এটা সাহায্য করবে!
width/ heightওভারডিডেনযুক্ত চিত্রগুলির সাথে কাজ করে না তবে এখনও সেরা সমাধানগুলির মধ্যে একটি।
ক্যানভাসের তুলনায় ২০১ coord সালে jQuery ব্যবহার করে ক্লিক স্থানাঙ্কগুলি পেতে, আমি এটি করি:
$(canvas).click(function(jqEvent) {
var coords = {
x: jqEvent.pageX - $(canvas).offset().left,
y: jqEvent.pageY - $(canvas).offset().top
};
});
এটি কাজ করে যেহেতু ক্যানভাস অফসেট () এবং jqEvent.pageX / Y উভয়ই স্ক্রোল অবস্থান নির্বিশেষে নথির সাথে সম্পর্কিত।
মনে রাখবেন যে আপনার ক্যানভাসটি যদি ছোট করে রাখা হয় তবে এই স্থানাঙ্কগুলি ক্যানভাস লজিক্যাল স্থানাঙ্কের মতো নয় । সেগুলি পেতে, আপনি এটিও করতে পারেন:
var logicalCoords = {
x: coords.x * (canvas.width / $(canvas).width()),
y: coords.y * (canvas.height / $(canvas).height())
}
সুতরাং এটি উভয়ই সহজ তবে এটি মনে হচ্ছে কিছু জটিল বিষয়।
প্রথমে এখানে সাধারণত বিবাদযুক্ত প্রশ্নগুলি রয়েছে
উপাদান সম্পর্কিত আপেক্ষিক মাউস স্থানাঙ্কগুলি কীভাবে পাবেন
2D ক্যানভাস এপিআই বা ওয়েবজিএলের জন্য ক্যানভাস পিক্সেল মাউস স্থানাঙ্কগুলি কীভাবে পাবেন
সুতরাং, উত্তর
উপাদানটি একটি ক্যানভাসের উপাদান সম্পর্কিত মাউস স্থানাঙ্কগুলি পেতে কিনা তা সমস্ত উপাদানগুলির জন্য একই।
"ক্যানভাস আপেক্ষিক মাউস স্থানাঙ্ক কিভাবে পাবেন" প্রশ্নের 2 টি সহজ উত্তর রয়েছে
offsetXএবংoffsetYcanvas.addEventListner('mousemove', (e) => {
const x = e.offsetX;
const y = e.offsetY;
});
এই উত্তরটি ক্রোম, ফায়ারফক্স এবং সাফারিতে কাজ করে। অন্যান্য ইভেন্ট ইভেন্টের মতো নয় offsetXএবং offsetYসিএসএস রূপান্তরগুলি অ্যাকাউন্টে নিন।
সঙ্গে সবচেয়ে বড় সমস্যা offsetXএবং offsetY2019/05 এর হিসাবে তারা স্পর্শ ইভেন্টের উপস্থিত না থাকার এবং তাই আইওএস সাফারি সঙ্গে ব্যবহার করা যেতে পারে। এটি পয়েন্টার ইভেন্টগুলিতে রয়েছে যা ক্রোম এবং ফায়ারফক্সে বিদ্যমান তবে সাফারি নয় যদিও দৃশ্যত সাফারি এতে কাজ করছে ।
আরেকটি বিষয় হ'ল ঘটনাগুলি ক্যানভাসে থাকা উচিত। আপনি যদি এগুলিকে অন্য কোনও উপাদান বা উইন্ডোতে রাখেন তবে পরে আপনার রেফারেন্স হিসাবে আপনি ক্যানভাসটি বেছে নিতে পারবেন না।
clientX, clientYএবংcanvas.getBoundingClientRectআপনি সিএসএস রূপান্তরগুলির যত্ন সম্পর্কে না করে পরের সহজ উত্তর থেকে কল হল canvas. getBoundingClientRect()থেকে বাম এবং বিয়োগ clientXএবং topথেকে clientYহিসেবে
canvas.addEventListener('mousemove', (e) => {
const rect = canvas.getBoundingClientRect();
const x = e.clientX - rect.left;
const y = e.clientY - rect.top;
});
এটি যতক্ষণ না সিএসএস রূপান্তরগুলি থাকবে ততক্ষণ কাজ করবে। এটি স্পর্শ ইভেন্টগুলির সাথেও কাজ করে এবং তাই সাফারি আইওএসের সাথেও কাজ করবে
canvas.addEventListener('touchmove', (e) => {
const rect = canvas. getBoundingClientRect();
const x = e.touches[0].clientX - rect.left;
const y = e.touches[0].clientY - rect.top;
});
এর জন্য আমাদের আমাদের যে মানগুলি পেয়েছে সেগুলি গ্রহণ করতে হবে এবং ক্যানভাসটি যে আকার থেকে ক্যানভাস প্রদর্শিত হবে তা থেকে ক্যানভাসের পিক্সেলের সংখ্যায় রূপান্তর করতে হবে
সঙ্গে canvas.getBoundingClientRectএবং clientXএবংclientY
canvas.addEventListener('mousemove', (e) => {
const rect = canvas.getBoundingClientRect();
const elementRelativeX = e.clientX - rect.left;
const elementRelativeY = e.clientY - rect.top;
const canvasRelativeX = elementRelativeX * canvas.width / rect.width;
const canvasRelativeY = elementRelativeY * canvas.height / rect.height;
});
বা সাথে offsetXএবংoffsetY
canvas.addEventListener('mousemove', (e) => {
const elementRelativeX = e.offsetX;
const elementRelativeX = e.offsetY;
const canvasRelativeX = elementRelativeX * canvas.width / canvas.clientWidth;
const canvasRelativeY = elementRelativeX * canvas.height / canvas.clientHeight;
});
কাজ করে উদাহরণ ব্যবহার করে event.offsetX,event.offsetY
ব্যবহার করে উদাহরণস্বরূপ canvas.getBoundingClientRectএবং event.clientXএবংevent.clientY
আমি এই লিঙ্কটি প্রস্তাব দিই- http://miloq.blogspot.in/2011/05/coordinates-mouse-click-canvas.html
<style type="text/css">
#canvas{background-color: #000;}
</style>
<script type="text/javascript">
document.addEventListener("DOMContentLoaded", init, false);
function init()
{
var canvas = document.getElementById("canvas");
canvas.addEventListener("mousedown", getPosition, false);
}
function getPosition(event)
{
var x = new Number();
var y = new Number();
var canvas = document.getElementById("canvas");
if (event.x != undefined && event.y != undefined)
{
x = event.x;
y = event.y;
}
else // Firefox method to get the position
{
x = event.clientX + document.body.scrollLeft +
document.documentElement.scrollLeft;
y = event.clientY + document.body.scrollTop +
document.documentElement.scrollTop;
}
x -= canvas.offsetLeft;
y -= canvas.offsetTop;
alert("x: " + x + " y: " + y);
}
</script>
x = new Number()? নীচে যে কোডটি পুনরায় xবরাদ্দ করা হয়েছে তার অর্থ বরাদ্দ করা নম্বরটি তাত্ক্ষণিকভাবে বাতিল করা হয়েছে
প্রোটোটাইপে, উপরের রায়ান আরটেকোনা দ্বারা উল্লিখিত পুনরাবৃত্ত সমষ্টি করতে संचयी অফসেট () ব্যবহার করুন।
আপনি ঠিক করতে পারেন:
var canvas = yourCanvasElement;
var mouseX = (event.clientX - (canvas.offsetLeft - canvas.scrollLeft)) - 2;
var mouseY = (event.clientY - (canvas.offsetTop - canvas.scrollTop)) - 2;
এটি আপনাকে মাউস পয়েন্টারটির সঠিক অবস্থান দেবে।
ডেমোটি দেখুন http://jsbin.com/ApuJOSA/1/edit?html , আউটপুট ।
function mousePositionOnCanvas(e) {
var el=e.target, c=el;
var scaleX = c.width/c.offsetWidth || 1;
var scaleY = c.height/c.offsetHeight || 1;
if (!isNaN(e.offsetX))
return { x:e.offsetX*scaleX, y:e.offsetY*scaleY };
var x=e.pageX, y=e.pageY;
do {
x -= el.offsetLeft;
y -= el.offsetTop;
el = el.offsetParent;
} while (el);
return { x: x*scaleX, y: y*scaleY };
}
উপরের রায়ান আর্তেকোনার সমাধানের কিছু পরিবর্তন এখানে দেওয়া হল।
function myGetPxStyle(e,p)
{
var r=window.getComputedStyle?window.getComputedStyle(e,null)[p]:"";
return parseFloat(r);
}
function myGetClick=function(ev)
{
// {x:ev.layerX,y:ev.layerY} doesn't work when zooming with mac chrome 27
// {x:ev.clientX,y:ev.clientY} not supported by mac firefox 21
// document.body.scrollLeft and document.body.scrollTop seem required when scrolling on iPad
// html is not an offsetParent of body but can have non null offsetX or offsetY (case of wordpress 3.5.1 admin pages for instance)
// html.offsetX and html.offsetY don't work with mac firefox 21
var offsetX=0,offsetY=0,e=this,x,y;
var htmls=document.getElementsByTagName("html"),html=(htmls?htmls[0]:0);
do
{
offsetX+=e.offsetLeft-e.scrollLeft;
offsetY+=e.offsetTop-e.scrollTop;
} while (e=e.offsetParent);
if (html)
{
offsetX+=myGetPxStyle(html,"marginLeft");
offsetY+=myGetPxStyle(html,"marginTop");
}
x=ev.pageX-offsetX-document.body.scrollLeft;
y=ev.pageY-offsetY-document.body.scrollTop;
return {x:x,y:y};
}
প্রথমত, অন্যরা যেমন বলেছে, ক্যানভাস উপাদানটির অবস্থান পেতে আপনার একটি ফাংশন প্রয়োজন । এই পৃষ্ঠার অন্য কিছু (আইএমএইচও) এর চেয়ে কিছুটা মার্জিত একটি পদ্ধতি এখানে। আপনি এটিকে যে কোনও উপাদানটি পাস করতে পারেন এবং নথিতে তার অবস্থান পেতে পারেন :
function findPos(obj) {
var curleft = 0, curtop = 0;
if (obj.offsetParent) {
do {
curleft += obj.offsetLeft;
curtop += obj.offsetTop;
} while (obj = obj.offsetParent);
return { x: curleft, y: curtop };
}
return undefined;
}
এখন এর সাথে সম্পর্কিত কার্সারের বর্তমান অবস্থান গণনা করুন:
$('#canvas').mousemove(function(e) {
var pos = findPos(this);
var x = e.pageX - pos.x;
var y = e.pageY - pos.y;
var coordinateDisplay = "x=" + x + ", y=" + y;
writeCoordinateDisplay(coordinateDisplay);
});
লক্ষ্য করুন যে আমি জেনেরিক findPosফাংশনটিকে ইভেন্ট হ্যান্ডলিং কোড থেকে আলাদা করেছি । ( যেমনটি হওয়া উচিত) We আমাদের প্রতিটি কাজকে একটি করে রাখার চেষ্টা করা উচিত))
এর মানগুলি offsetLeftএবং offsetTopএর সাথে সম্পর্কিত offsetParent, যা কিছু মোড়কের divনোড (বা অন্য কোনও কিছু, সে ক্ষেত্রে হতে পারে )। যখন কোনও উপাদান মোড়ানো না থাকে canvasসেগুলি তারা সম্পর্কিত হয় body, তাই বিয়োগ করার কোনও অফসেট নেই। এ কারণেই আমাদের অন্য কিছু করার আগে আমাদের ক্যানভাসের অবস্থান নির্ধারণ করা দরকার।
অনুরূপ, e.pageXএবং e.pageYনথির সাথে সম্পর্কিত কার্সারের অবস্থান দিন। সে কারণেই আমরা সত্য অবস্থানে পৌঁছানোর জন্য ক্যানভাসের অফসেটটি সেই মানগুলি থেকে বিয়োগ করে।
একটা বিকল্প স্থান উপাদান সরাসরি মান ব্যবহার করা e.layerXএবং e.layerY। এটি দুটি কারণের জন্য উপরের পদ্ধতির চেয়ে কম নির্ভরযোগ্য:
থ্রিজেএস আর 77
var x = event.offsetX == undefined ? event.layerX : event.offsetX;
var y = event.offsetY == undefined ? event.layerY : event.offsetY;
mouse2D.x = ( x / renderer.domElement.width ) * 2 - 1;
mouse2D.y = - ( y / renderer.domElement.height ) * 2 + 1;
অনেক সমাধান চেষ্টা করার পরে। এটি আমার পক্ষে কাজ করেছে। অন্য কারও জন্য পোস্ট করতে সহায়তা করতে পারে। এখান থেকে পেয়েছি
এখানে একটি সরলিকৃত সমাধান (এটি সীমানা / স্ক্রোলিংয়ের সাথে কাজ করে না):
function click(event) {
const bound = event.target.getBoundingClientRect();
const xMult = bound.width / can.width;
const yMult = bound.height / can.height;
return {
x: Math.floor(event.offsetX / xMult),
y: Math.floor(event.offsetY / yMult),
};
}
আমি একটি পিডিএফ-এর উপর ক্যানভাসযুক্ত একটি অ্যাপ্লিকেশন তৈরি করছিলাম , এতে পিডিএফ-ইন এবং আউট জুম করার মতো ক্যানভাসের অনেক আকার পরিবর্তন করা হয়েছিল এবং পিডিএফ-এর প্রতিটি জুম-ইন / আউট চালু করার জন্য আমাকে ক্যানভাসটির আকার পরিবর্তন করতে হয়েছিল পিডিএফ আকার, আমি স্ট্যাকওভারফ্লোতে প্রচুর উত্তর দিয়েছি, এবং একটি নিখুঁত সমাধান খুঁজে পাইনি যা শেষ পর্যন্ত সমস্যার সমাধান করবে।
আমি rxjs এবং কৌণিক 6 ব্যবহার করছিলাম , এবং নতুন সংস্করণে নির্দিষ্ট কোনও উত্তর খুঁজে পাইনি found
ক্যানভাসের শীর্ষে আঁকতে rxjs উপার্জনকারী যে কোনও ব্যক্তির পক্ষে এখানে পুরো কোড স্নিপেটটি সহায়ক হবে ।
private captureEvents(canvasEl: HTMLCanvasElement) {
this.drawingSubscription = fromEvent(canvasEl, 'mousedown')
.pipe(
switchMap((e: any) => {
return fromEvent(canvasEl, 'mousemove')
.pipe(
takeUntil(fromEvent(canvasEl, 'mouseup').do((event: WheelEvent) => {
const prevPos = {
x: null,
y: null
};
})),
takeUntil(fromEvent(canvasEl, 'mouseleave')),
pairwise()
)
})
)
.subscribe((res: [MouseEvent, MouseEvent]) => {
const rect = this.cx.canvas.getBoundingClientRect();
const prevPos = {
x: Math.floor( ( res[0].clientX - rect.left ) / ( rect.right - rect.left ) * this.cx.canvas.width ),
y: Math.floor( ( res[0].clientY - rect.top ) / ( rect.bottom - rect.top ) * this.cx.canvas.height )
};
const currentPos = {
x: Math.floor( ( res[1].clientX - rect.left ) / ( rect.right - rect.left ) * this.cx.canvas.width ),
y: Math.floor( ( res[1].clientY - rect.top ) / ( rect.bottom - rect.top ) * this.cx.canvas.height )
};
this.coordinatesArray[this.file.current_slide - 1].push(prevPos);
this.drawOnCanvas(prevPos, currentPos);
});
}
এবং এখানে স্নিপেট যা স্থির করে দেয়, মাউস ক্যানভাসের আকারের সাথে তুলনা করে আপনি ক্যানভাসটিকে কীভাবে জুম-ইন / আউট করেন তা নির্বিশেষে।
const prevPos = {
x: Math.floor( ( res[0].clientX - rect.left ) / ( rect.right - rect.left ) * this.cx.canvas.width ),
y: Math.floor( ( res[0].clientY - rect.top ) / ( rect.bottom - rect.top ) * this.cx.canvas.height )
};
const currentPos = {
x: Math.floor( ( res[1].clientX - rect.left ) / ( rect.right - rect.left ) * this.cx.canvas.width ),
y: Math.floor( ( res[1].clientY - rect.top ) / ( rect.bottom - rect.top ) * this.cx.canvas.height )
};
আরে, এটি ডোজোতে রয়েছে, একটি প্রকল্পের জন্য ইতিমধ্যে আমার কোড যা ছিল তা ঘটান।
এটি কীভাবে নন ডোজো ভ্যানিলা জাভাস্ক্রিপ্টে রূপান্তর করতে হবে তা মোটামুটি স্পষ্ট হওয়া উচিত।
function onMouseClick(e) {
var x = e.clientX;
var y = e.clientY;
}
var canvas = dojo.byId(canvasId);
dojo.connect(canvas,"click",onMouseClick);
আশা করি এইটি কাজ করবে.