Search

[Mac] 카라비너(Karabiner) Complex Modifications 단축키 설정 방법

Last update: @3/10/2023

맥 단축키 설정

맥 단축키 설정에 쓰이는 대표적인 두 가지 프로그램이 있다.
키보드 마에스트로(Keyboard Maestro) 유료
대부분의 매핑이 가능하고 여러 기능들을 지원함
UI가 편리함
하지만 유료이고 꽤 비쌈
카라비너 엘리먼츠(Karabiner Elements) 무료
GUI만으로는 매우 한정적인 기능을 지원함(키 하나를 다른 키로 바꾸는 매핑만 가능)
하지만 약간의 코딩만으로 키보드 마에스트로는 불가능한 온갖 매핑이 가능해짐
무엇보다 무료

카라비너를 쓰는 이유

나는 아래 예시 같은 일반키 없는 특수키 조합들을 사용하는데, 이는 키보드 마에스트로는 불가능하다.
왼쪽 Shift + 오른쪽 Shift End (줄 맨 오른쪽으로)
오른쪽 Shift + 왼쪽 Shift Home (줄 맨 왼쪽으로)
오른쪽 Shift + space 아래로
왼쪽 Shift + space 위로
왼쪽 CMD + 왼쪽 Shift → 왼쪽으로
왼쪽 CMD + 오른쪽 Shift → 오른쪽으로
윈도우를 쓰던 때부터 AutoHotKey로 매핑해서 쓰던 버릇이 있어 맥으로 옮겨오느라 카라비너를 사용하게 됐다. 국내에는 complex modification(복합 매핑)에 관한 자료가 거의 없어서 혼자 많은 삽질을 하며 배웠다.

설치 및 사용

위 링크를 따라 카라비너를 설치하면 아래 두가지 앱이 깔린다
Karabiner Elements
본체
Karabiner EventViewer
현재 눌린 키, 최상단 앱, 변수 상태 등을 보여주는 디버깅 툴
여기에 코드를 편집하기 위한 적당한 에디터가 필요한데, 가벼운 VSCode를 추천한다

karabiner.json

단축키 설정은 karabiner.json 파일을 수정해서 이루어진다. 파일 위치는 아래와 같다.
/Users/{사용자이름}/.config/karabiner/karabiner.json
Java
복사
사용자 폴더에 들어가서 shift + CMD + .을 눌러 숨김폴더를 표시하면 보인다.
파일을 열면 아래처럼 생겼다.
결론부터 말하면, 아래와 같은 설정 정보 하나 하나가 매핑의 단위다.
{ "description": "LShift + Spacebar -> up_arrow", "manipulators": [ { "from": { "key_code": "spacebar", "modifiers": { "mandatory": "left_shift" } }, "to": [ { "key_code": "up_arrow" } ], "type": "basic" } ] }
Java
복사
위 매핑 단위를 아래 전체 코드 구조에서 매핑1, 매핑2, … 위치에 원하는 만큼 넣으면 된다
{ "global": { ...생략... }, "profiles": [ { "complex_modifications": { "parameters": { ...생략... }, "rules": [ {매핑1}, {매핑2}, ... {매핑n} ] }, ...생략... } ] }
Java
복사
complex modifications만 별도 파일로 빼서 import할 수 있지만 수정 사항이 자동 반영되게 하려면 본 설정파일에 넣어줘야 함
카라비너 complex modification은 JSON(JavaScript Oject Notation, 제이슨)이라는 파일 형식을 이용한다. JSON은 간단한 두 가지 규칙만 알면 된다.
1.
중괄호({})는 오브젝트(Object)를 나타내는데, 오브젝트는 키:값 쌍이 하나 이상 들어 있는 자료형이다.
{"key_code":"left_command"}
Java
복사
key_code 속성에 left_command를 지정한다는 의미이다.
아래처럼 값 안에 다시 오브젝트가 들어갈 수 있다.
{ "modifiers": { "mandatory": "left_shift" } }
Java
복사
키:값 쌍은 여러 개 들어갈 수 있다.
{ "from": { "key_code": "spacebar", "modifiers": { "mandatory": "left_shift" } } }
Java
복사
2.
대괄호([])는 배열을 나타내는데, 오브젝트나 문자열(큰따옴표(””)로 감싸진 글자들) 등 여러 자료를 하나로 묶어주는 자료형이다. 위쪽의 “to” 키에 대응하는 값에 이 배열이 왔다.
"to":[{"key_code": "up_arrow"}]
Java
복사
배열이기 때문에 여러 오브젝트가 들어올 수 있다
{ "to":[ {"key_code": "up_arrow"}, {"key_code": "right_arrow"} ] }
Java
복사
이렇게 하면 위 화살표와 오른쪽 화살표가 차례대로 실행된다.
오브젝트와 배열 조합이 모여 아래같은 하나의 조작 단위(manipulator)를 구성한다.
"manipulators": [ { "from": { "key_code": "spacebar", "modifiers": { "mandatory": "left_shift" } }, "to": [ { "key_code": "up_arrow" } ], "type": "basic" } ]
Java
복사
위 manipulator 해석해보면, “왼쪽 쉬프트를 누른 채 스페이스바를 누르면(from) 위쪽 화살표를 누른다(to)” 라는 뜻이다.

이벤트 뷰어

카라비너를 설치하면 기본으로 같이 설치되는 보조 어플

현재 누르는 키의 key code 확인하기

key code를 직접
매핑하고 싶은 키의 key code를 확인하려면 이벤트뷰어의 Main 탭에서 키를 직접 눌러보면 확인 가능하다.

최상단 앱 확인하기

특저 앱에서만 쓰고싶은 매핑을 설정할 때, 해당 앱의 id(Bundle identifier)를 알아낼 때 사용

변수 정보 확인하기

한쪽 키를 연속 두 번 눌렀을 때 등의 경우에 변수를 사용하게 됨
Variables 탭을 눌러 최하단쪽으로 가보면 variables라고 해서 사용자가 지정한 변수의 값들을 모니터링할 수 있음

오류 메시지 확인하기

코드에 오류가 있을 경우 Complex Modifications가 깨끗해지며 매핑이 해제되는데, Karabiner Elements(본 앱)의 log 탭을 들어가면 정확한 오류 지점을 알 수 있어 빠른 디버깅이 가능하다
위의 경우 44번째줄에서 문제가 발생한 것
보통 오류의 90% 이상은 쉼표, 괄호 등 사소한 문제에서 발생한다.

사용 예시

구구절절한 설명보다는 실 사용 예시를 보면 어떻게 사용해야할 지 감이 온다.

Caps Lock → Semi-Hyper Key (⌃⌥⌘)

카라비너 사용 시 많이들 사용하는 캡스락→세미하이퍼 키
캡스락을 누를 경우 왼쪽 command + control + opition키를 동시에 누른 것과 같은 효과를 줘서 캡스락으로 다른 여러 키를 매핑할 수 있도록 함. 본인만의 고유한 매핑을 수십 가지 만들 수 있도록 도와줌
캡스락을 단독으로 눌러 대문자 상태로 전환되면 세미하이퍼키가 먹지 않음. 세미 하이퍼키가 적용되게 하려면 다시 한 번 캡스락을 단독으로 눌러 소문자로 전환해야 함
{//Caps Lock → Semi-Hyper Key (⌃⌥⌘) (Caps Lock if alone) "description": "Caps Lock → Semi-Hyper Key (⌃⌥⌘) (Caps Lock if alone)", "manipulators": [ { "from": { "key_code": "caps_lock" }, "to": [ { "key_code": "left_command", "modifiers": [ "left_control", "left_option" ] } ], "to_if_alone": [ { "key_code": "caps_lock" } ], "type": "basic" } ] }
JSON
복사

Semi-Hyper Key (⌃⌥⌘) + c → cmd + c

캡스락 + c 를 cmd + c로 매핑
이런 식으로 z, x, c, v 등을 윈도우에서 오토핫키 등으로 똑같이 매핑하면 OS에 상관 없이 캡스락으로 단축키를 통일해서 헷갈리지 않고 사용할 수 있다.
{//CapsLock -> CMD for c "description": "CapsLock -> CMD for c", "manipulators": [ { "from": { "key_code": "c", "modifiers": { "mandatory": [ "left_command", "left_control", "left_option" ] } }, "to": [ { "key_code": "c", "modifiers": [ "left_command" ] } ], "type": "basic" } ] }
JSON
복사

Semi-Hyper Key (⌃⌥⌘) + i → end + enter

캡스락 + i → 줄의 맨 끝으로 이동 후 엔터
to에 키를 여러개 매핑해서 연속 동작으로 만들어줄 수 있음
{//CapsLock + i -> end + enter "description": "CapsLock + i -> insert and move to line below", "manipulators": [ { "from": { "key_code": "i", "modifiers": { "mandatory": [ "left_command", "left_control", "left_option" ] } }, "to": [ { "key_code": "right_arrow", "modifiers": [ "left_command" ] }, { "key_code": "return_or_enter" } ], "type": "basic" } ] },
JSON
복사

왼쪽 Shift + 오른쪽 Shift → end

{//LShift+RShift -> to end of line "description": "LShift+RShift -> to end of line", "manipulators": [ { "from": { "key_code": "right_shift", "modifiers": { "mandatory": "left_shift" } }, "to": [ { "key_code": "right_arrow", "modifiers": [ "left_command" ] } ], "type": "basic" } ] }
JSON
복사
위와 같은 방법으로 특수 키들만 조합해서 매핑을 할 수 있다.

[Chrome 사용 시] cmd + d → cmd + l (주소창으로 이동)

윈도우 단축키와 일치시키기 위해 사용
아래처럼 conditionsbundle_identifiers 옵션을 넣으면 특정 앱에서만 단축키를 매핑할 수 있다.
{//Chrome Command+d -> address bar(CMD+i) "description": "Chrome command+d -> address bar(CMD+i)", "manipulators": [ { "conditions": [ { "bundle_identifiers": [ "^com\\.google\\.Chrome$" ], "type": "frontmost_application_if" } ], "from": { "key_code": "d", "modifiers": { "mandatory": [ "left_command" ] } }, "to": [ { "key_code": "l", "modifiers": [ "left_command" ] } ], "type": "basic" } ] }
JSON
복사

shift + option + s → 부분 스크린샷

윈도우 스크린샷 단축키를 그대로 매핑
{//Option+Shift+s -> partial screenshot to clipboard "description": "Option+Shift+s -> partial screenshot to clipboard", "manipulators": [ { "from": { "key_code": "s", "modifiers": { "mandatory": [ "left_option", "left_shift" ] } }, "to": [ { "key_code": "4", "modifiers": [ "left_control", "left_command", "left_shift" ] } ], "type": "basic" } ] }
JSON
복사

Semi-Hyper Key (⌃⌥⌘) + L → 여러 줄 선택

캡스락 + L을 누른 횟수 만큼 줄을 선택
루프를 돌려서 코드를 짧게 만들 수 있을 것 같지만, 카라비너 변수가 의도하는 대로 동작하지 않아서 어쩔 수 없이 반복 코드를 작성해야 함
주석 // n이라고 된 매핑은 conditions의 변수 name 부분에 line_selection_(n-1), 나머지 to 부분의 변수 name 부분에 line_selection_n이라고 적는다.
10번 밑에 9 ~ 2까지 숫자만 바꾼 똑같은 매핑을 8개 만들고, // 1 초기 라인 선택 부분을 넣으면 캡스락 + L을 1~10번 누르면 1~10줄이 선택된다.
원하는 최대 수치까지 코드를 복제하면 됨
{//CapsLock + l -> select lines "description": "CapsLock + l -> select lines", "manipulators": [ { // 10 "type": "basic", "conditions": [ { "type": "variable_if", "name": "line_selection_9", "value": 1 } ], "from": { "key_code": "l", "modifiers": { "mandatory": [ "left_command", "left_control", "left_option" ] } }, "to": [ { "key_code": "down_arrow", "modifiers": [ "left_shift" ] }, { "key_code": "right_arrow", "modifiers": [ "left_shift", "left_command" ] }, { "set_variable": { "name": "line_selection_10", "value": 1 } } ], "to_delayed_action": { "to_if_invoked": [ { "set_variable": { "name": "line_selection_10", "value": 0 } } ], "to_if_canceled": [ { "set_variable": { "name": "line_selection_10", "value": 0 } } ] } }, { // 9 "type": "basic", "conditions": [ { "type": "variable_if", "name": "line_selection_8", "value": 1 } ], "from": { "key_code": "l", "modifiers": { "mandatory": [ "left_command", "left_control", "left_option" ] } }, "to": [ { "key_code": "down_arrow", "modifiers": [ "left_shift" ] }, { "key_code": "right_arrow", "modifiers": [ "left_shift", "left_command" ] }, { "set_variable": { "name": "line_selection_9", "value": 1 } } ], "to_delayed_action": { "to_if_invoked": [ { "set_variable": { "name": "line_selection_9", "value": 0 } } ], "to_if_canceled": [ { "set_variable": { "name": "line_selection_9", "value": 0 } } ] } }, ... 위와 같은 코드가 2~8까지 7개 더 있음 ... { // 1 초기 라인 선택 "type": "basic", "conditions": [ { "type": "variable_if", "name": "line_selection_0", "value": 0 } ], "from": { "key_code": "l", "modifiers": { "mandatory": [ "left_command", "left_control", "left_option" ] } }, "to": [ { "key_code": "left_arrow", "modifiers": [ "left_command" ] }, { "key_code": "right_arrow", "modifiers": [ "left_shift", "left_command" ] }, { "set_variable": { "name": "line_selection_1", "value": 1 } } ], "to_delayed_action": { "to_if_invoked": [ { "set_variable": { "name": "line_selection_1", "value": 0 } } ], "to_if_canceled": [ { "set_variable": { "name": "line_selection_1", "value": 0 } } ] } } ] }
JSON
복사

Complex Modifications JSON 자동 생성 사이트

원하는 키를 설정하면 자동으로 코드를 만들어주는 사이트
개인적으로 사용하지 않지만, 코딩이 부담스럽고 시간아까운 분들에게는 좋을 듯 하다.