Skip to content

Instantly share code, notes, and snippets.

@novelview9
Created April 10, 2026 15:24
Show Gist options
  • Select an option

  • Save novelview9/3c86de4acda7f1fc52fd6ad3380f780c to your computer and use it in GitHub Desktop.

Select an option

Save novelview9/3c86de4acda7f1fc52fd6ad3380f780c to your computer and use it in GitHub Desktop.
Ghost Library: 한글 입력기 스펙 (gureum/gureum 기반)

Ghost Library: 한글 입력기 (Korean Input Method)

원본 프로젝트: gureum/gureum — macOS/iOS 한글 입력기, Swift ~10K LOC (BSD + LGPL) 핵심 의존: libhangul (C, 한글 조합 상태 머신), Apple InputMethodKit 증류 기준: gureum v1.13.2 (commit b495b70 시점 소스 분석)

이 문서는 gureum 입력기의 아키텍처를 분석·증류하여, AI 코딩 에이전트가 동등한 입력기를 재구현할 수 있도록 작성한 Ghost Library입니다.


Phase 0: 최소 입력기

한글 1개 자판(두벌식) + 영문 전환이 되는 최소 동작 입력기.

아키텍처

참조: OSXCore/InputController.swift, OSXCore/InputReceiver.swift, OSXCore/InputMethodServer.swift

macOS TSM → IMKServer (싱글턴)
  → InputController (IMKInputController)
  → InputReceiver (전처리, 커밋/업데이트 흐름)
  → Composer Chain
      ├─ HangulComposer (libhangul 래핑)
      └─ RomanComposer (패스스루)

3계층 분리: IMK 인터페이스 → 처리 로직 → 조합 로직 (플랫폼 무관)

Composer 프로토콜 (핵심 추상화)

참조: OSXCore/Composer.swift

protocol Composer {
    var delegate: Composer! { get set }
    var composedString: String { get }     // 조합 중 (밑줄)
    var commitString: String { get }        // 확정 대기
    func dequeueCommitString() -> String    // 소비 후 비움
    func cancelComposition()
    func input(text:key:modifiers:client:) -> InputResult
}
  • 기본 구현이 모든 호출을 delegate로 위임
  • 이중 버퍼: composedString(밑줄) / commitString(확정) + dequeue 큐 패턴

한글 조합 흐름

참조: OSXCore/HangulComposer.swift, libhangul HGInputContext

"r"(ㄱ) → process → preedit=[ㄱ]         → 밑줄 "ㄱ"
"k"(ㅏ) → process → preedit=[가]         → 밑줄 "가"
"s"(ㄴ) → process → commit=[가] preedit=[ㄴ] → "가" 확정, 밑줄 "ㄴ"

libhangul의 HGInputContext가 초성/중성/종성 상태 머신을 관리. HangulComposer는 얇은 래퍼.

유니코드

  • libhangul 출력: 첫가끝(U+1100대) → representableString()으로 호환 자모(U+3131대) 변환
  • 옛한글은 원본 유지, 초성/중성 필러(U+115F, U+1160) 제거

한영 전환

참조: OSXCore/GureumComposer.swift

  • GureumComposerdelegate를 HangulComposer ↔ RomanComposer로 교체 (Strategy)
  • 전환 시 cancelAndCommit() → 조합 확정 → selectMode() → macOS에 알림

Phase 1: 다중 자판 + 전환 옵션

12종 한글 자판

참조: OSXCore/HangulComposer.swiftComposerType enum, OSXCore/data/ (키보드/조합 규칙 XML)

두벌식, 두벌식 옛글, 세벌식(최종/390/순아래/옛글/2011/2012/2014/2015), 안마태, 로마자 — setKeyboard(identifier:)로 libhangul 키-자모 매핑 테이블 변경.

로마자 레이아웃

참조: OSXCore/RomanComposer.swift

QWERTY/Dvorak/Colemak — keyMap: [Character: Character] 딕셔너리로 매핑. system 타입은 OS 기본 사용.

전환 트리거 확장

참조: OSXCore/InputMethodServer.swiftIOKitty 클래스, OSXCore/InputController.swifthandle(_:client:)

트리거 감지 비고
커스텀 단축키 filterCommand() 설정 가능
CapsLock <0.5초 IOKitty (IOHIDManager) NSEvent 불가, 하드웨어 선점 필요
CapsLock ≥0.5초 IOKitty 원래 CapsLock 유지
우측 Alt/Ctrl IOKitty 우측 modifier 감지
ESC (Vi 모드) filterCommand() 코딩용

IOHIDManager를 쓰는 이유: macOS가 CapsLock을 입력기 전에 자체 처리하므로 NSEvent로는 짧게/길게 구분 불가.

설정 체계

참조: OSXCore/Configuration.swift

UserDefaults 싱글턴 (suite name 기반). 마지막 한글/로마자 모드 기억, 단축키 커스텀, 옵션 키 동작 선택. HangulComposer가 KVO로 설정 변경 실시간 반영.


Phase 2: 한자/이모지 후보 검색

SearchComposer

참조: OSXCore/SearchComposer.swift, OSXCore/SearchPool.swift

이중 위임: GureumComposer → SearchComposer → HangulComposer

한글 입력을 delegate에 위임하면서 조합 결과를 가로채어 검색.

  • 비동기 검색: DispatchQueue.global + DispatchWorkItem 취소 (debounce)
  • 후보창: IMKCandidates 활용
  • 후보 선택: "한자:뜻" 형식에서 한자만 추출 커밋
  • ESC 탈출, 조합/커밋 비어있으면 자동 복귀

호환 모드

참조: OSXCore/Configuration.swift, OSXCore/HangulComposer.swift

설정 용도
` → ₩ 변환 한글 모드 원화 기호
JDK 호환 기호도 조합 상태 유지
MS Windows 호환 종성 결합 허용
모아치기 자동 교정 동시 타건 순서 무관
세벌식 정석 엄격 조합 규칙

Phase 3: iOS 키보드 확장

참조: iOSShared/, iOSApp/

macOS와 공유하는 것은 libhangul 조합 로직뿐. 나머지는 완전히 별도 아키텍처.

ViewController 계층

참조: iOSShared/InputViewController.swift

UIInputViewController
  → BasicInputViewController (텍스트 입출력, 문서 컨텍스트)
  → InputViewController (스와이프 제스처, 자동 대문자화)

레이아웃 시스템

참조: iOSShared/GRKeyboardLayoutHelper.swift, iOSShared/QwertyKeyboardLayout.swift, iOSShared/TenkeyKeyboardLayout.swift

GRKeyboardLayoutHelper — Position(row, column) + delegate 프로토콜 기반 그리드 엔진. 버튼 생성과 배치 분리.

지원 레이아웃: QWERTY(10-9-7), 기호 2세트, 두벌식(KS X 5002), 단모음(8-8-6), 천지인, 천지인+, 텐키 숫자/영문, 숫자패드, 이모티콘

한글 조합 (iOS)

참조: iOSShared/Hangeul.swift

Hangeul.swift — 기존 조합과 새 조합의 diff를 계산해 deleteBackward/insertText로 최소 변경만 적용.

테마

참조: iOSShared/Theme.swift, iOSShared/Preferences.swift

JSON 기반. 디바이스/방향별 trait → 그룹(qwerty/tenkey/numpad) → 분류(key/special/function) → 캡션 클래스 cascade. 리소스는 Base64로 App Group UserDefaults에 저장.


Phase 4: AI 한글 입력 보조

이 Phase는 gureum 원본에 없는 확장 기능 제안임.

영타 자동 감지

"gksrmf" 입력 중 한글 모드가 아닌 것을 감지 → "한글" 제안 (Ghost Text).

문맥 기반 한자 순위

단순 음절 매칭이 아닌 문장 맥락으로 후보 순위 결정. 로컬 n-gram 또는 경량 모델.

맞춤법 제안

조합 완료된 문장에 밑줄 표시 + 교정 후보. macOS NSSpellChecker 연동 또는 자체 사전.


핵심 구현 노트

  1. Composer Chain이 전체 확장성의 열쇠 — 새 기능 = 새 Composer + 라우터에 연결. → Composer.swift
  2. 이중 버퍼 + dequeue는 IMK 필수 패턴 — 조합 중(밑줄)과 확정을 반드시 분리. → InputReceiver.swift
  3. IOHIDManager는 macOS 입력기의 현실적 제약 해결책 — 접근성 권한 필요. → InputMethodServer.swift
  4. libhangul이 한글 조합 복잡성을 캡슐화 — 직접 구현하지 않는다. → libhangul
  5. iOS는 별도 아키텍처 — 공유하는 것은 조합 엔진뿐. → iOSShared/

참조 소스 목록

파일 경로 역할
Composer.swift OSXCore/ Composer 프로토콜 + 기본 구현
GureumComposer.swift OSXCore/ 최상위 라우터, 입력 모드 전환
HangulComposer.swift OSXCore/ libhangul 래핑, 한글 조합
RomanComposer.swift OSXCore/ 로마자 레이아웃 매핑
SearchComposer.swift OSXCore/ 한자/이모지 검색
InputController.swift OSXCore/ IMK 이벤트 핸들러
InputReceiver.swift OSXCore/ 입력 처리 오케스트레이터
InputMethodServer.swift OSXCore/ IMKServer + IOKitty
Configuration.swift OSXCore/ 설정 관리 (UserDefaults)
KeyCode.swift OSXCore/ 하드웨어 키 코드 정의
InputViewController.swift iOSShared/ iOS 키보드 컨트롤러
Hangeul.swift iOSShared/ iOS 한글 조합 엔진
Theme.swift iOSShared/ iOS 테마 시스템
GureumTests.swift GureumTests/ 테스트 (930줄, 모아치기 포함)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment