그리드 튜닝 참고자료

그리드를 내 입맛대로 손보는 법

OPEN_GRID v1.0.4의 내부 구조와 설계 그림, 그리고 그리드 동작을 바꾸는 override 튜닝을 전문 용어 없이 차근차근 풀어 설명합니다. 어려운 단어는 풀어 쓰되, 사실은 빠짐없이 담았습니다.

Overview

그리드 튜닝이란? 왜 필요한가

"그리드"는 엑셀처럼 행과 열로 데이터를 보여 주고 편집하게 해 주는 화면 부품입니다. "튜닝"은 그 부품의 기본 동작을 우리 업무에 맞게 살짝 바꾸는 일을 말합니다.

OPEN_GRID는 처음부터 많은 기능을 갖추고 있지만, 모든 회사·모든 화면이 똑같이 동작하길 원하지는 않습니다. 예를 들어 "전화번호를 보여줄 때 가운데 네 자리를 별표로 가리고 싶다", "행을 지우기 전에 한 번 더 확인하고 싶다", "엑셀로 내보낼 때 날짜 형식을 우리 회사 양식으로 바꾸고 싶다" 같은 요구가 생깁니다. 이렇게 기본 동작 위에 우리만의 규칙을 덧입히는 일이 바로 튜닝입니다.

한 줄 비유

OPEN_GRID는 잘 만들어진 완성 자동차입니다. 튜닝은 엔진을 뜯어 새로 만드는 게 아니라, 시트 커버를 씌우고 내비게이션을 바꾸는 것처럼 차는 그대로 두고 필요한 부분만 덧대는 것입니다.

OPEN_GRID의 튜닝이 특별한 이유는 원래 코드(자동차 본체)를 한 줄도 고치지 않고 동작을 바꿀 수 있다는 점입니다. 본체를 안 건드리니, 나중에 OPEN_GRID가 새 버전으로 업데이트되어도 우리가 덧입힌 규칙이 깨지거나 충돌할 걱정이 적습니다. 이 방식의 이름이 override(오버라이드, "덮어쓰기")입니다.

참고로 OPEN_GRID의 현재 정식 버전은 1.0.4입니다. override 튜닝 기능은 정식 출시인 1.0.0부터 제공되며, 이 자료에 보이는 "v1.0.0" 표기는 그 기능이 처음 포함된 릴리스를 가리킵니다. (1.0.1~1.0.4는 버그 수정·라이선스 정비·문서 보강 패치입니다.)

File Structure

파일 구조 — 어떤 파일이 무슨 일을 하나

OPEN_GRID의 핵심 코드는 src/core/ 폴더 한곳에 모여 있습니다. 파일이 많아 보이지만, 역할별로 묶어 보면 "한 부서씩 일을 나눠 맡은 회사"처럼 깔끔하게 정리됩니다.

큰 그림: 안내데스크 한 곳 + 전문 부서 여럿

OpenGrid.ts(파사드)는 손님이 처음 만나는 안내데스크입니다. 손님(개발자)은 안내데스크에만 말을 걸고, 안내데스크가 각 전문 부서(매니저·엔진)에 일을 나눠 줍니다. 부서가 20종이 넘지만, 우리는 안내데스크 하나만 알면 됩니다.

역할별로 묶어 본 핵심 파일

안내데스크 · 튜닝 창구

OpenGrid.ts · OverrideKernel.ts · types.ts · index.ts

모든 부서를 조립하고 손님 요청을 받는 정문. OverrideKernel.ts가 바로 "덮어쓰기 튜닝"을 처리하는 새 부품이고, types.ts는 주고받는 데이터의 규격서입니다.

데이터 보관 · 정렬 · 필터

DataLayer.ts · RowManager.ts · ColumnLayout.ts

실제 데이터를 들고 있고, 무엇이 바뀌었는지 기억하며, 정렬·필터·행 추가삭제·열 폭 계산을 맡습니다.

셀 편집 · 키보드 · 찾기

CellEditManager.ts · CellEventHandler.ts · CellTypeRegistry.ts · KeyboardManager.ts · FindBarManager.ts

셀을 클릭해 고치고, 키보드로 이동하고, 원하는 값을 찾는 등 "사용자가 직접 만지는" 동작을 담당합니다.

정렬 · 필터 · 페이지

SortFilterManager.ts · FilterPanel.ts · FilterSelect.ts · Pagination.ts

정렬·필터의 현재 상태를 관리하고, 필터 패널 화면과 페이지 나누기를 그립니다.

화면 그리기 · 스크롤

GridRenderer.ts · VirtualScroll.ts

실제 표를 화면에 그리는 가장 큰 부서. 데이터가 수만 건이어도 "지금 눈에 보이는 부분만" 그려서 빠릅니다.

합계 · 그룹 · 트리 · 피벗 · 수식

FooterManager.ts · GroupEngine.ts · GroupTreeManager.ts · TreeEngine.ts · PivotEngine.ts · FormulaEngine.ts

맨 아래 합계줄, 같은 값끼리 묶는 그룹, 펼치고 접는 트리, 피벗 표, 셀 수식 계산을 처리합니다.

내보내기 · 변환

ExportManager.ts · WorksheetManager.ts · XmlConverter.ts

엑셀·CSV로 내보내고, 여러 시트(탭)를 관리하고, XML/SAP 형식을 읽고 씁니다.

그리드↔그리드 (크로스그리드)

CrossGridMapper.ts · CrossGridRegistry.ts · GridShuttle.ts · RowDragDrop.ts · DragVisuals.ts

두 그리드 사이에서 행을 끌어다 옮기고, 열을 서로 짝지어 주고, 드래그할 때 시각 효과를 보여 줍니다.

기타 UI · 도메인

ContextMenu.ts · OrgChart.ts · MergeEngine.ts · MaskingEngine.ts

마우스 우클릭 메뉴, 조직도 보기, 셀 병합, 개인정보 가리기(마스킹)를 담당합니다.

수치 · 공통 도구

OGDecimal.ts · MathUtils.ts · EventEmitter.ts · TriggerManager.ts

정밀한 소수 계산, 공통 수학 도구, "무슨 일이 일어났다"는 알림(이벤트), 동작을 막거나 취소하는 트리거를 제공합니다.

에디터 · 렌더러 묶음

editors/ (CellEditor · DateEditor · SelectEditor) · renderers/ (CellRenderer)

셀을 고칠 때 뜨는 입력 도구(기본·날짜·선택)와, 셀 값을 보기 좋게 그려 주는 렌더러가 하위 폴더에 모여 있습니다.

프레임워크 어댑터

src/react/ (OpenGrid.tsx) · src/vue/ (OpenGrid.vue)

React·Vue에서도 그대로 쓸 수 있게 감싸 주는 어댑터. React 18 이상, Vue 3 이상에서 선택적으로 동작합니다.

한눈에 보는 파일 트리

소스(src/)·빌드 산출물(dist/)·배포 페이지(deploy/)·설계 문서(docs/)의 구조를 트리로 정리했습니다.

OPEN_GRID/ ├─ src/ ← 개발 소스 │ ├─ core/ ← 그리드 핵심 엔진 │ │ ├─ OpenGrid.ts ← 안내데스크(파사드) │ │ ├─ OverrideKernel.ts ← override 튜닝 부품 ★ │ │ ├─ types.ts ← 공통 타입 규격서 │ │ ├─ DataLayer.ts │ │ ├─ RowManager.ts │ │ ├─ GridRenderer.ts │ │ ├─ VirtualScroll.ts │ │ ├─ CellEditManager.ts │ │ ├─ SortFilterManager.ts │ │ ├─ ExportManager.ts │ │ ├─ CrossGridMapper.ts │ │ ├─ GroupEngine.ts · PivotEngine.ts · FormulaEngine.ts │ │ ├─ editors/ ← CellEditor · DateEditor · SelectEditor │ │ └─ renderers/ ← CellRenderer │ ├─ react/ │ │ └─ OpenGrid.tsx ← React 18+ 어댑터 │ └─ vue/ │ └─ OpenGrid.vue ← Vue 3+ 어댑터 ├─ dist/ ← 빌드 산출물(배포용) │ ├─ open-grid.js ← 코어 번들 │ ├─ open-grid.esm.js │ ├─ OverrideKernel.d.ts ← override 타입 정의 ★ │ ├─ open-grid-react.js │ ├─ open-grid-vue.js │ ├─ style.css │ └─ xlsx.worker.js ← 엑셀 전용(선택 로드) ├─ deploy/ ← 배포 사이트 소스 │ ├─ grid-tuning/ ← 이 페이지 │ │ ├─ index.html │ │ ├─ OPEN_GRID_GUIDE.md ← 개발자 가이드 (다운로드) ★ │ │ ├─ AI_OPEN_GRID_GUIDE.md ← AI override 가이드 (다운로드) ★ │ │ └─ img/ ← UML SVG 15종 + hero │ └─ demo/v2/ ← 라이브 데모 (서버 전용) ├─ docs/design/uml/ ← PlantUML 설계 원본 │ ├─ *.puml ← 다이어그램 소스 │ └─ _panel/ ← 최종 설계 종합(94_final_synthesis.md 등) ├─ package.json ← version 1.0.4 └─ index.ts ← 패키지 진입점

완성품(빌드 산출물)은 어떤 모습인가

개발용 코드(src/)는 빌드를 거쳐 dist/ 폴더의 실제 배포 파일이 됩니다. 사용자는 코어(open-grid.js), React용, Vue용, 그리고 스타일(style.css)을 골라 가져다 씁니다. 엑셀 기능에 쓰이는 무거운 부분(xlsx)은 따로 떼어 두어, 필요할 때만 불러오도록 했습니다. 튜닝 부품인 OverrideKernel의 타입 정의(OverrideKernel.d.ts)도 빌드 결과물에 포함되어 있어, 이미 사용할 준비가 되어 있습니다.

튜닝과 직접 연결된 두 가지 핵심 사실

Design Diagrams

UML 설계 그림 — 이 그림은 무엇을 말하나

UML은 "코드를 그림으로 그린 설계도"입니다. 글로 길게 설명할 구조를 한 장의 그림으로 보여 줍니다. 여기서는 프로젝트 전체 구조 10장과, 튜닝(override) 설계 5장을 차례로 보고, 각 그림이 무엇을 말하는지 한 단락씩 풀어 봅니다.

가. 프로젝트 전반 설계 그림 10종

모두 실제 코드와 1:1로 대조해 검수를 마친(결함 0·회귀 0) 그림입니다.

1. 4계층 조감도

component

전체를 위에서 내려다본 지도입니다. 위에서부터 프레임워크 어댑터 → 안내데스크(파사드) → 6개 도메인 부서 → 순수 계산 엔진과 화면(DOM) 순으로, 일이 어느 방향으로 흐르는지를 한 장에 담았습니다.

4계층 아키텍처 조감도

2. 안내데스크 + 6부서 합성도

class

안내데스크(OpenGrid)가 여섯 개의 핵심 부서를 어떻게 품고, 필요한 도구를 각 부서에 넣어 주는지를 보여 줍니다. "누가 누구를 가지고 있나"를 한눈에 알 수 있습니다.

파사드와 도메인 매니저 합성 클래스도

3. 데이터 보관소(DataLayer) 모델

class

데이터를 담는 부서의 속을 들여다본 그림입니다. 각 행이 어떤 정보를 들고 있고, "안 바뀜·추가됨·수정됨·삭제됨" 같은 상태를 어떻게 기억하는지 그 구조를 보여 줍니다.

DataLayer 데이터 모델 클래스도

4. 데이터 채워 넣기(setData) 흐름

sequence

그리드에 데이터를 한꺼번에 넣을 때 일이 일어나는 순서를 시간 순으로 그렸습니다. 넣기 전후의 트리거 점검, 필터 적용, 트리·그룹으로 나뉘는 갈림길까지 차례대로 따라갈 수 있습니다.

setData 데이터 적재 시퀀스도

5. 가상 스크롤 렌더 사이클

sequence

데이터가 아주 많아도 빠른 비결을 보여 줍니다. 화면을 다시 그릴 적절한 타이밍을 잡고, "지금 눈에 보이는 범위"만 계산해 그 부분만 그리는 과정을 순서대로 설명합니다.

가상 스크롤 렌더 시퀀스도

6. 셀 편집 라이프사이클

sequence

셀 하나를 고치는 전 과정입니다. 편집해도 되는 셀인지 판단하고, 입력 도구(에디터)를 띄우고, 다 고치면 값을 확정해 닫기까지 — 클릭에서 저장까지의 흐름을 따라갑니다.

셀 편집 라이프사이클 시퀀스도

7. 그리드↔그리드 행 이동

sequence

한 그리드의 행을 다른 그리드로 끌어다 옮길 때의 순서입니다. 드래그나 셔틀로 행을 옮기면서, 열을 서로 짝짓고, 3단계 이벤트가 차례로 발생하는 과정을 보여 줍니다.

크로스그리드 행 이동 시퀀스도

8. 행 상태 전이도

state

한 행이 "안 바뀜 → 추가됨 → 수정됨 → 삭제됨" 같은 상태들 사이를 어떤 조건에서 오가는지를 신호등처럼 그렸습니다. 어떤 동작이 어떤 상태 변화를 일으키는지 알 수 있습니다.

행 변경 상태 전이도

9. 빌드 · 배포 파이프라인

activity

개발 코드가 배포 파일로 바뀌는 작업 라인입니다. 라이브러리 빌드 → 데모 사이트 빌드 → 코드 난독화 순으로 이어지는 공정을 순서도로 보여 줍니다.

빌드 배포 파이프라인 액티비티도

10. 프레임워크 어댑터 통합

component

React·Vue 어댑터가 코어를 어떻게 감싸 안고, 각 프레임워크의 생애주기(생성·소멸)에 맞춰 그리드를 켜고 끄는지를 보여 줍니다.

프레임워크 어댑터 통합 컴포넌트도

나. override 튜닝 설계 그림 5종

"본문을 한 줄도 안 고치고(C1) 어떻게 커스터마이징할 수 있나"를 풀어낸 설계 그림들입니다.

11. 도입 전 모습 (BEFORE)

before

override가 없던 시절의 그림입니다. 옵션·이벤트·트리거만으로는 바꿀 수 있는 게 제한적이었다는 점, 즉 "왜 새 방법이 필요했는가"의 출발점을 보여 줍니다.

override 도입 전 v0.4.0 구조

12. 도입 후 모습 (AFTER, 상세)

after

튜닝 부품(OverrideKernel)이 더해진 뒤의 구조입니다. 두 가지 튜닝 방식(본문 무수정 순수 래핑 ✅ / 슬롯 교체 🔧), 무한 반복을 막는 안전장치, 프레임워크 연결까지 자세히 담겨 있습니다.

override 도입 후 v0.5.0 상세 구조

13. 도입 전후 한 세트 비교

before · after

앞의 BEFORE와 AFTER를 한 장에 나란히 놓고, override가 둘을 어떻게 잇는지 화살표로 보여 줍니다. "본문을 안 고친다(C1)"는 약속이 그림 범례로 정리되어 있습니다.

override 도입 전후 비교 한 세트

14. 여러 튜닝이 겹칠 때의 합성 방식

composition

같은 동작에 튜닝을 여러 번 겹쳐 입혔을 때 어떤 순서로 실행되는지를 보여 줍니다. 먼저 등록한 것이 안쪽(원본에 가까움), 나중에 등록한 것이 바깥쪽이 되며, 안쪽 원본은 orig() 호출로 불려 나옵니다.

override 합성 포맷 (FIFO 레이어)

15. 무엇을 쓸지 고르는 판단 기준

decision

상황에 따라 override·strategy·trigger 중 무엇을 써야 하는지 판단을 도와주는 흐름도입니다. "동작을 감쌀까, 알고리즘을 갈아낄까, 막거나 취소할까"를 선택하는 지도 역할을 합니다.

override vs strategy vs trigger 의사결정 기준
Override Tuning

override 튜닝 — 쉽게 풀어 보기

이제 핵심입니다. override는 그리드의 동작을 "본체를 안 고치고" 바꾸는 방법입니다. 어떻게 그런 일이 가능한지, 그리고 두 종류의 튜닝이 어떻게 다른지 차근차근 살펴봅니다.

비유: 동작을 감싸는 "포장지"

그리드의 어떤 동작(예: 행 삭제)을 선물 상자라고 합시다. override는 그 상자를 새 포장지로 한 번 더 싸는 일입니다. 포장지(우리 규칙) 안에는 원래 상자(orig, 원본 동작)가 그대로 들어 있어, 우리가 원할 때 orig()를 불러 원래 동작을 실행할 수 있습니다. 포장만 바꿨을 뿐 상자 자체는 손대지 않았으니, 언제든 포장을 벗기면(restore) 원래대로 돌아옵니다.

두 가지 튜닝 방식 — ✅ 순수 래핑 vs 🔧 슬롯 교체

✅ 순수 래핑 (본문 무수정)

바깥에 보이는 정문(공개 메서드)을 그대로 감싸는 방식

  • grid.override(이름, 함수) 형태로 사용
  • 원본 코드는 한 줄도 바뀌지 않습니다
  • 예: 표시값 후처리(getDisplayValue), 데이터 넣기(setData), 셀 쓰기(writeCell), 행 삭제 확인(deleteRow), 엑셀 내보내기 감싸기(exportExcel) 등
  • 가장 안전하고 흔히 쓰이는 방식

🔧 슬롯 교체 (최소 침습)

부서 안에 미리 뚫어 둔 "교체 구멍(슬롯)"에 새 부품을 끼우는 방식

  • grid.override.strategy(슬롯, 함수) 형태로 사용
  • 부서 본문에 슬롯 참조 한 줄이 미리 심겨 있어야 동작 (정의상 본문에 최소한의 준비가 필요)
  • 6개 슬롯: sortComparator(정렬), filterPredicate(필터), displayFormatter(표시 형식), cellSerializer(내보내기 변환), summaryOp(합계), groupKeyFn(그룹 기준)
  • 정렬·필터 같은 "계산 규칙 자체"를 갈아끼울 때 사용

주요 API 한눈에

grid.override(name, (orig, ...args) => result) // 순수 래핑 (공개 메서드 감싸기) grid.override.strategy(slot, fn) // 🔧 슬롯 교체 (알고리즘 6종) grid.restore(name) // 메서드 하나 원래대로 grid.restoreAll() // 전부 원래대로 (그리드 종료 시 자동) grid.hasOverride(name) / grid.getOverrideNames() // 무엇이 튜닝됐는지 조회 OpenGrid.defaultOverride(name, fn, opts?) // 앞으로 만들 모든 그리드에 기본 적용 OpenGrid.defaults.strategy(slot, fn) // 모든 그리드 기본 슬롯

안전장치 — 튜닝이 사고로 이어지지 않게

꼭 알아 둘 주의점

override · strategy · trigger 역할 구분

세 가지는 비슷해 보여도 쓰임이 다릅니다. 트리거(TriggerManager)는 동작을 막거나 취소할 때, 이벤트(EventEmitter)는 무슨 일이 일어났는지 구경만 할 때, 오버라이드(OverrideKernel)는 동작 자체를 감싸 바꿀 때 씁니다. 셋이 깔끔히 나뉘어 있어 서로 충돌하지 않으며, override 안에서 orig()를 부르면 기존 트리거도 함께 작동합니다(정문을 거치는 동작에 한함).