Skip to content

HWPX slash/backSlash 형태 enum 파싱 분리 (#1038)#1039

Closed
planet6897 wants to merge 1 commit into
edwardkim:develfrom
planet6897:task1038-hwpx-slash-diagonal
Closed

HWPX slash/backSlash 형태 enum 파싱 분리 (#1038)#1039
planet6897 wants to merge 1 commit into
edwardkim:develfrom
planet6897:task1038-hwpx-slash-diagonal

Conversation

@planet6897

Copy link
Copy Markdown
Contributor

문제

일부 HWPX 표 셀(borderFill에 <hh:slash type="CENTER"> 만 있고 <hh:diagonal> 요소가 없는 경우)에 한컴 편집기/PDF에는 없는 검정 대각선이 그려진다.

예: samples/2. 인공지능(AI) 기반 재정통합시스템 구축 용역 제안요청서.hwpx 4페이지 헤딩 "Ⅰ 사업안내"(1×3 표). 한컴 2022 PDF p4에는 대각선이 없다.

원인

HWPX borderFill에서 셀 대각선은 독립된 두 요소로 표현된다:

  • <hh:slash>/<hh:backSlash> type → 대각선 방향/형태 enum (NONE/CENTER/…)
  • <hh:diagonal> type/width/color → 실제 선 종류·굵기·색 (HWP5 attr 비트 + DiagonalLine 과 1:1)

기존 파서는 slash/backSlash의 type("CENTER")을 선 종류 파서(parse_border_line_type_code)에 넘겨 Solid로 폴백시키고 diagonal.diagonal_type=1을 설정했다. 선 정의(<hh:diagonal>)가 없는 셀에도 렌더 트리거(border_rendering.rs, diagonal_type != 0)가 켜져 기본 검정 실선이 그려졌다.

수정 (src/parser/hwpx/header.rs 단일 파일)

  • parse_slash_shape_code() 신규: slash 형태 enum → HWP5 attr 3비트 방향 코드 (NONE→0, CENTER→0b010, CENTER_BELOW→0b011, CENTER_ABOVE→0b110, 기타→0b111).
  • set_diagonal_attr_bits(): 3비트 코드를 그대로 기록(기존 nonzero→0b010 축소 제거).
  • slash/backSlash 핸들러: type을 방향 비트(attr)만 설정하도록 분리. diagonal_type 할당·width/color 분기 제거. 선 종류/굵기/색은 <hh:diagonal>가 단독 책임.

렌더러/모델/HWP5·HWP3 경로 무수정.

검증

  • cargo test 전체 통과(실패 0) + 신규 단위/회귀 테스트 4건.
  • 문제 샘플 p4 헤딩: 검정 대각선 3→0 (한컴 PDF 정합).
  • 실제 <hh:diagonal> 보유 표(tac-img-02.hwpx, slash CENTER + diagonal SOLID 셀 포함): 대각선 정상 유지(회귀 없음).

closes #1038

🤖 Generated with Claude Code

## 문제
일부 HWPX 표 셀(borderFill에 <hh:slash type="CENTER"> 만 있고 <hh:diagonal>
요소가 없는 경우)에 한컴 편집기/PDF에는 없는 검정 대각선이 그려졌다.

## 원인
HWPX borderFill에서 셀 대각선은 독립된 두 요소로 표현된다:
- <hh:slash>/<hh:backSlash> type → 대각선 방향/형태 enum (NONE/CENTER/…)
- <hh:diagonal> type/width/color → 실제 선 종류·굵기·색 (HWP5 attr 비트 + DiagonalLine 대응)

기존 파서는 slash/backSlash의 type("CENTER")을 선 종류 파서에 넘겨 Solid로
폴백시키고 diagonal.diagonal_type=1을 설정했다. 선 정의(<hh:diagonal>)가 없는
셀에도 렌더 트리거(diagonal_type != 0)가 켜져 기본 검정 실선이 그려졌다.

## 수정 (src/parser/hwpx/header.rs)
- parse_slash_shape_code() 신규: slash 형태 enum → HWP5 attr 3비트 방향 코드
  (NONE→0, CENTER→0b010, CENTER_BELOW→0b011, CENTER_ABOVE→0b110, 기타→0b111).
- set_diagonal_attr_bits(): 3비트 코드를 그대로 기록(기존 nonzero→0b010 축소 제거).
- slash/backSlash 핸들러: type을 방향 비트(attr)만 설정하도록 분리. diagonal_type
  할당·width/color 분기 제거. 선 종류/굵기/색은 <hh:diagonal>가 단독 책임.

렌더러/모델/HWP5·HWP3 경로 무수정.

## 검증
- cargo test 전체 통과(실패 0) + 신규 단위/회귀 테스트 4건.
- 문제 샘플 p4 헤딩: 검정 대각선 3→0 (한컴 PDF 정합).
- 실제 <hh:diagonal> 보유 표(tac-img-02): 대각선 정상 유지(회귀 없음).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@edwardkim edwardkim self-requested a review May 20, 2026 22:09
@edwardkim edwardkim added the bug Something isn't working label May 20, 2026
@edwardkim edwardkim added this to the v1.0.0 milestone May 20, 2026
@edwardkim

Copy link
Copy Markdown
Owner

검토 완료 — merge 수용. devel 에 반영합니다.

검증 결과

  • CI 전체 pass (Build & Test / Analyze rust·js·py / CodeQL)
  • 본 환경 cargo test --release --lib: 1323 passed, 0 failed (이전 1308 + PR 신규 단위 테스트 4건)
  • cargo fmt --check 통과
  • 책임 분리 설계 (slash/backSlash=방향/형태 enum vs <hh:diagonal>=선 종류·굵기·색) 가 HWPX spec 1:1 정합 확인

처리

  • 단일 본질 commit (3d5c0ead) author (planet6897) 보존 cherry-pick
  • 코드 품질 지적 사항 없음 (clean-up 후속 commit 불필요)

평가

HWPX spec 의 두 요소 (방향/형태 enum vs 선 정의) 책임 분리가 명료합니다. 기존 set_diagonal_attr_bits 의 3비트→1비트 축소를 해소하여 backSlash 분리 + CENTER_BELOW/ABOVE 구분까지 정보 보존된 점도 향후 회귀 방지에 도움됩니다.

신규 단위 테스트 4건 (enum 매핑 + 비트 설정 + #1038 회귀 가드 + 비회귀 보장) 동봉이 본 PR 평가의 핵심이었습니다. 결정적 측정 (검정 대각선 3→0) + 회귀 가드 + parser-only scope 3 조건 정합으로 정량 게이트가 시각 판정을 결정적으로 대체할 수 있었습니다.

scope 정직 ("렌더러/모델/HWP5·HWP3 경로 무수정") 도 본 환경 변경 파일 검증으로 일치 확인했습니다.

기여 감사합니다.

@edwardkim

Copy link
Copy Markdown
Owner

devel 반영 완료 (cherry-pick). PR close 합니다.

@edwardkim edwardkim closed this May 21, 2026
edwardkim pushed a commit that referenced this pull request May 21, 2026
HWPX slash/backSlash 형태 enum 파싱 분리. 책임 분리 설계 (slash/
backSlash=방향/형태 vs <hh:diagonal>=선 종류·굵기·색) 가 HWPX spec
1:1 정합. CI 전부 pass + 신규 단위 테스트 4건 (#1038 회귀 가드 +
비회귀 보장) → merge 수용. 시각 판정 면제 (작업지시자 결정) —
결정적 측정(3→0) + 회귀 가드 테스트 + parser-only scope 3 조건
동시 만족으로 정량 게이트가 시각 판정 대체.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
edwardkim pushed a commit that referenced this pull request May 21, 2026
- PR #950 (HWPX fragment paste support, dragonnite1221-lgtm) — 메인테이너
  hands-on 테스트에서 B1 빈 HWPX paste 실패 + B2 확인 버튼 무동작
  발견으로 close. 재제출 시 권고 사항 (B1+B2+M1+M2+R1) 정리.
- PR #1039 (HWPX slash/backSlash 형태 enum 파싱 분리, planet6897, closes
  #1038) — merge 수용. "정량 게이트 충족 시 시각 판정 면제" 첫 권위
  사례 (결정적 측정 3→0 + 회귀 가드 단위 테스트 4건 + parser-only
  scope 3 조건 동시 만족).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
edwardkim pushed a commit that referenced this pull request May 21, 2026
Task #1043 중첩 표 1×1 wrapper 외곽 테두리 lookup off-by-one 정정.
src/renderer/layout/table_layout.rs:239 1 라인 정정 (다른 lookup 들과
일관성 확보) + 본 환경 재현 가능 회귀 가드 (k-water-rfp.hwp p19).
CI 전부 pass + cargo test 1323 passed + 회귀 가드 본 환경 실증 +
작업지시자 시각 판정 통과 → merge 수용.

PR #1039 의 "정량 게이트 충족 시 시각 판정 면제 가능" 패턴 강화 사례
(본 환경 회귀 재현 + 시각 판정 동시 통과).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
edwardkim pushed a commit that referenced this pull request May 21, 2026
…okup off-by-one 정정

table_layout.rs:239 의 1-based borderFillIDRef 를 0-based Vec
인덱스로 그대로 사용한 off-by-one 정정 (다른 lookup 들과 일관성
확보). 본 환경 회귀 가드 (k-water-rfp.hwp p19) 실증 + 작업지시자
시각 판정 통과.

PR #1039 의 "정량 게이트 충족 시 시각 판정 면제 가능" 패턴 강화
사례 — 회귀 가드 본 환경 재현 + 시각 판정 동시 통과.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
edwardkim pushed a commit that referenced this pull request May 22, 2026
3 PR 본질 + 3 archives 통합 — author 보존 cherry-pick:
- PR #1054 (closes #1049, Jaeook Ryu): VPOS_CORR lazy_base trailing-ls
  bridge 정합. #1046 가설 반증 후 진짜 원인 (이중 차감) 정확 식별.
- PR #1059 (HaimLee-4869): U+00B7 폭 폰트 metric 정합 — 비례폰트
  .notdef 위장값 가드. native·WASM 공유 함수 가드.
- PR #1057 (Refs #536, seorii): CanvasKit direct replay contract harden
  (P17). 4 path 동시 정합 + Copilot 6/6 반영.

본 환경 cargo test --release --lib 1324 passed, 0 failed. CI 전부 pass.
시각 판정 면제 (모두 정량 게이트 충족) — 메모리 룰 후보 권위 사례
누적 (PR #1039#1044#1054#1059#1057 5 사례).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants