mirror of
https://github.com/moonlight-stream/moonlight-chrome.git
synced 2025-08-17 16:46:31 +00:00
Rendering WIP
This commit is contained in:
parent
1f8549fbeb
commit
e67a841a3e
2
Makefile
2
Makefile
@ -13,7 +13,7 @@ include $(NACL_SDK_ROOT)/tools/common.mk
|
|||||||
HTTPD_PY := $(HTTPD_PY) --no-dir-check
|
HTTPD_PY := $(HTTPD_PY) --no-dir-check
|
||||||
|
|
||||||
|
|
||||||
LIBS = ppapi ppapi_cpp pthread nacl_io
|
LIBS = ppapi_gles2 ppapi ppapi_cpp pthread nacl_io
|
||||||
|
|
||||||
CFLAGS = -Wall -Wno-missing-braces
|
CFLAGS = -Wall -Wno-missing-braces
|
||||||
SOURCES = \
|
SOURCES = \
|
||||||
|
18
main.cpp
18
main.cpp
@ -96,24 +96,6 @@ bool MoonlightInstance::Init(uint32_t argc,
|
|||||||
const char* argn[],
|
const char* argn[],
|
||||||
const char* argv[]) {
|
const char* argv[]) {
|
||||||
g_Instance = this;
|
g_Instance = this;
|
||||||
|
|
||||||
int32_t context_attributes[] = {
|
|
||||||
PP_GRAPHICS3DATTRIB_ALPHA_SIZE, 8,
|
|
||||||
PP_GRAPHICS3DATTRIB_BLUE_SIZE, 8,
|
|
||||||
PP_GRAPHICS3DATTRIB_GREEN_SIZE, 8,
|
|
||||||
PP_GRAPHICS3DATTRIB_RED_SIZE, 8,
|
|
||||||
PP_GRAPHICS3DATTRIB_DEPTH_SIZE, 0,
|
|
||||||
PP_GRAPHICS3DATTRIB_STENCIL_SIZE, 0,
|
|
||||||
PP_GRAPHICS3DATTRIB_SAMPLES, 0,
|
|
||||||
PP_GRAPHICS3DATTRIB_SAMPLE_BUFFERS, 0,
|
|
||||||
PP_GRAPHICS3DATTRIB_WIDTH, 500,
|
|
||||||
PP_GRAPHICS3DATTRIB_HEIGHT, 500,
|
|
||||||
PP_GRAPHICS3DATTRIB_NONE,
|
|
||||||
};
|
|
||||||
m_Graphics3D = new pp::Graphics3D(this, context_attributes);
|
|
||||||
assert(!m_Graphics3D->is_null());
|
|
||||||
assert(BindGraphics(*m_Graphics3D));
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -6,6 +6,9 @@
|
|||||||
#include "ppapi/cpp/video_decoder.h"
|
#include "ppapi/cpp/video_decoder.h"
|
||||||
|
|
||||||
#include "ppapi/c/ppb_gamepad.h"
|
#include "ppapi/c/ppb_gamepad.h"
|
||||||
|
#include "ppapi/c/ppb_opengles2.h"
|
||||||
|
#include "ppapi/cpp/graphics_3d.h"
|
||||||
|
#include "ppapi/cpp/graphics_3d_client.h"
|
||||||
|
|
||||||
#include "ppapi/utility/completion_callback_factory.h"
|
#include "ppapi/utility/completion_callback_factory.h"
|
||||||
|
|
||||||
@ -13,17 +16,27 @@
|
|||||||
|
|
||||||
#include <Limelight.h>
|
#include <Limelight.h>
|
||||||
|
|
||||||
class MoonlightInstance : public pp::Instance, public pp::MouseLock {
|
struct Shader {
|
||||||
|
Shader() : program(0), texcoord_scale_location(0) {}
|
||||||
|
~Shader() {}
|
||||||
|
|
||||||
|
GLuint program;
|
||||||
|
GLint texcoord_scale_location;
|
||||||
|
};
|
||||||
|
|
||||||
|
class MoonlightInstance : public pp::Instance, public pp::MouseLock, public pp::Graphics3DClient {
|
||||||
public:
|
public:
|
||||||
MoonlightInstance(PP_Instance instance) :
|
MoonlightInstance(PP_Instance instance) :
|
||||||
pp::Instance(instance),
|
pp::Instance(instance),
|
||||||
pp::MouseLock(this),
|
pp::MouseLock(this),
|
||||||
|
pp::Graphics3DClient(this),
|
||||||
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!)
|
||||||
nacl_io_init_ppapi(pp_instance(), pp::Module::Get()->get_browser_interface());
|
nacl_io_init_ppapi(pp_instance(), pp::Module::Get()->get_browser_interface());
|
||||||
|
|
||||||
m_GamepadApi = static_cast<const PPB_Gamepad*>(pp::Module::Get()->GetBrowserInterface(PPB_GAMEPAD_INTERFACE));
|
m_GamepadApi = static_cast<const PPB_Gamepad*>(pp::Module::Get()->GetBrowserInterface(PPB_GAMEPAD_INTERFACE));
|
||||||
|
m_GlesApi = static_cast<const PPB_OpenGLES2*>(pp::Module::Get()->GetBrowserInterface(PPB_OPENGLES2_INTERFACE));
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual ~MoonlightInstance();
|
virtual ~MoonlightInstance();
|
||||||
@ -42,6 +55,9 @@ class MoonlightInstance : public pp::Instance, public pp::MouseLock {
|
|||||||
void OnConnectionStopped(uint32_t unused);
|
void OnConnectionStopped(uint32_t unused);
|
||||||
void OnConnectionStarted(uint32_t error);
|
void OnConnectionStarted(uint32_t error);
|
||||||
|
|
||||||
|
void DidChangeView(const pp::Rect& position,
|
||||||
|
const pp::Rect& clip_ignored);
|
||||||
|
|
||||||
static void* ConnectionThreadFunc(void* context);
|
static void* ConnectionThreadFunc(void* context);
|
||||||
|
|
||||||
static void ClStageStarting(int stage);
|
static void ClStageStarting(int stage);
|
||||||
@ -51,6 +67,12 @@ class MoonlightInstance : public pp::Instance, public pp::MouseLock {
|
|||||||
static void ClDisplayMessage(char* message);
|
static void ClDisplayMessage(char* message);
|
||||||
static void ClDisplayTransientMessage(char* message);
|
static void ClDisplayTransientMessage(char* message);
|
||||||
|
|
||||||
|
|
||||||
|
virtual void Graphics3DContextLost() {}
|
||||||
|
static Shader CreateProgram(const char* vertexShader, const char* fragmentShader);
|
||||||
|
static void CreateShader(GLuint program, GLenum type, const char* source, int size);
|
||||||
|
static void PaintPicture(PP_VideoPicture picture);
|
||||||
|
|
||||||
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);
|
||||||
|
|
||||||
@ -64,6 +86,12 @@ class MoonlightInstance : public pp::Instance, public pp::MouseLock {
|
|||||||
|
|
||||||
pp::Graphics3D* m_Graphics3D;
|
pp::Graphics3D* m_Graphics3D;
|
||||||
pp::VideoDecoder* m_VideoDecoder;
|
pp::VideoDecoder* m_VideoDecoder;
|
||||||
|
pp::Size m_ViewSize;
|
||||||
|
const PPB_OpenGLES2* m_GlesApi;
|
||||||
|
Shader m_Texture2DShader;
|
||||||
|
Shader m_RectangleArbShader;
|
||||||
|
Shader m_ExternalOesShader;
|
||||||
|
|
||||||
double m_LastPadTimestamps[4];
|
double m_LastPadTimestamps[4];
|
||||||
const PPB_Gamepad* m_GamepadApi;
|
const PPB_Gamepad* m_GamepadApi;
|
||||||
pp::CompletionCallbackFactory<MoonlightInstance> m_CallbackFactory;
|
pp::CompletionCallbackFactory<MoonlightInstance> m_CallbackFactory;
|
||||||
|
194
viddec.cpp
194
viddec.cpp
@ -1,10 +1,111 @@
|
|||||||
#include "moonlight.hpp"
|
#include "moonlight.hpp"
|
||||||
|
|
||||||
|
#include <GLES2/gl2.h>
|
||||||
|
#include <GLES2/gl2ext.h>
|
||||||
|
|
||||||
#define INITIAL_DECODE_BUFFER_LEN 128 * 1024
|
#define INITIAL_DECODE_BUFFER_LEN 128 * 1024
|
||||||
|
|
||||||
static unsigned char* s_DecodeBuffer;
|
static unsigned char* s_DecodeBuffer;
|
||||||
static unsigned int s_DecodeBufferLength;
|
static unsigned int s_DecodeBufferLength;
|
||||||
|
|
||||||
|
#define assertNoGLError() assert(!g_Instance->m_GlesApi->GetError(g_Instance->m_Graphics3D->pp_resource()))
|
||||||
|
|
||||||
|
static const char k_VertexShader[] =
|
||||||
|
"varying vec2 v_texCoord; \n"
|
||||||
|
"attribute vec4 a_position; \n"
|
||||||
|
"attribute vec2 a_texCoord; \n"
|
||||||
|
"uniform vec2 v_scale; \n"
|
||||||
|
"void main() \n"
|
||||||
|
"{ \n"
|
||||||
|
" v_texCoord = v_scale * a_texCoord; \n"
|
||||||
|
" gl_Position = a_position; \n"
|
||||||
|
"}";
|
||||||
|
|
||||||
|
static const char k_FragmentShader2D[] =
|
||||||
|
"precision mediump float; \n"
|
||||||
|
"varying vec2 v_texCoord; \n"
|
||||||
|
"uniform sampler2D s_texture; \n"
|
||||||
|
"void main() \n"
|
||||||
|
"{"
|
||||||
|
" gl_FragColor = texture2D(s_texture, v_texCoord); \n"
|
||||||
|
"}";
|
||||||
|
|
||||||
|
static const char k_FragmentShaderRectangle[] =
|
||||||
|
"#extension GL_ARB_texture_rectangle : require\n"
|
||||||
|
"precision mediump float; \n"
|
||||||
|
"varying vec2 v_texCoord; \n"
|
||||||
|
"uniform sampler2DRect s_texture; \n"
|
||||||
|
"void main() \n"
|
||||||
|
"{"
|
||||||
|
" gl_FragColor = texture2DRect(s_texture, v_texCoord).rgba; \n"
|
||||||
|
"}";
|
||||||
|
|
||||||
|
static const char k_FragmentShaderExternal[] =
|
||||||
|
"#extension GL_OES_EGL_image_external : require\n"
|
||||||
|
"precision mediump float; \n"
|
||||||
|
"varying vec2 v_texCoord; \n"
|
||||||
|
"uniform samplerExternalOES s_texture; \n"
|
||||||
|
"void main() \n"
|
||||||
|
"{"
|
||||||
|
" gl_FragColor = texture2D(s_texture, v_texCoord); \n"
|
||||||
|
"}";
|
||||||
|
|
||||||
|
void MoonlightInstance::DidChangeView(const pp::Rect& position,
|
||||||
|
const pp::Rect& clip) {
|
||||||
|
|
||||||
|
if (position.width() == 0 || position.height() == 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (m_ViewSize.width()) {
|
||||||
|
assert(position.size() == m_ViewSize);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
m_ViewSize = position.size();
|
||||||
|
printf("View size: %dx%d\n", m_ViewSize.width(), m_ViewSize.height());
|
||||||
|
|
||||||
|
int32_t contextAttributes[] = {
|
||||||
|
PP_GRAPHICS3DATTRIB_ALPHA_SIZE, 8,
|
||||||
|
PP_GRAPHICS3DATTRIB_BLUE_SIZE, 8,
|
||||||
|
PP_GRAPHICS3DATTRIB_GREEN_SIZE, 8,
|
||||||
|
PP_GRAPHICS3DATTRIB_RED_SIZE, 8,
|
||||||
|
PP_GRAPHICS3DATTRIB_DEPTH_SIZE, 0,
|
||||||
|
PP_GRAPHICS3DATTRIB_STENCIL_SIZE, 0,
|
||||||
|
PP_GRAPHICS3DATTRIB_SAMPLES, 0,
|
||||||
|
PP_GRAPHICS3DATTRIB_SAMPLE_BUFFERS, 0,
|
||||||
|
PP_GRAPHICS3DATTRIB_WIDTH, g_Instance->m_ViewSize.width(),
|
||||||
|
PP_GRAPHICS3DATTRIB_HEIGHT, g_Instance->m_ViewSize.height(),
|
||||||
|
PP_GRAPHICS3DATTRIB_NONE,
|
||||||
|
};
|
||||||
|
g_Instance->m_Graphics3D = new pp::Graphics3D(g_Instance, contextAttributes);
|
||||||
|
assert(!g_Instance->m_Graphics3D->is_null());
|
||||||
|
|
||||||
|
assert(BindGraphics(*m_Graphics3D));
|
||||||
|
|
||||||
|
PP_Resource graphics3D = g_Instance->m_Graphics3D->pp_resource();
|
||||||
|
|
||||||
|
g_Instance->m_GlesApi->ClearColor(graphics3D, 1, 0, 0, 1);
|
||||||
|
g_Instance->m_GlesApi->Clear(graphics3D, GL_COLOR_BUFFER_BIT);
|
||||||
|
|
||||||
|
assertNoGLError();
|
||||||
|
|
||||||
|
static const float k_Vertices[] = {
|
||||||
|
-1, -1, -1, 1, 1, -1, 1, 1, // Position coordinates.
|
||||||
|
0, 1, 0, 0, 1, 1, 1, 0, // Texture coordinates.
|
||||||
|
};
|
||||||
|
|
||||||
|
GLuint buffer;
|
||||||
|
g_Instance->m_GlesApi->GenBuffers(graphics3D, 1, &buffer);
|
||||||
|
g_Instance->m_GlesApi->BindBuffer(graphics3D, GL_ARRAY_BUFFER, buffer);
|
||||||
|
|
||||||
|
g_Instance->m_GlesApi->BufferData(graphics3D,
|
||||||
|
GL_ARRAY_BUFFER,
|
||||||
|
sizeof(k_Vertices),
|
||||||
|
k_Vertices,
|
||||||
|
GL_STATIC_DRAW);
|
||||||
|
assertNoGLError();
|
||||||
|
}
|
||||||
|
|
||||||
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) {
|
||||||
g_Instance->m_VideoDecoder = new pp::VideoDecoder(g_Instance);
|
g_Instance->m_VideoDecoder = new pp::VideoDecoder(g_Instance);
|
||||||
|
|
||||||
@ -30,6 +131,19 @@ void MoonlightInstance::DispatchGetPicture(uint32_t unused) {
|
|||||||
void MoonlightInstance::VidDecCleanup(void) {
|
void MoonlightInstance::VidDecCleanup(void) {
|
||||||
free(s_DecodeBuffer);
|
free(s_DecodeBuffer);
|
||||||
delete g_Instance->m_VideoDecoder;
|
delete g_Instance->m_VideoDecoder;
|
||||||
|
|
||||||
|
PP_Resource graphics3D = g_Instance->m_Graphics3D->pp_resource();
|
||||||
|
if (g_Instance->m_Texture2DShader.program) {
|
||||||
|
g_Instance->m_GlesApi->DeleteProgram(graphics3D, g_Instance->m_Texture2DShader.program);
|
||||||
|
}
|
||||||
|
if (g_Instance->m_RectangleArbShader.program) {
|
||||||
|
g_Instance->m_GlesApi->DeleteProgram(graphics3D, g_Instance->m_RectangleArbShader.program);
|
||||||
|
}
|
||||||
|
if (g_Instance->m_ExternalOesShader.program) {
|
||||||
|
g_Instance->m_GlesApi->DeleteProgram(graphics3D, g_Instance->m_ExternalOesShader.program);
|
||||||
|
}
|
||||||
|
|
||||||
|
delete g_Instance->m_Graphics3D;
|
||||||
}
|
}
|
||||||
|
|
||||||
int MoonlightInstance::VidDecSubmitDecodeUnit(PDECODE_UNIT decodeUnit) {
|
int MoonlightInstance::VidDecSubmitDecodeUnit(PDECODE_UNIT decodeUnit) {
|
||||||
@ -58,12 +172,90 @@ int MoonlightInstance::VidDecSubmitDecodeUnit(PDECODE_UNIT decodeUnit) {
|
|||||||
return DR_OK;
|
return DR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void MoonlightInstance::CreateShader(GLuint program, GLenum type,
|
||||||
|
const char* source, int size) {
|
||||||
|
PP_Resource graphics3D = g_Instance->m_Graphics3D->pp_resource();
|
||||||
|
GLuint shader = g_Instance->m_GlesApi->CreateShader(graphics3D, type);
|
||||||
|
g_Instance->m_GlesApi->ShaderSource(graphics3D, shader, 1, &source, &size);
|
||||||
|
g_Instance->m_GlesApi->CompileShader(graphics3D, shader);
|
||||||
|
g_Instance->m_GlesApi->AttachShader(graphics3D, program, shader);
|
||||||
|
g_Instance->m_GlesApi->DeleteShader(graphics3D, shader);
|
||||||
|
}
|
||||||
|
|
||||||
|
Shader MoonlightInstance::CreateProgram(const char* vertexShader, const char* fragmentShader) {
|
||||||
|
Shader shader;
|
||||||
|
PP_Resource graphics3D = g_Instance->m_Graphics3D->pp_resource();
|
||||||
|
|
||||||
|
shader.program = g_Instance->m_GlesApi->CreateProgram(graphics3D);
|
||||||
|
CreateShader(shader.program, GL_VERTEX_SHADER, vertexShader, strlen(vertexShader));
|
||||||
|
CreateShader(shader.program, GL_FRAGMENT_SHADER, fragmentShader, strlen(fragmentShader));
|
||||||
|
g_Instance->m_GlesApi->LinkProgram(graphics3D, shader.program);
|
||||||
|
g_Instance->m_GlesApi->UseProgram(graphics3D, shader.program);
|
||||||
|
|
||||||
|
g_Instance->m_GlesApi->Uniform1i(graphics3D,
|
||||||
|
g_Instance->m_GlesApi->GetUniformLocation(graphics3D, shader.program, "s_texture"), 0);
|
||||||
|
assertNoGLError();
|
||||||
|
|
||||||
|
shader.texcoord_scale_location = g_Instance->m_GlesApi->GetUniformLocation(graphics3D, shader.program, "v_scale");
|
||||||
|
|
||||||
|
GLint pos_location = g_Instance->m_GlesApi->GetAttribLocation(graphics3D, shader.program, "a_position");
|
||||||
|
GLint tc_location = g_Instance->m_GlesApi->GetAttribLocation(graphics3D, shader.program, "a_texCoord");
|
||||||
|
assertNoGLError();
|
||||||
|
|
||||||
|
g_Instance->m_GlesApi->EnableVertexAttribArray(graphics3D, pos_location);
|
||||||
|
g_Instance->m_GlesApi->VertexAttribPointer(graphics3D, pos_location, 2, GL_FLOAT, GL_FALSE, 0, 0);
|
||||||
|
g_Instance->m_GlesApi->EnableVertexAttribArray(graphics3D, tc_location);
|
||||||
|
g_Instance->m_GlesApi->VertexAttribPointer(graphics3D, tc_location, 2, GL_FLOAT, GL_FALSE, 0, static_cast<float*>(0) + 8);
|
||||||
|
|
||||||
|
g_Instance->m_GlesApi->UseProgram(graphics3D, 0);
|
||||||
|
assertNoGLError();
|
||||||
|
return shader;
|
||||||
|
}
|
||||||
|
|
||||||
|
void MoonlightInstance::PaintPicture(PP_VideoPicture picture) {
|
||||||
|
PP_Resource graphics3D = g_Instance->m_Graphics3D->pp_resource();
|
||||||
|
|
||||||
|
if (picture.texture_target == GL_TEXTURE_2D) {
|
||||||
|
if (!g_Instance->m_Texture2DShader.program) {
|
||||||
|
g_Instance->m_Texture2DShader = CreateProgram(k_VertexShader, k_FragmentShader2D);
|
||||||
|
}
|
||||||
|
g_Instance->m_GlesApi->UseProgram(graphics3D, g_Instance->m_Texture2DShader.program);
|
||||||
|
g_Instance->m_GlesApi->Uniform2f(graphics3D, g_Instance->m_Texture2DShader.texcoord_scale_location,
|
||||||
|
1.0, 1.0);
|
||||||
|
}
|
||||||
|
else if (picture.texture_target == GL_TEXTURE_RECTANGLE_ARB) {
|
||||||
|
if (!g_Instance->m_RectangleArbShader.program) {
|
||||||
|
g_Instance->m_RectangleArbShader = CreateProgram(k_VertexShader, k_FragmentShaderRectangle);
|
||||||
|
}
|
||||||
|
g_Instance->m_GlesApi->UseProgram(graphics3D, g_Instance->m_RectangleArbShader.program);
|
||||||
|
g_Instance->m_GlesApi->Uniform2f(graphics3D, g_Instance->m_RectangleArbShader.texcoord_scale_location,
|
||||||
|
picture.texture_size.width, picture.texture_size.height);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (!g_Instance->m_ExternalOesShader.program) {
|
||||||
|
g_Instance->m_ExternalOesShader = CreateProgram(k_VertexShader, k_FragmentShaderExternal);
|
||||||
|
}
|
||||||
|
g_Instance->m_GlesApi->UseProgram(graphics3D, g_Instance->m_ExternalOesShader.program);
|
||||||
|
g_Instance->m_GlesApi->Uniform2f(graphics3D, g_Instance->m_ExternalOesShader.texcoord_scale_location,
|
||||||
|
1.0, 1.0);
|
||||||
|
}
|
||||||
|
|
||||||
|
g_Instance->m_GlesApi->Viewport(graphics3D, 0, 0, g_Instance->m_ViewSize.width(), g_Instance->m_ViewSize.height());
|
||||||
|
g_Instance->m_GlesApi->ActiveTexture(graphics3D, GL_TEXTURE0);
|
||||||
|
g_Instance->m_GlesApi->BindTexture(graphics3D, picture.texture_target, picture.texture_id);
|
||||||
|
g_Instance->m_GlesApi->DrawArrays(graphics3D, GL_TRIANGLE_STRIP, 0, 4);
|
||||||
|
g_Instance->m_GlesApi->UseProgram(graphics3D, 0);
|
||||||
|
|
||||||
|
g_Instance->m_Graphics3D->SwapBuffers(pp::BlockUntilComplete());
|
||||||
|
}
|
||||||
|
|
||||||
void MoonlightInstance::PictureReady(int32_t result, PP_VideoPicture picture) {
|
void MoonlightInstance::PictureReady(int32_t result, PP_VideoPicture picture) {
|
||||||
if (result == PP_ERROR_ABORTED) {
|
if (result == PP_ERROR_ABORTED) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// FIXME: Draw video
|
// Paint the image on screen
|
||||||
|
PaintPicture(picture);
|
||||||
|
|
||||||
g_Instance->m_VideoDecoder->RecyclePicture(picture);
|
g_Instance->m_VideoDecoder->RecyclePicture(picture);
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user