Skip to content

Task #280: 수식 SVG 폰트 스택 재정렬 — Cambria Math 제거#284

Merged
edwardkim merged 5 commits into
edwardkim:develfrom
planet6897:local/task280
Apr 24, 2026
Merged

Task #280: 수식 SVG 폰트 스택 재정렬 — Cambria Math 제거#284
edwardkim merged 5 commits into
edwardkim:develfrom
planet6897:local/task280

Conversation

@planet6897

Copy link
Copy Markdown
Contributor

Summary

  • samples/equation-lim.hwp 수식이 한컴 PDF 대비 "볼드처럼 두껍게" 렌더링되던 문제를 폰트 스택 재정렬로 해소 (수식 SVG 렌더링: 폰트가 볼드처럼 보임 (Cambria Math 폴백) — 폰트 스택 재정렬 #280)
  • src/renderer/equation/{svg_render,canvas_render}.rs 각 1줄 — Cambria Math 제거, Times New Roman 등 얇은 세리프 폴백 추가
  • 레이아웃 계산 불변. 함수명(lim/sin/ln/∫) 크기 규칙 변경 없음 (조사 결과 1.2x 확대는 HWP 일반 규칙 아님을 데이터로 확정)

Root Cause

변경 전 폰트 스택 (svg_render.rs:11):

'Latin Modern Math', 'STIX Two Math', 'Cambria Math', 'Pretendard', serif

Windows 기본 환경에서 앞 두 폰트(Latin Modern Math / STIX Two Math)는 미설치 → Cambria Math (Office 설치 시 자동 포함)가 매칭. Cambria Math는 수학 디스플레이용 heavy-stroke 폰트라 일반 Times 세리프보다
확연히 두꺼움 → 사용자가 "볼드"로 인지.

조사: "lim 1.2x 확대 규칙" 가설 기각

PDF 콘텐츠 스트림을 뜯어보니 BT /F1 110 Tf ... lim ... vs /F1 92 Tf ... f(2+h) ...lim(110pt) 이 본체(92pt) 대비 1.2x 크게 렌더링됨. "함수명 확대 규칙" 의심으로 출발.

그러나 samples/exam_math.hwp 내 수식 16개의 bbox 높이 비교 결과:

수식 bbox 높이 font_size 대비
"b= log 2" 1125 HWPUNIT 1.02x (단순 수식과 동일)
"1", "5" (단일 숫자) 1125 1.02x
"f left(1 right)" 1125 1.02x
"f(x)=x³-8x+7" (위첨자) 1313 1.19x

log가 확대되면 bbox≈1320이어야 하나 1125 → 함수명 1.2x 규칙 없음. PDF의 110/92 차이는 HyhwpEQ 폰트의 ASCII 글리프(l,i,m) vs PUA 수식 글리프(f,h,(,)) em 박스 차이를 HWP 엔진이 보정한 것.

이 가설 기각이 이번 PR의 핵심 — 잘못 적용했으면 다른 수식들이 깨졌을 것.

변경 내역

src/renderer/equation/svg_render.rs:11 + canvas_render.rs:223 (동일 스택 동기):

-'Latin Modern Math', 'STIX Two Math', 'Cambria Math', 'Pretendard', serif
+'Latin Modern Math', 'STIX Two Text', 'STIX Two Math', 'Times New Roman', 'Times', serif

설계 근거:

  • Latin Modern Math 첫 번째 유지 → svg.rs:332--embed-fonts 파이프라인이 "Latin Modern Math" 키 고정 사용. LaTeX 설치 환경에서는 기존처럼 LM Math가 매칭되어 최고 품질 유지.
  • STIX Two Text 추가 → STIX 설치 환경용. Math 변형보다 얇은 본문용.
  • Times New Roman, Times 추가 → Windows/Mac/Linux 공통. Windows에서 여기서 stop되어 볼드 인상 해소.
  • Cambria Math 제거 → Windows 볼드 인상의 근본 원인.
  • Pretendard 제거 → 산세리프(한글+라틴 sans), 수식 부적합.

폴백 시나리오

환경 매칭 결과
LaTeX 설치 Latin Modern Math PDF와 가장 유사 (기존 유지)
Mac + STIX STIX Two Text 얇고 깔끔한 세리프
Windows 기본 Times New Roman 볼드 인상 해소

Before / After / PDF

이미지 설명
mydocs/working/task_m100_280_stage1/before_crop.png 변경 전 (Cambria Math — 두꺼운 획)
mydocs/working/task_m100_280_stage4/after_crop.png 변경 후 (Times New Roman — 얇은 세리프)
mydocs/working/task_m100_280_stage1/pdf_crop.png 한컴 PDF (HyhwpEQ 기준)

HyhwpEQ는 한컴 독점 폰트라 픽셀 단위 일치는 불가. "충분히 근접" 목표 달성.

범위 외 (후속 이슈)

Test plan

  • cargo test --lib equation — 48 pass / 0 fail (수식 전 단위 테스트)
  • cargo test --test svg_snapshot — 3 pass
  • cargo clippy --lib -- -D warnings — clean
  • cargo check --target wasm32-unknown-unknown --lib — clean
  • cargo build --release — success
  • cargo test --lib 전체 — 949 pass / 14 pre-existing fail (git stash 비교로 본 PR 무관 확인 — CFB writer Windows path)
  • samples/equation-lim.hwp — before/after/pdf 3종 시각 비교
  • samples/exam_math.hwp 5개 페이지 회귀 (p001/005/009/013/017):
    • p013에서 lim·sin·ln· 동시 렌더 → 모두 본문과 동일 크기 확인 (함수명 1.2x 없음)
    • 분수, 제곱근, 집합 기호(∩∪), 벡터 화살표, 이탤릭 변수 모두 정상
  • 특수 기호(→, √, ∫, ∑, ∩, ∪) 브라우저 폴백 정상

Closes #280

planet6897 and others added 5 commits April 24, 2026 11:31
- samples/equation-lim.{hwp,pdf} 재현 샘플 추가
- 수행계획서 + 구현계획서 + 단계1 보고서
- 변경 전 SVG/PNG 스냅샷 (before.*) + 한컴 PDF 참조 이미지 (pdf.*)
- 단계4 시각 비교용 before_crop.png / pdf_crop.png 확보

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
- canvas_render.rs:223 set_font 함수가 폰트 문자열 중복 보유 → svg_render.rs 와 동시 수정 필요 (1줄씩)
- svg.rs:332 폰트 임베딩 로직은 "Latin Modern Math" 키 고정 사용 → 새 스택에서 Latin Modern Math 를 첫 번째로 유지해 파이프라인 호환
- 최종 제안 스택: 'Latin Modern Math', 'STIX Two Text', 'STIX Two Math', 'Times New Roman', 'Times', serif
  (Cambria Math 및 Pretendard 제거)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
svg_render.rs EQ_FONT_FAMILY 와 canvas_render.rs set_font 양쪽에서
Cambria Math + Pretendard 제거, STIX Two Text + Times New Roman 추가.

최종 스택: 'Latin Modern Math', 'STIX Two Text', 'STIX Two Math', 'Times New Roman', 'Times', serif

Windows 기본 환경에서 Cambria Math 가 매칭되어 "볼드 인상" 을 유발하던
문제를 Times New Roman 폴백으로 해소. Latin Modern Math 는 첫 번째로
유지해 svg.rs:332 의 폰트 임베딩 파이프라인 호환성 보존.

회귀:
- cargo test --lib equation: 48 passed / 0 failed
- cargo test --test svg_snapshot: 3 passed
- cargo clippy --lib -- -D warnings: clean
- cargo check --target wasm32-unknown-unknown: clean
- cargo test --lib 전체 14건 실패는 기존 CFB writer Windows path 문제 (무관)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
equation-lim.hwp after 이미지 생성:
- after.svg / after.png / after_crop.png
- before_crop 와 비교: "lim" 및 변수 글자가 두꺼운 Cambria Math → 얇은 Times New Roman 으로 변경 확인
- PDF(HyhwpEQ) 와의 격차가 유의미하게 좁혀짐

exam_math.hwp 5개 페이지 회귀 검증 (PNG):
- p001: f(x)=x^3-8x+7, lim, piecewise, 분수
- p005: prime 기호(f'), sin, sqrt
- p009: 집합 기호 (∩, ∪), 분수
- p013: lim, sin, ln, ∫ - 모두 본문과 동일 크기 확인 (함수명 1.2x 확대 없음)
- p017: 벡터 화살표 (Decoration)

전 케이스 레이아웃 변화 없이 폰트 두께만 완화됨. 특수 기호(∩, ∪, ∫ 등)는
브라우저 글리프 폴백으로 정상 표시.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
- mydocs/report/task_m100_280_report.md: 최종 결과 보고서
- mydocs/orders/20260424.md: Task edwardkim#280 섹션 추가 + 종료/대기 이슈 갱신
- GitHub edwardkim#283 등록: 괄호 path 폭 조정 (Phase 2 후속)

이 타스크의 실질적 가치:
- PDF "110 vs 92" 수치로 함수명 1.2x 확대 규칙 의심 → 샘플 bbox 다수 교차
  비교로 규칙 없음 확정 → 잘못된 방향 수정 회피
- Cambria Math 제거 + Times New Roman 폴백의 단순 수정으로 볼드 인상 해소
- exam_math p013 (lim/sin/ln/∫ 동시) 에서 모두 본문 크기 렌더링 재확인

Closes edwardkim#280

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

@edwardkim edwardkim left a comment

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Approved. 🎉

검토 결과

@planet6897 님, 훌륭한 조사 + 최소 수정 PR 감사합니다.

특히 인상 깊은 부분

  • "lim 1.2x 확대 규칙" 가설 기각 — PDF 숫자(110/92) 단일 근거로 판단하지 않고 exam_math.hwp 16개 수식 bbox 교차 비교로 규칙 없음을 데이터 확정. 잘못 적용했으면 log/sin/cos/ln이 모두 깨졌을 것.
  • 설계 안전성Latin Modern Math 첫 번째 유지로 svg.rs:332 임베딩 파이프라인 호환성 보존. 회귀 리스크 최소화.
  • 범위 분리 명확 — 괄호 path 폭 조정은 #283으로 분리 (→ PR #285).

메인테이너 검증

항목 결과
cargo test --lib equation ✅ 48 / 0
cargo test --test svg_snapshot ✅ 3 / 0
cargo test --lib 전체 ✅ 963 / 0 / 1 ignored
cargo clippy --lib -- -D warnings ✅ clean
cargo check --target wasm32 ✅ clean
WASM Docker 빌드 ✅ 성공
rhwp-studio 브라우저 시각 검증 ✅ 볼드 인상 해소 확인

PR 설명의 "14건 pre-existing fail"은 로컬 검증에서 0건이었습니다 (최근 devel 수정으로 자연 해소).

Merge 진행합니다.

@edwardkim edwardkim merged commit 37921ed into edwardkim:devel Apr 24, 2026
6 checks passed
edwardkim added a commit to seanshin/rhwp that referenced this pull request Apr 24, 2026
# Conflicts:
#	mydocs/orders/20260424.md
edwardkim added a commit that referenced this pull request Apr 24, 2026
- 작성자: @planet6897 (Task #280, PR #284)
- Merge commit: 37921ed
- 이슈 #280 closed

검증:
- cargo test --lib: 963 passed / 0 failed
- cargo clippy + wasm32 check: clean
- WASM Docker 빌드 + rhwp-studio 브라우저 시각 검증 성공

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
edwardkim added a commit that referenced this pull request Apr 24, 2026
- 작성자: @planet6897 (Task #283, PR #285)
- Merge commit: 54188ef
- 이슈 #283 closed

검증:
- cargo test --lib: 964 passed / 0 failed (신규 test_paren_stretch_svg 포함)
- cargo clippy + wasm32 check: clean
- WASM Docker 빌드 + rhwp-studio 브라우저 시각 검증 성공

수식 그룹 (#284 + #285) 처리 완료.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
edwardkim added a commit that referenced this pull request Apr 24, 2026
…r 복구 (closes #275)

- 작성자: @planet6897 (Task #275, PR #278)
- Merge commit: 2a27b36 (admin merge, orders 문서 충돌 직접 해결)
- 이슈 #275 closed
- 커뮤니티 리뷰: @seanshin APPROVED

처리 절차:
- PR 브랜치에 origin/devel 머지 → orders 문서 충돌 해결 (Task #275 섹션 "## 5" 재배치)
- planet6897/local/task275에 push (maintainerCanModify 허용)
- 재승인 + admin merge

검증:
- cargo test --lib svg_fragment: 19 passed / 0 failed
- cargo test --lib: 983 passed / 0 failed / 1 ignored (+19 신규 svg_fragment)
- cargo clippy + wasm32 check: clean
- svg_snapshot: 6 passed

파급 효과: WASM canvas 에서 OLE 네이티브 이미지/EMF/OOXML 차트/Placeholder 모두 복구

===== 오늘 처리 5개 PR 완료 =====
#284 (#280) @planet6897 - 수식 폰트 스택
#285 (#283) @planet6897 - 수식 파렌 글리프
#266 (#157/#103) @seanshin - 비-TAC 표 out-of-flow
#273 (#267) @seanshin - right tab 공백 처리
#277 (#147) @seanshin - MEMO 바탕쪽 오분류
#278 (#275) @planet6897 - WASM OLE RawSvg/Placeholder

별도 추적: 이슈 #291 (KTX.hwp 2단 TAC 표 회귀, 핀셋 처리 예정)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
edwardkim added a commit that referenced this pull request Apr 24, 2026
 #297)

- 작성자: @planet6897 (Task #297, PR #300, 오늘 6번째 기여)
- Merge commit: 0e3fb02 (admin merge, orders 3구간 충돌 직접 해결)
- 이슈 #297 CLOSED

처리 절차:
- PR 브랜치에 origin/devel 머지 → orders 섹션 3구간 해결 (#295 "## 7", #296 "## 8", #297 "## 9")
- planet6897/task297 에 push
- 재승인 + admin merge

변경 (1파일):
- src/renderer/layout/table_layout.rs +5 -2:
  - VertRelTo::Page => (col_area.y, col_area.height)  [쪽 본문 영역]
  - VertRelTo::Paper => (0, page_h_approx)  [용지 전체, 유지]
  - HWP 스펙 Page=쪽 본문, Paper=용지 전체 반영

성과:
- pi=22 "* 확인 사항" 박스 y: 1371.5 → 1224.07 (PDF 1226.5 ±2 일치)
- 145 샘플 중 본문 Page 표 13건 + 바탕쪽 5건 회귀 스캔 완료 (의도 범위 외 무회귀)

검증:
- cargo test --lib: 992 passed
- svg_snapshot: 6 passed (golden 유지)
- 실제 SVG y 좌표 확인: 1224.07px (PDF 일치)

#295#297 연결 모범 사례: PR #298 리뷰 중 사전 존재 버그로 분리 → 1시간 만에 PR #300 해결.
초기 가설(바탕쪽 Paper) 폐기 → pdftotext 실측으로 근본 원인(enum 미구분) 발견 → 1줄 수정.

===== 오늘 9번째 PR 머지 =====
#284 #285 #266 #273 #277 #278 #289 #292 #298 #300
+ 메인테이너 핀셋 #296

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@planet6897 planet6897 deleted the local/task280 branch April 30, 2026 00:04
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants