LangCursor :: 한영키 오타를 방지하는 IntelliJ 플러그인 개발기

숑숑·2024년 1월 21일
10

회고

목록 보기
7/7
post-thumbnail

코드는 대부분 영어로 되어있습니다.
그래서 한국인은 한영키 때문에 오타를 많이 내곤 하는데요...

그런데 왜 키가 한글이라는걸 꼭 쳐봐야만 아는걸까요??
지금 한영 상태가 뭔지, 작성하기 전에 미리 알 순 없을까요?
혹시 키보드가 한글일 때 을 바꿔주면 큰 도움이 될 것 같아요.

그래서 만들게된 IntelliJ-based IDE 플러그인을 소개하고자 합니다.


LangCursor

현재 키보드 언어가 영어가 아닐 때 커서 색깔을 바꿔줍니다. (Vim 호환 가능)

  • 지원 환경
    • 지원 OS: Windows / macOS
    • OS 기본 입력기 사용 (ex. 구름입력기 등 서드파티 입력기 사용 중인 경우 동작하지 않을 수 있음)

이렇게 한영키에 따라 커서 색을 바꿔준다면, 지금 영어키가 맞는지 바로 알 수 있습니다.
Vim 모드 커서와도 호환됩니다!

Settings

  • 기본은 빨간색으로, 세팅화면을 통해 커서 색을 바꿀 수 있습니다.
  • Settings > Tools > LangCursor

🤔 왜 만들었을까?

여러분은 Vim을 자주 쓰시나요?
Vim 모드를 사용하다보면, 한글키가 더욱 치명적인(?) 경우가 많다고 생각하는데요.
아래처럼 v키로 코드를 셀렉한 상태에서 한글키를 누르면 다 지워집니다 ㅎㅎ

이렇게 한글키 때문에 코드가 다 지워지는 일이 일수였습니다.
물론 macOS의 경우, 아래처럼 한영키 상태를 맥북 상단바로 알아낼 수 있습니다.

그래도 시선 이동 거리가 너무 길어서, 차라리 오타 한번 내는게 낫더라구요.

생각해보면 코딩할 때 저희 시선은 항상 커서에 고정되어 있습니다.

그럼 한글키일 때 커서 색을 바꿔주자!!!라는 생각이 들었고, IntelliJ 플러그인으로 개발하기로 마음 먹었습니다.
그리고 이왕이면, 굳이 한글에만 제한을 두지 않을 생각입니다.

간단하게 정의한 기획은 아래와 같습니다.

모토: 비영어권 개발자를 위한 오타 예방 플러그인

  • 현재 키가 ‘영어가 아닐 때’ 커서 색상을 바꿔준다.
  • 커서 색상은 설정으로 변경할 수 있도록 한다.

더 많은 기능이 떠올랐지만, 일단 제가 가장 필요했던 기능만 남기고 진행하기로 합니다.
아이디어가 간단하기에 개발도 간단할거라 생각했습니다.
그 때까진 몰랐죠…

😰 한영키 구분하는 법

기술적으로 한영키를 구분해내는 것이 어려운 포인트였습니다.
사실 이거 때문에 첫 아이디어를 생각한지 6개월 후에나 릴리즈 할 수 있었던건데요.

제가 시도해본 방법들을 하나씩 소개하고, 왜 구현할 수 없었는지 설명하겠습니다.
어려울 수 있으니, 궁금하지 않다면 결론으로 넘기셔도 좋을 내용입니다.

Java InputContext

왜 안 되는가?
OS 별로 동작이 다르다. (JVM이 플랫폼을 타네요..???)

InputContext는 사용자의 입력과 관련된 정보를 추상화해 Java에서 공식 지원하는 클래스입니다.
내부적으로 OS 별 Native 구현이 되어있기에 가장 먼저 떠올린 방법입니다.

그런데.. 테스트 해봤을 때, OS 별로 결과값이 달랐습니다. (틀리게 나온다기보다는, 현재 키 레이아웃이 영어라고 표현하는 방식이 다르더군요.)

저는 OS-specific한 플러그인을 만들고 싶지 않았습니다.
사용자가 제한되는 것도 있지만, OS는 계속 새로운 버전이 나오기 때문에 앞으로 유지보수가 굉장히 힘들거 같았습니다.

이와 관련된 스택오버플로우를 참고했을 때, 일단 Linux 환경에서는 InputContext가 올바르게 동작하지 않을 수 있겠다는 생각이 들었습니다.

어디에 OS 별 결과값이 문서화라도 되어있으면 모르겠는데, 그게 없어서 테스트하면서 케이스를 떼우는 방법 밖에는 모르겠더구요;;

그럼 일단 Java InputContext가 내부적으로 키 레이아웃을 구별하는 방법을 따라하면 되지 않을까?
이 생각으로 Native API를 활용한 구현을 조사해보게 됩니다.

Native API

왜 안 되는가?

  • 공식 문서 부재
  • 잦은 I/O로 인해 느려지는 커서 색상 전환 속도

Java InputContext 클래스에서 키보드 언어를 구별하는 핵심 로직을 알아내기 위해,
플러그인에서 사용하는 JDK인 JetbrainsRuntime을 파내려가봤습니다.

아래는 macOS에서 InputMethod를 구별하는 클래스의 코드입니다.
언어는 C# 인듯합니다.

static void initializeInputMethodController() {
    static BOOL checkedJRSInputMethodController = NO;
    if (!checkedJRSInputMethodController && (inputMethodController == nil)) {
        id jrsInputMethodController = objc_lookUpClass("JRSInputMethodController");
        if (jrsInputMethodController != nil) {
            inputMethodController = [jrsInputMethodController performSelector:@selector(controller)];
        }
        checkedJRSInputMethodController = YES;
    }
}

JRSInputMethodController 라는 MacOS 내부 클래스의 메소드를 호출해서 분별하는 걸로 보입니다.

JRSInputMethodController 라는걸 파보면 한영키 구분 코드를 알아낼 수 있을거 같은데요, 리포지토리 어디에도 저 클래스가 보이지 않습니다...(??)

네??

결론적으로, 저 클래스는 macOS 내부 클래스라서 리포지토리에서 찾을 수 없는게 맞고,
Jetbrains처럼 JDK를 직접 구현하는 사람들은 노하우(?)가 있기 때문에 활용이 가능하다고 합니다.
어쨌든 Apple이 공식적으로 지원하는 클래스가 아니니 쓰지 않는걸 강력하게 권장한다고 합니다.

이해가 갈듯 말듯 하지만, 쓰더라도 나중에 유지보수는 거의 못한다는 소리네요.
그만 알아보기로 합니다...

macOS는 아래와 같이 쉘 커맨드로 현재 키 레이아웃을 알아보는 방법도 있습니다.

# command
defaults read ~/Library/Preferences/com.apple.HIToolbox.plist AppleSelectedInputSources

# output
(
        {
        "Bundle ID" = "com.apple.PressAndHold";
        InputSourceKind = "Non Keyboard Input Method";
    },
        {
        InputSourceKind = "Keyboard Layout";
        "KeyboardLayout ID" = 252;
        "KeyboardLayout Name" = ABC;	# 현재 영문 상태
    }
)

이 방법을 사용하려면 I/O 호출이 매번 일어납니다.
빠르게 동작할 수 없을거란 생각을 했습니다.
실제로 위 방법대로 구현 후 비교했을 때, 커서 색상 전환 딜레이가 좀 더 체감되었습니다.

타이핑하다 커서 색상 전환 딜레이를 느끼게 하는건 플러그인의 쓸모를 떨어뜨리기에 치명적이라고 생각했습니다.
그래서 일단 이 방법으로도 구현하지 못했습니다.

그렇다면 OS로 지금 언어 상태를 알아내려 하지 말고,
사용자에게 한영키 키맵을 입력 받아서, 해당 키맵이 인식된 경우 커서 색상을 바꿔주면 어떨까요 ??

사용자 지정 한영키 키맵 활용

왜 안 되는가?

  • 한영키처럼 시스템에서 활용 중인 키맵인 경우, 플러그인이 이벤트를 잡아내지 못함

실제 테스트 해봤을 때, 한영키를 포함한 시스템 키맵만 잡아내지 못하더군요...ㅜㅜ
결국 한영 여부는 OS에 의존해서 구별할 수 밖에 없었습니다.

요약

  1. 한영키 체크 주기: 키 이벤트에 따라 트리거하는건 어려움, 일정한 시간(x00ms ~ 1초 사이)마다 주기적으로 체크해야함
  2. 한영키 구분 방법: 모든 OS 통일할 방법 없음, OS 각각 개발하자니 유지보수가 어려움, 사용자에게 한영키 키맵을 받아 처리할 수도 없음

🥹 결국 선택한 방법

  • 일정 주기(200ms)마다 한영키 체크 로직 실행
  • Java InputContext 로 한영키 구분
  • 정책적으로 OS 제한 (Windows, macOS만 지원)
    - Linux 환경인 경우 IDE Notification으로 동작하지 않을 수도 있음을 알린다.

한영키 체크 주기는 '빠른 속도로 타이핑하고 있어도 한영키에 즉각 반응하는 것처럼 보이는 정도' 를 찾으려 여러번 테스트를 거쳤고 200ms로 정했습니다.
이건 아직도 이 방법이 최선일지 고민 중인 부분입니다.

로컬 환경이 워낙 다양하다보니, 예외 케이스가 분명 있을 것 같습니다. (구름입력기 케이스 제보해주신 분 감사합니다 💖)

PR은 언제나 받고 있으니 전달해주시면 큰 도움이 될 것 같습니다!!


릴리즈! 🎉

전작에 고생했던 경험으로 이번엔 한번에 심사를 통과했습니다.
(생각보다 플러그인 description까지도 꼼꼼하게 봅니다. 혹시 플러그인 개발해볼 생각이 있으신 분들은 참고하세요!)

아직 따로 해외에 홍보해보진 않았는데요,
예상했던대로 비영어권 사용자에게 먼저 반응이 보이는거 같습니다.
(전작은 처음부터 미국 사용자가 가장 많았습니다.)


FAQ

제 개인 SNS, 글또(💖) 슬랙에는 먼저 홍보를 했는데요.
감사하게도 관심을 많이 가져주시고, 플러그인에 대한 질문도 몇가지 받았습니다.
자주 받았던 질문을 몇개만 정리하고 글을 마무리하려 합니다.

1️⃣ VSCode 버전으로 출시할 계획은 없나요?

이 질문 거의 열몇개 받은거 같아요!
정말 하고싶은데, 하더라도 오래 걸릴거 같아요. (제 현생도 있지만, LangCursor를 재활용할 수 있는 부분이 거의 없다시피 합니다.)
일단 구현 가능한지, LangCursor 만큼 빠른 색상 전환이 가능한지 등 짬짬이 조사를 해보려고 합니다.

2️⃣ 지금은 1.0.2 버전이던데, 업데이트 사항이 뭐였나요 ?

v1.0.2 릴리즈 노트

성능 개선을 (꽤 많이) 했습니다!
IntelliJ Profiler로 돌려본 메모리 전후 차이를 보여드리면 아래와 같습니다.
(CPU 점유율은 큰 차이가 안 나는데, 메모리가 90% 가까이 절감되었습니다.)

이전

  • 오픈한 프로젝트 별로 각각 한영키 체크 로직이 실행되는 구조라, 여러개 프로젝트 실행 시 리소스가 낭비되었습니다.
  • 모든 IDE Event 종료 시마다 한영키 체크 로직을 실행하게 했었습니다. 한영키에 따라 반응이 매우 빠르기는 하나, 그렇게까지 빠르게 하면서 리소스를 차지할 필요는 없었습니다.

이후

  • 프로젝트 개수에 상관없이 한영키 체크하는 스레드가 단 하나만 존재하도록 수정했습니다.
  • 한영키 체크 로직 주기를 200ms로 고정했습니다.

3️⃣ 한글일 때도 커서 색상 바꿀 수 있게 해주면 안 되나요?

다음 버전 기능으로 개발 중입니다! >.0

4️⃣ JetBrains IDE의 플러그인을 개발해보고 싶은데, 어떻게 하면 되나요 ?

사실 JetBrains 플러그인의 경우 한국어 자료가 매우 부족합니다. (영어도 그렇게 많은거 같지는...)
저도 거의 공식 문서만 더듬더듬 찾아가면서 한거라 따로 비법(?)같은게 없습니다.

우선 주 언어는 Kotlin이나, Java를 사용하셔야 합니다.

저는 JetBrains에서 제공하는 플러그인 개발 템플릿의 도움을 많이 받았습니다.
샘플코드, CI/CD 까지 전부 제공해주니 사용하시면 좀 더 편하게 개발하실 수 있을겁니다.
템플릿 리드미가 상세하게 잘 되어있는 편이라, 보시면서 Jetbrains 플러그인 구조 파악에 도움이 되실겁니다.

그리고 플러그인 개발 공식 문서를 참고해가며 그때그때 필요한 클래스를 찾으시면 될 것 같습니다.

전 기존에 공개된 다른 플러그인들의 코드를 어느정도 참고해가면서 도움을 얻었습니다.

profile
툴 만들기 좋아하는 삽질 전문(...) 주니어 백엔드 개발자입니다.

12개의 댓글

comment-user-thumbnail
2024년 1월 22일

숑숑님 덕분에 바로 플러그인 설치하고 며칠 사용해봤습니다!
caps lock을 누를 때 정확성이 높아져서 생각보다 좋은 것 같아요!
저도 플러그인을 만들어보고픈 마음이 스멀스멀 올라왔네요. 감사합니다.

1개의 답글
comment-user-thumbnail
2024년 1월 23일

제가 너무나도 원하던 기능이라 바로 깔아서 사용해봤는데.... 한글이든 영어든 모두 빨간색으로 표시되네요 ㅜ

1개의 답글
comment-user-thumbnail
2024년 2월 4일

우와 아이디어도 너무 좋고 실행력도 대단하세요!

1개의 답글
comment-user-thumbnail
2024년 2월 13일

감사합니다
덕분에 코딩할때 너무 편해졌어요!

답글 달기
comment-user-thumbnail
2024년 2월 14일

안녕하세요, 숑숑님 덕분에 너무나 편하게 사용하고 있습니다!
그런데 설 지나고부터 영문일때 빨간 커서이고, 색상을 바꾸면 기본 커서 색이 변경됩니다..
이전에는 영문일때 기본 커서이고 한글일때 빨간색이었던 것 같은데 혹시 기능이 변경되었나요?

3개의 답글