EGL поворачивает все кадры на 90 градусов - PullRequest
0 голосов
/ 24 февраля 2020

Я использую EGL в Android, где я в основном пытаюсь повернуть все буферы изображения, отображаемые на экране, на 90 градусов. когда я инициализирую свой объект Renderer, я передаю ссылку на объект NativeWindow и пытаюсь использовать ANativeWindow_setBuffersTransform, чтобы повернуть все буферы на 90 градусов (используя флаг ANATIVEWINDOW_TRANSFORM_ROTATE_90), однако это, похоже, не работает вообще.

Может кто-нибудь сказать мне, возможно ли настроить все кадры так, чтобы они поворачивались на 90 градусов по умолчанию или мне нужно манипулировать каждым кадром, который я получаю, перед его рисованием?

bool Renderer::initialize()
{
    const EGLint attribs[] = {
            EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
            EGL_BLUE_SIZE, 8,
            EGL_GREEN_SIZE, 8,
            EGL_RED_SIZE, 8,
            EGL_ALPHA_SIZE, 8,
            EGL_NONE
    };
    EGLDisplay display;
    EGLConfig config;
    EGLint numConfigs;
    EGLint format;
    EGLSurface surface;
    EGLContext context;
    GLfloat ratio;

    LOG_INFO("Initializing context");

    if ((display = eglGetDisplay(EGL_DEFAULT_DISPLAY)) == EGL_NO_DISPLAY)
    {
        LOG_ERROR("eglGetDisplay() returned error %d", eglGetError());
        return false;
    }
    if (!eglInitialize(display, 0, 0))
    {
        LOG_ERROR("eglInitialize() returned error %d", eglGetError());
        return false;
    }

    if (!eglChooseConfig(display, attribs, &config, 1, &numConfigs))
    {
        LOG_ERROR("eglChooseConfig() returned error %d", eglGetError());
        destroy();
        return false;
    }

    if (!eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &format))
    {
        LOG_ERROR("eglGetConfigAttrib() returned error %d", eglGetError());
        destroy();
        return false;
    }

    ANativeWindow_setBuffersGeometry(_window, 0, 0, format);
    ANativeWindow_setBuffersTransform(_window,ANATIVEWINDOW_TRANSFORM_ROTATE_90);

    if (!(surface = eglCreateWindowSurface(display, config, _window, 0)))
    {
        LOG_ERROR("eglCreateWindowSurface() returned error %d", eglGetError());
        destroy();
        return false;
    }

    EGLint ctxattr[] = {
            0x3098, 2,
            0x30FB, 0,
            EGL_NONE
    };

    if (!(context = eglCreateContext(display, config, 0, ctxattr)))
    {
        LOG_ERROR("eglCreateContext() returned error %d", eglGetError());
        destroy();
        return false;
    }

    if (!eglMakeCurrent(display, surface, surface, context))
    {
        LOG_ERROR("eglMakeCurrent() returned error %d", eglGetError());
        destroy();
        return false;
    }

    if (!eglQuerySurface(display, surface, EGL_WIDTH, &mWidth) ||
        !eglQuerySurface(display, surface, EGL_HEIGHT, &mHeight))
    {
        LOG_ERROR("eglQuerySurface() returned error %d", eglGetError());
        destroy();
        return false;
    }

    _display = display;
    _surface = surface;
    _context = context;

    if (Shader::load(vertexSource, fragmentSource, mProgram))
    {
        // Create a new texture from the camera frame data, display that using the shaders
        glGenTextures(1, &mVideoFrameTexture);
        glErrorCheck();
        glBindTexture(GL_TEXTURE_2D, mVideoFrameTexture);
        glErrorCheck();
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
        // This is necessary for non-power-of-two textures
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
        // Using BGRA extension to pull in video frame data directly
        //GL_API void GL_APIENTRY glTexImage2D (GLenum target, GLint level, GLint internalformat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, const void *pixels);
        glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, (GLsizei) mWidth, (GLsizei) mHeight, 0, GL_RGBA,
                     GL_UNSIGNED_BYTE, nullptr);
        glErrorCheck();
        GLint videoFrame = glGetUniformLocation(mProgram, "videoFrame");
        uniforms[UNIFORM_VIDEOFRAME] = videoFrame;
        setupVertexBuffer(mVao, mVertexBuffer, mIndexBuffer);
        return true;
    }

    return false;
}
...