/*
* Copyright (C) 2016 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

#pragma once

#include <GLES2/gl2.h>
#include <GLES2/gl2ext.h>

#include "FrameworkFormats.h"

#include <stdint.h>
#include <cstring>
#include <vector>

namespace gfxstream {
namespace gl {

enum class YUVPlane {
    Y = 0,
    U = 1,
    V = 2,
    UV = 3,
};

// The purpose of YUVConverter is to use
// OpenGL shaders to convert YUV images to RGB
// images that can be displayed on screen.
// Doing this on the GPU can be much faster than
// on the CPU.

// Usage:
// 0. Have a current OpenGL context working.
// 1. Constructing the YUVConverter object will allocate
//    OpenGL resources needed to convert, given the desired
//    |width| and |height| of the buffer.
// 2. To convert a given YUV buffer of |pixels|, call
//    the drawConvert method (with x, y, width, and height
//    arguments depicting the region to convert).
//    The RGB version of the YUV buffer will be drawn
//    to the current framebuffer. To retrieve
//    the result, if the user of the result is an OpenGL texture,
//    it suffices to have that texture be the color attachment
//    of the framebuffer object. Or, if you want the results
//    on the CPU, call glReadPixels() after the call to drawConvert().
class YUVConverter {
public:
    // call ctor when creating a gralloc buffer
    // with YUV format
    YUVConverter(int width, int height, FrameworkFormat format);
    // destroy when ColorBuffer is destroyed
    ~YUVConverter();
    // call when gralloc_unlock updates
    // the host color buffer
    // (rcUpdateColorBuffer)
    void drawConvert(int x, int y, int width, int height, const char* pixels);
    void drawConvertFromFormat(FrameworkFormat format, int x, int y, int width, int height,
                               const char* pixels);

    uint32_t getDataSize();
    // read YUV data into pixels, exactly pixels_size bytes;
    // if size mismatches, will read nothing.
    void readPixels(uint8_t* pixels, uint32_t pixels_size);

    void swapTextures(FrameworkFormat type, GLuint* textures);

    // public so other classes can call
    static void createYUVGLTex(GLenum textureUnit,
                               GLsizei width,
                               GLsizei height,
                               FrameworkFormat format,
                               YUVPlane plane,
                               GLuint* outTextureName);
private:
    void init(int w, int h, FrameworkFormat format);
    void reset();

    void createYUVGLShader();
    void createYUVGLFullscreenQuad();

    // For dealing with n-pixel-aligned buffers
    void updateCutoffs(float yWidth, float yStridePixels,
                       float uvWidth, float uvStridePixels);

    int mWidth = 0;
    int mHeight = 0;
    FrameworkFormat mFormat;
    // colorbuffer w/h/format, could be different
    FrameworkFormat mColorBufferFormat;
    // We need the following GL objects:
    GLuint mProgram = 0;
    GLuint mQuadVertexBuffer = 0;
    GLuint mQuadIndexBuffer = 0;
    GLuint mTextureY = 0;
    GLuint mTextureU = 0;
    GLuint mTextureV = 0;
    bool mTexturesSwapped = false;
    GLint mUniformLocYWidthCutoff = -1;
    GLint mUniformLocUVWidthCutoff = -1;
    GLint mUniformLocSamplerY = -1;
    GLint mUniformLocSamplerU = -1;
    GLint mUniformLocSamplerV = -1;
    GLint mAttributeLocPos = -1;
    GLint mAttributeLocTexCoord = -1;

    float mYWidthCutoff = 1.0;
    float mUVWidthCutoff = 1.0;
    bool mHasGlsl3Support = false;

    // YUVConverter can end up being used
    // in a TextureDraw / subwindow context, and subsequently
    // overwrite the previous state.
    // This section is so YUVConverter can be used in the middle
    // of any GL context without impacting what's
    // already going on there, by saving/restoring the state
    // that it is impacting.
    void saveGLState();
    void restoreGLState();
    // Impacted state
    GLfloat mCurrViewport[4] = {};
    GLint mCurrTexUnit = 0;
    GLint mCurrProgram = 0;
    GLint mCurrTexBind = 0;
    GLint mCurrVbo = 0;
    GLint mCurrIbo = 0;
};

}  // namespace gl
}  // namespace gfxstream
