mirror of
https://github.com/moonlight-stream/moonlight-chrome.git
synced 2025-08-17 16:46:31 +00:00
Increase rendering performance significantly
This commit is contained in:
parent
b7032a8957
commit
f77979d904
@ -17,6 +17,8 @@
|
|||||||
|
|
||||||
#include "nacl_io/nacl_io.h"
|
#include "nacl_io/nacl_io.h"
|
||||||
|
|
||||||
|
#include <queue>
|
||||||
|
|
||||||
#include <Limelight.h>
|
#include <Limelight.h>
|
||||||
|
|
||||||
struct Shader {
|
struct Shader {
|
||||||
@ -32,6 +34,7 @@ class MoonlightInstance : public pp::Instance, public pp::MouseLock {
|
|||||||
explicit MoonlightInstance(PP_Instance instance) :
|
explicit MoonlightInstance(PP_Instance instance) :
|
||||||
pp::Instance(instance),
|
pp::Instance(instance),
|
||||||
pp::MouseLock(this),
|
pp::MouseLock(this),
|
||||||
|
m_IsPainting(false),
|
||||||
m_CallbackFactory(this),
|
m_CallbackFactory(this),
|
||||||
m_MouseLocked(false) {
|
m_MouseLocked(false) {
|
||||||
// This function MUST be used otherwise sockets don't work (nacl_io_init() doesn't work!)
|
// This function MUST be used otherwise sockets don't work (nacl_io_init() doesn't work!)
|
||||||
@ -70,11 +73,11 @@ class MoonlightInstance : public pp::Instance, public pp::MouseLock {
|
|||||||
|
|
||||||
static Shader CreateProgram(const char* vertexShader, const char* fragmentShader);
|
static Shader CreateProgram(const char* vertexShader, const char* fragmentShader);
|
||||||
static void CreateShader(GLuint program, GLenum type, const char* source, int size);
|
static void CreateShader(GLuint program, GLenum type, const char* source, int size);
|
||||||
static void PaintPicture(PP_VideoPicture picture);
|
|
||||||
|
|
||||||
void DispatchRendering(int32_t unused);
|
void PaintFinished(int32_t result);
|
||||||
void DispatchGetPicture(uint32_t unused);
|
void DispatchGetPicture(uint32_t unused);
|
||||||
void PictureReady(int32_t result, PP_VideoPicture picture);
|
void PictureReady(int32_t result, PP_VideoPicture picture);
|
||||||
|
void PaintPicture(void);
|
||||||
|
|
||||||
static void VidDecSetup(int width, int height, int redrawRate, void* context, int drFlags);
|
static void VidDecSetup(int width, int height, int redrawRate, void* context, int drFlags);
|
||||||
static void VidDecCleanup(void);
|
static void VidDecCleanup(void);
|
||||||
@ -90,7 +93,8 @@ class MoonlightInstance : public pp::Instance, public pp::MouseLock {
|
|||||||
Shader m_Texture2DShader;
|
Shader m_Texture2DShader;
|
||||||
Shader m_RectangleArbShader;
|
Shader m_RectangleArbShader;
|
||||||
Shader m_ExternalOesShader;
|
Shader m_ExternalOesShader;
|
||||||
PP_VideoPicture m_LastPicture;
|
std::queue<PP_VideoPicture> m_PendingPictureQueue;
|
||||||
|
bool m_IsPainting;
|
||||||
|
|
||||||
double m_LastPadTimestamps[4];
|
double m_LastPadTimestamps[4];
|
||||||
const PPB_Gamepad* m_GamepadApi;
|
const PPB_Gamepad* m_GamepadApi;
|
||||||
|
50
viddec.cpp
50
viddec.cpp
@ -108,7 +108,7 @@ void MoonlightInstance::DidChangeView(const pp::Rect& position,
|
|||||||
GL_STATIC_DRAW);
|
GL_STATIC_DRAW);
|
||||||
assertNoGLError();
|
assertNoGLError();
|
||||||
|
|
||||||
g_Instance->m_Graphics3D.SwapBuffers(g_Instance->m_CallbackFactory.NewCallback(&MoonlightInstance::DispatchRendering));
|
g_Instance->m_Graphics3D.SwapBuffers(pp::BlockUntilComplete());
|
||||||
}
|
}
|
||||||
|
|
||||||
void MoonlightInstance::VidDecSetup(int width, int height, int redrawRate, void* context, int drFlags) {
|
void MoonlightInstance::VidDecSetup(int width, int height, int redrawRate, void* context, int drFlags) {
|
||||||
@ -128,12 +128,6 @@ void MoonlightInstance::VidDecSetup(int width, int height, int redrawRate, void*
|
|||||||
}
|
}
|
||||||
|
|
||||||
void MoonlightInstance::DispatchGetPicture(uint32_t unused) {
|
void MoonlightInstance::DispatchGetPicture(uint32_t unused) {
|
||||||
/*glClearColor(0.5, 0.5, 0.5, 1);
|
|
||||||
glClear(GL_COLOR_BUFFER_BIT);
|
|
||||||
|
|
||||||
m_Graphics3D.SwapBuffers(
|
|
||||||
m_CallbackFactory.NewCallback(&MoonlightInstance::DispatchGetPicture));*/
|
|
||||||
|
|
||||||
// Queue the initial GetPicture callback on the main thread
|
// Queue the initial GetPicture callback on the main thread
|
||||||
g_Instance->m_VideoDecoder->GetPicture(
|
g_Instance->m_VideoDecoder->GetPicture(
|
||||||
g_Instance->m_CallbackFactory.NewCallbackWithOutput(&MoonlightInstance::PictureReady));
|
g_Instance->m_CallbackFactory.NewCallbackWithOutput(&MoonlightInstance::PictureReady));
|
||||||
@ -217,7 +211,18 @@ Shader MoonlightInstance::CreateProgram(const char* vertexShader, const char* fr
|
|||||||
return shader;
|
return shader;
|
||||||
}
|
}
|
||||||
|
|
||||||
void MoonlightInstance::PaintPicture(PP_VideoPicture picture) {
|
void MoonlightInstance::PaintPicture(void) {
|
||||||
|
m_IsPainting = true;
|
||||||
|
|
||||||
|
// Free and skip all frames except the latest one
|
||||||
|
PP_VideoPicture picture;
|
||||||
|
while (m_PendingPictureQueue.size() > 1) {
|
||||||
|
picture = m_PendingPictureQueue.front();
|
||||||
|
m_PendingPictureQueue.pop();
|
||||||
|
g_Instance->m_VideoDecoder->RecyclePicture(picture);
|
||||||
|
}
|
||||||
|
|
||||||
|
picture = m_PendingPictureQueue.front();
|
||||||
if (picture.texture_target == GL_TEXTURE_2D) {
|
if (picture.texture_target == GL_TEXTURE_2D) {
|
||||||
if (!g_Instance->m_Texture2DShader.program) {
|
if (!g_Instance->m_Texture2DShader.program) {
|
||||||
g_Instance->m_Texture2DShader = CreateProgram(k_VertexShader, k_FragmentShader2D);
|
g_Instance->m_Texture2DShader = CreateProgram(k_VertexShader, k_FragmentShader2D);
|
||||||
@ -249,12 +254,21 @@ void MoonlightInstance::PaintPicture(PP_VideoPicture picture) {
|
|||||||
glUseProgram(0);
|
glUseProgram(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
g_Instance->m_Graphics3D.SwapBuffers(g_Instance->m_CallbackFactory.NewCallback(&MoonlightInstance::DispatchRendering));
|
g_Instance->m_Graphics3D.SwapBuffers(
|
||||||
|
g_Instance->m_CallbackFactory.NewCallback(&MoonlightInstance::PaintFinished));
|
||||||
}
|
}
|
||||||
|
|
||||||
void MoonlightInstance::DispatchRendering(int32_t unused) {
|
void MoonlightInstance::PaintFinished(int32_t result) {
|
||||||
// Paint the image on screen
|
m_IsPainting = false;
|
||||||
PaintPicture(m_LastPicture);
|
|
||||||
|
// Recycle the picture now that it's been painted
|
||||||
|
g_Instance->m_VideoDecoder->RecyclePicture(m_PendingPictureQueue.front());
|
||||||
|
m_PendingPictureQueue.pop();
|
||||||
|
|
||||||
|
// Keep painting if we still have frames
|
||||||
|
if (!m_PendingPictureQueue.empty()) {
|
||||||
|
PaintPicture();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void MoonlightInstance::PictureReady(int32_t result, PP_VideoPicture picture) {
|
void MoonlightInstance::PictureReady(int32_t result, PP_VideoPicture picture) {
|
||||||
@ -262,16 +276,14 @@ void MoonlightInstance::PictureReady(int32_t result, PP_VideoPicture picture) {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Replace the last picture with this one and free the old one
|
m_PendingPictureQueue.push(picture);
|
||||||
PP_VideoPicture oldPic = m_LastPicture;
|
|
||||||
m_LastPicture = picture;
|
|
||||||
if (oldPic.texture_target) {
|
|
||||||
g_Instance->m_VideoDecoder->RecyclePicture(oldPic);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Queue another callback
|
|
||||||
g_Instance->m_VideoDecoder->GetPicture(
|
g_Instance->m_VideoDecoder->GetPicture(
|
||||||
g_Instance->m_CallbackFactory.NewCallbackWithOutput(&MoonlightInstance::PictureReady));
|
g_Instance->m_CallbackFactory.NewCallbackWithOutput(&MoonlightInstance::PictureReady));
|
||||||
|
|
||||||
|
if (!m_IsPainting) {
|
||||||
|
PaintPicture();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
DECODER_RENDERER_CALLBACKS MoonlightInstance::s_DrCallbacks = {
|
DECODER_RENDERER_CALLBACKS MoonlightInstance::s_DrCallbacks = {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user