asciidoctor / asciidoctor-pdf

:page_with_curl: Asciidoctor PDF: A native PDF converter for AsciiDoc based on Asciidoctor and Prawn, written entirely in Ruby.
https://docs.asciidoctor.org/pdf-converter/latest/
MIT License
1.14k stars 501 forks source link

Add support for fit=none to inline image #2428

Closed mojavelinux closed 1 year ago

mojavelinux commented 1 year ago

Normally, an inline image will be scaled down until it fits into the available height. As a result, it may not honor the pdfwidth specified by the author. However, there are times when this behavior is not desirable. One example is in a normal table cell. The bounds of a table cell is reported as the height of the lines of text that it contains. The author may want the image to be slightly larger than this height, potentially causing the height of the table cell to increase.

To accommodate this scenario, add support for fit=none on an inline image. This communicates to the converter to not attempt to scale down the image to fit within the available height, trusting the size that the author provides. It is possible that this could result in a layout error if used on a large (in dimensions) image, but unlikely in cases when the image is an icon that is being fit within a line.

mojavelinux commented 1 year ago

The bounds of a table cell is reported as the height of the lines of text that it contains.

The explanation in this issue is inaccurate. An inline image in a normal table cell is permimtted to increase the height of the table cell if it's taller than the line height. That's not the issue here. The issue is with how prawn-table rendered table cells.

prawn-table renders a table cell in two stages:

  1. conduct a dry run to determine the height of the content in the table cell
  2. render the cell in a text box that is restricted to the calculated height

The problem comes in step 1. prawn-table does not always compute the height of the table cell correctly because it does not properly account for the built-in line height of the font. As a result, when it performs step 2, it can cause the image to no longer fit within the allocated height. There's no way for the inline image arranger in Asciidoctor PDF to know this is happening, so it incorrectly scales the image down to fit in this case. This never seems to happen with Noto Sans, but does happen with Arial and M+ 1mn.

The proposed fix is still the right one. We need to allow the author to provide a hint to the convert to not attempt to fit the image. This attribute should be used be used as a workaround for this problem.

mojavelinux commented 1 year ago

I found a way to prevent the inline image from being scaled down during the rendering of a table cell when the image fit during the dry run. But we'll still support fit=none to cover any unforeseen edge cases.