#include "InputFrameTexture.h" InputFrameTexture::~InputFrameTexture() { ShutdownGl(); } GLuint InputFrameTexture::PollAndUpload(InputFrameMailbox* mailbox) { if (mailbox == nullptr) return mTexture; InputFrame frame; if (!mailbox->TryAcquireLatest(frame)) { ++mUploadMisses; return mTexture; } if (frame.bytes != nullptr && frame.pixelFormat == VideoIOPixelFormat::Bgra8 && EnsureTexture(frame)) { glBindTexture(GL_TEXTURE_2D, mTexture); glPixelStorei(GL_UNPACK_ALIGNMENT, 4); glPixelStorei(GL_UNPACK_ROW_LENGTH, frame.rowBytes > 0 ? static_cast(frame.rowBytes / 4) : 0); glTexSubImage2D( GL_TEXTURE_2D, 0, 0, 0, static_cast(frame.width), static_cast(frame.height), GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, frame.bytes); glPixelStorei(GL_UNPACK_ROW_LENGTH, 0); glBindTexture(GL_TEXTURE_2D, 0); ++mUploadedFrames; } mailbox->Release(frame); return mTexture; } void InputFrameTexture::ShutdownGl() { if (mTexture != 0) glDeleteTextures(1, &mTexture); mTexture = 0; mWidth = 0; mHeight = 0; } bool InputFrameTexture::EnsureTexture(const InputFrame& frame) { if (frame.width == 0 || frame.height == 0) return false; if (mTexture != 0 && mWidth == frame.width && mHeight == frame.height) return true; ShutdownGl(); glGenTextures(1, &mTexture); glBindTexture(GL_TEXTURE_2D, mTexture); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA8, static_cast(frame.width), static_cast(frame.height), 0, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, nullptr); glBindTexture(GL_TEXTURE_2D, 0); mWidth = frame.width; mHeight = frame.height; return mTexture != 0; }