[Bf-blender-cvs] [4f1e311] multiview: Compositor: File Output
Dalai Felinto
noreply at git.blender.org
Mon Aug 25 15:49:43 CEST 2014
Commit: 4f1e311d1b39d27fc2227b790714b81697e57ded
Author: Dalai Felinto
Date: Fri Aug 22 19:32:49 2014 +0200
Branches: multiview
https://developer.blender.org/rB4f1e311d1b39d27fc2227b790714b81697e57ded
Compositor: File Output
File output working for stereo output
(so each individual input can be outputted as a separated stereo format)
Not supported at the moment:
* Multilayer + stereo output
Not fully working (though it should):
* Multiview
===================================================================
M source/blender/compositor/nodes/COM_OutputFileNode.cpp
M source/blender/compositor/operations/COM_OutputFileMultiViewOperation.cpp
M source/blender/compositor/operations/COM_OutputFileMultiViewOperation.h
M source/blender/compositor/operations/COM_OutputFileOperation.cpp
M source/blender/compositor/operations/COM_OutputFileOperation.h
M source/blender/imbuf/intern/openexr/openexr_api.cpp
M source/blender/imbuf/intern/openexr/openexr_multi.h
M source/blender/imbuf/intern/openexr/openexr_stub.cpp
===================================================================
diff --git a/source/blender/compositor/nodes/COM_OutputFileNode.cpp b/source/blender/compositor/nodes/COM_OutputFileNode.cpp
index 70bb548..3dd25e6 100644
--- a/source/blender/compositor/nodes/COM_OutputFileNode.cpp
+++ b/source/blender/compositor/nodes/COM_OutputFileNode.cpp
@@ -26,6 +26,8 @@
#include "COM_OutputFileMultiViewOperation.h"
#include "COM_ExecutionSystem.h"
+#include "BKE_scene.h"
+
#include "BLI_path_util.h"
OutputFileNode::OutputFileNode(bNode *editorNode) : Node(editorNode)
@@ -84,16 +86,30 @@ void OutputFileNode::convertToOperations(NodeConverter &converter, const Composi
NodeImageMultiFileSocket *sockdata = (NodeImageMultiFileSocket *)input->getbNodeSocket()->storage;
ImageFormatData *format = (sockdata->use_node_format ? &storage->format : &sockdata->format);
char path[FILE_MAX];
-
+
/* combine file path for the input */
BLI_join_dirfile(path, FILE_MAX, storage->base_path, sockdata->path);
-
- OutputSingleLayerOperation *outputOperation = new OutputSingleLayerOperation(
- context.getRenderData(), context.getbNodeTree(), input->getDataType(), format, path,
- context.getViewSettings(), context.getDisplaySettings(), context.getViewId());
+
+ NodeOperation *outputOperation = NULL;
+
+ if (format->imtype == R_IMF_IMTYPE_MULTIVIEW) {
+ outputOperation = new OutputOpenExrMultiViewOperation(
+ context.getRenderData(), context.getbNodeTree(), path, format->exr_codec, context.getViewId());
+ }
+ else if (format->views_output == R_IMF_VIEWS_INDIVIDUAL) {
+ outputOperation = new OutputSingleLayerOperation(
+ context.getRenderData(), context.getbNodeTree(), input->getDataType(), format, path,
+ context.getViewSettings(), context.getDisplaySettings(), context.getViewId());
+ }
+ else { /* R_IMF_VIEWS_STEREO_3D */
+ outputOperation = new OutputStereoOperation(
+ context.getRenderData(), context.getbNodeTree(), input->getDataType(), format, path,
+ sockdata->layer, context.getViewSettings(), context.getDisplaySettings(), context.getViewId());
+ }
+
converter.addOperation(outputOperation);
-
converter.mapInputSocket(input, outputOperation->getInputSocket(0));
+
if (!previewAdded) {
converter.addNodeInputPreview(input);
previewAdded = true;
diff --git a/source/blender/compositor/operations/COM_OutputFileMultiViewOperation.cpp b/source/blender/compositor/operations/COM_OutputFileMultiViewOperation.cpp
index 0f1543a..1e34db4 100644
--- a/source/blender/compositor/operations/COM_OutputFileMultiViewOperation.cpp
+++ b/source/blender/compositor/operations/COM_OutputFileMultiViewOperation.cpp
@@ -32,6 +32,7 @@
#include "BKE_image.h"
#include "BKE_global.h"
#include "BKE_main.h"
+#include "BKE_scene.h"
#include "DNA_color_types.h"
#include "MEM_guardedalloc.h"
@@ -138,7 +139,7 @@ void OutputOpenExrMultiViewOperation::deinitExecution()
char filename[FILE_MAX];
BKE_makepicstring_from_type(filename, this->m_path, bmain->name, this->m_rd->cfra, R_IMF_IMTYPE_MULTIVIEW,
- (this->m_rd->scemode & R_EXTENSION), true, "");
+ (this->m_rd->scemode & R_EXTENSION), true, "");
exrhandle = this->get_handle(filename);
@@ -198,3 +199,115 @@ void OutputOpenExrMultiViewOperation::deinitExecution()
IMB_exr_close(exrhandle);
}
}
+
+
+/******************************** Stereo3D ******************************/
+
+static int get_datatype_size(DataType datatype)
+{
+ switch (datatype) {
+ case COM_DT_VALUE: return 1;
+ case COM_DT_VECTOR: return 3;
+ case COM_DT_COLOR: return 4;
+ default: return 0;
+ }
+}
+
+OutputStereoOperation::OutputStereoOperation(
+ const RenderData *rd, const bNodeTree *tree, DataType datatype, ImageFormatData *format, const char *path,
+ const char *name, const ColorManagedViewSettings *viewSettings, const ColorManagedDisplaySettings *displaySettings,
+ const int actview):
+ OutputSingleLayerOperation(rd, tree, datatype, format, path, viewSettings, displaySettings, actview)
+{
+ BLI_strncpy(this->m_name, name, sizeof(this->m_name));
+ this->m_channels = get_datatype_size(datatype);
+}
+
+void *OutputStereoOperation::get_handle(const char* filename)
+{
+ size_t width = this->getWidth();
+ size_t height = this->getHeight();
+ const char *names[2] = {STEREO_LEFT_NAME, STEREO_RIGHT_NAME};
+ size_t i;
+
+ if (width != 0 && height != 0) {
+ void *exrhandle;
+
+ exrhandle = IMB_exr_get_handle_name(filename);
+
+ if (this->m_actview > 0) {
+ return exrhandle;
+ }
+
+ IMB_exr_clear_channels(exrhandle);
+
+ for (i = 0; i < 2; i++) {
+ IMB_exr_add_view(exrhandle, names[i]);
+ }
+
+ return exrhandle;
+ }
+ return NULL;
+}
+
+void OutputStereoOperation::deinitExecution()
+{
+ unsigned int width = this->getWidth();
+ unsigned int height = this->getHeight();
+
+ if (width != 0 && height != 0) {
+ void *exrhandle;
+ char view[64];
+
+ exrhandle = this->get_handle(m_path);
+ IMB_exr_get_multiView_name(exrhandle, this->m_actview, view);
+
+ float *buf = this->m_outputBuffer;
+
+ /* populate single EXR channel with view data */
+ IMB_exr_add_channel(exrhandle, NULL, m_name, view, 1, this-> m_channels * width * height, buf);
+
+ this->m_imageInput = NULL;
+ this->m_outputBuffer = NULL;
+
+ /* create stereo ibuf */
+ if (this->m_actview >= BKE_render_num_views(this->m_rd) - 1) {
+ ImBuf *ibuf[3] = {NULL};
+ const char *names[2] = {STEREO_LEFT_NAME, STEREO_RIGHT_NAME};
+ Main *bmain = G.main; /* TODO, have this passed along */
+ char filename[FILE_MAX];
+ int i;
+
+ /* get rectf from EXR */
+ for (i = 0; i < 2; i++) {
+ float *rectf = IMB_exr_channel_rect(exrhandle, NULL, this->m_name, names[i]);
+ ibuf[i]= IMB_allocImBuf(width, height, this->m_format->planes, 0);
+
+ ibuf[i]->channels = this->m_channels;
+ ibuf[i]->rect_float = rectf;
+ ibuf[i]->mall |= IB_rectfloat;
+ ibuf[i]->dither = this->m_rd->dither_intensity;
+
+ /* do colormanagement in the individual views, so it doesn't need to do in the stereo */
+ IMB_colormanagement_imbuf_for_write(ibuf[i], true, false, this->m_viewSettings,
+ this->m_displaySettings, this->m_format);
+ IMB_prepare_write_ImBuf(IMB_isfloat(ibuf[i]), ibuf[i]);
+ }
+
+ /* create stereo buffer */
+ ibuf[2] = IMB_stereoImBuf(this->m_format, ibuf[0], ibuf[1]);
+
+ BKE_makepicstring(filename, this->m_path, bmain->name, this->m_rd->cfra, this->m_format,
+ (this->m_rd->scemode & R_EXTENSION) != 0, true, NULL);
+
+ BKE_imbuf_write(ibuf[2], filename, this->m_format);
+
+ /* cleanup */
+ /* imbuf knows which rects are not part of ibuf */
+ for (i = 0; i < 3; i++) {
+ IMB_freeImBuf(ibuf[i]);
+ }
+ IMB_exr_close(exrhandle);
+ }
+ }
+}
diff --git a/source/blender/compositor/operations/COM_OutputFileMultiViewOperation.h b/source/blender/compositor/operations/COM_OutputFileMultiViewOperation.h
index bb22bcd..c7246bb 100644
--- a/source/blender/compositor/operations/COM_OutputFileMultiViewOperation.h
+++ b/source/blender/compositor/operations/COM_OutputFileMultiViewOperation.h
@@ -30,6 +30,7 @@
#include "BLI_path_util.h"
#include "DNA_color_types.h"
+#include "DNA_userdef_types.h"
#include "intern/openexr/openexr_multi.h"
@@ -43,4 +44,18 @@ public:
void deinitExecution();
};
+/**/
+class OutputStereoOperation : public OutputSingleLayerOperation {
+private:
+ char m_name[FILE_MAX];
+ size_t m_channels;
+public:
+ OutputStereoOperation(const RenderData *rd, const bNodeTree *tree, DataType datatype,
+ struct ImageFormatData *format, const char *path, const char *name,
+ const ColorManagedViewSettings *viewSettings,
+ const ColorManagedDisplaySettings *displaySettings, int actview);
+ void *get_handle(const char *filename);
+ void deinitExecution();
+};
+
#endif
diff --git a/source/blender/compositor/operations/COM_OutputFileOperation.cpp b/source/blender/compositor/operations/COM_OutputFileOperation.cpp
index 879f746..c004188 100644
--- a/source/blender/compositor/operations/COM_OutputFileOperation.cpp
+++ b/source/blender/compositor/operations/COM_OutputFileOperation.cpp
@@ -182,6 +182,7 @@ void OutputSingleLayerOperation::deinitExecution()
this->m_imageInput = NULL;
}
+/******************************* MultiLayer *******************************/
OutputOpenExrLayer::OutputOpenExrLayer(const char *name_, DataType datatype_, bool use_layer_)
{
diff --git a/source/blender/compositor/operations/COM_OutputFileOperation.h b/source/blender/compositor/operations/COM_OutputFileOperation.h
index 875e47f..8d882b7 100644
--- a/source/blender/compositor/operations/COM_OutputFileOperation.h
+++ b/source/blender/compositor/operations/COM_OutputFileOperation.h
@@ -34,7 +34,7 @@
/* Writes the image to a single-layer file. */
class OutputSingleLayerOperation : public NodeOperation {
-private:
+protected:
const RenderData *m_rd;
const bNodeTree *m_tree;
diff --git a/source/blender/imbuf/intern/openexr/openexr_api.cpp b/source/blender/imbuf/intern/openexr/openexr_api.cpp
index be1f232..f8e0c16 100644
--- a/source/blender/imbuf/intern/openexr/openexr_api.cpp
+++ b/source/blender/imbuf/intern/openexr/openexr_api.cpp
@@ -1056,6 +1056,34 @@ void IMB_exr_set_channel(void *handle, const char *layname, const char *passname
printf("IMB_exr_set_channel error %s\n", name);
}
+float *IMB_exr_channel_rect(void *handle, const char *layname, const char *passname, const char *view)
+{
+ ExrHandle *data = (ExrHandle *)handle;
+ ExrChannel *echan;
+ char name[EXR_TOT_MAXNAME + 1];
+
+ if (layname) {
+ char lay[EXR_LAY_MAXNAME + 1], pass[EXR_PASS_MAXNAME + 1];
+ BLI_strncpy(lay, layname, EXR_LAY_MAXNAME);
+ BLI_strncpy(pass, passname, EXR_PASS_MAXNAME);
+
+ BLI_snprintf(name, sizeof(name), "%s.%s", lay, pass);
+ }
+ else
+ BLI_strncpy(name, passname, EXR_TOT_MAXNAME - 1);
+
+ /* name has to be unique, thus it's a combination of layer, pass, view, and channel */
+ std::string raw_name = imb_exr_insert_view_name(name, view);
+ BLI_strncpy(name, raw_name.c
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list