Skip to content

fix(pages): break the lines beside a square-wrapped object placed on the paper - #660

Merged
airmang merged 2 commits into
mainfrom
fix/text-beside-square-object-on-the-paper
Nov 4, 2026
Merged

airmang merged 2 commits into
mainfrom
fix/text-beside-square-object-on-the-paper

Conversation

@airmang

@airmang airmang commented Nov 3, 2026

Copy link
Copy Markdown
Owner

무엇을 고쳤나

종이(또는 쪽) 기준으로 놓인 어울림 개체 곁에 글이 오면 estimate_pages가 지금까지 그 구역을 지원 밖(text beside an object placed on the paper)으로 두었습니다. 이제 한/글이 하는 대로 줄을 나눕니다.

  • 개체가 놓인 쪽에서 개체 띠에 걸치는 줄을 모두 좁힙니다. 걸친다는 것은 줄 위가 띠 아래보다 위이고, 줄 위에 글자 높이를 더한 값이 띠 위보다 아래라는 뜻입니다. 개체를 품은 문단보다 앞에 있는 문단의 줄도 포함합니다.
  • 양쪽에 자리가 있으면 한 높이에 두 조각으로 나눕니다.
  • 곁 줄은 문단 여백에서 개체까지, 또는 개체에서 문단 여백까지입니다. 개체 쪽 문단 여백은 따로 더 빼지 않습니다.
  • 다음 쪽으로 넘어간 문단의 나머지는 그 쪽에서 전체 폭으로 다시 나눕니다.
  • 종이 가로 가운데에 놓인 어울림 개체의 곁 너비를 바르게 잽니다. 전에는 오른쪽 기준처럼 쟀습니다.
  • 종이 기준 개체가 여럿이면 앞 개체가 자리를 잡으면서 뒤 개체가 놓일 쪽이 바뀔 수 있습니다. 그래서 개체마다 배치를 한 번씩 더 다시 합니다(최대 24번).

다음 경우는 계속 지원 밖으로 둡니다.

  • 개체나 각주가 든 문단이 띠에 닿을 때
  • 한 문단이 띠 둘에 걸칠 때
  • 표나 다른 개체가 띠에 닿을 때
  • 여러 단일 때

줄 캐시는 원래 어울림 개체가 있는 쪽을 쓰지 않으므로 바뀐 것이 없습니다.

시험

  • pages_square_object_on_the_paper(8쪽)
    • 개체 가로 위치 넷: 본문 왼쪽, 가운데, 오른쪽, 여백에 걸침
    • 개체를 품은 문단 둘: 첫 문단, 일곱째 문단
  • pages_square_object_on_the_paper_beside_margins(19쪽)
    • 개체 가로 위치 셋: 왼쪽, 가운데, 오른쪽
    • 문단 여백 셋: 왼쪽 5mm·오른쪽 10mm, 왼쪽 10mm·오른쪽 5mm, 왼쪽·오른쪽 10mm에 내어쓰기
  • 두 판 모두 한/글이 저장한 줄 위치와 같습니다. 고치기 전에는 캐시를 지운 시험이 실패합니다.
  • 이미 있던 한/글 저장 시험 4개(종이 위 그림 곁 줄)는 캐시를 지운 판도 지원 밖이 아니라 한/글과 같게 놓이도록 기대값을 바꿨습니다.

🤖 Generated with Claude Code

@airmang airmang left a comment

Copy link
Copy Markdown
Owner Author

Choose a reason for hiding this comment

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

검토한 head: 2428843, base: 5ca12c7. 정확한 head의 CI 7,641개 및 Ruff/mypy/Pyright 통과 로그와 로컬 관련 테스트 103개를 확인했습니다. 그러나 새 paper-band 재배치 경로에서 글자 테두리 높이가 사라지는 P2를 독립 공개 API 호출로 재현하여 병합을 보류합니다. 자기 PR이므로 COMMENT로 기록합니다.

Comment thread src/hwpx/layout/pages.py
paras.append(replace(para, paper=on_paper, held=held) if on_paper else para)
paper = {index: para.paper for index, para in enumerate(paras) if para.paper}
if not page.rebreak and any(band[4] is not None for objects in paper.values() for band in objects):
return _paginate(measure, section, replace(page, rebreak=True), notes, moved) # lines broken beside them

Copy link
Copy Markdown
Owner Author

Choose a reason for hiding this comment

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

[P2] 새 종이 어울림 경로에서도 글자 테두리 높이를 보존해 주세요. 이 재귀가 만드는 _Reflow는 _held_sizes를 저장하지 않고, banded()도 _line_metrics에 held를 넘기지 않습니다. 공개 API 재현: 기존 pages_character_border_line_height.hwpx에서 모든 linesegarray를 제거하고, 실제 글자가 위·아래 테두리를 가진 첫 문단 바로 앞에 빈 앵커 문단을 둡니다. 앵커에 1000×50000 사각형을 추가하여 textWrap=SQUARE,textFlow=RIGHT_ONLY,treatAsChar=0,vertRelTo=PAGE,horzRelTo=PAPER,TOP/LEFT,offsets=0으로 놓습니다. 그림은 본문 왼쪽 여백에 완전히 놓이며 줄 너비는 양쪽 모두 42520입니다. 같은 빈 앵커만 있는 입력과 비교하면 unsupported 없이 뒤 세 문단 vertpos가 4888/6576/8264에서 4800/6400/8000으로 줄어듭니다(26쪽 유지). 사각형이 차지하지 않는 본문의 테두리 줄 높이가 reflow 중 사라진 결과입니다. held/end/head를 banded/at 및 이어지는 쪽에 오프셋을 맞춰 전달하거나 지원 불가로 처리하고, 테두리 글자가 있는 공개 회귀를 추가해 주세요.

airmang and others added 2 commits November 4, 2026 09:53
…the paper

Hancom narrows every line of the page whose top is above such an object's
foot and whose characters reach below its top, in any paragraph there
(those before its anchor too), or splits it in two pieces at one height
with room on both sides. The estimate now breaks those lines beside the
object's band as it does for a band that went on to a page's top, instead
of leaving the section unsupported; the rest of a paragraph going on to
the next page is broken there at the whole width. A square-wrapped object
centred on the paper now leaves the room beside it measured from its
centre.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…paragraph's margins

Beside a square-wrapped object placed on the paper, Hancom runs a line
from the paragraph's margin to the object, or from the object to the
margin: the margin on the object's side takes no more than the object
does. The estimate now does so instead of taking both away. Several such
objects settle their pages one after another, so the section is laid out
again up to once more for each of them.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@airmang
airmang force-pushed the fix/text-beside-square-object-on-the-paper branch from 2428843 to 1a84625 Compare November 4, 2026 00:56

@airmang airmang left a comment

Copy link
Copy Markdown
Owner Author

Choose a reason for hiding this comment

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

새 head 1a84625 / base edfaa654d0388dce9cd5ffc0f5d41a8f16392399를 재검토했습니다. 이전 head와의 변경은 main의 #661 통합이며, 이 PR 자체의 소스·테스트 추가/삭제 줄과 새 fixture 두 개는 동일합니다. 충돌은 해소됐고 정확한 head의 전체 CI 7,643 passed/18 skipped/1 xfailed 및 Ruff/mypy/Pyright 통과 로그를 확인했습니다. 그러나 기존 공개 API 재현은 최신 head에서도 세 문단 vertpos 4888/6576/8264 → 4800/6400/8000으로 동일하게 발생합니다. 본문 밖 여백 그림에 의해 테두리 줄 높이가 사라지는 기존 P2와 해당 미해결 스레드(https://github.com/airmang/python-hwpx/pull/660#discussion_r4461977621)를 유지하므로 병합을 보류합니다. 동일한 인라인 지적은 반복하지 않습니다. 자기 PR이므로 COMMENT로 기록합니다.

@airmang
airmang merged commit 3a9f37a into main Nov 4, 2026
13 checks passed
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.

1 participant