Create links in HTML canvas
There is no easy way. You will have to draw the link text onto the canvas and then check for mouseclicks. Here is a demo html page:
<html>
<head>
<script type="text/javascript">
var canvas = document.getElementById("myCanvas");
var ctx;
var linkText="https://stackoverflow.com";
var linkX=5;
var linkY=15;
var linkHeight=10;
var linkWidth;
var inLink = false;
// draw the balls on the canvas
function draw(){
canvas = document.getElementById("myCanvas");
// check if supported
if(canvas.getContext){
ctx=canvas.getContext("2d");
//clear canvas
ctx.clearRect(0, 0, canvas.width, canvas.height);
//draw the link
ctx.font='10px sans-serif';
ctx.fillStyle = "#0000ff";
ctx.fillText(linkText,linkX,linkY);
linkWidth=ctx.measureText(linkText).width;
//add mouse listeners
canvas.addEventListener("mousemove", on_mousemove, false);
canvas.addEventListener("click", on_click, false);
}
}
//check if the mouse is over the link and change cursor style
function on_mousemove (ev) {
var x, y;
// Get the mouse position relative to the canvas element.
if (ev.layerX || ev.layerX == 0) { //for firefox
x = ev.layerX;
y = ev.layerY;
}
x-=canvas.offsetLeft;
y-=canvas.offsetTop;
//is the mouse over the link?
if(x>=linkX && x <= (linkX + linkWidth) && y<=linkY && y>= (linkY-linkHeight)){
document.body.style.cursor = "pointer";
inLink=true;
}
else{
document.body.style.cursor = "";
inLink=false;
}
}
//if the link has been clicked, go to link
function on_click(e) {
if (inLink) {
window.location = linkText;
}
}
</script>
</head>
<body onload="draw()">
<center>
<canvas id="myCanvas" width="200" height="200" style="border-style:solid;border-width:1px">Canvas not supported.</canvas>
</center>
</body>
</html>
Add Href to canvas element
You can test which hexagon you mouse clicked using context.isPointInPath
.
- Listen for mousedown events
- In mousedown, fetch the mouseX, mouseY
- Recreate each of your hex paths (no need to actually stroke/fill them).
- For each hex, use
.isPointInPath(mouseX,mouseY)
to see if the mouse clicked in this hex. - If you find a clicked hex, use
window.open(theUrl, '_blank')
to navigate to its associated url.
In Hexagon Tools, each hex has a points
property which you can use to receate each of your hex paths.
Here's example code and a Demo:
var canvas=document.getElementById("canvas");var ctx=canvas.getContext("2d");var cw=canvas.width;var ch=canvas.height;function reOffset(){ var BB=canvas.getBoundingClientRect(); offsetX=BB.left; offsetY=BB.top; }var offsetX,offsetY;reOffset();window.onscroll=function(e){ reOffset(); }window.onresize=function(e){ reOffset(); }
var isDown=false;var startX,startY;
var hexes=[];hexes.push({ points:[{x:57.5,y:63},{x:42.5,y:63},{x:35,y:50},{x:42.5,y:37},{x:57.5,y:37},{x:65,y:50}], url:'http://stackoverflow.com',});
draw();
$("#canvas").mousedown(function(e){handleMouseDown(e);});
function draw(){ for(var i=0;i<hexes.length;i++){ var h=hexes[i]; ctx.beginPath(); ctx.moveTo(h.points[0].x,h.points[0].y); for(var j=1;j<h.points.length;j++){ ctx.lineTo(h.points[j].x,h.points[j].y); } ctx.closePath(); ctx.stroke(); }}
function handleMouseDown(e){ // tell the browser we're handling this event e.preventDefault(); e.stopPropagation();
mouseX=parseInt(e.clientX-offsetX); mouseY=parseInt(e.clientY-offsetY);
for(var i=0;i<hexes.length;i++){ var h=hexes[i]; ctx.beginPath(); ctx.moveTo(h.points[0].x,h.points[0].y); for(var j=1;j<h.points.length;j++){ ctx.lineTo(h.points[j].x,h.points[j].y); } ctx.closePath(); //if(ctx.isPointInPath(mouseX,mouseY)){ window.open(h.url, '_blank'); } if(ctx.isPointInPath(mouseX,mouseY)){ alert('Navigate to: '+h.url); } }}
body{ background-color: ivory; }#canvas{border:1px solid red; margin:0 auto; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script><h4>Click in the hexagon to navigate to Stackoverflow.com</h4><canvas id="canvas" width=300 height=300></canvas>
How to add hyperlink to image in canvas element?
I got it working. Here is the [DEMO]
var canvas = document.getElementById("myCanvas");
var ctx;
var linkText="http://google.com";
var linkX=5;
var linkY=15;
var linkHeight=10;
var linkWidth;
var inLink = false;
// draw the balls on the canvas
function draw(){
canvas = document.getElementById("myCanvas");
// check if supported
if(canvas.getContext){
ctx=canvas.getContext("2d");
//clear canvas
ctx.clearRect(0, 0, canvas.width, canvas.height);
//draw the link
ctx.font='10px sans-serif';
ctx.fillStyle = "#0000ff";
ctx.fillText(linkText,linkX,linkY);
linkWidth=ctx.measureText(linkText).width;
//add mouse listeners
canvas.addEventListener("mousemove", on_mousemove, false);
canvas.addEventListener("click", on_click, false);
}
}
//check if the mouse is over the link and change cursor style
function on_mousemove (ev) {
var x, y;
// Get the mouse position relative to the canvas element.
if (ev.layerX || ev.layerX == 0) { //for firefox
x = ev.layerX;
y = ev.layerY;
}
x-=canvas.offsetLeft;
y-=canvas.offsetTop;
//is the mouse over the link?
if(x>=linkX && x <= (linkX + linkWidth) && y<=linkY && y>= (linkY-linkHeight)){
document.body.style.cursor = "pointer";
inLink=true;
}
else{
document.body.style.cursor = "";
inLink=false;
}
}
//if the link has been clicked, go to link
function on_click(e) {
if (inLink) {
window.location = linkText;
}
}
draw();
creating multiple links on html5 canvas
I can see a couple of problems here.
(1) you reset inLink to "" inside the loop. This means that if you hover over a link, remaining links in the loop will not be hovered over, and will reset inLink to "" - fix = set inLink to "" once, before the loop (you can't hover over more than one link at a time, so it can only be set once inside the loop)
(2) You've inconsistently 'spelt' inLink
. - fix = ensure capitalization is the same for all instances of the variable (inLink is different to inlink)
(3) The placement of brackets in the check if you're over a link has the potential to be ambiguous.
(4) By using links.length in the for loop, it needs to be recalculated each time through the loop. A better approach is to read this value once and store it in a temporary variable.
Here's a rough example of the code working just fine, as tested in Chrome (no FF here, unfortunately)
Note: I've also added the break
to discontinue the loop if a hovered link is found - there's no need to check the remaining ones in the loop if you find one successfully. (This speeds up execution, while also achieving the same effect as point #1)
Note2: It is faster to iterate through the loop from n-1 to 0, as you had initially done - I just prefer to go forwards.
<!DOCTYPE html>
<html>
<head>
<script>
function byId(e){return document.getElementById(e);}
window.addEventListener('load', onDocLoaded, false);
function onDocLoaded()
{
outlineLinks();
byId('can').addEventListener("mousemove", on_mousemove, false);
// byId('can').addEventListener("click", on_click2, false);
byId('can').addEventListener("click", on_click, false);
}
// var link = ["websitelink1", "websitelink2"];
var link = ["http://stackoverflow.com/questions/24650947/creating-multiple-links-on-html5-canvas/24652217", "http://stackoverflow.com/"];
var links = [[0,0,100,20],[0,25,100,20]];
var inLink = "";
function outlineLinks()
{
var canvas = byId('can');
var ctx = canvas.getContext('2d');
var i, n = links.length;
for (i=0; i<n; i++)
ctx.strokeRect( links[i][0], links[i][1], links[i][2], links[i][3] );
}
function on_mousemove(evt)
{
var mouse_x, mouse_y;
// Get the mouse position relative to the canvas element.
if (evt.layerX || evt.layerX)
{ //for firefox
mouse_x = evt.layerX;
mouse_y = evt.layerY;
}
mouse_x -= this.offsetLeft;
mouse_y -= this.offsetTop;
byId('coords').innerHTML = "Mouse Pos: " + mouse_x + "," + mouse_y;
var n = links.length;
inLink = "";
for(i=0; i<n; i++)
{
var linkX = parseInt(links[i][0]),
linkY = parseInt(links[i][1]),
linkwidth = parseInt(links[i][2]),
linkheight = parseInt(links[i][3]);
//is the mouse over the link?
if( (mouse_x >= linkX) && (mouse_x <= (linkX + linkwidth)) && (mouse_y >= linkY) && (mouse_y <= (linkY + linkheight)))
{
document.body.style.cursor = "pointer";
inLink = link[i];
break;
}
else{
document.body.style.cursor = "";
}
}
}
function on_click(evt)
{
if (inLink != "")
window.open(inLink);
}
function on_click2(evt)
{
if (inLink != "")
byId('tgt').innerHTML = "Navigating to: " + inLink;
else
byId('tgt').innerHTML = "No link is hovered";
}
</script>
<style>
</style>
</head>
<body>
<div id='tgt'> </div>
<div id='coords'> </div>
<canvas id='can'></canvas>
</body>
</html>
Adding a link to a dynamic canvas
I have managed to click on a certain element in a canvas.
I have tried to explain with comments what it does.
I have made 3 limits as shown in the image below.
And I'm comparing only with x value, if it's in between these limits. It can be more complex so getCursorPosition()
method returns an object with x and y components, just in case if you need to make more comparisons.
https://jsfiddle.net/_jserodio/asa10pye/
var canvas; var ctx;
// first get your canvas canvas = document.getElementById('canvas'); canvas.width = 253; canvas.heigth = 68;
// assign the context ctx = canvas.getContext("2d");
// asign click event to the canvas addEventListener("click", listener, false);
function listener(e) { // if you have 3 buttons var position = getCursorPosition(e);
var limit1 = canvas.width / 3; //console.log("limit1: " + limit1); var limit2 = canvas.width * 2 / 3; //console.log("limit2: " + limit2); var limit3 = canvas.width; //console.log("limit3: " + limit3);
if (position.x < limit1) { console.log("go to facebook"); //window.open("http://www.facebook.com"); } else if (position.x < limit2) { console.log("go to twitter"); //window.open("http://www.twitter.com"); } else if (position.x < limit3) { console.log("go to whatsapp"); //window.open("http://www.whatsapp.com"); }
//console.log("\nx" + position.x); //console.log("y" + position.y); }
function getCursorPosition(event) { var rect = canvas.getBoundingClientRect(); var x = event.clientX - rect.left; var y = event.clientY - rect.top; var data = { x: x, y: y }; return data; }
// load image from data url var imageObj = new Image(); imageObj.onload = function() { ctx.drawImage(this, 0, 0); };
imageObj.src = 'https://justpaste.it/files/justpaste/d307/a11791570/file1.png';
<canvas id='canvas' width="253" height="68">
</canvas>
Related Topics
Understanding CSS2.1 Specification Regarding Height on Inline-Level Boxes
How to Have Two Items on Opposite Sides on The Same Line
An Url to a Windows Shared Folder
Why Would The Height Increase with a Smaller Font Size
Items That Span All Columns/Rows Using CSS Grid Layout
How to Extract Data from HTML Table in Shell Script
Adding Icon to Rails Application
Height: 100% for <Div> Inside <Div> with Display: Table-Cell
2 Colors in One Placeholder of Input Field
How to Add a Highlight Behind The Text via CSS So It Looks Like Instagram-One Below
Can You Have a <Span> Within a <Span>
Can't Show Some Websites in Iframe Tag
HTMLagilitypack Drops Option End Tags
Add External CSS File to Blogger Template