#include "ofxsSupportPrivate.h"
#include <algorithm>
namespace OFX {
static OfxPointD getPixelScale(const PropertySet &props)
{
OfxPointD pixelScale;
pixelScale.x = props.propGetDouble(kOfxInteractPropPixelScale, 0);
pixelScale.y = props.propGetDouble(kOfxInteractPropPixelScale, 1);
return pixelScale;
}
static OfxPointD getRenderScale(const PropertySet &props)
{
OfxPointD v;
v.x = props.propGetDouble(kOfxImageEffectPropRenderScale, 0);
v.y = props.propGetDouble(kOfxImageEffectPropRenderScale, 1);
return v;
}
static OfxRGBColourD getBackgroundColour(const PropertySet &props)
{
OfxRGBColourD backGroundColour;
backGroundColour.r = props.propGetDouble(kOfxInteractPropBackgroundColour, 0);
backGroundColour.g = props.propGetDouble(kOfxInteractPropBackgroundColour, 1);
backGroundColour.b = props.propGetDouble(kOfxInteractPropBackgroundColour, 2);
return backGroundColour;
}
static ImageEffect *retrieveEffectFromInteractHandle(OfxInteractHandle handle)
{
OfxPropertySetHandle propHandle;
OfxStatus stat = OFX::Private::gInteractSuite->interactGetPropertySet(handle, &propHandle);
throwSuiteStatusException(stat);
PropertySet interactProperties(propHandle);
OfxImageEffectHandle effectHandle = (OfxImageEffectHandle) interactProperties.propGetPointer(kOfxPropEffectInstance);
return OFX::Private::retrieveImageEffectPointer(effectHandle);
}
Interact::Interact(OfxInteractHandle handle)
: _interactHandle(handle)
, _effect(0)
{
OfxPropertySetHandle propHandle;
OfxStatus stat = OFX::Private::gInteractSuite->interactGetPropertySet(handle, &propHandle);
throwSuiteStatusException(stat);
_interactProperties.propSetHandle(propHandle);
_interactProperties.propSetPointer(kOfxPropInstanceData, (void *)this);
_effect = retrieveEffectFromInteractHandle(handle);
}
Interact::~Interact()
{
}
int
Interact::getBitDepth(void) const
{
return _interactProperties.propGetInt(kOfxInteractPropBitDepth);
}
bool
Interact::hasAlpha(void) const
{
return _interactProperties.propGetInt(kOfxInteractPropHasAlpha) != 0;
}
OfxPointD
Interact::getPixelScale(void) const
{
OfxPointD v;
v.x = _interactProperties.propGetDouble(kOfxInteractPropPixelScale, 0);
v.y = _interactProperties.propGetDouble(kOfxInteractPropPixelScale, 1);
return v;
}
bool
Interact::getSuggestedColour(OfxRGBColourD &c) const
{
OfxStatus stat = OFX::Private::gPropSuite->propGetDouble(_interactProperties.propSetHandle(), kOfxInteractPropSuggestedColour, 0, &c.r);
if (stat != kOfxStatOK) {
return false; }
stat = OFX::Private::gPropSuite->propGetDouble(_interactProperties.propSetHandle(), kOfxInteractPropSuggestedColour, 1, &c.g);
if (stat != kOfxStatOK) {
return false; }
stat = OFX::Private::gPropSuite->propGetDouble(_interactProperties.propSetHandle(), kOfxInteractPropSuggestedColour, 2, &c.b);
if (stat != kOfxStatOK) {
return false; }
return true;
}
void
Interact::requestRedraw(void) const
{
OfxStatus stat = OFX::Private::gInteractSuite->interactRedraw(_interactHandle);
throwSuiteStatusException(stat);
}
void
Interact::swapBuffers(void) const
{
OfxStatus stat = OFX::Private::gInteractSuite->interactSwapBuffers(_interactHandle);
throwSuiteStatusException(stat);
}
void
Interact::addParamToSlaveTo(Param *p)
{
std::list<Param *>::iterator i;
i = std::find(_slaveParams.begin(), _slaveParams.end(), p);
if(i == _slaveParams.end()) {
_slaveParams.push_back(p);
int n = _interactProperties.propGetDimension(kOfxInteractPropSlaveToParam);
_interactProperties.propSetString(kOfxInteractPropSlaveToParam, p->getName(), n);
}
}
void
Interact::removeParamToSlaveTo(Param *p)
{
std::list<Param *>::iterator i;
i = std::find(_slaveParams.begin(), _slaveParams.end(), p);
if(i != _slaveParams.end()) {
_slaveParams.erase(i);
_interactProperties.propReset(kOfxInteractPropSlaveToParam);
int n = 0;
for(i = _slaveParams.begin(); i != _slaveParams.end(); ++i, ++n) {
_interactProperties.propSetString(kOfxInteractPropSlaveToParam, (*i)->getName(), n);
}
}
}
OfxRGBColourD Interact::getBackgroundColour(void) const
{
return OFX::getBackgroundColour(_interactProperties);
}
bool
Interact::draw(const DrawArgs &)
{
return false;
}
bool
Interact::penMotion(const PenArgs &)
{
return false;
}
bool
Interact::penDown(const PenArgs &)
{
return false;
}
bool
Interact::penUp(const PenArgs &)
{
return false;
}
bool
Interact::keyDown(const KeyArgs &)
{
return false;
}
bool
Interact::keyUp(const KeyArgs &)
{
return false;
}
bool
Interact::keyRepeat(const KeyArgs &)
{
return false;
}
void
Interact::gainFocus(const FocusArgs &)
{
}
void
Interact::loseFocus(const FocusArgs &)
{
}
OverlayInteract::OverlayInteract(OfxInteractHandle handle)
: Interact(handle)
{
if(_effect)
_effect->addOverlayInteract(this);
}
OverlayInteract::~OverlayInteract()
{
if(_effect)
_effect->removeOverlayInteract(this);
}
InteractArgs::InteractArgs(const PropertySet &props)
{
time = props.propGetDouble(kOfxPropTime);
renderScale = getRenderScale(props);
}
DrawArgs::DrawArgs(const PropertySet &props)
: InteractArgs(props)
{
#ifdef kOfxInteractPropViewportSize
viewportSize.x = props.propGetDouble(kOfxInteractPropViewportSize, 0, false);
viewportSize.y = props.propGetDouble(kOfxInteractPropViewportSize, 1, false);
#endif
backGroundColour = getBackgroundColour(props);
pixelScale = getPixelScale(props);
}
PenArgs::PenArgs(const PropertySet &props)
: InteractArgs(props)
{
#ifdef kOfxInteractPropViewportSize
viewportSize.x = props.propGetDouble(kOfxInteractPropViewportSize, 0, false);
viewportSize.y = props.propGetDouble(kOfxInteractPropViewportSize, 1, false);
#endif
pixelScale = getPixelScale(props);
backGroundColour = getBackgroundColour(props);
penPosition.x = props.propGetDouble(kOfxInteractPropPenPosition, 0);
penPosition.y = props.propGetDouble(kOfxInteractPropPenPosition, 1);
try {
penViewportPosition.x = props.propGetInt(kOfxInteractPropPenViewportPosition, 0);
penViewportPosition.y = props.propGetInt(kOfxInteractPropPenViewportPosition, 1);
} catch (OFX::Exception::PropertyUnknownToHost) {
penViewportPosition.x = penViewportPosition.y = -1.;
}
penPressure = props.propGetDouble(kOfxInteractPropPenPressure);
}
KeyArgs::KeyArgs(const PropertySet &props)
: InteractArgs(props)
{
time = props.propGetDouble(kOfxPropTime);
renderScale = getRenderScale(props);
keyString = props.propGetString(kOfxPropKeyString);
keySymbol = props.propGetInt(kOfxPropKeySym);
}
FocusArgs::FocusArgs(const PropertySet &props)
: InteractArgs(props)
{
#ifdef kOfxInteractPropViewportSize
viewportSize.x = props.propGetDouble(kOfxInteractPropViewportSize, 0, false);
viewportSize.y = props.propGetDouble(kOfxInteractPropViewportSize, 1, false);
#endif
pixelScale = getPixelScale(props);
backGroundColour = getBackgroundColour(props);
}
void ParamInteractDescriptor::setInteractSizeAspect(double asp)
{
_props->propSetDouble(kOfxParamPropInteractSizeAspect , asp);
}
void ParamInteractDescriptor::setInteractMinimumSize(int x, int y)
{
_props->propSetInt(kOfxParamPropInteractMinimumSize, x, 0);
_props->propSetInt(kOfxParamPropInteractMinimumSize, y, 1);
}
void ParamInteractDescriptor::setInteractPreferredSize(int x, int y)
{
_props->propSetInt(kOfxParamPropInteractPreferedSize, x, 0);
_props->propSetInt(kOfxParamPropInteractPreferedSize, y, 1);
}
ParamInteract::ParamInteract(OfxInteractHandle handle, ImageEffect* effect):Interact(handle), _effect(effect)
{}
OfxPointI ParamInteract::getInteractSize() const
{
OfxPointI ret;
ret.x = _interactProperties.propGetInt(kOfxParamPropInteractSize, 0);
ret.y = _interactProperties.propGetInt(kOfxParamPropInteractSize, 1);
return ret;
}
namespace Private {
static
Interact *retrieveInteractPointer(OfxInteractHandle handle)
{
Interact *instance;
OfxPropertySetHandle propHandle;
OfxStatus stat = OFX::Private::gInteractSuite->interactGetPropertySet(handle, &propHandle);
throwSuiteStatusException(stat);
PropertySet props(propHandle);
instance = (Interact *) props.propGetPointer(kOfxPropInstanceData);
OFX::Log::error(instance == 0, "Instance data handle in effect instance properties is NULL!");
return instance;
}
static
OfxStatus
interactMainEntry(const std::string &action,
OfxInteractHandle handle,
PropertySet inArgs,
PropertySet )
{
OfxStatus stat = kOfxStatReplyDefault;
Interact *interact = retrieveInteractPointer(handle);
if(!interact)
return stat;
if(action == kOfxActionDestroyInstance) {
delete interact;
stat = kOfxStatOK;
}
else if(action == kOfxInteractActionDraw) {
DrawArgs drawArgs(inArgs);
if(interact->draw(drawArgs))
stat = kOfxStatOK;
}
else if(action == kOfxInteractActionPenMotion) {
PenArgs args(inArgs);
if(interact->penMotion(args))
stat = kOfxStatOK;
}
else if(action == kOfxInteractActionPenDown) {
PenArgs args(inArgs);
if(interact->penDown(args))
stat = kOfxStatOK;
}
else if(action == kOfxInteractActionPenUp) {
PenArgs args(inArgs);
if(interact->penUp(args))
stat = kOfxStatOK;
}
else if(action == kOfxInteractActionKeyDown) {
KeyArgs args(inArgs);
if(interact->keyDown(args))
stat = kOfxStatOK;
}
else if(action == kOfxInteractActionKeyUp) {
KeyArgs args(inArgs);
if(interact->keyUp(args))
stat = kOfxStatOK;
}
else if(action == kOfxInteractActionKeyRepeat) {
KeyArgs args(inArgs);
if(interact->keyRepeat(args))
stat = kOfxStatOK;
}
else if(action == kOfxInteractActionGainFocus) {
FocusArgs args(inArgs);
interact->gainFocus(args);
}
else if(action == kOfxInteractActionLoseFocus) {
FocusArgs args(inArgs);
interact->loseFocus(args);
}
return stat;
}
OfxStatus interactMainEntry(const char *actionRaw,
const void *handleRaw,
OfxPropertySetHandle inArgsRaw,
OfxPropertySetHandle outArgsRaw,
InteractDescriptor& desc)
{
OFX::Log::print("********************************************************************************");
OFX::Log::print("START overlayInteractMainEntry (%s)", actionRaw);
OFX::Log::indent();
OfxStatus stat = kOfxStatReplyDefault;
try {
OfxInteractHandle handle = (OfxInteractHandle) handleRaw;
OFX::PropertySet inArgs(inArgsRaw);
OFX::PropertySet outArgs(outArgsRaw);
std::string action(actionRaw);
if (action == kOfxActionDescribe) {
OfxPropertySetHandle propHandle;
OfxStatus stat = OFX::Private::gInteractSuite->interactGetPropertySet(handle, &propHandle);
throwSuiteStatusException(stat);
PropertySet interactProperties(propHandle);
desc.setPropertySet(&interactProperties);
desc.describe();
}
else if (action == kOfxActionCreateInstance)
{
ImageEffect *effect = retrieveEffectFromInteractHandle(handle);
OFX::Interact* interact = desc.createInstance(handle, effect);
(void)interact;
stat = kOfxStatOK;
}
else {
stat = interactMainEntry(action, handle, inArgs, outArgs);
}
}
catch(...)
{
stat = kOfxStatFailed;
}
OFX::Log::outdent();
OFX::Log::print("STOP overlayInteractMainEntry (%s)", actionRaw);
return stat;
}
};
};