Menu

#835 DPI support for raster terminals

Version 6
closed-accepted
5
1 day ago
2026-04-23
Sethur
No

Hi @sfeam!

During the last weeks, I spend considerable effort on implementing a new feature for Gnuplot that I was sorely missing for many years, and that is the ability to render rasterized graph output to an arbitrary resolution, i.e. DPI. As with my last patch, I used AI (Claude Opus 4.6 and 4.7) to help with the code generation and generation of accompanying patch commentaries, but I reviewed everything the AI produced throughly. I also spended many hours testing this patch, including side-by-side comparison of the relevant new output.

The motivation for this patch, provided in raster-term-dpi-and-various-fixes.mbox is as follows: Although it is most efficient and recommended to use vector graphs for publications, etc., it is often still required by many journals or even by programs like MS Word (which historically struggled to render supported vector output like EMF in many cases) to use raster graphics at high some mandatory minimum DPI, so it was often required to take your PDF or EPS Gnuplot output and rasterize it to some required resolution (e.g. by using GhostScript, GIMP, ImageMagick, etc.). This is cumbersome, but the alternative of directly creating high-resolution output with Gnuplot involved rescaling all font sizes, line sizes, tick sizes, marker sizes, etc., manually, which is even worse.

So my idea was to introduce a backwards-compatible option for all raster terminals (libgd, cairo and webp) that allows giving the size in units of length (inches, centimeters, etc.) as already possible for the vector terminals and additionally supplying the resolution in DPI, like so

set terminal pngcairo/png/webp/etc. size 12cm,9cm resolution 300

This would of course entail that the respective terminal drivers scale everything (font sizes, line widths, etc.) correctly for the requested resolution, but it turns out this was a feasible change without too many intrusive code changes. I have taken care to make this fully backwards-compatible, so that not specifying a resolution and giving size in pixels for the raster terminals will not change behavior. I have also taken care that the resolution meta data is embedded into the output formats wherever possible (this was not the case for pngcairo and webp before).

While implementing this, I targeted the visual appearance of pdfcairo, so line widths and font sizes are scaled accordingly. Along the way, I realized that - likely for historical reasons - the actual font sizes rendered by the postscript terminal in eps mode and by the pdfcairo terminal are too small and do not match the user requested point size, i.e., when the user requests "Arial,12pt", it is really rendered as 8pt by pdfcairo. The only exception to this is postscript in non-eps mode, where font sizes are rendered at their real size. For my patch, I did not change this behavior, so fonts are rendered as they would in pdfcairo. I have a patch on-hold that introduces a new option called "realfontsizes" that would make all affected terminals render at the true font size the user requested, but I did not want to include it here, as it would make an already large patch even more complicated. If you are, however, interested in the current situation of the font scaling, I have included an AI summary at document postscript_vs_cairo_sizing.md

While implementing the DPI feature and comparing the output of png and pngcairo with rasterized versions of the same output of pdfcairo and postscript (color eps), I came across a range of unrelated bugs, for which I have included fixes in this formatted patch. For convenience, each fix is in its own commit and should not be necessary to get the main feature running, but I would highly suggest to pull at least the libgd clipping fix, since this corrects some issues that I have introduced with my previous patch that added dashtype support for libgd.

To easily test this feature, I have included a ZIP of a minimal testing script together with all of the (slightly adapted) demos and associated data files. The testing script requires ghostscript, the main feature commit and the string_result_only fix to work. It will take the DPI as an argument and produce png output for the following terminals: png, pngcairo, pdfcairo and postscript, where the raster terminals er in eps mode with size 12cm,9cm at the requested DPI and font "Arial", and the vector terminals get rasterized to the requested DPI.

I will now list the commits this patch contains in reverse order with some comments by myself, but every one of those commits also comes with a detailed mark down documents that I had the AI write and that I personally reviewed.

405e4827f Implement DPI-scaling for libgd, cairo and web raster terminals
This is the main feature implementation, it contains everything described above. The associated document is: dpi_aware_libgd_and_cairo_feature.md

1c2ef330b Fix string_result_only flag leaking into function block evaluation
This is a fix to an issue I stumbled upon when I tried to call Gnuplot functions inside set output. It is required for the attached run_dpi_test.sh script to work properly. Its associated document is: fix_string_result_only_leak.md

78283c3ed Fix Adobe glyph name truncation in PostScript terminal
This fixes an issue where Adobe glyph names for unicode characters where truncated by one character due do improper memory allocation. This lead to, for example, /pi becoming /p, which was then rendered as a Latin letter "p" instead of a greek pi. The associated document is: fix_adobe_glyph_name_truncation.md

56d442126 Fix slow QT font-metric initialization and noisy warning
This fixed a Windows issue I encountered when switching the terminal to "qt" and plotting for the first time. Under these circumstances, I always got a "Slow font initialization" warning, which probably plaques many Windows users right now. The associated document is: fix_slow_qt_font_init.md

8e90f6c5f Fix oversized Pango hex box rendering with cairo oversampling
This is a fix to a cairo issue (both pngcairo and pdfcairo) I found in the output of demos using unicode characters that are not included in the supplied font. Previously, they were rendered much to large and covered to whole graph. The associated document is: fix_pango_hexbox_oversampling.md

9848b2ad4 Fix libgd clipping and libgd/cairo border rendering issues
This fixes a libgd png terminal issue that was introduced by my previous patch that clipped too much of the border surrounding a plot. This is most visible at larger line thicknesses. It also fixes a long-standing issue where the border for png and pngcairo hat a square cutout (for thick enough lines) at the upper left corner due to closed paths not being implemented properly in these terminals. The associated document is: fix_libgd_clipping_and_libgd+cairo_border_rendering_issues.md

cb5606523 Fix mingw makefile missing DLL dependencies
This fixed an issue with missing DLL dependencies for wgnuplot.exe and wgnuplot_pipes.exe in the Windows mingw Makefile. The associated document is: fix_mingw_missing_dll_dependencies.md

00dcd312c (HEAD -> raster-term-dpi) Add Apr 2026 changelog entries to terminal source headers
Lastly, this introduces short CHANGELOG style messages at the header of touched source files that already had time (like gd.trm). However, they summarize changes for all the commits above, so if you want to use them while not picking certain commits, they likely need to be adapted. I was not sure whether you wanted those messages at all, so I included them in their own commit.

The commits listed above all include a longer commit message that you could directly use when merging. I tried to keep it short but, as it is know, they might still be a little too detailed for your taste. Let me know if you want them shorter.

I realize that this is a lot of content, and since an AI was involved, you are probably sceptical about the quality. I can assure you, however, that these fixes have all been hand-vetted by me and tested over several weeks until I arrived at this point. This is still no guarantee that they are free from errors, but I hope that the code quality is good enough for you to consider merging these patches or at least most of them.

I have included some demo output at various DPIs for you to gain an impression of what this patch would make possible.

Cheers!

37 Attachments

Discussion

<< < 1 2 3 (Page 3 of 3)
  • Sethur

    Sethur - 2026-07-06

    Hi @sfeam!

    I realized that we should maybe also implement this for the windows terminal. I have attached a patch that introduces the scaling option there as well. I tested it on Windows and it seemed to work fine with both backends, although I did not plot anything fancy. It also synchronizes the "scale" properly to show terminal and save .

    This patch is on top of the other patches. The order is reflected in the numbers in the patch prefixes.

     
    • Ethan Merritt

      Ethan Merritt - 2026-07-06

      I have played some, but only a little, with the qt and wxt plot + scale combination. I have not made up my mind what the ideal output of "show terminal" would be. But one thing is clear: it is pointless to report the scale value without also reporting the size in pixels. Since the purpose of "show terminal" is to allow reproducing what is currently on the screen, both the scale and size are necessary. As it stands now, a size is reported only if it was part of the original set terminal command. Furthermore, after set termoption scale it no longer reports the size at all:

      gnuplot> show terminal
           terminal type is qt 0 size 700, 440 font "ArnoPro,12"
      gnuplot> set termoption scale 1.5
      gnuplot> show terminal
           terminal type is qt 0 font "ArnoPro,12" scale 1.5
      gnuplot> save '|grep terminal'
      # set terminal qt 0 font "ArnoPro,12" scale 1.5   
      

      Thus the information saved for a later replot would retain the scale but not the size that the scale is appropriate for.

      Side note: the wxt terminal does update the scale shown by show terminal if the window is resized, but the qt terminal does not. If we do go with patch 0003 that should be fixed, but see below.

      As I said, I am not sure what the ideal output of "show terminal" or "save" would be. But for now I think it is better not to apply your patch 0003. That way the saved information is consistent (original size and scale from the set terminal command) even if the display window was later resized and/or rescaled. Possibly the save and show terminal commands could be changed to emit two lines of output, something like

      # set terminal qt 0 size 700, 440 font "ArnoPro, 12" scale 1.0
      # terminal later reset to size xxx, yyy scale z.zz
      

      That looks messy also, so I don't know. I will think about it some more.

      • Ethan
       
      • Sethur

        Sethur - 2026-07-06

        I agree that size should be updated as well when the window is resized (I should have implemented this together with the scale synchronization). I could update the patches above to include that if you decide to keep both settings (scale and size) in sync.

        Alternatives to keeping scale and size in sync automatically would be to:
        1) Introduce an option that keeps those settings in sync only if it is switched on
        2) Introduce a button that explicitly updates them
        3) Your suggested approach of remembering the original settings and printing both

        Side note: the wxt terminal does update the scale shown by show terminal if the window is resized, but the qt terminal does not. If we do go with patch 0003 that should be fixed, but see below.

        That is weird, I have tested this with QT under Windows, and for me, scale was kept in sync when I resized the Window. I will test this on Linux as well to see if I can reproduce the behavior and include a potential fix in the updated QT patch.

        Let me know what option you prefer regarding the sync and I will update all patches (including the new patch for the windows terminal) accordingly.

         
        • Ethan Merritt

          Ethan Merritt - 2026-07-08

          Never mind. My fault. I managed to test with a mismatch between the gnuplot and gnuplot_qt versions. Usually that results in an obvious failure but in this case it was a silent error. I think I should add an explicit version check when the initial connection between the two processes is made.

           
          • Sethur

            Sethur - 2 days ago

            Hi @sfeam,

            did you come to a decision regarding the issue of keeping scale and size in sync with the terminal options yet?

             
            • Ethan Merritt

              Ethan Merritt - 1 day ago

              Yes. I committed the patch series together with modifications to wxt and qt so that both the current size and the current scale are always reported by "show terminal".

              Can you do the same for the windows terminal?

               
  • Ethan Merritt

    Ethan Merritt - 2026-06-12
    • status: open --> pending-accepted
     
  • Ethan Merritt

    Ethan Merritt - 2 days ago
    • Status: pending-accepted --> closed-accepted
     
<< < 1 2 3 (Page 3 of 3)

Log in to post a comment.