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

#ifndef GrRecordingContextPriv_DEFINED
#define GrRecordingContextPriv_DEFINED

#include "include/core/SkPaint.h"
#include "include/gpu/GrRecordingContext.h"
#include "src/gpu/RefCntedCallback.h"
#include "src/gpu/ganesh/Device_v1.h"
#include "src/gpu/ganesh/GrImageContextPriv.h"
#include "src/text/gpu/SDFTControl.h"

class GrImageInfo;
class SkDeferredDisplayList;
namespace skgpu {
    class Swizzle;
}
namespace skgpu::v1 {
    class SurfaceContext;
    class SurfaceFillContext;
}

/** Class that exposes methods on GrRecordingContext that are only intended for use internal to
    Skia. This class is purely a privileged window into GrRecordingContext. It should never have
    additional data members or virtual methods. */
class GrRecordingContextPriv : public GrImageContextPriv {
public:
    GrRecordingContext* context() { return static_cast<GrRecordingContext*>(fContext); }
    const GrRecordingContext* context() const {
        return static_cast<const GrRecordingContext*>(fContext);
    }

    GrProxyProvider* proxyProvider() { return this->context()->proxyProvider(); }
    const GrProxyProvider* proxyProvider() const { return this->context()->proxyProvider(); }

    GrDrawingManager* drawingManager() { return this->context()->drawingManager(); }

    SkArenaAlloc* recordTimeAllocator() { return this->context()->arenas().recordTimeAllocator(); }
    sktext::gpu::SubRunAllocator* recordTimeSubRunAllocator() {
        return this->context()->arenas().recordTimeSubRunAllocator();
    }
    GrRecordingContext::Arenas arenas() { return this->context()->arenas(); }

    GrRecordingContext::OwnedArenas&& detachArenas() { return this->context()->detachArenas(); }

    void recordProgramInfo(const GrProgramInfo* programInfo) {
        this->context()->recordProgramInfo(programInfo);
    }

    void detachProgramData(SkTArray<GrRecordingContext::ProgramData>* dst) {
        this->context()->detachProgramData(dst);
    }

    sktext::gpu::TextBlobRedrawCoordinator* getTextBlobCache() {
        return this->context()->getTextBlobRedrawCoordinator();
    }

    GrThreadSafeCache* threadSafeCache() { return this->context()->threadSafeCache(); }

    void moveRenderTasksToDDL(SkDeferredDisplayList*);

    /**
     * Registers an object for flush-related callbacks. (See GrOnFlushCallbackObject.)
     *
     * NOTE: the drawing manager tracks this object as a raw pointer; it is up to the caller to
     * ensure its lifetime is tied to that of the context.
     */
    void addOnFlushCallbackObject(GrOnFlushCallbackObject*);

    GrAuditTrail* auditTrail() { return this->context()->fAuditTrail.get(); }

#if GR_TEST_UTILS
    // Used by tests that intentionally exercise codepaths that print warning messages, in order to
    // not confuse users with output that looks like a testing failure.
    class AutoSuppressWarningMessages {
    public:
        AutoSuppressWarningMessages(GrRecordingContext* context) : fContext(context) {
            ++fContext->fSuppressWarningMessages;
        }
        ~AutoSuppressWarningMessages() {
            --fContext->fSuppressWarningMessages;
        }
    private:
        GrRecordingContext* fContext;
    };
    void incrSuppressWarningMessages() { ++this->context()->fSuppressWarningMessages; }
    void decrSuppressWarningMessages() { --this->context()->fSuppressWarningMessages; }
#endif

    void printWarningMessage(const char* msg) const {
#if GR_TEST_UTILS
        if (this->context()->fSuppressWarningMessages > 0) {
            return;
        }
#endif
        SkDebugf("%s", msg);
    }

    GrRecordingContext::Stats* stats() {
        return &this->context()->fStats;
    }

#if GR_GPU_STATS && GR_TEST_UTILS
    using DMSAAStats = GrRecordingContext::DMSAAStats;
    DMSAAStats& dmsaaStats() { return this->context()->fDMSAAStats; }
#endif

    sktext::gpu::SDFTControl getSDFTControl(bool useSDFTForSmallText) const;

    /**
     * Create a GrRecordingContext without a resource cache
     */
    static sk_sp<GrRecordingContext> MakeDDL(sk_sp<GrContextThreadSafeProxy>);

    sk_sp<skgpu::v1::Device> createDevice(GrColorType,
                                          sk_sp<GrSurfaceProxy>,
                                          sk_sp<SkColorSpace>,
                                          GrSurfaceOrigin,
                                          const SkSurfaceProps&,
                                          skgpu::v1::Device::InitContents);
    sk_sp<skgpu::v1::Device> createDevice(SkBudgeted,
                                          const SkImageInfo&,
                                          SkBackingFit,
                                          int sampleCount,
                                          GrMipmapped,
                                          GrProtected,
                                          GrSurfaceOrigin,
                                          const SkSurfaceProps&,
                                          skgpu::v1::Device::InitContents);

    // If the passed in GrSurfaceProxy is renderable this will return a SurfaceDrawContext,
    // otherwise it will return a SurfaceContext.
    std::unique_ptr<skgpu::v1::SurfaceContext> makeSC(GrSurfaceProxyView readView,
                                                      const GrColorInfo&);

    // Makes either a SurfaceContext, SurfaceFillContext, or a SurfaceDrawContext, depending on
    // GrRenderable and the GrImageInfo.
    std::unique_ptr<skgpu::v1::SurfaceContext> makeSC(const GrImageInfo&,
                                                      const GrBackendFormat&,
                                                      std::string_view label,
                                                      SkBackingFit = SkBackingFit::kExact,
                                                      GrSurfaceOrigin = kTopLeft_GrSurfaceOrigin,
                                                      GrRenderable = GrRenderable::kNo,
                                                      int renderTargetSampleCnt = 1,
                                                      GrMipmapped = GrMipmapped::kNo,
                                                      GrProtected = GrProtected::kNo,
                                                      SkBudgeted = SkBudgeted::kYes);

    /**
     * Uses GrImageInfo's color type to pick the default texture format. Will return a
     * SurfaceDrawContext if possible.
     */
    std::unique_ptr<skgpu::v1::SurfaceFillContext> makeSFC(
        GrImageInfo,
        std::string_view label,
        SkBackingFit = SkBackingFit::kExact,
        int sampleCount = 1,
        GrMipmapped = GrMipmapped::kNo,
        GrProtected = GrProtected::kNo,
        GrSurfaceOrigin = kTopLeft_GrSurfaceOrigin,
        SkBudgeted = SkBudgeted::kYes);

    /**
     * Makes a custom configured SurfaceFillContext where the caller specifies the specific
     * texture format and swizzles. The color type will be kUnknown. Returns a SurfaceDrawContext
     * if possible.
     */
    std::unique_ptr<skgpu::v1::SurfaceFillContext> makeSFC(SkAlphaType,
                                                           sk_sp<SkColorSpace>,
                                                           SkISize dimensions,
                                                           SkBackingFit,
                                                           const GrBackendFormat&,
                                                           int sampleCount,
                                                           GrMipmapped,
                                                           GrProtected,
                                                           skgpu::Swizzle readSwizzle,
                                                           skgpu::Swizzle writeSwizzle,
                                                           GrSurfaceOrigin,
                                                           SkBudgeted,
                                                           std::string_view label);

    /**
     * Like the above but uses GetFallbackColorTypeAndFormat to find a fallback color type (and
     * compatible format) if the passed GrImageInfo's color type is not renderable.
     */
    std::unique_ptr<skgpu::v1::SurfaceFillContext> makeSFCWithFallback(
            GrImageInfo,
            SkBackingFit = SkBackingFit::kExact,
            int sampleCount = 1,
            GrMipmapped = GrMipmapped::kNo,
            GrProtected = GrProtected::kNo,
            GrSurfaceOrigin = kTopLeft_GrSurfaceOrigin,
            SkBudgeted = SkBudgeted::kYes);

    /**
     * Creates a SurfaceFillContext from an existing GrBackendTexture. The GrColorInfo's color
     * type must be compatible with backend texture's format or this will fail. All formats are
     * considered compatible with kUnknown. Returns a SurfaceDrawContext if possible.
     */
    std::unique_ptr<skgpu::v1::SurfaceFillContext> makeSFCFromBackendTexture(
            GrColorInfo,
            const GrBackendTexture&,
            int sampleCount,
            GrSurfaceOrigin,
            sk_sp<skgpu::RefCntedCallback> releaseHelper);

protected:
    explicit GrRecordingContextPriv(GrRecordingContext* rContext) : GrImageContextPriv(rContext) {}

private:
    GrRecordingContextPriv(const GrRecordingContextPriv&) = delete;
    GrRecordingContextPriv& operator=(const GrRecordingContextPriv&) = delete;

    // No taking addresses of this type.
    const GrRecordingContextPriv* operator&() const;
    GrRecordingContextPriv* operator&();

    friend class GrRecordingContext; // to construct/copy this type.

    using INHERITED = GrImageContextPriv;
};

inline GrRecordingContextPriv GrRecordingContext::priv() { return GrRecordingContextPriv(this); }

inline const GrRecordingContextPriv GrRecordingContext::priv () const {  // NOLINT(readability-const-return-type)
    return GrRecordingContextPriv(const_cast<GrRecordingContext*>(this));
}

#endif
