본질
rhwp-studio/src/view/virtual-scroll.ts는 zoom ≤ 0.5 + pages > 1 + viewport > 0 일 때 다중 열 그리드 배치로 분기하며 각 페이지의 X 좌표를 pageLefts[i] = marginLeft + col * (pw + gap) 로 열별 계산. canvas-view.ts 는 canvas.style.left = ${pageLefts[i]}px 로 페이지 element 위치 결정.
그러나 input-handler-mouse.ts 는 getPageLeft(pageIdx) 를 0회 호출, 14곳 분기 모두 단일 컬럼 가정 공식 사용:
const pageLeft = (scrollContent.clientWidth - pageDisplayWidth) / 2;
→ 그리드 모드에서 모든 페이지의 click 좌표가 어긋남.
정량 측정 (e2e, 2026-05-07)
samples/exam_kor.hwp (20p) + viewport 1600×1000 + headless Chrome.
zoom=0.5 (columns=2)
| col |
correct (pageLefts[i]) |
buggy (단일 컬럼) |
delta_px |
| 0 |
223.8 |
509.4 |
+285.6 |
| 1 |
795.0 |
509.4 |
−285.6 |
zoom=0.25 (columns=5)
| col |
correct |
buggy |
delta_px |
| 0 |
68.4 |
649.7 |
+581.3 |
| 1 |
359.1 |
649.7 |
+290.6 |
| 2 |
649.7 |
649.7 |
0.0 |
| 3 |
940.3 |
649.7 |
−290.6 |
| 4 |
1230.9 |
649.7 |
−581.3 |
→ 가운데 열 (col 2 @ columns=5) 만 우연히 0px. 양 끝 열 ±581.3px 어긋남.
zoom=1.0 (단일 컬럼 baseline)
모든 페이지 delta=0 → 단일 컬럼 모드 정상 (correct=−1 sentinel → fallback 공식 = buggy 공식 결과).
실제 click 검증
zoom=0.5 + page 1 (col 1) hwpX=100 의도:
- CORRECT click @(865.0) → cursor.pos =
{sec:0, para:39, char:70} (정상)
- BUGGY click @(579.4) → cursor.pos =
{sec:0, para:31, char:0} (page 0 영역 떨어짐)
영향 분기 (14곳)
| Line |
함수 |
트리거 |
| 23 |
onConnectorMouseDown |
연결선 모드 click |
| 129 |
onMouseDown (표 객체) |
선택된 표 click |
| 176 |
onMouseDown (multi picture) |
multi-picture handle |
| 279 |
onMouseDown (line endpoint) |
line endpoint handle |
| 296 |
onMouseDown (rotate) |
rotate handle |
| 357 |
onMouseDown (single picture) |
선택된 그림 본체 |
| 431 |
onMouseDown (table resize) |
표 border |
| 475 |
onMouseDown (일반 click) |
left mousedown 전반 |
| 811 |
onDblClick |
left dblclick |
| 889 |
onContextMenu |
right click |
| 931 |
onMouseMove (connector) |
connector mousemove |
| 1146 |
onMouseMove (picture hover) |
mousemove during picture hover |
| 1196 |
onMouseMove (table hover) |
mousemove during table hover |
| 1243 |
handleResizeHover |
표 border mousemove |
핵심 사용자 영향: 475 / 811 / 889 — 일반 click / dblclick / context menu.
정정 방향
virtualScroll.getPageLeftResolved(pageIdx, containerWidth) 헬퍼 도입:
getPageLeftResolved(pageIdx: number, containerWidth: number): number {
const pl = this.pageLefts[pageIdx] ?? -1;
if (pl >= 0) return pl; // 그리드 모드
const pw = this.pageWidths[pageIdx] ?? 0;
return (containerWidth - pw) / 2; // 단일 컬럼 fallback
}
→ input-handler-mouse 의 14곳 모두 virtualScroll.getPageLeftResolved(pageIdx, sc.clientWidth) 한 줄로 치환. 단일 컬럼 모드는 무회귀 (sentinel −1 → 기존 공식).
한컴 호환 결함
한컴 오피스도 다중 페이지 그리드 모드 (여러 페이지 동시 보기) 가 존재하며, 그 모드에서 click 좌표는 정확히 처리됨 (사용자 직접 시연 확인, 2026-05-07). RHWP 만 그리드 모드에서 click 좌표 어긋남 → 한컴 호환 결함.
본 정정의 기대 동작: 한컴 그리드 모드와 동일하게 클릭 → 클릭한 페이지 안의 정확한 위치에 cursor 배치.
우선순위
High (UX-blocking) — 줌 25%/50% 사용 시 마우스 동작 전반 어긋남.
참고
본질
rhwp-studio/src/view/virtual-scroll.ts는 zoom ≤ 0.5 + pages > 1 + viewport > 0 일 때 다중 열 그리드 배치로 분기하며 각 페이지의 X 좌표를
pageLefts[i] = marginLeft + col * (pw + gap)로 열별 계산. canvas-view.ts 는canvas.style.left = ${pageLefts[i]}px로 페이지 element 위치 결정.그러나 input-handler-mouse.ts 는
getPageLeft(pageIdx)를 0회 호출, 14곳 분기 모두 단일 컬럼 가정 공식 사용:→ 그리드 모드에서 모든 페이지의 click 좌표가 어긋남.
정량 측정 (e2e, 2026-05-07)
samples/exam_kor.hwp(20p) + viewport 1600×1000 + headless Chrome.zoom=0.5 (columns=2)
zoom=0.25 (columns=5)
→ 가운데 열 (col 2 @ columns=5) 만 우연히 0px. 양 끝 열 ±581.3px 어긋남.
zoom=1.0 (단일 컬럼 baseline)
모든 페이지 delta=0 → 단일 컬럼 모드 정상 (correct=−1 sentinel → fallback 공식 = buggy 공식 결과).
실제 click 검증
zoom=0.5 + page 1 (col 1) hwpX=100 의도:
{sec:0, para:39, char:70}(정상){sec:0, para:31, char:0}(page 0 영역 떨어짐)영향 분기 (14곳)
핵심 사용자 영향: 475 / 811 / 889 — 일반 click / dblclick / context menu.
정정 방향
virtualScroll.getPageLeftResolved(pageIdx, containerWidth)헬퍼 도입:→ input-handler-mouse 의 14곳 모두
virtualScroll.getPageLeftResolved(pageIdx, sc.clientWidth)한 줄로 치환. 단일 컬럼 모드는 무회귀 (sentinel −1 → 기존 공식).한컴 호환 결함
한컴 오피스도 다중 페이지 그리드 모드 (여러 페이지 동시 보기) 가 존재하며, 그 모드에서 click 좌표는 정확히 처리됨 (사용자 직접 시연 확인, 2026-05-07). RHWP 만 그리드 모드에서 click 좌표 어긋남 → 한컴 호환 결함.
본 정정의 기대 동작: 한컴 그리드 모드와 동일하게 클릭 → 클릭한 페이지 안의 정확한 위치에 cursor 배치.
우선순위
High (UX-blocking) — 줌 25%/50% 사용 시 마우스 동작 전반 어긋남.
참고
mydocs/troubleshootings/grid_mode_click_coord.mdrhwp-studio/e2e/grid-mode-click-coord.test.mjs