OverviewFilesCommitsIssuesDocsReleasesPeers

keet-tui / lib / views / help.js

72 lines · javascript ref:
import * as style from '../style.js'

const HELP = [
  ['', style.bold('Navigation')],
  ['Tab / Shift+Tab', 'Cycle focus: Rooms → Chat → Members'],
  ['', ''],
  ['', style.bold('Room List (when focused)')],
  ['\u2191 / \u2193 or j / k', 'Move selection up / down'],
  ['Enter', 'Open selected room'],
  ['', ''],
  ['', style.bold('Chat (when focused)')],
  ['Type + Enter', 'Send a message'],
  ['Page Up / Page Down', 'Scroll message history'],
  ['\u2190 / \u2192', 'Move cursor in input'],
  ['Home / Ctrl+A', 'Cursor to start of line'],
  ['End / Ctrl+E', 'Cursor to end of line'],
  ['Ctrl+W', 'Delete word backward'],
  ['Ctrl+U', 'Clear input line'],
  ['Backspace / Delete', 'Delete character'],
  ['', ''],
  ['', style.bold('Global')],
  ['?', 'Toggle this help screen'],
  ['Ctrl+C', 'Quit']
]

export function helpView (model, width, height) {
  const lines = []
  const boxWidth = Math.min(60, width - 4)
  const boxLeft = Math.floor((width - boxWidth) / 2)
  const pad = ' '.repeat(boxLeft)

  const contentHeight = HELP.length + 4 // title + borders + bottom
  const topPad = Math.max(1, Math.floor((height - contentHeight) / 2))

  for (let i = 0; i < topPad; i++) lines.push('')

  // Top border
  const inner = boxWidth - 2
  const title = ' Keybindings '
  const titlePad = Math.max(0, inner - title.length)
  const leftBar = Math.floor(titlePad / 2)
  const rightBar = titlePad - leftBar
  lines.push(pad + style.cyan('\u256d' + '\u2500'.repeat(leftBar) + title + '\u2500'.repeat(rightBar) + '\u256e'))

  // Content rows
  for (const [key, desc] of HELP) {
    let row
    if (!key && desc) {
      // Section header
      row = '  ' + desc
    } else if (!key && !desc) {
      // Blank line
      row = ''
    } else {
      const keyCol = style.bold(style.yellow(style.padRight(key, 22)))
      row = '  ' + keyCol + desc
    }
    const rowContent = style.truncate(row, inner)
    lines.push(pad + style.cyan('\u2502') + style.padRight(rowContent, inner) + style.cyan('\u2502'))
  }

  // Bottom border with dismiss hint
  const hint = ' Press ? to close '
  const hintPad = Math.max(0, inner - hint.length)
  const hintLeft = Math.floor(hintPad / 2)
  const hintRight = hintPad - hintLeft
  lines.push(pad + style.cyan('\u2570' + '\u2500'.repeat(hintLeft) + hint + '\u2500'.repeat(hintRight) + '\u256f'))

  while (lines.length < height) lines.push('')
  return lines
}