Skip to content

fix: Supplementary PUA-A (U+F02B1~F02C4) SVG 출력 정정 (closes #513)#600

Closed
oksure wants to merge 2 commits into
edwardkim:develfrom
oksure:contrib/fix-pua-supplementary-svg
Closed

fix: Supplementary PUA-A (U+F02B1~F02C4) SVG 출력 정정 (closes #513)#600
oksure wants to merge 2 commits into
edwardkim:develfrom
oksure:contrib/fix-pua-supplementary-svg

Conversation

@oksure

@oksure oksure commented May 5, 2026

Copy link
Copy Markdown
Contributor

문제

Task #509 에서 map_pua_bullet_char 에 Supplementary PUA-A (U+F02B1F02B9 → ①⑨) 매핑을 추가했으나, convert_pua_enclosed_numbers (composer) 가 동일 범위를 CharOverlap(border_type=3, 사각형 안의 숫자) 으로 먼저 변환하여 매핑이 도달하지 못했습니다.

결과: SVG 에 ① 대신 "1" (사각형 박스) 이 렌더링됨.

수정 내용

  1. pua_enclosed_border_type: F02B1~F02C4 범위 제거 — CharOverlap 대상에서 제외
  2. map_pua_bullet_char: F02BAF02C4 (⑩⑳) 매핑 추가 — 전체 20자 완성
  3. 반전 사각형 (F02CE~F02E1): CharOverlap 유지 (표준 Unicode 대응 문자 부재)

검증

cargo test   # 전체 통과
cargo clippy -- -D warnings   # 경고 없음
  • samples/mel-001.hwp p2: ①②③ <text> 요소 정상 출력 (기존: "1" "2" "3" CharOverlap)
  • samples/pua-test.hwp: ①~⑨ 총 9개 SVG text 확인 (기존: 0개)

영향 범위

샘플 사용 codepoint 변경 전 변경 후
mel-001 F02B1~F02B3 "1" "2" "3" 박스 ① ② ③
kps-ai F02B1, F02B2 "1" "2" 박스 ① ②
KTX F02EF · (circle) · (circle, 변경 없음)

이 변경이 프로젝트 방향과 맞지 않으면 피드백 부탁드립니다.

)

근본 원인: convert_pua_enclosed_numbers (composer) 가 F02B1~F02C4 를
CharOverlap(border_type=3) 으로 변환하여, map_pua_bullet_char 의
①~⑨ 매핑이 도달하지 못함.

수정:
- pua_enclosed_border_type 에서 F02B1~F02C4 범위 제거 (CharOverlap 제외)
- map_pua_bullet_char 에 F02BA~F02C4 → ⑩~⑳ 매핑 추가
- 반전 사각형 (F02CE~F02E1) 은 CharOverlap 유지 (표준 Unicode 부재)

검증: mel-001.hwp, pua-test.hwp — ①②③ SVG text 요소 정상 출력 확인.
Copilot AI review requested due to automatic review settings May 5, 2026 03:39

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Pull request overview

Supplementary PUA-A(U+F02B1F02C4) 문자가 SVG 등 렌더링에서 CharOverlap(사각형 박스 숫자)로 먼저 처리되어 원문자(①⑳) 매핑이 적용되지 않던 문제를 해결하려는 PR입니다.

Changes:

  • map_pua_bullet_char에 Supplementary PUA-A 원문자 매핑을 ⑩~⑳까지 확장
  • convert_pua_enclosed_numbers의 CharOverlap 대상에서 U+F02B1~F02C4 범위를 제외
  • 관련 주석/설명 업데이트

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 3 comments.

File Description
src/renderer/layout/paragraph_layout.rs Supplementary PUA-A 원문자 매핑 확장(①~⑳)
src/renderer/composer.rs CharOverlap(PUA 테두리 숫자) 판별에서 U+F02B1~F02C4 제외하여 텍스트 렌더링 매핑이 도달하도록 조정

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines 2913 to +2933
@@ -2920,6 +2920,17 @@
0xF02B7 => '\u{2466}', // ⑦
0xF02B8 => '\u{2467}', // ⑧
0xF02B9 => '\u{2468}', // ⑨
0xF02BA => '\u{2469}', // ⑩
0xF02BB => '\u{246A}', // ⑪
0xF02BC => '\u{246B}', // ⑫
0xF02BD => '\u{246C}', // ⑬
0xF02BE => '\u{246D}', // ⑭
0xF02BF => '\u{246E}', // ⑮
0xF02C0 => '\u{246F}', // ⑯
0xF02C1 => '\u{2470}', // ⑰
0xF02C2 => '\u{2471}', // ⑱
0xF02C3 => '\u{2472}', // ⑲
0xF02C4 => '\u{2473}', // ⑳
Comment on lines 2904 to 2915
/// **Supplementary PUA-A (0xF02B0~0xF02FF)** — 한컴 자체 PUA 영역.
/// 원문자 (①~⑨, U+2460~U+2468) 와 별 (★ U+2605) 등을 본 영역에 저장.
/// Task #509 의 한컴 PDF 정답지 시각 검증으로 매핑 확정.
pub(crate) fn map_pua_bullet_char(ch: char) -> char {
let code = ch as u32;

// Supplementary PUA-A — 한컴 자체 영역 (Task #509 한컴 정답지 정합)
if (0xF02B0..=0xF02FF).contains(&code) {
return match code {
// 원문자 ①~ (mel-001 / kps-ai 사용 영역, 한컴 PDF 시각 검증)
// 원문자 ①~ (mel-001 / kps-ai 사용 영역, 한컴 PDF 시각 검증)
0xF02B1 => '\u{2460}', // ①
0xF02B2 => '\u{2461}', // ②
Comment thread src/renderer/composer.rs
Comment on lines 988 to 1006
@@ -1003,11 +1000,7 @@ fn pua_enclosed_border_type(ch: char) -> Option<u8> {
/// draw_char_overlap()에서 호출하여, 실제 렌더링 시에만 변환한다.
pub fn pua_to_display_text(ch: char) -> Option<String> {
let cp = ch as u32;
// 사각형 안의 숫자: U+F02B1(1) ~ U+F02C4(20)
if (0xF02B1..=0xF02C4).contains(&cp) {
let num = cp - 0xF02B0;
return Some(format!("{}", num));
}
// U+F02B1~F02C4 는 map_pua_bullet_char 에서 ①~⑳ 으로 매핑 — 여기 도달 불가
// 반전 사각형 안의 숫자: U+F02CE(1) ~ U+F02E1(20)
if (0xF02CE..=0xF02E1).contains(&cp) {
let num = cp - 0xF02CD;
- 테스트: supplementary_pua_a_maps_circled_digits 에 F02BA~F02C4 검증 추가
- 주석: "①~⑨, U+2460~U+2468" → "①~⑳, U+2460~U+2473" 으로 갱신
- 폭 계산: seg_widths 루프에서 map_pua_bullet_char 적용 후 estimate_text_width
  호출 — PUA 원본 (메트릭 부재 → 0.5em 폴백) 대신 매핑된 문자 (① 등 전각)
  기준으로 폭 계산하여 정합 유지
@oksure

oksure commented May 5, 2026

Copy link
Copy Markdown
Contributor Author

Addressed review feedback in aafe85a:

  • ⑳ (F02BAF02C4) 테스트 추가
  • 주석 ①⑨ → ①⑳ 갱신
  • seg_widths 폭 계산에 map_pua_bullet_char 적용 — PUA 원본 대신 매핑된 문자 기준으로 폭 추정하여 레이아웃 정합 유지

edwardkim added a commit that referenced this pull request May 5, 2026
PR #600 (closes #513, @oksure Hyunwoo Park) 1차 검토:
- 본질 결함: Task #509 의 map_pua_bullet_char 매핑이
  convert_pua_enclosed_numbers (composer) 의 CharOverlap 변환에 막혀 도달 못 함
- 본질 정정: composer.rs 에서 F02B1~F02C4 CharOverlap 제외 +
  paragraph_layout.rs 에 ⑩~⑳ 매핑 추가 (전체 20자 완성)
- Copilot review 3개 응답 (aafe85a): ⑩~⑳ 테스트 + 주석 + 폭 계산 정합
- PR base skew (PR #571/#599 패턴) — UI MERGEABLE 표시지만 PR base diff
  가 본 사이클 cherry-pick 모두 revert
- 그러나 본질 commit 영역이 본 사이클 처리분과 0 중첩
  (PR #592 의 SPUA-A 저영역 F0000~F00CF 와 다른 코드포인트 영역)
  → commit 단위 cherry-pick 가능
- 본 환경 임시 검증: 2 commits cherry-pick 충돌 0 +
  cargo test --lib --release 1134 passed (회귀 0) + clippy 0건 +
  PUA 테스트 12 passed

권장 처리: 옵션 A — commit 단위 cherry-pick (2 commits, 단순 머지 절대 금지) +
결정적 검증 + 광범위 sweep + 작업지시자 시각 판정.
edwardkim added a commit that referenced this pull request May 5, 2026
…A SVG 출력 정정 — @oksure 2 commits + 시각 판정 ★ 통과)

PR #600 (closes #513, @oksure Hyunwoo Park):
- 본질 결함: Task #509 의 map_pua_bullet_char 매핑이
  convert_pua_enclosed_numbers (composer) 의 CharOverlap 변환에 막혀 도달 못 함
- 본질 정정: composer.rs 에서 F02B1~F02C4 CharOverlap 제외 +
  paragraph_layout.rs 에 ⑩~⑳ 매핑 추가 (전체 20자 완성)
- Copilot review 3개 응답 (aafe85a): ⑩~⑳ 테스트 + 주석 + 폭 계산 정합

PR base skew (PR #571/#599 패턴) — UI MERGEABLE 표시지만 PR base diff
가 본 사이클 cherry-pick 모두 revert. 그러나 본질 commit 영역이
본 사이클 처리분과 0 중첩 (PR #592 의 SPUA-A 저영역 F0000~F00CF 와
다른 코드포인트 영역 F02B1~F02C4) → commit 단위 cherry-pick 가능.

cherry-pick 2 commits (충돌 0, author Hyunwoo Park 보존):
- 34f8547 fix: Supplementary PUA-A (U+F02B1~F02C4) SVG 출력 정정
- 14f30e8 address review: ⑩~⑳ 테스트 추가 + 주석 갱신 + 폭 계산 정합

검증:
- cargo test --lib --release 1134 passed (회귀 0)
- cargo test --lib pua 12 passed (supplementary_pua_a_maps_circled_digits ⑩~⑳ GREEN)
- svg_snapshot 6/6 / issue_546 1 / issue_554 12 / clippy 0 / build --release
- 광범위 페이지네이션 sweep: 164 fixture / 1,614 페이지 / 회귀 0
- SVG 정량 (원문자 출현): pua-test 0→9 / mel-001 20→34 / kps-ai 32→34 /
  KTX 변경 없음 (PR 본문 100% 재현)

시각 판정 ★ 통과.

별개 영역 발견: pua-test U+F53A 옛한글 자모 시퀀스의 아래아 (U+119E ᆞ)
글리프 미렌더 — 별도 이슈 #615 등록 (옛한글 폰트 fallback 영역).

closes #513.
@edwardkim

Copy link
Copy Markdown
Owner

@oksure 님 안녕하세요.

본 PR 의 본질 2 commits 핀셋 cherry-pick 후 devel merge 완료되었습니다 (`9768819`).

처리 결과

본질 cherry-pick

  • `77986135` 본질 정정 (composer.rs F02B1F02C4 CharOverlap 제외 + paragraph_layout.rs ⑩⑳ 매핑 추가)
  • `aafe85ae` Copilot review 응답 (⑩~⑳ 테스트 + 주석 + 폭 계산 정합)
  • 충돌 0건 (PR mergeable=MERGEABLE 이지만 PR base 가 본 devel 보다 광범위 뒤처짐. 단순 머지 시 본 사이클 cherry-pick 모두 revert 위험 → commit 단위 cherry-pick 으로 처리. 다행히 본 PR 의 본질 영역이 PR [m100] exam_eng.hwp p7 #40 글상자 사이 화살표 누락 — PUA U+F003B → ↓ 매핑 추가 (closes #588) #592 의 SPUA-A 저영역과 다른 코드포인트라 0 중첩 → 깨끗한 cherry-pick 가능)
  • author Hyunwoo Park 보존

결정적 검증

  • `cargo test --lib --release` 1134 passed (회귀 0)
  • `cargo test --lib pua` 12 passed (`supplementary_pua_a_maps_circled_digits` ⑩~⑳ GREEN)
  • `cargo test --test svg_snapshot/issue_546/issue_554` 모두 통과
  • `cargo clippy --release --lib` 0건

광범위 페이지네이션 sweep

  • 164 fixture / 1,614 페이지 / 페이지 수 회귀 0

SVG 정량 측정 (PR 본문 100% 재현)

Fixture byte 차이 원문자 출현 (before → after)
pua-test 1/1 0 → 9 ✓ (PR 본문 명시 정합)
mel-001 15/21 20 → 34 (+14)
kps-ai 1/80 32 → 34 (+2)
KTX 0/27 변경 없음 ✓ (PR 본문 명시 정합)

시각 판정 (★ 게이트)

작업지시자 시각 검증 결과: ★ 통과. ① ~ ⑳ 정상 출력 + KTX 회귀 0 확인.

본 PR 의 본질 — Task #509 후속 정정

Task #509 의 `map_pua_bullet_char` 매핑이 `convert_pua_enclosed_numbers` (composer) 의 CharOverlap 변환에 막혀 도달 못 하던 결함을 정확히 식별 + 단순 정정 (composer.rs CharOverlap 범위 축소 + paragraph_layout.rs 매핑 확장). 케이스별 명시 가드 (F02B1F02C4 CharOverlap 제외 vs F02CEF02E1 CharOverlap 유지) + Copilot review 의 폭 계산 정합 응답 으로 매핑 우선순위 결함을 깨끗하게 해결한 우수 사례입니다.

별개 영역 발견 — 이슈 #615

본 PR 시각 판정 중 별개 결함 발견 — `samples/pua-test.hwp` 의 U+0F53A 가 `pua_oldhangul.rs:5022` 에서 자모 시퀀스 (ᄒᆞᆫ) 로 임의 변환되지만, 한컴 PDF 정답지는 "Basic-out, 매핑 표 외" 빈 공백 처리. 즉 본 환경의 `pua_oldhangul.rs` 매핑이 한컴 정답지와 정합 안 함.

별도 이슈 #615 등록되었습니다. 본 PR 본질 (Supplementary PUA-A 영역) 과 별개 영역이라 본 PR 은 그대로 close 처리.

처리 보고서: `mydocs/pr/archives/pr_600_report.md` (작성 후 push 됩니다).

본 PR 도 4번째 PR (PR #581/#582/#583 모두 cherry-pick 완료) 에서 일관 우수한 진단 + 정정 + Copilot review 응답 흐름이었습니다. 감사합니다.

@edwardkim edwardkim closed this May 5, 2026
edwardkim added a commit that referenced this pull request May 5, 2026
- 처리 보고서 추가: mydocs/pr/archives/pr_600_report.md
  PR #600 (closes #513, @oksure) commit 단위 cherry-pick 2 commits +
  결정적 검증 + 광범위 sweep (164 fixture / 1,614 페이지 / 회귀 0) +
  SVG 정량 (pua-test 0→9 / mel-001 +14 / kps-ai +2 / KTX 변경 없음) +
  시각 판정 ★ 통과
- 검토 보고서 archives 이동:
  mydocs/pr/pr_600_review.md → mydocs/pr/archives/pr_600_review.md
- 5/5 orders 갱신: PR #600 + Issue #615 항목 추가

별개 영역 발견 + 후속 이슈:
- Issue #615: pua-test U+F53A 가 pua_oldhangul.rs:5022 에서 자모 시퀀스
  (ᄒᆞᆫ) 로 임의 변환되지만 한컴 PDF 정답지는 "Basic-out, 매핑 표 외"
  빈 공백 처리 — pua_oldhangul.rs 매핑 한컴 정합 안 함

PUA 회귀 패턴 인식 — 작업지시자 안내 "PUA 가 계속 회귀되는 현상":
PR #587/#562/#592/#600 + Issue #615 누적의 두더지 잡기 패턴.
PUA 매핑 표 통합 재검증 별도 광범위 task 후보.
edwardkim added a commit that referenced this pull request May 5, 2026
v0.7.9 후속 patch 사이클 (5/4 ~ 5/6).

## 신규 기능

- **CLI 바이너리 릴리즈** (Issue #608/#612, @almet 의 요청)
  - 4 플랫폼 GitHub Release 자산 첨부 (Linux x86_64 / macOS x86_64+aarch64 /
    Windows x86_64) + SHA-256 체크섬
- **PNG raster backend** (PR #599, @seo-rii) — render P4 단계
  - native Skia 기반 PageLayerTree → PNG export, native-skia feature gate
  - **AI 파이프라인 + VLM 연동 도입** (메인테이너 후속 정정):
    - --vlm-target claude (1568 longest edge / 1.15 MP, Claude Vision 정합)
    - --scale / --max-dimension (자동 scale 계산)
    - export-png CLI 명령 + 매뉴얼 (한글 + 영문 dual)
    - 한글 폰트 fallback chain + char 단위 fallback (공백 두부 정정) +
      --font-path 동적 로딩

## 외부 PR cherry-pick (13 PR / 7 컨트리뷰터)

- @planet6897 / Jaeook Ryu (협업): PR #587/#589/#561/#564/#570/#575/
  #580/#584/#592/#593/#567
- @oksure (Hyunwoo Park): PR #600 (closes #513)
- @seo-rii: PR #599 (refs #536)
- @cskwork / @johndoekim / @nameofSEOKWONHONG / @jangster77 — 사이클 누적

## 메인테이너 정정

Skia 폰트 영역 5개 정정 (한글 fallback / font-path / char-fallback /
VLM 옵션 / export-png CLI).

## 인프라

- CI 빌드 안정성 (Cargo.toml [[example]] required-features)
- 광범위 페이지네이션 회귀 sweep 도구 (164 fixture / 1,614 페이지 자동)

## 후속 이슈

- #613 (VLM 프리셋 확장)
- #614 (DPI 메타데이터)
- #615 (pua_oldhangul.rs U+F53A 한컴 정합)
- #598 (rhwp-studio 각주 삭제, 외부 컨트리뷰터 공개)

## 잔여 PR (v0.7.11 후속 patch)

PR #601, #602 (@oksure) / PR #607 (@dicebattle) / PR #609 (@jangster77,
Task #604) / PR #611 (@kihyunnn).

상세: CHANGELOG.md (한글) / CHANGELOG_EN.md (영문).
edwardkim added a commit that referenced this pull request May 9, 2026
table-vpos-01.hwpx p.5 12 추진과제 번호 PUA U+F02B1~F02BC 매핑 결함:
- 한컴 PDF 권위: 사각형 안 숫자 1~12
- 본 환경 출력: 원문자 ①~⑫ (PR #600 도입), 10~12 두부 (폰트 폴백)
- 작업지시자 권위 판정: 사각형 안 숫자 정답지

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
edwardkim added a commit that referenced this pull request May 10, 2026
… 외' 정합

PR #737 (@oksure) 옵션 A 처리 — 2 commits cherry-pick + no-ff merge.

본질 정정 (1 file, +24/-4):
- src/renderer/pua_oldhangul.rs (+24/-4):
  · U+F53A 매핑 항목 제거 (line 5022) — hwpspec "Basic-out (매핑 표 외)" 정합
  · 매핑 수 5660 → 5659 동기화 (헤더 doc + test_map_size)
  · 자동 생성 안전성 코멘트 추가 (scripts/gen_pua_oldhangul_rs.py 영역 영역 재생성 시 주의)
  · 회귀 가드 신규: test_hwpspec_unmapped_codepoints_not_in_table (재삽입 차단)

본질 (Issue #615):
- samples/pua-test.hwp 영역 U+F53A 처리 영역 영역 한컴 정답지 (hwpspec "Basic-out, 매핑 표 외", 빈 공백) 영역 정합 부재
- 본 환경 영역 영역 임의 매핑 (자모 시퀀스 ᄒᆞᆫ, [\u{1112}, \u{119E}, \u{11AB}]) 영역 영역 옛한글 자모 글리프 미렌더 영역 영역 박스 표시 영역 영역
- 매핑 단순 제거 영역 영역 한컴 정답지 정합 (빈 공백)

Copilot 리뷰 반영 (commit `efe1867e`): 헤더 매핑 수 5660→5659 + 재생성 안전성 코멘트.

PR supersede 체인 — 별 패턴:
- PR #600 (closes #513, @oksure) Supplementary PUA-A 시각 판정 중 발견된 별 결함 영역 영역 별 PR 영역 영역 분리 후속

자기 검증:
- cherry-pick 충돌 0건
- cargo build/test --release ✅ ALL GREEN
- pua tests ✅ 13 PASS (신규 1건 + 기존 12건, map_size 5659)
- 광범위 sweep 7 fixture / 170 페이지 / 회귀 0 ✅
- WASM 빌드 4.66 MB
- 작업지시자 SVG 시각 판정 ✅ 통과 (samples/pua-test.hwp 영역 영역 빈 공백 정합)

opt-in 정합:
- 단일 코드포인트 영역 영역 case 가드 (feedback_hancom_compat_specific_over_general 정합)
- 다른 PUA 매핑 5658개 영역 영역 보존
- HWP3 한자 영역 (johab_map.rs) 영역 영역 무관 (별 영역)

closes #615
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.

3 participants