void ZCombineNode::convertToOperations(NodeConverter &converter, const CompositorContext &context) const { if ((context.getRenderData()->scemode & R_FULL_SAMPLE) || this->getbNode()->custom2) { ZCombineOperation *operation = NULL; if (this->getbNode()->custom1) { operation = new ZCombineAlphaOperation(); } else { operation = new ZCombineOperation(); } converter.addOperation(operation); converter.mapInputSocket(getInputSocket(0), operation->getInputSocket(0)); converter.mapInputSocket(getInputSocket(1), operation->getInputSocket(1)); converter.mapInputSocket(getInputSocket(2), operation->getInputSocket(2)); converter.mapInputSocket(getInputSocket(3), operation->getInputSocket(3)); converter.mapOutputSocket(getOutputSocket(0), operation->getOutputSocket()); MathMinimumOperation *zoperation = new MathMinimumOperation(); converter.addOperation(zoperation); converter.mapInputSocket(getInputSocket(1), zoperation->getInputSocket(0)); converter.mapInputSocket(getInputSocket(3), zoperation->getInputSocket(1)); converter.mapOutputSocket(getOutputSocket(1), zoperation->getOutputSocket()); } else { /* XXX custom1 is "use_alpha", what on earth is this supposed to do here?!? */ // not full anti alias, use masking for Z combine. be aware it uses anti aliasing. // step 1 create mask NodeOperation *maskoperation; if (this->getbNode()->custom1) { maskoperation = new MathGreaterThanOperation(); converter.addOperation(maskoperation); converter.mapInputSocket(getInputSocket(1), maskoperation->getInputSocket(0)); converter.mapInputSocket(getInputSocket(3), maskoperation->getInputSocket(1)); } else { maskoperation = new MathLessThanOperation(); converter.addOperation(maskoperation); converter.mapInputSocket(getInputSocket(1), maskoperation->getInputSocket(0)); converter.mapInputSocket(getInputSocket(3), maskoperation->getInputSocket(1)); } // step 2 anti alias mask bit of an expensive operation, but does the trick AntiAliasOperation *antialiasoperation = new AntiAliasOperation(); converter.addOperation(antialiasoperation); converter.addLink(maskoperation->getOutputSocket(), antialiasoperation->getInputSocket(0)); // use mask to blend between the input colors. ZCombineMaskOperation *zcombineoperation = this->getbNode()->custom1 ? new ZCombineMaskAlphaOperation() : new ZCombineMaskOperation(); converter.addOperation(zcombineoperation); converter.addLink(antialiasoperation->getOutputSocket(), zcombineoperation->getInputSocket(0)); converter.mapInputSocket(getInputSocket(0), zcombineoperation->getInputSocket(1)); converter.mapInputSocket(getInputSocket(2), zcombineoperation->getInputSocket(2)); converter.mapOutputSocket(getOutputSocket(0), zcombineoperation->getOutputSocket()); MathMinimumOperation *zoperation = new MathMinimumOperation(); converter.addOperation(zoperation); converter.mapInputSocket(getInputSocket(1), zoperation->getInputSocket(0)); converter.mapInputSocket(getInputSocket(3), zoperation->getInputSocket(1)); converter.mapOutputSocket(getOutputSocket(1), zoperation->getOutputSocket()); } }
void ZCombineNode::convertToOperations(ExecutionSystem *system, CompositorContext *context) { if ((context->getRenderData()->scemode & R_FULL_SAMPLE) || this->getbNode()->custom2) { if (this->getOutputSocket(0)->isConnected()) { ZCombineOperation *operation = NULL; if (this->getbNode()->custom1) { operation = new ZCombineAlphaOperation(); } else { operation = new ZCombineOperation(); } this->getInputSocket(0)->relinkConnections(operation->getInputSocket(0), 0, system); this->getInputSocket(1)->relinkConnections(operation->getInputSocket(1), 1, system); this->getInputSocket(2)->relinkConnections(operation->getInputSocket(2), 2, system); this->getInputSocket(3)->relinkConnections(operation->getInputSocket(3), 3, system); this->getOutputSocket(0)->relinkConnections(operation->getOutputSocket()); system->addOperation(operation); if (this->getOutputSocket(1)->isConnected()) { MathMinimumOperation *zoperation = new MathMinimumOperation(); addLink(system, operation->getInputSocket(1)->getConnection()->getFromSocket(), zoperation->getInputSocket(0)); addLink(system, operation->getInputSocket(3)->getConnection()->getFromSocket(), zoperation->getInputSocket(1)); this->getOutputSocket(1)->relinkConnections(zoperation->getOutputSocket()); system->addOperation(zoperation); } } else { if (this->getOutputSocket(1)->isConnected()) { MathMinimumOperation *zoperation = new MathMinimumOperation(); this->getInputSocket(1)->relinkConnections(zoperation->getInputSocket(0), 1, system); this->getInputSocket(3)->relinkConnections(zoperation->getInputSocket(1), 3, system); this->getOutputSocket(1)->relinkConnections(zoperation->getOutputSocket()); system->addOperation(zoperation); } } } else { // not full anti alias, use masking for Z combine. be aware it uses anti aliasing. // step 1 create mask NodeOperation *maskoperation; if (this->getbNode()->custom1) { maskoperation = new MathGreaterThanOperation(); this->getInputSocket(1)->relinkConnections(maskoperation->getInputSocket(0), 3, system); this->getInputSocket(3)->relinkConnections(maskoperation->getInputSocket(1), 1, system); } else { maskoperation = new MathLessThanOperation(); this->getInputSocket(1)->relinkConnections(maskoperation->getInputSocket(0), 1, system); this->getInputSocket(3)->relinkConnections(maskoperation->getInputSocket(1), 3, system); } // step 2 anti alias mask bit of an expensive operation, but does the trick AntiAliasOperation *antialiasoperation = new AntiAliasOperation(); addLink(system, maskoperation->getOutputSocket(), antialiasoperation->getInputSocket(0)); // use mask to blend between the input colors. ZCombineMaskOperation *zcombineoperation = this->getbNode()->custom1?new ZCombineMaskAlphaOperation():new ZCombineMaskOperation(); addLink(system, antialiasoperation->getOutputSocket(), zcombineoperation->getInputSocket(0)); this->getInputSocket(0)->relinkConnections(zcombineoperation->getInputSocket(1), 0, system); this->getInputSocket(2)->relinkConnections(zcombineoperation->getInputSocket(2), 2, system); this->getOutputSocket(0)->relinkConnections(zcombineoperation->getOutputSocket()); system->addOperation(maskoperation); system->addOperation(antialiasoperation); system->addOperation(zcombineoperation); if (this->getOutputSocket(1)->isConnected()) { MathMinimumOperation *zoperation = new MathMinimumOperation(); addLink(system, maskoperation->getInputSocket(0)->getConnection()->getFromSocket(), zoperation->getInputSocket(0)); addLink(system, maskoperation->getInputSocket(1)->getConnection()->getFromSocket(), zoperation->getInputSocket(1)); this->getOutputSocket(1)->relinkConnections(zoperation->getOutputSocket()); system->addOperation(zoperation); } } }
void KeyingNode::convertToOperations(ExecutionSystem *graph, CompositorContext *context) { InputSocket *inputImage = this->getInputSocket(0); InputSocket *inputScreen = this->getInputSocket(1); InputSocket *inputGarbageMatte = this->getInputSocket(2); InputSocket *inputCoreMatte = this->getInputSocket(3); OutputSocket *outputImage = this->getOutputSocket(0); OutputSocket *outputMatte = this->getOutputSocket(1); OutputSocket *outputEdges = this->getOutputSocket(2); OutputSocket *postprocessedMatte = NULL, *postprocessedImage = NULL, *originalImage = NULL, *edgesMatte = NULL; bNode *editorNode = this->getbNode(); NodeKeyingData *keying_data = (NodeKeyingData *) editorNode->storage; /* keying operation */ KeyingOperation *keyingOperation = new KeyingOperation(); keyingOperation->setScreenBalance(keying_data->screen_balance); inputScreen->relinkConnections(keyingOperation->getInputSocket(1), 1, graph); if (keying_data->blur_pre) { /* chroma preblur operation for input of keying operation */ OutputSocket *preBluredImage = setupPreBlur(graph, inputImage, keying_data->blur_pre, &originalImage); addLink(graph, preBluredImage, keyingOperation->getInputSocket(0)); } else { inputImage->relinkConnections(keyingOperation->getInputSocket(0), 0, graph); originalImage = keyingOperation->getInputSocket(0)->getConnection()->getFromSocket(); } graph->addOperation(keyingOperation); postprocessedMatte = keyingOperation->getOutputSocket(); /* black / white clipping */ if (keying_data->clip_black > 0.0f || keying_data->clip_white < 1.0f) { postprocessedMatte = setupClip(graph, postprocessedMatte, keying_data->edge_kernel_radius, keying_data->edge_kernel_tolerance, keying_data->clip_black, keying_data->clip_white, false); } /* output edge matte */ if (outputEdges->isConnected()) { edgesMatte = setupClip(graph, postprocessedMatte, keying_data->edge_kernel_radius, keying_data->edge_kernel_tolerance, keying_data->clip_black, keying_data->clip_white, true); } /* apply garbage matte */ if (inputGarbageMatte->isConnected()) { SetValueOperation *valueOperation = new SetValueOperation(); MathSubtractOperation *subtractOperation = new MathSubtractOperation(); MathMinimumOperation *minOperation = new MathMinimumOperation(); valueOperation->setValue(1.0f); addLink(graph, valueOperation->getOutputSocket(), subtractOperation->getInputSocket(0)); inputGarbageMatte->relinkConnections(subtractOperation->getInputSocket(1), 0, graph); addLink(graph, subtractOperation->getOutputSocket(), minOperation->getInputSocket(0)); addLink(graph, postprocessedMatte, minOperation->getInputSocket(1)); postprocessedMatte = minOperation->getOutputSocket(); graph->addOperation(valueOperation); graph->addOperation(subtractOperation); graph->addOperation(minOperation); } /* apply core matte */ if (inputCoreMatte->isConnected()) { MathMaximumOperation *maxOperation = new MathMaximumOperation(); inputCoreMatte->relinkConnections(maxOperation->getInputSocket(0), 0, graph); addLink(graph, postprocessedMatte, maxOperation->getInputSocket(1)); postprocessedMatte = maxOperation->getOutputSocket(); graph->addOperation(maxOperation); } /* apply blur on matte if needed */ if (keying_data->blur_post) postprocessedMatte = setupPostBlur(graph, postprocessedMatte, keying_data->blur_post); /* matte dilate/erode */ if (keying_data->dilate_distance != 0) { postprocessedMatte = setupDilateErode(graph, postprocessedMatte, keying_data->dilate_distance); } /* matte feather */ if (keying_data->feather_distance != 0) { postprocessedMatte = setupFeather(graph, context, postprocessedMatte, keying_data->feather_falloff, keying_data->feather_distance); } /* set alpha channel to output image */ SetAlphaOperation *alphaOperation = new SetAlphaOperation(); addLink(graph, originalImage, alphaOperation->getInputSocket(0)); addLink(graph, postprocessedMatte, alphaOperation->getInputSocket(1)); postprocessedImage = alphaOperation->getOutputSocket(); /* despill output image */ if (keying_data->despill_factor > 0.0f) { postprocessedImage = setupDespill(graph, postprocessedImage, keyingOperation->getInputSocket(1)->getConnection()->getFromSocket(), keying_data->despill_factor, keying_data->despill_balance); } /* connect result to output sockets */ outputImage->relinkConnections(postprocessedImage); outputMatte->relinkConnections(postprocessedMatte); if (edgesMatte) outputEdges->relinkConnections(edgesMatte); graph->addOperation(alphaOperation); }