Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'source/blender/imbuf')
-rw-r--r--source/blender/imbuf/intern/openexr/openexr_api.cpp63
1 files changed, 57 insertions, 6 deletions
diff --git a/source/blender/imbuf/intern/openexr/openexr_api.cpp b/source/blender/imbuf/intern/openexr/openexr_api.cpp
index 8d8bb938e98..2dca3114765 100644
--- a/source/blender/imbuf/intern/openexr/openexr_api.cpp
+++ b/source/blender/imbuf/intern/openexr/openexr_api.cpp
@@ -1124,6 +1124,27 @@ static const char *exr_rgba_channelname(InputFile *file, const char *chan)
return chan;
}
+static bool exr_has_rgb(InputFile *file)
+{
+ return file->header().channels().findChannel("R") != NULL &&
+ file->header().channels().findChannel("G") != NULL &&
+ file->header().channels().findChannel("B") != NULL;
+}
+
+static bool exr_has_luma(InputFile *file)
+{
+ /* Y channel is the luma and should always present fir luma space images,
+ * optionally it could be also channels for chromas called BY and RY.
+ */
+ return file->header().channels().findChannel("Y") != NULL;
+}
+
+static bool exr_has_chroma(InputFile *file)
+{
+ return file->header().channels().findChannel("BY") != NULL &&
+ file->header().channels().findChannel("RY") != NULL;
+}
+
static int exr_has_zbuffer(InputFile *file)
{
return !(file->header().channels().findChannel("Z") == NULL);
@@ -1219,6 +1240,8 @@ struct ImBuf *imb_load_openexr(unsigned char *mem, size_t size, int flags, char
}
}
else {
+ const bool has_rgb = exr_has_rgb(file);
+ const bool has_luma = exr_has_luma(file);
FrameBuffer frameBuffer;
float *first;
int xstride = sizeof(float) * 4;
@@ -1231,12 +1254,22 @@ struct ImBuf *imb_load_openexr(unsigned char *mem, size_t size, int flags, char
/* but, since we read y-flipped (negative y stride) we move to last scanline */
first += 4 * (height - 1) * width;
- frameBuffer.insert(exr_rgba_channelname(file, "R"),
- Slice(Imf::FLOAT, (char *) first, xstride, ystride));
- frameBuffer.insert(exr_rgba_channelname(file, "G"),
- Slice(Imf::FLOAT, (char *) (first + 1), xstride, ystride));
- frameBuffer.insert(exr_rgba_channelname(file, "B"),
- Slice(Imf::FLOAT, (char *) (first + 2), xstride, ystride));
+ if (has_rgb) {
+ frameBuffer.insert(exr_rgba_channelname(file, "R"),
+ Slice(Imf::FLOAT, (char *) first, xstride, ystride));
+ frameBuffer.insert(exr_rgba_channelname(file, "G"),
+ Slice(Imf::FLOAT, (char *) (first + 1), xstride, ystride));
+ frameBuffer.insert(exr_rgba_channelname(file, "B"),
+ Slice(Imf::FLOAT, (char *) (first + 2), xstride, ystride));
+ }
+ else if (has_luma) {
+ frameBuffer.insert(exr_rgba_channelname(file, "Y"),
+ Slice(Imf::FLOAT, (char *) first, xstride, ystride));
+ frameBuffer.insert(exr_rgba_channelname(file, "BY"),
+ Slice(Imf::FLOAT, (char *) (first + 1), xstride, ystride, 1, 1, 0.5f));
+ frameBuffer.insert(exr_rgba_channelname(file, "RY"),
+ Slice(Imf::FLOAT, (char *) (first + 2), xstride, ystride, 1, 1, 0.5f));
+ }
/* 1.0 is fill value, this still needs to be assigned even when (is_alpha == 0) */
frameBuffer.insert(exr_rgba_channelname(file, "A"),
@@ -1264,6 +1297,24 @@ struct ImBuf *imb_load_openexr(unsigned char *mem, size_t size, int flags, char
// if (flag & IM_rect)
// IMB_rect_from_float(ibuf);
+ if (!has_rgb && has_luma) {
+ size_t a;
+ if (exr_has_chroma(file)) {
+ for (a = 0; a < (size_t) ibuf->x * ibuf->y; ++a) {
+ float *color = ibuf->rect_float + a * 4;
+ ycc_to_rgb(color[0] * 255.0f, color[1] * 255.0f, color[2] * 255.0f,
+ &color[0], &color[1], &color[2],
+ BLI_YCC_ITU_BT709);
+ }
+ }
+ else {
+ for (a = 0; a < (size_t) ibuf->x * ibuf->y; ++a) {
+ float *color = ibuf->rect_float + a * 4;
+ color[1] = color[2] = color[0];
+ }
+ }
+ }
+
/* file is no longer needed */
delete file;
}