167 lines
4.6 KiB
HTML
167 lines
4.6 KiB
HTML
<!DOCTYPE html>
|
|
<html>
|
|
<head>
|
|
<meta charset="utf-8">
|
|
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
|
|
<title>ping.clerie.de</title>
|
|
<style>
|
|
#canvas {
|
|
width: 100%;
|
|
height: 100%;
|
|
display: block;
|
|
position: fixed;
|
|
top: 0;
|
|
left: 0;
|
|
z-index: -9999;
|
|
}
|
|
</style>
|
|
</head>
|
|
<body>
|
|
<h1>ping.clerie.de</h1>
|
|
<span id="audio_toggle">🕨</span>
|
|
<canvas id="canvas" width="500" height="50"></canvas>
|
|
<ul id="ping">
|
|
</ul>
|
|
<p><small>Is it already broken yet? <a href="https://git.clerie.de/clerie/ping.clerie.de">Host yourself :3</a></small></p>
|
|
|
|
<script>
|
|
function httpGet(url, loaded, error) {
|
|
var xmlHttp = new XMLHttpRequest();
|
|
xmlHttp.open("GET", url + ((/\?/).test(url) ? "&" : "?") + (new Date()).getTime(), true);
|
|
xmlHttp.onload = () => {
|
|
loaded();
|
|
};
|
|
xmlHttp.onerror = () => {error();};
|
|
xmlHttp.send(null);
|
|
}
|
|
|
|
function displayPing(text) {
|
|
document.getElementById("ping").innerHTML += "<li>" + text + "</li>";
|
|
}
|
|
|
|
let ac;
|
|
let gain;
|
|
let osc;
|
|
let withAudio = false;
|
|
|
|
let audio_toggle = document.getElementById("audio_toggle");
|
|
|
|
audio_toggle.onclick = () => {
|
|
if (!withAudio) {
|
|
ac = new AudioContext();
|
|
|
|
osc = ac.createOscillator();
|
|
gain = ac.createGain();
|
|
|
|
osc.connect(gain);
|
|
gain.connect(ac.destination)
|
|
|
|
gain.gain.setValueAtTime(0, ac.currentTime);
|
|
osc.start();
|
|
|
|
audio_toggle.innerText = "🕪";
|
|
withAudio = true;
|
|
} else {
|
|
osc.stop();
|
|
audio_toggle.innerText = "🕨";
|
|
withAudio = false;
|
|
}
|
|
}
|
|
|
|
let playing = false;
|
|
|
|
function beepOn() {
|
|
if (!playing) {
|
|
if (withAudio) {
|
|
gain.gain.setValueCurveAtTime([0,1], ac.currentTime, 0.08);
|
|
}
|
|
playing = true;
|
|
}
|
|
}
|
|
|
|
function beepOff() {
|
|
if (playing) {
|
|
if (withAudio) {
|
|
gain.gain.setValueCurveAtTime([1,0], ac.currentTime, 0.08);
|
|
}
|
|
playing = false;
|
|
}
|
|
}
|
|
|
|
let reachability = [];
|
|
let reachability_size = 10;
|
|
|
|
let cv = document.getElementById("canvas");
|
|
cv.width = window.innerWidth;
|
|
cv.height = window.innerHeight;
|
|
let ctx = canvas.getContext('2d');
|
|
let zoom = 10;
|
|
|
|
function resizeCanvas() {
|
|
cv.width = window.innerWidth;
|
|
cv.height = window.innerHeight;
|
|
}
|
|
|
|
window.onresize = resizeCanvas;
|
|
|
|
function plotLoop() {
|
|
let currentTime = (new Date()).getTime();
|
|
ctx.lineWidth = 4;
|
|
ctx.clearRect(0, 0, cv.width, cv.height);
|
|
ctx.beginPath();
|
|
if (reachability.length >= 1 && reachability[reachability.length-1][1] === undefined) {
|
|
ctx.moveTo(cv.width - ((currentTime - reachability[reachability.length-1][0]) / zoom), cv.height/2);
|
|
} else {
|
|
ctx.moveTo(cv.width, cv.height/2);
|
|
}
|
|
for (let i = reachability.length-1; i > 0; i--) {
|
|
if (reachability[i][0] !== undefined) {
|
|
ctx.lineTo(cv.width - ((currentTime - reachability[i][1]) / zoom), cv.height/2);
|
|
}
|
|
ctx.moveTo(cv.width - ((currentTime - reachability[i][0]) / zoom), cv.height/2);
|
|
|
|
if (cv.width - ((currentTime - reachability[i][0]) / zoom) < 0) {
|
|
reachability_size = reachability.length - i;
|
|
break;
|
|
}
|
|
}
|
|
ctx.lineTo(0, cv.height/2);
|
|
ctx.stroke();
|
|
window.requestAnimationFrame(plotLoop);
|
|
}
|
|
|
|
function loop() {
|
|
setTimeout(() => {
|
|
beepOn();
|
|
let startTime = (new Date()).getTime();
|
|
if (reachability.length > reachability_size-1) {
|
|
reachability = reachability.slice(-reachability_size-1);
|
|
}
|
|
reachability.push([startTime, undefined]);
|
|
httpGet("https://ip6.clerie.de/",
|
|
() => {
|
|
let endTime = (new Date()).getTime();
|
|
reachability[reachability.length-1][1] = endTime;
|
|
let rtt = endTime - startTime;
|
|
if (rtt < 1000) {
|
|
setTimeout(() => {
|
|
beepOff();
|
|
loop();
|
|
}, 1000 - rtt);
|
|
} else {
|
|
loop();
|
|
}
|
|
},
|
|
() => {
|
|
loop();
|
|
}
|
|
);
|
|
}, 1000);
|
|
}
|
|
|
|
loop();
|
|
window.requestAnimationFrame(plotLoop);
|
|
</script>
|
|
</body>
|
|
</html>
|