Learn session forecasts from training blocks and clarify progress UI
This commit is contained in:
@@ -0,0 +1,39 @@
|
||||
/* Delegation survives HTMX swaps; all readout values are plain text. */
|
||||
(() => {
|
||||
if (window.workoutForecastEvents) return;
|
||||
window.workoutForecastEvents = true;
|
||||
function inspect(hit) {
|
||||
const panel = hit.closest('.exercise-progress');
|
||||
if (!panel) return;
|
||||
for (const key of ['kind', 'date', 'e1rm', 'topset', 'range']) {
|
||||
const field = panel.querySelector(`[data-readout="${key}"]`);
|
||||
if (field) field.textContent = hit.dataset[key];
|
||||
}
|
||||
const cursor = panel.querySelector('.forecast-cursor');
|
||||
if (cursor) {
|
||||
cursor.setAttribute('x1', hit.dataset.position);
|
||||
cursor.setAttribute('x2', hit.dataset.position);
|
||||
}
|
||||
panel.querySelectorAll('.forecast-hit').forEach(p => p.removeAttribute('data-selected'));
|
||||
hit.dataset.selected = 'true';
|
||||
}
|
||||
for (const event of ['pointerover', 'click']) {
|
||||
document.addEventListener(event, e => {
|
||||
const hit = e.target.closest?.('.forecast-hit');
|
||||
if (hit) inspect(hit);
|
||||
});
|
||||
}
|
||||
document.addEventListener('keydown', e => {
|
||||
if (!e.target.matches?.('.forecast-chart') || !['ArrowLeft', 'ArrowRight', 'Home', 'End'].includes(e.key)) return;
|
||||
const hits = [...e.target.querySelectorAll('.forecast-hit')];
|
||||
if (!hits.length) return;
|
||||
let index = hits.findIndex(p => p.dataset.selected);
|
||||
if (index < 0) {
|
||||
index = hits.findIndex(p => p.dataset.kind === 'Current reading');
|
||||
if (index < 0) index = hits.length - 1;
|
||||
}
|
||||
index = e.key === 'Home' ? 0 : e.key === 'End' ? hits.length - 1 : Math.max(0, Math.min(hits.length - 1, index + (e.key === 'ArrowRight' ? 1 : -1)));
|
||||
e.preventDefault();
|
||||
inspect(hits[index]);
|
||||
});
|
||||
})();
|
||||
Reference in New Issue
Block a user