123 lines
3.6 KiB
HTML
123 lines
3.6 KiB
HTML
<!DOCTYPE html>
|
|
<title>base32 color</title>
|
|
<link rel="preconnect" href="https://fonts.googleapis.com" />
|
|
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
|
|
<link
|
|
href="https://fonts.googleapis.com/css2?family=Atkinson+Hyperlegible&display=swap"
|
|
rel="stylesheet"
|
|
/>
|
|
<script
|
|
src="https://cdnjs.cloudflare.com/ajax/libs/gl-matrix/3.4.2/gl-matrix-min.js"
|
|
referrerpolicy="no-referrer"
|
|
></script>
|
|
<style>
|
|
:root {
|
|
font-family: "Atkinson Hyperlegible", sans-serif;
|
|
background-color: black;
|
|
color: #efefef;
|
|
}
|
|
|
|
section {
|
|
padding: 2em;
|
|
}
|
|
|
|
#color-box {
|
|
width: 300px;
|
|
height: 300px;
|
|
background-color: var(--color);
|
|
}
|
|
</style>
|
|
|
|
<noscript>
|
|
unfortunately we need javascript to do math, please enable <333
|
|
</noscript>
|
|
<main>
|
|
<section>colors are hot</section>
|
|
<section>
|
|
<form id="form">
|
|
<input id="input" type="text" maxlength="9" value="girltwink" />
|
|
</form>
|
|
<label for="input">9 character word (case insensitive)</label>
|
|
<button id="update">update</button>
|
|
</section>
|
|
<section>
|
|
<div id="color-box"></div>
|
|
<ul>
|
|
<li id="rgb">rgb(-1,-1,-1)</li>
|
|
<li id="hex">#HHHHHH</li>
|
|
<li id="rgb2">high precision rgb(-1,-1,-1)</li>
|
|
</ul>
|
|
</section>
|
|
<section>
|
|
<p>warning: math</p>
|
|
<p>
|
|
a 9-character single-case string could be interpreted as 3 triplets of
|
|
base32. this allows for a 0-46655 range per channel!
|
|
</p>
|
|
<ol>
|
|
<li>our example "girltwink" turns into (gir, ltw, ink)</li>
|
|
<li>which turns into decimal (21411, 28292, 24176)</li>
|
|
<li>
|
|
we change this to linear by dividing by 46655 ( 0.45892187332547424,
|
|
0.6064087450434037, 0.5181866895295253 )
|
|
</li>
|
|
<li>
|
|
and then up to 8 bit 0-255 ( 117.02507769799593, 154.63422998606794,
|
|
132.13760583002895 )
|
|
</li>
|
|
<li>
|
|
but probably too precise of a color :3 so <b>( 117, 155, 132 )</b>
|
|
</li>
|
|
</ol>
|
|
</section>
|
|
</main>
|
|
|
|
<script>
|
|
const inputEl = document.querySelector("#input");
|
|
const updateEl = document.querySelector("#update");
|
|
const colorBoxEl = document.querySelector("#color-box");
|
|
const hexEl = document.querySelector("#hex");
|
|
const rgbEl = document.querySelector("#rgb");
|
|
const rgb2El = document.querySelector("#rgb2");
|
|
|
|
const setColor = (r, g, b) => {
|
|
colorBoxEl.setAttribute("style", `--color: rgb(${r}, ${g}, ${b})`);
|
|
hexEl.innerHTML = `#${(
|
|
Math.round(r).toString(16).padStart(2, "0") +
|
|
Math.round(g).toString(16).padStart(2, "0") +
|
|
Math.round(b).toString(16).padStart(2, "0")
|
|
).toLowerCase()}`;
|
|
rgbEl.innerHTML = `rgb(${Math.round(r)}, ${Math.round(g)}, ${Math.round(
|
|
b
|
|
)})`;
|
|
rgb2El.innerHTML = `highp rgb(${r}, ${g}, ${b})`;
|
|
};
|
|
|
|
const base32to8bit = (b32) => (parseInt(b32, 36) / 46655) * 255;
|
|
|
|
const inputToColor = (inputRaw) => {
|
|
const input = inputRaw + "000000000";
|
|
// Input will be 0-9A-Z,
|
|
const r = base32to8bit(input.substr(0, 3));
|
|
const g = base32to8bit(input.substr(3, 3));
|
|
const b = base32to8bit(input.substr(6, 3));
|
|
|
|
return { r, g, b };
|
|
};
|
|
|
|
const onUpdate = (event) => {
|
|
console.log("onUpdate", { event, inputEl });
|
|
const { r, g, b } = inputToColor(event.target.value);
|
|
setColor(r, g, b);
|
|
};
|
|
|
|
setTimeout(() => {
|
|
onUpdate({ target: document.querySelector("#input") });
|
|
});
|
|
|
|
inputEl.addEventListener("keyup", onUpdate);
|
|
inputEl.addEventListener("change", onUpdate);
|
|
inputEl.addEventListener("keypress", onUpdate);
|
|
inputEl.addEventListener("blur", onUpdate);
|
|
update.addEventListener("click", onUpdate.bind(null, { target: inputEl }));
|
|
</script>
|