#include "rive/animation/keyed_property.hpp"
#include "rive/animation/keyed_object.hpp"
#include "rive/animation/keyframe.hpp"
#include "rive/importers/import_stack.hpp"
#include "rive/importers/keyed_object_importer.hpp"

using namespace rive;

KeyedProperty::~KeyedProperty() {
    for (auto keyframe : m_KeyFrames) {
        delete keyframe;
    }
}

void KeyedProperty::addKeyFrame(KeyFrame* keyframe) { m_KeyFrames.push_back(keyframe); }

void KeyedProperty::apply(Core* object, float seconds, float mix) {
    assert(!m_KeyFrames.empty());

    int idx = 0;
    int mid = 0;
    float closestSeconds = 0.0f;
    int start = 0;
    auto numKeyFrames = static_cast<int>(m_KeyFrames.size());
    int end = numKeyFrames - 1;
    while (start <= end) {
        mid = (start + end) >> 1;
        closestSeconds = m_KeyFrames[mid]->seconds();
        if (closestSeconds < seconds) {
            start = mid + 1;
        } else if (closestSeconds > seconds) {
            end = mid - 1;
        } else {
            idx = start = mid;
            break;
        }
        idx = start;
    }
    int pk = propertyKey();

    if (idx == 0) {
        m_KeyFrames[0]->apply(object, pk, mix);
    } else {
        if (idx < numKeyFrames) {
            KeyFrame* fromFrame = m_KeyFrames[idx - 1];
            KeyFrame* toFrame = m_KeyFrames[idx];
            if (seconds == toFrame->seconds()) {
                toFrame->apply(object, pk, mix);
            } else {
                if (fromFrame->interpolationType() == 0) {
                    fromFrame->apply(object, pk, mix);
                } else {
                    fromFrame->applyInterpolation(object, pk, seconds, toFrame, mix);
                }
            }
        } else {
            m_KeyFrames[idx - 1]->apply(object, pk, mix);
        }
    }
}

StatusCode KeyedProperty::onAddedDirty(CoreContext* context) {
    StatusCode code;
    for (auto keyframe : m_KeyFrames) {
        if ((code = keyframe->onAddedDirty(context)) != StatusCode::Ok) {
            return code;
        }
    }
    return StatusCode::Ok;
}

StatusCode KeyedProperty::onAddedClean(CoreContext* context) {
    StatusCode code;
    for (auto keyframe : m_KeyFrames) {
        if ((code = keyframe->onAddedClean(context)) != StatusCode::Ok) {
            return code;
        }
    }
    return StatusCode::Ok;
}

StatusCode KeyedProperty::import(ImportStack& importStack) {
    auto importer = importStack.latest<KeyedObjectImporter>(KeyedObjectBase::typeKey);
    if (importer == nullptr) {
        return StatusCode::MissingObject;
    }
    importer->addKeyedProperty(this);
    return Super::import(importStack);
}
