/*
 * Copyright 2021 Google LLC
 *
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */

#include "include/core/SkCanvas.h"
#include "include/core/SkPaint.h"
#include "include/effects/SkImageFilters.h"
#include "include/effects/SkRuntimeEffect.h"
#include "include/private/SkSpinlock.h"
#include "src/core/SkImageFilter_Base.h"
#include "src/core/SkReadBuffer.h"
#include "src/core/SkRuntimeEffectPriv.h"
#include "src/core/SkSpecialImage.h"
#include "src/core/SkSpecialSurface.h"
#include "src/core/SkWriteBuffer.h"
#include "src/effects/imagefilters/SkRuntimeImageFilter.h"

#ifdef SK_ENABLE_SKSL

class SkRuntimeImageFilter final : public SkImageFilter_Base {
public:
    SkRuntimeImageFilter(sk_sp<SkRuntimeEffect> effect,
                         sk_sp<SkData> uniforms,
                         sk_sp<SkImageFilter> input)
            : INHERITED(&input, 1, /*cropRect=*/nullptr)
            , fShaderBuilder(std::move(effect), std::move(uniforms))
            , fChildShaderNames(&fShaderBuilder.effect()->children().front().name, 1) {}
    SkRuntimeImageFilter(const SkRuntimeShaderBuilder& builder,
                         const char* childShaderNames[],
                         const sk_sp<SkImageFilter> inputs[],
                         int inputCount)
            : INHERITED(inputs, inputCount, /*cropRect=*/nullptr)
            , fShaderBuilder(builder) {
        for (int i = 0; i < inputCount; i++) {
            fChildShaderNames.push_back(SkString(childShaderNames[i]));
        }
    }

    bool onAffectsTransparentBlack() const override { return true; }
    MatrixCapability onGetCTMCapability() const override { return MatrixCapability::kTranslate; }

protected:
    void flatten(SkWriteBuffer&) const override;
    sk_sp<SkSpecialImage> onFilterImage(const Context&, SkIPoint* offset) const override;

private:
    friend void ::SkRegisterRuntimeImageFilterFlattenable();
    SK_FLATTENABLE_HOOKS(SkRuntimeImageFilter)

    mutable SkSpinlock fShaderBuilderLock;
    mutable SkRuntimeShaderBuilder fShaderBuilder;
    SkSTArray<1, SkString> fChildShaderNames;

    using INHERITED = SkImageFilter_Base;
};

sk_sp<SkImageFilter> SkMakeRuntimeImageFilter(sk_sp<SkRuntimeEffect> effect,
                                              sk_sp<SkData> uniforms,
                                              sk_sp<SkImageFilter> input) {
    // Rather than replicate all of the checks from makeShader here, just try to create a shader
    // once, to determine if everything is valid.
    sk_sp<SkShader> child = nullptr;
    auto shader = effect->makeShader(uniforms, &child, 1);
    if (!shader) {
        // Could be wrong signature, wrong uniform block size, wrong number/type of children, etc...
        return nullptr;
    }

    return sk_sp<SkImageFilter>(
            new SkRuntimeImageFilter(std::move(effect), std::move(uniforms), std::move(input)));
}

void SkRegisterRuntimeImageFilterFlattenable() {
    SK_REGISTER_FLATTENABLE(SkRuntimeImageFilter);
}

sk_sp<SkFlattenable> SkRuntimeImageFilter::CreateProc(SkReadBuffer& buffer) {
    // We don't know how many inputs to expect yet. Passing -1 allows any number of children.
    SK_IMAGEFILTER_UNFLATTEN_COMMON(common, -1);
    if (common.cropRect()) {
        return nullptr;
    }

    // Read the SkSL string and convert it into a runtime effect
    SkString sksl;
    buffer.readString(&sksl);
    auto effect = SkMakeCachedRuntimeEffect(SkRuntimeEffect::MakeForShader, std::move(sksl));
    if (!buffer.validate(effect != nullptr)) {
        return nullptr;
    }

    // Read the uniform data and make sure it matches the size from the runtime effect
    sk_sp<SkData> uniforms = buffer.readByteArrayAsData();
    if (!buffer.validate(uniforms->size() == effect->uniformSize())) {
        return nullptr;
    }

    // Read the child shader names
    SkSTArray<4, const char*> childShaderNames;
    SkSTArray<4, SkString> childShaderNameStrings;
    childShaderNames.resize(common.inputCount());
    childShaderNameStrings.resize(common.inputCount());
    for (int i = 0; i < common.inputCount(); i++) {
        buffer.readString(&childShaderNameStrings[i]);
        childShaderNames[i] = childShaderNameStrings[i].c_str();
    }

    SkRuntimeShaderBuilder builder(std::move(effect), std::move(uniforms));

    // Populate the builder with the corresponding children
    for (auto& child : builder.effect()->children()) {
        const char* name = child.name.c_str();
        switch (child.type) {
            case SkRuntimeEffect::ChildType::kBlender: {
                builder.child(name) = buffer.readBlender();
                break;
            }
            case SkRuntimeEffect::ChildType::kColorFilter: {
                builder.child(name) = buffer.readColorFilter();
                break;
            }
            case SkRuntimeEffect::ChildType::kShader: {
                builder.child(name) = buffer.readShader();
                break;
            }
        }
    }

    if (!buffer.isValid()) {
        return nullptr;
    }

    return SkImageFilters::RuntimeShader(
            builder, childShaderNames.data(), common.inputs(), common.inputCount());
}

void SkRuntimeImageFilter::flatten(SkWriteBuffer& buffer) const {
    this->INHERITED::flatten(buffer);
    fShaderBuilderLock.acquire();
    buffer.writeString(fShaderBuilder.effect()->source().c_str());
    buffer.writeDataAsByteArray(fShaderBuilder.uniforms().get());
    for (const SkString& name : fChildShaderNames) {
        buffer.writeString(name.c_str());
    }
    for (size_t x = 0; x < fShaderBuilder.numChildren(); x++) {
        buffer.writeFlattenable(fShaderBuilder.children()[x].flattenable());
    }
    fShaderBuilderLock.release();
}

///////////////////////////////////////////////////////////////////////////////////////////////////

sk_sp<SkSpecialImage> SkRuntimeImageFilter::onFilterImage(const Context& ctx,
                                                          SkIPoint* offset) const {
    SkIRect outputBounds = SkIRect(ctx.desiredOutput());
    sk_sp<SkSpecialSurface> surf(ctx.makeSurface(outputBounds.size()));
    if (!surf) {
        return nullptr;
    }

    SkMatrix ctm = ctx.ctm();
    SkMatrix inverse;
    SkAssertResult(ctm.invert(&inverse));

    const int inputCount = this->countInputs();
    SkASSERT(inputCount == fChildShaderNames.count());

    SkSTArray<1, sk_sp<SkShader>> inputShaders;
    for (int i = 0; i < inputCount; i++) {
        SkIPoint inputOffset = SkIPoint::Make(0, 0);
        sk_sp<SkSpecialImage> input(this->filterInput(i, ctx, &inputOffset));
        if (!input) {
            return nullptr;
        }

        SkMatrix localM = inverse * SkMatrix::Translate(inputOffset);
        sk_sp<SkShader> inputShader =
                input->asShader(SkSamplingOptions(SkFilterMode::kLinear), localM);
        SkASSERT(inputShader);
        inputShaders.push_back(std::move(inputShader));
    }

    // lock the mutation of the builder and creation of the shader so that the builder's state is
    // const and is safe for multi-threaded access.
    fShaderBuilderLock.acquire();
    for (int i = 0; i < inputCount; i++) {
        fShaderBuilder.child(fChildShaderNames[i].c_str()) = inputShaders[i];
    }
    sk_sp<SkShader> shader = fShaderBuilder.makeShader();
    // Remove the inputs from the builder to avoid unnecessarily prolonging the shader's lifetime
    for (int i = 0; i < inputCount; i++) {
        fShaderBuilder.child(fChildShaderNames[i].c_str()) = nullptr;
    }
    fShaderBuilderLock.release();

    SkASSERT(shader.get());

    SkPaint paint;
    paint.setShader(std::move(shader));
    paint.setBlendMode(SkBlendMode::kSrc);

    SkCanvas* canvas = surf->getCanvas();
    SkASSERT(canvas);

    // Translate from layer space into surf's image space
    canvas->translate(-outputBounds.fLeft, -outputBounds.fTop);
    // Ensure shader parameters are relative to parameter space, not layer space
    canvas->concat(ctx.ctm());

    canvas->drawPaint(paint);

    *offset = outputBounds.topLeft();
    return surf->makeImageSnapshot();
}

static bool child_is_shader(const SkRuntimeEffect::Child* child) {
    return child && child->type == SkRuntimeEffect::ChildType::kShader;
}

sk_sp<SkImageFilter> SkImageFilters::RuntimeShader(const SkRuntimeShaderBuilder& builder,
                                                   const char* childShaderName,
                                                   sk_sp<SkImageFilter> input) {
    // if no childShaderName is provided check to see if we can implicitly assign it to the only
    // child in the effect
    if (childShaderName == nullptr) {
        auto children = builder.effect()->children();
        if (children.size() != 1) {
            return nullptr;
        }
        childShaderName = children.front().name.c_str();
    }

    return SkImageFilters::RuntimeShader(builder, &childShaderName, &input, 1);
}

sk_sp<SkImageFilter> SkImageFilters::RuntimeShader(const SkRuntimeShaderBuilder& builder,
                                                   const char* childShaderNames[],
                                                   const sk_sp<SkImageFilter> inputs[],
                                                   int inputCount) {
    for (int i = 0; i < inputCount; i++) {
        const char* name = childShaderNames[i];
        // All names must be non-null, and present as a child shader in the effect:
        if (!name || !child_is_shader(builder.effect()->findChild(name))) {
            return nullptr;
        }

        // We don't allow duplicates, either:
        for (int j = 0; j < i; j++) {
            if (!strcmp(name, childShaderNames[j])) {
                return nullptr;
            }
        }
    }

    return sk_sp<SkImageFilter>(
            new SkRuntimeImageFilter(builder, childShaderNames, inputs, inputCount));
}

#endif  // SK_ENABLE_SKSL
