Commit: 259e9ad00d8ca08579db455bbc07698b324d16a0
Author: Sergey Sharybin
Date:   Mon Oct 2 15:54:08 2017 +0500
Branches: blender-v2.79a-release
https://developer.blender.org/rB259e9ad00d8ca08579db455bbc07698b324d16a0

Fix T52927: Compositor wrong scale when scale size input is connected to 
complex node

The issue here is that we can not read scale from socket when determining
dependent area of interest. This area will depend on current pixel. Now fall
back to more stupid but reliable thing: if scale size input is connected to some
nodes, we use the whole frame as area of interest.

===================================================================

M       source/blender/compositor/nodes/COM_ScaleNode.cpp
M       source/blender/compositor/operations/COM_ScaleOperation.cpp
M       source/blender/compositor/operations/COM_ScaleOperation.h

===================================================================

diff --git a/source/blender/compositor/nodes/COM_ScaleNode.cpp 
b/source/blender/compositor/nodes/COM_ScaleNode.cpp
index 61eea9227dc..ef4128a78b4 100644
--- a/source/blender/compositor/nodes/COM_ScaleNode.cpp
+++ b/source/blender/compositor/nodes/COM_ScaleNode.cpp
@@ -52,6 +52,9 @@ void ScaleNode::convertToOperations(NodeConverter &converter, 
const CompositorCo
                        converter.mapInputSocket(inputXSocket, 
operation->getInputSocket(1));
                        converter.mapInputSocket(inputYSocket, 
operation->getInputSocket(2));
                        converter.mapOutputSocket(outputSocket, 
operation->getOutputSocket(0));
+
+                       operation->setVariableSize(inputXSocket->isLinked() ||
+                                                  inputYSocket->isLinked());
                        break;
                }
                case CMP_SCALE_SCENEPERCENT:
@@ -67,6 +70,10 @@ void ScaleNode::convertToOperations(NodeConverter 
&converter, const CompositorCo
                        
converter.addLink(scaleFactorOperation->getOutputSocket(), 
operation->getInputSocket(1));
                        
converter.addLink(scaleFactorOperation->getOutputSocket(), 
operation->getInputSocket(2));
                        converter.mapOutputSocket(outputSocket, 
operation->getOutputSocket(0));
+
+                       operation->setVariableSize(inputXSocket->isLinked() ||
+                                                  inputYSocket->isLinked());
+
                        break;
                }
                case CMP_SCALE_RENDERPERCENT:
@@ -81,9 +88,13 @@ void ScaleNode::convertToOperations(NodeConverter 
&converter, const CompositorCo
                        operation->setNewHeight(rd->ysch * rd->size / 100.0f);
                        
operation->getInputSocket(0)->setResizeMode(COM_SC_NO_RESIZE);
                        converter.addOperation(operation);
-                       
+
                        converter.mapInputSocket(inputSocket, 
operation->getInputSocket(0));
                        converter.mapOutputSocket(outputSocket, 
operation->getOutputSocket(0));
+
+                       operation->setVariableSize(inputXSocket->isLinked() ||
+                                                  inputYSocket->isLinked());
+
                        break;
                }
                case CMP_SCALE_ABSOLUTE:
@@ -91,11 +102,15 @@ void ScaleNode::convertToOperations(NodeConverter 
&converter, const CompositorCo
                        /* TODO: what is the use of this one.... perhaps some 
issues when the ui was updated... */
                        ScaleAbsoluteOperation *operation = new 
ScaleAbsoluteOperation();
                        converter.addOperation(operation);
-                       
+
                        converter.mapInputSocket(inputSocket, 
operation->getInputSocket(0));
                        converter.mapInputSocket(inputXSocket, 
operation->getInputSocket(1));
                        converter.mapInputSocket(inputYSocket, 
operation->getInputSocket(2));
                        converter.mapOutputSocket(outputSocket, 
operation->getOutputSocket(0));
+
+                       operation->setVariableSize(inputXSocket->isLinked() ||
+                                                  inputYSocket->isLinked());
+
                        break;
                }
        }
diff --git a/source/blender/compositor/operations/COM_ScaleOperation.cpp 
b/source/blender/compositor/operations/COM_ScaleOperation.cpp
index 46e155e43b5..b498b359144 100644
--- a/source/blender/compositor/operations/COM_ScaleOperation.cpp
+++ b/source/blender/compositor/operations/COM_ScaleOperation.cpp
@@ -36,6 +36,7 @@ BaseScaleOperation::BaseScaleOperation()
 #else
        m_sampler = -1;
 #endif
+       m_variable_size = false;
 }
 
 ScaleOperation::ScaleOperation() : BaseScaleOperation()
@@ -87,20 +88,27 @@ void ScaleOperation::executePixelSampled(float output[4], 
float x, float y, Pixe
 bool ScaleOperation::determineDependingAreaOfInterest(rcti *input, 
ReadBufferOperation *readOperation, rcti *output)
 {
        rcti newInput;
-       float scaleX[4];
-       float scaleY[4];
-
-       this->m_inputXOperation->readSampled(scaleX, 0, 0, COM_PS_NEAREST);
-       this->m_inputYOperation->readSampled(scaleY, 0, 0, COM_PS_NEAREST);
+       if (!m_variable_size) {
+               float scaleX[4];
+               float scaleY[4];
 
-       const float scx = scaleX[0];
-       const float scy = scaleY[0];
+               this->m_inputXOperation->readSampled(scaleX, 0, 0, 
COM_PS_NEAREST);
+               this->m_inputYOperation->readSampled(scaleY, 0, 0, 
COM_PS_NEAREST);
 
-       newInput.xmax = this->m_centerX + (input->xmax - this->m_centerX) / scx;
-       newInput.xmin = this->m_centerX + (input->xmin - this->m_centerX) / scx;
-       newInput.ymax = this->m_centerY + (input->ymax - this->m_centerY) / scy;
-       newInput.ymin = this->m_centerY + (input->ymin - this->m_centerY) / scy;
+               const float scx = scaleX[0];
+               const float scy = scaleY[0];
 
+               newInput.xmax = this->m_centerX + (input->xmax - 
this->m_centerX) / scx;
+               newInput.xmin = this->m_centerX + (input->xmin - 
this->m_centerX) / scx;
+               newInput.ymax = this->m_centerY + (input->ymax - 
this->m_centerY) / scy;
+               newInput.ymin = this->m_centerY + (input->ymin - 
this->m_centerY) / scy;
+       }
+       else {
+               newInput.xmax = this->getWidth();
+               newInput.xmin = 0;
+               newInput.ymax = this->getHeight();
+               newInput.ymin = 0;
+       }
        return BaseScaleOperation::determineDependingAreaOfInterest(&newInput, 
readOperation, output);
 }
 
@@ -162,24 +170,32 @@ void ScaleAbsoluteOperation::executePixelSampled(float 
output[4], float x, float
 bool ScaleAbsoluteOperation::determineDependingAreaOfInterest(rcti *input, 
ReadBufferOperation *readOperation, rcti *output)
 {
        rcti newInput;
-       float scaleX[4];
-       float scaleY[4];
-
-       this->m_inputXOperation->readSampled(scaleX, 0, 0, COM_PS_NEAREST);
-       this->m_inputYOperation->readSampled(scaleY, 0, 0, COM_PS_NEAREST);
-
-       const float scx = scaleX[0];
-       const float scy = scaleY[0];
-       const float width = this->getWidth();
-       const float height = this->getHeight();
-       //div
-       float relateveXScale = scx / width;
-       float relateveYScale = scy / height;
-
-       newInput.xmax = this->m_centerX + (input->xmax - this->m_centerX) / 
relateveXScale;
-       newInput.xmin = this->m_centerX + (input->xmin - this->m_centerX) / 
relateveXScale;
-       newInput.ymax = this->m_centerY + (input->ymax - this->m_centerY) / 
relateveYScale;
-       newInput.ymin = this->m_centerY + (input->ymin - this->m_centerY) / 
relateveYScale;
+       if (!m_variable_size) {
+               float scaleX[4];
+               float scaleY[4];
+
+               this->m_inputXOperation->readSampled(scaleX, 0, 0, 
COM_PS_NEAREST);
+               this->m_inputYOperation->readSampled(scaleY, 0, 0, 
COM_PS_NEAREST);
+
+               const float scx = scaleX[0];
+               const float scy = scaleY[0];
+               const float width = this->getWidth();
+               const float height = this->getHeight();
+               //div
+               float relateveXScale = scx / width;
+               float relateveYScale = scy / height;
+
+               newInput.xmax = this->m_centerX + (input->xmax - 
this->m_centerX) / relateveXScale;
+               newInput.xmin = this->m_centerX + (input->xmin - 
this->m_centerX) / relateveXScale;
+               newInput.ymax = this->m_centerY + (input->ymax - 
this->m_centerY) / relateveYScale;
+               newInput.ymin = this->m_centerY + (input->ymin - 
this->m_centerY) / relateveYScale;
+       }
+       else {
+               newInput.xmax = this->getWidth();
+               newInput.xmin = 0;
+               newInput.ymax = this->getHeight();
+               newInput.ymin = 0;
+       }
 
        return BaseScaleOperation::determineDependingAreaOfInterest(&newInput, 
readOperation, output);
 }
diff --git a/source/blender/compositor/operations/COM_ScaleOperation.h 
b/source/blender/compositor/operations/COM_ScaleOperation.h
index 706a5898027..17cd31f9710 100644
--- a/source/blender/compositor/operations/COM_ScaleOperation.h
+++ b/source/blender/compositor/operations/COM_ScaleOperation.h
@@ -28,6 +28,7 @@
 class BaseScaleOperation : public NodeOperation {
 public:
        void setSampler(PixelSampler sampler) { this->m_sampler = (int) 
sampler; }
+       void setVariableSize(bool variable_size) { m_variable_size = 
variable_size; };
 
 protected:
        BaseScaleOperation();
@@ -35,6 +36,7 @@ protected:
        PixelSampler getEffectiveSampler(PixelSampler sampler) { return 
(m_sampler == -1) ? sampler : (PixelSampler) m_sampler;  }
 
        int m_sampler;
+       bool m_variable_size;
 };
 
 class ScaleOperation : public BaseScaleOperation {

_______________________________________________
Bf-blender-cvs mailing list
Bf-blender-cvs@blender.org
https://lists.blender.org/mailman/listinfo/bf-blender-cvs

Reply via email to