AcademySoftwareFoundation / OpenImageIO

Reading, writing, and processing images in a wide variety of file formats, using a format-agnostic API, aimed at VFX applications.
https://openimageio.readthedocs.org
Apache License 2.0
1.98k stars 597 forks source link

Text with shadow rendering #3932

Open progweb opened 1 year ago

progweb commented 1 year ago

As render text with shadow with channel alpha, I don't get the same result that without channel alpha.

Without channel alpha, shadow option permit to draw a dilated text in black, whereas with channel alpha, OIIO makes a gap...

Working with dev-2.2 branch, I can see the same issue on master branch.

[Note]: OpenImageIO is used in the gpx2video project.

progweb commented 1 year ago
From bec7340a06844588d5364f444033624bfe8d8559 Mon Sep 17 00:00:00 2001
From: Nicolas VIVIEN <nicolas@vivien.fr>
Date: Mon, 31 Jul 2023 13:44:22 +0200
Subject: [PATCH] Fix shadow text rendering on alpha buffer

---
 src/libOpenImageIO/imagebufalgo_draw.cpp | 13 +++++++++++--
 1 file changed, 11 insertions(+), 2 deletions(-)

diff --git a/src/libOpenImageIO/imagebufalgo_draw.cpp b/src/libOpenImageIO/imagebufalgo_draw.cpp
index 376f66451..18dc7c527 100644
--- a/src/libOpenImageIO/imagebufalgo_draw.cpp
+++ b/src/libOpenImageIO/imagebufalgo_draw.cpp
@@ -930,7 +930,10 @@ ImageBufAlgo::render_text(ImageBuf& R, int x, int y, string_view text,
         // If the buffer doesn't have an alpha, but the text color passed
         // has 4 values, assume the last value is supposed to be alpha.
         textalpha = textcolor[3];
+       alpha_channel = 3;
     }
+    } else
+       alpha_channel = -1;

     // Convert the UTF to 32 bit unicode
     std::vector<uint32_t> utext;
@@ -1009,8 +1012,14 @@ ImageBufAlgo::render_text(ImageBuf& R, int x, int y, string_view text,
         float val   = t[0];
         float alpha = a[0] * textalpha;
         R.getpixel(r.x(), r.y(), pixelcolor);
-        for (int c = 0; c < nchannels; ++c)
-            pixelcolor[c] = val * textcolor[c] + (1.0f - alpha) * pixelcolor[c];
+       if (alpha == 0.0)
+           continue;
+        for (int c = 0; c < nchannels; ++c) {
+           if (c == alpha_channel)
+               pixelcolor[c] = alpha + (1.0f - alpha) * pixelcolor[c];
+           else 
+               pixelcolor[c] = (val * alpha * textcolor[c]) + (1.0f - alpha) * pixelcolor[c];
+       }
         R.setpixel(r.x(), r.y(), pixelcolor);
     }

-- 
2.39.0
progweb commented 1 year ago

In using this patch, shadow option works as expected on image with alpha buffer.

lgritz commented 1 year ago

Hi, can you please submit this as a actual PR so it will run in CI, reviewed with comments, and then easily merged?