CCCPaste

COmpREss.html.txt

<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width,initial-scale=1" />
<title>21-bit to Integer Converter</title>
<style>
body { font-family: system-ui, -apple-system, "Segoe UI", Roboto, "Helvetica Neue", Arial; margin: 24px; color:#111; }
h1 { margin-bottom: 8px; }
.card { border:1px solid #e1e4e8; border-radius:8px; padding:16px; max-width:820px; background:#fff; box-shadow:0 1px 2px rgba(0,0,0,0.03); }
label { display:block; margin-bottom:8px; font-weight:600; }
input[type="text"] { width:100%; padding:10px 12px; font-size:16px; border:1px solid #cbd5e1; border-radius:6px; box-sizing:border-box; }
button { margin-top:12px; padding:8px 12px; font-size:15px; border-radius:6px; border:0; background:#0366d6; color:#fff; cursor:pointer; }
button.secondary { background:#6b7280; }
.error { color:#b91c1c; margin-top:8px; }
pre { background:#f6f8fa; padding:12px; border-radius:6px; overflow:auto; }
.steps { margin-top:12px; }
.result { margin-top:12px; font-weight:700; font-size:18px; }
.small { font-size:13px; color:#374151; }
.row { display:flex; gap:8px; align-items:center; margin-top:8px; }
.copy { background:#10b981; }
</style>
</head>
<body>
<div class="card">
<h1>21-bit to Integer Converter</h1>
<div class="small">Enter exactly 21 bits. The app follows your rule set and subtracts 1,000,000 at the end.</div>

<label for="bits">Bits</label>
<input id="bits" type="text" placeholder="e.g. 010101001110000111000" maxlength="21" />
<div class="row">
<button id="compute">Compute</button>
<button id="example" class="secondary">Fill Example</button>
<button id="copy" class="copy">Copy Result</button>
</div>
<div id="error" class="error" role="status" aria-live="polite"></div>

<div id="output" class="steps" aria-live="polite"></div>
</div>

<script>
const bitsInput = document.getElementById('bits');
const computeBtn = document.getElementById('compute');
const exampleBtn = document.getElementById('example');
const copyBtn = document.getElementById('copy');
const errorEl = document.getElementById('error');
const outputEl = document.getElementById('output');

function validateBits(s) {
if (!s) return 'Input is empty';
if (s.length !== 21) return 'Input must be exactly 21 bits';
if (!/^[01]{21}$/.test(s)) return 'Input must contain only 0 and 1';
return '';
}

function computeFromBits(bitString) {
// Use BigInt for safety with large intermediate values
const MILLION = 1000000n;
const bits = bitString.split('').map(b => b === '1' ? 1 : 0);

// initial value
let value = bits[0] === 0 ? 2n : 3n;
const trace = [];
trace.push({ step: 0, bit: bits[0], op: `start`, value: value.toString() });

for (let i = 1; i < bits.length; i++) {
const b = bits[i];
if (b === 0) {
value = value * 2n;
trace.push({ step: i, bit: 0, op: `×2`, value: value.toString() });
} else {
value = value * 2n - 1n;
trace.push({ step: i, bit: 1, op: `×2 − 1`, value: value.toString() });
}
}

const finalBeforeSubtract = value;
const finalAfterSubtract = value - MILLION;
return { trace, finalBeforeSubtract: finalBeforeSubtract.toString(), finalAfterSubtract: finalAfterSubtract.toString() };
}

function renderResult(resultObj) {
const { trace, finalBeforeSubtract, finalAfterSubtract } = resultObj;
let html = '';
html += '<div class="small"><strong>Trace</strong></div>';
html += '<pre>';
html += 'Step Bit Operation Value\n';
html += '---- --- --------- ----------------\n';
trace.forEach(t => {
const step = String(t.step).padEnd(4, ' ');
const bit = String(t.bit).padEnd(3, ' ');
const op = String(t.op).padEnd(9, ' ');
const val = t.value;
html += `${step} ${bit} ${op} ${val}\n`;
});
html += '</pre>';

html += `<div class="result"><strong>Value before subtracting 1,000,000</strong>: ${finalBeforeSubtract}</div>`;
html += `<div class="result"><strong>Final output</strong>: ${finalAfterSubtract}</div>`;

outputEl.innerHTML = html;
}

computeBtn.addEventListener('click', () => {
errorEl.textContent = '';
outputEl.innerHTML = '';
const s = bitsInput.value.trim();
const v = validateBits(s);
if (v) {
errorEl.textContent = v;
return;
}
try {
const result = computeFromBits(s);
renderResult(result);
} catch (err) {
errorEl.textContent = 'Computation error';
console.error(err);
}
});

exampleBtn.addEventListener('click', () => {
// Example 21-bit string
bitsInput.value = '010101001110000111000';
errorEl.textContent = '';
outputEl.innerHTML = '';
});

copyBtn.addEventListener('click', async () => {
const out = outputEl.innerText || '';
if (!out) {
errorEl.textContent = 'Nothing to copy';
return;
}
try {
await navigator.clipboard.writeText(out);
errorEl.textContent = 'Result copied to clipboard';
setTimeout(() => { errorEl.textContent = ''; }, 2000);
} catch (e) {
errorEl.textContent = 'Copy failed';
}
});

// allow Enter to compute
bitsInput.addEventListener('keydown', (e) => {
if (e.key === 'Enter') {
computeBtn.click();
}
});
</script>
</body>
</html>