How to Implement Keyboard Shortcuts: Claude Code 활용 가이드
implement keyboard shortcuts: Claude Code 활용. 실용적인 코드 예시와 단계별 가이드를 포함합니다.
キーボードショートカットで操作効率を向上
キーボードショートカットは、パワー사용자の操作効率を劇的に向上させる機能です。Claude Code를 활용하면 ショートカットの등록・관리・ヘルプ표시を体系的に구현할 수 있습니다。
ショートカット관리システムの구축
> Web앱用のキーボードショートカットシステム를 구현해줘。
> 修飾キー대응、スコープ관리、コンフリクト検出をサポートして。
// lib/shortcuts.ts
type ShortcutHandler = (e: KeyboardEvent) => void;
interface Shortcut {
key: string;
modifiers: ('ctrl' | 'shift' | 'alt' | 'meta')[];
handler: ShortcutHandler;
description: string;
scope?: string;
}
class ShortcutManager {
private shortcuts: Map<string, Shortcut> = new Map();
private activeScope: string = 'global';
constructor() {
window.addEventListener('keydown', this.handleKeyDown.bind(this));
}
private buildId(key: string, modifiers: string[]): string {
return [...modifiers.sort(), key.toLowerCase()].join('+');
}
register(shortcut: Shortcut): () => void {
const id = this.buildId(shortcut.key, shortcut.modifiers);
if (this.shortcuts.has(id)) {
console.warn(`ショートカットの競合: ${id}`);
}
this.shortcuts.set(id, shortcut);
return () => this.shortcuts.delete(id);
}
setScope(scope: string): void {
this.activeScope = scope;
}
private handleKeyDown(e: KeyboardEvent): void {
// 입력フィールドでは무효化
const target = e.target as HTMLElement;
if (['INPUT', 'TEXTAREA', 'SELECT'].includes(target.tagName)) return;
if (target.isContentEditable) return;
const modifiers: string[] = [];
if (e.ctrlKey) modifiers.push('ctrl');
if (e.shiftKey) modifiers.push('shift');
if (e.altKey) modifiers.push('alt');
if (e.metaKey) modifiers.push('meta');
const id = this.buildId(e.key, modifiers);
const shortcut = this.shortcuts.get(id);
if (shortcut && (!shortcut.scope || shortcut.scope === this.activeScope)) {
e.preventDefault();
shortcut.handler(e);
}
}
getAll(): Shortcut[] {
return Array.from(this.shortcuts.values());
}
destroy(): void {
window.removeEventListener('keydown', this.handleKeyDown);
this.shortcuts.clear();
}
}
export const shortcuts = new ShortcutManager();
Reactフックでの利用
// hooks/useShortcut.ts
import { useEffect } from 'react';
import { shortcuts } from '../lib/shortcuts';
export function useShortcut(
key: string,
modifiers: ('ctrl' | 'shift' | 'alt' | 'meta')[],
handler: () => void,
description: string
) {
useEffect(() => {
const unregister = shortcuts.register({
key,
modifiers,
handler,
description,
});
return unregister;
}, [key, modifiers, handler, description]);
}
// Usage example
function BlogEditor() {
useShortcut('s', ['ctrl'], () => saveDraft(), '下書き保存');
useShortcut('Enter', ['ctrl'], () => publish(), '公開');
useShortcut('p', ['ctrl', 'shift'], () => togglePreview(), 'プレビュー切替');
return <div>{/* エディタUI */}</div>;
}
ショートカットヘルプ다이얼로그
// components/ShortcutHelp.tsx
import { useState, useEffect } from 'react';
import { shortcuts } from '../lib/shortcuts';
export function ShortcutHelp() {
const [isOpen, setIsOpen] = useState(false);
useEffect(() => {
const unregister = shortcuts.register({
key: '?',
modifiers: ['shift'],
handler: () => setIsOpen(prev => !prev),
description: 'ショートカット一覧を表示',
});
return unregister;
}, []);
if (!isOpen) return null;
const allShortcuts = shortcuts.getAll();
const grouped = Object.groupBy(allShortcuts, s => s.scope ?? 'global');
return (
<div className="fixed inset-0 z-50 flex items-center justify-center bg-black/50">
<div className="w-full max-w-md rounded-xl bg-white p-6 dark:bg-gray-800">
<h2 className="mb-4 text-xl font-bold">キーボードショートカット</h2>
{Object.entries(grouped).map(([scope, items]) => (
<div key={scope} className="mb-4">
<h3 className="mb-2 text-sm font-semibold uppercase text-gray-500">
{scope}
</h3>
{items?.map(s => (
<div key={s.description} className="flex items-center justify-between py-1">
<span>{s.description}</span>
<kbd className="rounded bg-gray-100 px-2 py-0.5 text-sm dark:bg-gray-700">
{[...s.modifiers, s.key].join(' + ')}
</kbd>
</div>
))}
</div>
))}
<button onClick={() => setIsOpen(false)} className="mt-4 w-full rounded bg-gray-100 py-2">
閉じる (Esc)
</button>
</div>
</div>
);
}
OS別のキー표시대응
function formatShortcut(modifiers: string[], key: string): string {
const isMac = navigator.platform.includes('Mac');
const symbolMap: Record<string, string> = isMac
? { ctrl: '⌃', shift: '⇧', alt: '⌥', meta: '⌘' }
: { ctrl: 'Ctrl', shift: 'Shift', alt: 'Alt', meta: 'Win' };
return [...modifiers.map(m => symbolMap[m]), key.toUpperCase()].join(isMac ? '' : '+');
}
정리
キーボードショートカットはコマンドパレットと연동させると最も効果的です。Claude Code를 활용하면 입력フィールドでの무효化やスコープ관리など、엣지ケースを考慮した堅牢な구현が가능합니다。アクセシビリティの観点からも、キーボード操作のサポートは중요합니다。ショートカット설계の모범 사례はNielsen Norman Group를 참고하세요.
무료 PDF: 5분 완성 Claude Code 치트시트
이메일 주소만 등록하시면 A4 한 장짜리 치트시트 PDF를 즉시 보내드립니다.
개인정보는 엄격하게 관리하며 스팸은 보내지 않습니다.
이 글을 작성한 사람
Masa
Claude Code를 적극 활용하는 엔지니어. 10개 언어, 2,000페이지 이상의 테크 미디어 claudecode-lab.com을 운영 중.
관련 글
Claude Code용 CLAUDE.md 템플릿 7선 | 실제 프로젝트에 바로 붙여 넣는 예시
개인 앱, 콘텐츠 사이트, API, 팀 저장소, 레거시 코드베이스에 맞는 실전 CLAUDE.md 템플릿 7개와 피해야 할 실패 사례를 정리했습니다.
Claude Code Approval / Sandbox Guide | 매일 안전하게 쓰는 설정법
Claude Code의 allow, ask, deny, sandbox를 어떻게 나눌지, 실전 settings와 hooks, 실패 사례와 함께 정리합니다.
Claude Code 완벽 입문 가이드 2026 | 제로부터 실무 활용까지 7단계
Claude Code를 처음 사용하는 분들을 위한 완전 입문 가이드. 설치부터 실제 개발 워크플로우에 녹이는 것까지 — Masa가 처음에 겪었던 모든 시행착오를 바탕으로 정리했습니다.