asciitorium
Version:
an ASCII CLUI framework
44 lines (43 loc) • 1.67 kB
JavaScript
export class ScrollableViewport {
calculateScrollWindow(content) {
const { items, totalCount, maxVisible, focusedIndex } = content;
// Calculate the starting index to keep focused item centered when possible
const startIdx = Math.max(0, Math.min(focusedIndex - Math.floor(maxVisible / 2), Math.max(0, totalCount - maxVisible)));
const visibleItems = items.slice(startIdx, startIdx + maxVisible);
return {
startIdx,
visibleItems,
showUpArrow: startIdx > 0,
showDownArrow: startIdx + maxVisible < totalCount
};
}
handleScrollEvent(event, currentFocusedIndex, totalCount) {
let newFocusedIndex = currentFocusedIndex;
if ((event === 'ArrowUp') && currentFocusedIndex > 0) {
newFocusedIndex = currentFocusedIndex - 1;
}
else if ((event === 'ArrowDown') &&
currentFocusedIndex < totalCount - 1) {
newFocusedIndex = currentFocusedIndex + 1;
}
return newFocusedIndex;
}
drawScrollIndicators(buffer, width, height, borderPad, showUpArrow, showDownArrow) {
// Scroll up indicator
if (showUpArrow) {
const y = borderPad;
const x = width - 2;
if (y >= 0 && y < height && x >= 0 && x < width) {
buffer[y][x] = '↑';
}
}
// Scroll down indicator
if (showDownArrow) {
const y = height - 1 - borderPad;
const x = width - 2;
if (y >= 0 && y < height && x >= 0 && x < width) {
buffer[y][x] = '↓';
}
}
}
}