Skip to main content

Lesson 6: Display Formatting

Render keyboard shortcuts in your UI with platform-aware labels and symbols.

The problem

You register 'Mod+Shift+S' as a binding. But what do you show the user?

  • On Mac: Cmd+Shift+S
  • On Windows: Ctrl+Shift+S
  • On Linux: Ctrl+Shift+S

And modifiers have different names across platforms: Alt on Windows is Opt on Mac, Meta on Linux is Super.


formatForDisplay

The primary function. Takes a binding string and returns a display string for the current (or specified) platform:

import { formatForDisplay } from '@gentleduck/vim/format'
 
formatForDisplay('Mod+S')                          // 'Cmd+S' on Mac, 'Ctrl+S' on Windows
formatForDisplay('Mod+S', { platform: 'mac' })     // 'Cmd+S' always
formatForDisplay('Mod+S', { platform: 'windows' }) // 'Ctrl+S' always
formatForDisplay('alt+k', { platform: 'mac' })     // 'Opt+K'
formatForDisplay('meta+enter', { platform: 'linux' }) // 'Super+Enter'
import { formatForDisplay } from '@gentleduck/vim/format'
 
formatForDisplay('Mod+S')                          // 'Cmd+S' on Mac, 'Ctrl+S' on Windows
formatForDisplay('Mod+S', { platform: 'mac' })     // 'Cmd+S' always
formatForDisplay('Mod+S', { platform: 'windows' }) // 'Ctrl+S' always
formatForDisplay('alt+k', { platform: 'mac' })     // 'Opt+K'
formatForDisplay('meta+enter', { platform: 'linux' }) // 'Super+Enter'

formatWithLabels

A more verbose format with wider spacing, useful for tooltips and help screens:

import { formatWithLabels } from '@gentleduck/vim/format'
 
formatWithLabels('Mod+Shift+S', { platform: 'mac' })
// 'Cmd + Shift + S'
 
formatWithLabels('ctrl+backspace')
// 'Ctrl + Backspace'
import { formatWithLabels } from '@gentleduck/vim/format'
 
formatWithLabels('Mod+Shift+S', { platform: 'mac' })
// 'Cmd + Shift + S'
 
formatWithLabels('ctrl+backspace')
// 'Ctrl + Backspace'

The default separator is ' + ' (with spaces), compared to '+' (no spaces) in formatForDisplay.


Custom separator

Both functions accept a separator option:

formatForDisplay('ctrl+shift+k', { separator: ' ' })
// 'Ctrl Shift K'
 
formatForDisplay('ctrl+shift+k', { separator: ' -> ' })
// 'Ctrl -> Shift -> K'
formatForDisplay('ctrl+shift+k', { separator: ' ' })
// 'Ctrl Shift K'
 
formatForDisplay('ctrl+shift+k', { separator: ' -> ' })
// 'Ctrl -> Shift -> K'

Rendering in React

Simple inline display

function ShortcutBadge({ binding }: { binding: string }) {
  return (
    <kbd className="text-xs bg-gray-100 px-1.5 py-0.5 rounded border border-gray-200">
      {formatForDisplay(binding)}
    </kbd>
  )
}
function ShortcutBadge({ binding }: { binding: string }) {
  return (
    <kbd className="text-xs bg-gray-100 px-1.5 py-0.5 rounded border border-gray-200">
      {formatForDisplay(binding)}
    </kbd>
  )
}

Formatting sequences

For multi-key sequences like g+d, the format functions work on individual steps. Format each step separately:

function SequenceDisplay({ steps }: { steps: string[] }) {
  return (
    <span className="inline-flex items-center gap-1">
      {steps.map((step, i) => (
        <span key={i} className="inline-flex items-center gap-1">
          {i > 0 && <span className="text-gray-400 text-xs">then</span>}
          <ShortcutKeys binding={step} />
        </span>
      ))}
    </span>
  )
}
 
// Usage:
// <SequenceDisplay steps={['g', 'd']} />
// Renders: [G] then [D]
//
// <SequenceDisplay steps={['ctrl+k', 'ctrl+c']} />
// Renders: [Ctrl][K] then [Ctrl][C]
function SequenceDisplay({ steps }: { steps: string[] }) {
  return (
    <span className="inline-flex items-center gap-1">
      {steps.map((step, i) => (
        <span key={i} className="inline-flex items-center gap-1">
          {i > 0 && <span className="text-gray-400 text-xs">then</span>}
          <ShortcutKeys binding={step} />
        </span>
      ))}
    </span>
  )
}
 
// Usage:
// <SequenceDisplay steps={['g', 'd']} />
// Renders: [G] then [D]
//
// <SequenceDisplay steps={['ctrl+k', 'ctrl+c']} />
// Renders: [Ctrl][K] then [Ctrl][C]

Platform-specific display reference

ModifierMacWindowsLinux
metaCmdWinSuper
ctrlCtrlCtrlCtrl
altOptAltAlt
shiftShiftShiftShift

Exercises

  1. Create a component that shows a shortcut hint at the bottom of a page.
  2. Format 'Mod+Shift+Z' for all three platforms and compare the output.
  3. Build a help overlay that lists all registered commands with formatted shortcuts.