Created
September 24, 2018 18:25
-
-
Save Ferdi265/5f3004a9efcdd2e4c40064465774f691 to your computer and use it in GitHub Desktop.
Name Slider Thingy
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!DOCTYPE html> | |
<html> | |
<head> | |
<meta charset="utf-8"> | |
<title>Name Slider Thingy</title> | |
<style type="text/css"> | |
#name { | |
margin-left: 1em; | |
} | |
.content { | |
border: 1px solid black; | |
width: 300px; | |
margin: 20vh auto auto auto; | |
padding: 1em; | |
border-radius: .5em; | |
text-align: center; | |
} | |
</style> | |
</head> | |
<body> | |
<div class="content"> | |
<div>Name: <input id="name" type="text"></div> | |
<canvas id="canvas" width="200" height="200"></canvas> | |
</div> | |
<script type="text/javascript"> | |
'use strict'; | |
const canvasEl = document.getElementById("canvas"); | |
const nameEl = document.getElementById("name"); | |
const ctx = canvasEl.getContext("2d"); | |
const sliderState = { | |
angle: 3*Math.PI/2, | |
direction: null, | |
text: "" | |
}; | |
ctx.strokeStyle = "black"; | |
ctx.fillStyle = "grey"; | |
ctx.font = "12px Arial"; | |
ctx.textBaseline = "middle"; | |
ctx.textAlign = "center"; | |
function base() { | |
ctx.clearRect(0, 0, 200, 200); | |
ctx.beginPath(); | |
ctx.arc(100, 100, 80, 0, 2*Math.PI); | |
ctx.stroke(); | |
ctx.beginPath(); | |
ctx.arc(100, 100, 40, 0, 2*Math.PI); | |
ctx.stroke(); | |
for (let i = 0; i < 26; i++) { | |
let a = 3*Math.PI/2 + 2*Math.PI/26*i; | |
ctx.fillText(String.fromCharCode(0x41 + i), 100+60*Math.cos(a), 100+60*Math.sin(a)); | |
} | |
} | |
function slider(angle) { | |
base(); | |
ctx.beginPath(); | |
ctx.arc(100, 100, 80, angle - Math.PI/7, angle - Math.PI/7); | |
ctx.arc(100, 100, 40, angle - Math.PI/7, angle - Math.PI/7); | |
ctx.stroke(); | |
ctx.beginPath(); | |
ctx.arc(100, 100, 80, angle + Math.PI/7, angle + Math.PI/7); | |
ctx.arc(100, 100, 40, angle + Math.PI/7, angle + Math.PI/7); | |
ctx.stroke(); | |
ctx.beginPath(); | |
ctx.arc(100, 100, 80, angle - Math.PI/7, angle + Math.PI/7); | |
ctx.arc(100, 100, 40, angle + Math.PI/7, angle - Math.PI/7, true); | |
ctx.closePath(); | |
ctx.fill(); | |
} | |
function getPos(e) { | |
let rect = canvas.getBoundingClientRect(); | |
return { | |
x: e.clientX - rect.left - document.documentElement.scrollLeft - 100, | |
y: e.clientY - rect.top - document.documentElement.scrollTop - 100 | |
}; | |
} | |
function getAngle(pos) { | |
let a = Math.atan(pos.y / pos.x); | |
if (pos.x < 0) { | |
return a + Math.PI; | |
} else { | |
return a; | |
} | |
} | |
function getRadius(pos) { | |
return Math.sqrt((pos.x * pos.x) + (pos.y * pos.y)); | |
} | |
function clampAngle(a) { | |
return a - Math.floor(a / (2*Math.PI)) * 2*Math.PI; | |
} | |
function isOnSlider(pos, sliderAngle) { | |
let a = clampAngle(getAngle(pos)); | |
let r = getRadius(pos); | |
let sliderLeftNormLeftA = clampAngle(sliderAngle - Math.PI/7); | |
let sliderLeftNormRightA = sliderLeftNormLeftA + 2*Math.PI/7; | |
let sliderRightNormRightA = clampAngle(sliderAngle + Math.PI/7); | |
let sliderRightNormLeftA = sliderRightNormRightA - 2*Math.PI/7; | |
return (r > 40) && (r < 80) && (((a > sliderLeftNormLeftA) && (a < sliderLeftNormRightA)) || ((a > sliderRightNormLeftA) && (a < sliderRightNormRightA))); | |
} | |
function getCharIdx(a) { | |
a = clampAngle(a - 3*Math.PI/2); | |
let l = a / (2*Math.PI/26); | |
let c = Math.round(l) % 26; | |
return c; | |
} | |
function onMouseMove(e) { | |
let p = getPos(e); | |
let a = clampAngle(getAngle(p)); | |
let c_old = getCharIdx(sliderState.angle); | |
let c_new = getCharIdx(a); | |
if (c_old !== c_new) { | |
let dir; | |
if (c_old > 17 && c_new < 9) { | |
dir = 1; | |
} else if (c_new > 17 && c_old < 9) { | |
dir = -1; | |
} else { | |
dir = Math.sign(c_new - c_old); | |
} | |
if (sliderState.direction === null) { | |
sliderState.direction = dir; | |
} else if (sliderState.direction !== dir) { | |
sliderState.text += String.fromCharCode(c_old + 0x41); | |
sliderState.direction = dir; | |
} | |
} | |
sliderState.angle = a; | |
slider(a); | |
nameEl.value = sliderState.text + String.fromCharCode(c_new + 0x41); | |
} | |
canvasEl.onmousedown = function (e) { | |
let p = getPos(e); | |
if (isOnSlider(p, sliderState.angle)) { | |
canvasEl.onmousemove = onMouseMove; | |
sliderState.direction = null; | |
sliderState.text = ""; | |
console.log("grabbing"); | |
} | |
}; | |
canvasEl.onmouseup = function (e) { | |
console.log("ungrabbing"); | |
canvasEl.onmousemove = null; | |
}; | |
slider(sliderState.angle); | |
</script> | |
</body> | |
</html> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment