diff options
-rw-r--r-- | gpu/command_buffer/client/gles2_demo.cc | 6 | ||||
-rw-r--r-- | gpu/command_buffer/client/gles2_demo_c.c | 2 | ||||
-rw-r--r-- | gpu/command_buffer/client/gles2_demo_c.h | 2 | ||||
-rw-r--r-- | gpu/command_buffer/client/gles2_demo_cc.cc | 73 | ||||
-rw-r--r-- | gpu/command_buffer/client/gles2_demo_cc.h | 3 | ||||
-rw-r--r-- | gpu/command_buffer/client/gles2_lib.cc | 1 | ||||
-rw-r--r-- | gpu/command_buffer/common/constants.h | 1 | ||||
-rw-r--r-- | gpu/command_buffer/service/gles2_cmd_decoder.cc | 2 | ||||
-rw-r--r-- | gpu/demos/framework/plugin.cc | 55 | ||||
-rw-r--r-- | gpu/demos/framework/plugin.h | 3 | ||||
-rw-r--r-- | gpu/pgl/pgl.cc | 85 | ||||
-rw-r--r-- | gpu/pgl/pgl.h | 18 | ||||
-rw-r--r-- | third_party/npapi/bindings/npapi_extensions.h | 15 | ||||
-rw-r--r-- | webkit/tools/pepper_test_plugin/plugin_object.cc | 72 | ||||
-rw-r--r-- | webkit/tools/pepper_test_plugin/plugin_object.h | 2 |
15 files changed, 232 insertions, 108 deletions
diff --git a/gpu/command_buffer/client/gles2_demo.cc b/gpu/command_buffer/client/gles2_demo.cc index 9b5977e..8992c2c 100644 --- a/gpu/command_buffer/client/gles2_demo.cc +++ b/gpu/command_buffer/client/gles2_demo.cc @@ -83,6 +83,8 @@ bool GLES2Demo::Setup(void* hwnd, int32 size) { transfer_buffer.ptr, transfer_buffer_id)); + GLFromCPPInit(); + return command_buffer.release() != NULL; } @@ -97,8 +99,8 @@ LRESULT CALLBACK WindowProc( PostQuitMessage(0); break; case WM_PAINT: { - GLFromCPPTestFunction(); - GLFromCTestFunction(); + GLFromCPPDraw(); + GLFromCDraw(); // TODO(gman): Not sure how SwapBuffer should be exposed. gles2::GetGLContext()->SwapBuffers(); break; diff --git a/gpu/command_buffer/client/gles2_demo_c.c b/gpu/command_buffer/client/gles2_demo_c.c index abba8b7..aa83b57 100644 --- a/gpu/command_buffer/client/gles2_demo_c.c +++ b/gpu/command_buffer/client/gles2_demo_c.c @@ -8,7 +8,7 @@ #include <GLES2/gl2.h> #include "gpu/command_buffer/client/gles2_demo_c.h" -void GLFromCTestFunction() { +void GLFromCDraw() { // glClear(GL_COLOR_BUFFER_BIT); } diff --git a/gpu/command_buffer/client/gles2_demo_c.h b/gpu/command_buffer/client/gles2_demo_c.h index 3ce07b2..d4d69e9 100644 --- a/gpu/command_buffer/client/gles2_demo_c.h +++ b/gpu/command_buffer/client/gles2_demo_c.h @@ -11,7 +11,7 @@ extern "C" { #endif -void GLFromCTestFunction(); +void GLFromCDraw(); #ifdef __cplusplus } diff --git a/gpu/command_buffer/client/gles2_demo_cc.cc b/gpu/command_buffer/client/gles2_demo_cc.cc index 2544f42..c6beff6 100644 --- a/gpu/command_buffer/client/gles2_demo_cc.cc +++ b/gpu/command_buffer/client/gles2_demo_cc.cc @@ -130,15 +130,43 @@ void InitShaders() { CheckGLError(); } -#define PI 3.1415926535897932384626433832795f +GLuint CreateCheckerboardTexture() { + static unsigned char pixels[] = { + 255, 255, 255, + 0, 0, 0, + 0, 0, 0, + 255, 255, 255, + }; + GLuint texture; + glGenTextures(1, &texture); + glBindTexture(GL_TEXTURE_2D, texture); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); + glPixelStorei(GL_UNPACK_ALIGNMENT, 1); + glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, 2, 2, 0, GL_RGB, GL_UNSIGNED_BYTE, + pixels); + return texture; +} + +} // anonymous namespace. + +void GLFromCPPInit() { + glClearColor(0.f, 0.f, .7f, 1.f); + g_texture = CreateCheckerboardTexture(); + InitShaders(); +} + +void GLFromCPPDraw() { + const float kPi = 3.1415926535897932384626433832795f; -void Draw() { // TODO(kbr): base the angle on time rather than on ticks g_angle = (g_angle + 1) % 360; // Rotate about the Z axis GLfloat rot_matrix[16]; - GLfloat cos_angle = cosf(static_cast<GLfloat>(g_angle) * PI / 180.0f); - GLfloat sin_angle = sinf(static_cast<GLfloat>(g_angle) * PI / 180.0f); + GLfloat cos_angle = cosf(static_cast<GLfloat>(g_angle) * kPi / 180.0f); + GLfloat sin_angle = sinf(static_cast<GLfloat>(g_angle) * kPi / 180.0f); // OpenGL matrices are column-major rot_matrix[0] = cos_angle; rot_matrix[1] = sin_angle; @@ -188,40 +216,3 @@ void Draw() { CheckGLError(); glFlush(); } - -GLuint CreateCheckerboardTexture() { - static unsigned char pixels[] = { - 255, 255, 255, - 0, 0, 0, - 0, 0, 0, - 255, 255, 255, - }; - GLuint texture; - glGenTextures(1, &texture); - glBindTexture(GL_TEXTURE_2D, texture); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); - glPixelStorei(GL_UNPACK_ALIGNMENT, 1); - glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, 2, 2, 0, GL_RGB, GL_UNSIGNED_BYTE, - pixels); - return texture; -} - -void Init() { - glClearColor(0.f, 0.f, .7f, 1.f); - g_texture = CreateCheckerboardTexture(); - InitShaders(); -} - -} // anonymous namespace. - -void GLFromCPPTestFunction() { - static bool initialized = false; - if (!initialized) { - initialized = true; - Init(); - } - Draw(); -} diff --git a/gpu/command_buffer/client/gles2_demo_cc.h b/gpu/command_buffer/client/gles2_demo_cc.h index ef074e0..158ba43 100644 --- a/gpu/command_buffer/client/gles2_demo_cc.h +++ b/gpu/command_buffer/client/gles2_demo_cc.h @@ -7,7 +7,8 @@ #ifndef GPU_COMMAND_BUFFER_CLIENT_GLES2_DEMO_CC_H #define GPU_COMMAND_BUFFER_CLIENT_GLES2_DEMO_CC_H -void GLFromCPPTestFunction(); +void GLFromCPPInit(); +void GLFromCPPDraw(); #endif // GPU_COMMAND_BUFFER_CLIENT_GLES2_DEMO_CC_H diff --git a/gpu/command_buffer/client/gles2_lib.cc b/gpu/command_buffer/client/gles2_lib.cc index 003a4cc..5753715 100644 --- a/gpu/command_buffer/client/gles2_lib.cc +++ b/gpu/command_buffer/client/gles2_lib.cc @@ -16,6 +16,7 @@ void Initialize() { void Terminate() { gpu::ThreadLocalFree(g_gl_context_key); + g_gl_context_key = 0; } gpu::gles2::GLES2Implementation* GetGLContext() { diff --git a/gpu/command_buffer/common/constants.h b/gpu/command_buffer/common/constants.h index b208153..2359bea 100644 --- a/gpu/command_buffer/common/constants.h +++ b/gpu/command_buffer/common/constants.h @@ -20,6 +20,7 @@ namespace error { kOutOfBounds, kUnknownCommand, kInvalidArguments, + kLostContext, kGenericError }; } diff --git a/gpu/command_buffer/service/gles2_cmd_decoder.cc b/gpu/command_buffer/service/gles2_cmd_decoder.cc index ddfc358..684e579 100644 --- a/gpu/command_buffer/service/gles2_cmd_decoder.cc +++ b/gpu/command_buffer/service/gles2_cmd_decoder.cc @@ -1549,8 +1549,6 @@ void GLES2DecoderImpl::DoLinkProgram(GLuint program) { } }; -// NOTE: If you need to know the results of SwapBuffers (like losing -// the context) then add a new command. Do NOT make SwapBuffers synchronous. void GLES2DecoderImpl::DoSwapBuffers() { #if defined(UNIT_TEST) #elif defined(OS_WIN) diff --git a/gpu/demos/framework/plugin.cc b/gpu/demos/framework/plugin.cc index 153cd97..0514f81 100644 --- a/gpu/demos/framework/plugin.cc +++ b/gpu/demos/framework/plugin.cc @@ -7,12 +7,13 @@ #include "base/logging.h" #include "gpu/demos/framework/demo_factory.h" +using gpu::demos::Plugin; + namespace { const int32 kCommandBufferSize = 1024 * 1024; NPExtensions* g_extensions = NULL; // Plugin class functions. -using gpu::demos::Plugin; NPObject* PluginAllocate(NPP npp, NPClass* the_class) { Plugin* plugin = new Plugin(npp); return plugin; @@ -97,7 +98,7 @@ Plugin::~Plugin() { demo_.reset(); pglMakeCurrent(NULL); - pglDestroyContext(pgl_context_); + DestroyContext(); } NPClass* Plugin::GetPluginClass() { @@ -116,20 +117,10 @@ void Plugin::New(NPMIMEType pluginType, } void Plugin::SetWindow(const NPWindow& window) { - if (!pgl_context_) { - // Initialize a 3D context. - NPDeviceContext3DConfig config; - config.commandBufferSize = kCommandBufferSize; - device3d_->initializeContext(npp_, &config, &context3d_); - - // Create a PGL context. - pgl_context_ = pglCreateContext(npp_, device3d_, &context3d_); + demo_->InitWindowSize(window.width, window.height); - // Initialize demo. - pglMakeCurrent(pgl_context_); - demo_->InitWindowSize(window.width, window.height); - CHECK(demo_->InitGL()); - pglMakeCurrent(NULL); + if (!pgl_context_) { + CreateContext(); } // Schedule the first call to Draw. @@ -137,8 +128,12 @@ void Plugin::SetWindow(const NPWindow& window) { } void Plugin::Paint() { - // Render some stuff. - pglMakeCurrent(pgl_context_); + if (!pglMakeCurrent(pgl_context_) && pglGetError() == PGL_CONTEXT_LOST) { + DestroyContext(); + CreateContext(); + pglMakeCurrent(pgl_context_); + } + demo_->Draw(); pglSwapBuffers(); pglMakeCurrent(NULL); @@ -147,5 +142,31 @@ void Plugin::Paint() { g_browser->pluginthreadasynccall(npp_, PaintCallback, this); } +void Plugin::CreateContext() { + DCHECK(!pgl_context_); + + // Initialize a 3D context. + NPDeviceContext3DConfig config; + config.commandBufferSize = kCommandBufferSize; + device3d_->initializeContext(npp_, &config, &context3d_); + + // Create a PGL context. + pgl_context_ = pglCreateContext(npp_, device3d_, &context3d_); + + // Initialize demo. + pglMakeCurrent(pgl_context_); + CHECK(demo_->InitGL()); + pglMakeCurrent(NULL); +} + +void Plugin::DestroyContext() { + DCHECK(pgl_context_); + + pglDestroyContext(pgl_context_); + pgl_context_ = NULL; + + device3d_->destroyContext(npp_, &context3d_); +} + } // namespace demos } // namespace gpu diff --git a/gpu/demos/framework/plugin.h b/gpu/demos/framework/plugin.h index 7832d3b..0f4b55e 100644 --- a/gpu/demos/framework/plugin.h +++ b/gpu/demos/framework/plugin.h @@ -31,6 +31,9 @@ class Plugin : public NPObject { void Paint(); private: + void CreateContext(); + void DestroyContext(); + // This class object needs to be safely casted to NPObject* and cross // c-c++ module boundaries. To accomplish that this class should not have // any virtual member function. diff --git a/gpu/pgl/pgl.cc b/gpu/pgl/pgl.cc index 41903e1..68a074f 100644 --- a/gpu/pgl/pgl.cc +++ b/gpu/pgl/pgl.cc @@ -7,6 +7,7 @@ #include "gpu/command_buffer/client/gles2_cmd_helper.h" #include "gpu/command_buffer/client/gles2_implementation.h" #include "gpu/command_buffer/client/gles2_lib.h" +#include "gpu/command_buffer/common/constants.h" #include "gpu/command_buffer/common/thread_local.h" #include "gpu/pgl/command_buffer_pepper.h" #include "gpu/pgl/pgl.h" @@ -22,16 +23,19 @@ class PGLContextImpl { ~PGLContextImpl(); // Initlaize a PGL context with a transfer buffer of a particular size. - bool Initialize(int32 transfer_buffer_size); + PGLBoolean Initialize(int32 transfer_buffer_size); // Destroy all resources associated with the PGL context. void Destroy(); // Make a PGL context current for the calling thread. - static bool MakeCurrent(PGLContextImpl* pgl_context); + static PGLBoolean MakeCurrent(PGLContextImpl* pgl_context); // Display all content rendered since last call to SwapBuffers. - bool SwapBuffers(); + PGLBoolean SwapBuffers(); + + // Get the current error code. + PGLInt GetError(); private: PGLContextImpl(const PGLContextImpl&); @@ -64,7 +68,7 @@ PGLContextImpl::~PGLContextImpl() { Destroy(); } -bool PGLContextImpl::Initialize(int32 transfer_buffer_size) { +PGLBoolean PGLContextImpl::Initialize(int32 transfer_buffer_size) { // Create and initialize the objects required to issue GLES2 calls. command_buffer_ = new CommandBufferPepper( npp_, device_, device_context_); @@ -80,13 +84,13 @@ bool PGLContextImpl::Initialize(int32 transfer_buffer_size) { transfer_buffer.size, transfer_buffer.ptr, transfer_buffer_id_); - return true; + return PGL_TRUE; } } // Tear everything down if initialization failed. Destroy(); - return false; + return PGL_FALSE; } void PGLContextImpl::Destroy() { @@ -105,22 +109,48 @@ void PGLContextImpl::Destroy() { command_buffer_ = NULL; } -bool PGLContextImpl::MakeCurrent(PGLContextImpl* pgl_context) { +PGLBoolean PGLContextImpl::MakeCurrent(PGLContextImpl* pgl_context) { if (!g_pgl_context_key) - return false; + return PGL_FALSE; gpu::ThreadLocalSetValue(g_pgl_context_key, pgl_context); - if (pgl_context) + if (pgl_context) { gles2::SetGLContext(pgl_context->gles2_implementation_); - else + + // Don't request latest error status from service. Just use the locally + // cached information from the last flush. + // TODO(apatrick): I'm not sure if this should actually change the + // current context if it fails. For now it gets changed even if it fails + // becuase making GL calls with a NULL context crashes. + if (pgl_context->device_context_->error != NPDeviceContext3DError_NoError) + return PGL_FALSE; + } + else { gles2::SetGLContext(NULL); + } - return true; + return PGL_TRUE; } -bool PGLContextImpl::SwapBuffers() { +PGLBoolean PGLContextImpl::SwapBuffers() { + // Don't request latest error status from service. Just use the locally cached + // information from the last flush. + if (device_context_->error != NPDeviceContext3DError_NoError) + return PGL_FALSE; + gles2_implementation_->SwapBuffers(); - return true; + return PGL_TRUE; +} + +PGLInt PGLContextImpl::GetError() { + gpu::CommandBuffer::State state = command_buffer_->GetState(); + if (state.error == gpu::error::kNoError) { + return PGL_SUCCESS; + } else { + // All command buffer errors are unrecoverable. The error is treated as a + // lost context: destroy the context and create another one. + return PGL_CONTEXT_LOST; + } } } // namespace anonymous @@ -128,20 +158,22 @@ extern "C" { PGLBoolean pglInitialize() { if (g_pgl_context_key) - return true; + return PGL_TRUE; gles2::Initialize(); g_pgl_context_key = gpu::ThreadLocalAlloc(); - return true; + return PGL_TRUE; } PGLBoolean pglTerminate() { if (!g_pgl_context_key) - return true; + return PGL_TRUE; gpu::ThreadLocalFree(g_pgl_context_key); + g_pgl_context_key = 0; + gles2::Terminate(); - return true; + return PGL_TRUE; } PGLContext pglCreateContext(NPP npp, @@ -175,23 +207,34 @@ PGLBoolean pglSwapBuffers(void) { PGLContextImpl* context = static_cast<PGLContextImpl*>( pglGetCurrentContext()); if (!context) - return false; + return PGL_FALSE; return context->SwapBuffers(); } PGLBoolean pglDestroyContext(PGLContext pgl_context) { if (!g_pgl_context_key) - return NULL; + return PGL_FALSE; if (!pgl_context) - return false; + return PGL_FALSE; if (pgl_context == pglGetCurrentContext()) pglMakeCurrent(NULL); delete static_cast<PGLContextImpl*>(pgl_context); - return true; + return PGL_TRUE; } +PGLInt pglGetError() { + if (!g_pgl_context_key) + return PGL_NOT_INITIALIZED; + + PGLContextImpl* context = static_cast<PGLContextImpl*>( + pglGetCurrentContext()); + if (!context) + return PGL_BAD_CONTEXT; + + return context->GetError(); +} } // extern "C" diff --git a/gpu/pgl/pgl.h b/gpu/pgl/pgl.h index 3a7735e..ac67ec1 100644 --- a/gpu/pgl/pgl.h +++ b/gpu/pgl/pgl.h @@ -8,12 +8,25 @@ #include "npapi.h" #include "npapi_extensions.h" +#define PGL_TRUE 1 +#define PGL_FALSE 0 + #ifdef __cplusplus extern "C" { #endif typedef void* PGLContext; -typedef bool PGLBoolean; +typedef unsigned int PGLBoolean; +typedef int32 PGLInt; + +// These are the same error codes as used by EGL. +enum { + PGL_SUCCESS = 0x3000, + PGL_NOT_INITIALIZED = 0x3001, + PGL_BAD_CONTEXT = 0x3006, + PGL_BAD_PARAMETER = 0x300C, + PGL_CONTEXT_LOST = 0x300E +}; // Initialize the PGL library. This must have completed before any other PGL // functions are invoked. @@ -40,6 +53,9 @@ PGLBoolean pglSwapBuffers(void); // Destroy the given PGL context. PGLBoolean pglDestroyContext(PGLContext pgl_context); +// Return the current PGL error. +PGLInt pglGetError(); + #ifdef __cplusplus } // extern "C" #endif diff --git a/third_party/npapi/bindings/npapi_extensions.h b/third_party/npapi/bindings/npapi_extensions.h index 1b775ba..b80e0bd 100644 --- a/third_party/npapi/bindings/npapi_extensions.h +++ b/third_party/npapi/bindings/npapi_extensions.h @@ -272,11 +272,26 @@ typedef struct _NPDeviceContext3DConfig { } NPDeviceContext3DConfig; typedef enum _NPDeviceContext3DError { + // No error has ocurred. NPDeviceContext3DError_NoError, + + // The size of a command was invalid. NPDeviceContext3DError_InvalidSize, + + // An offset was out of bounds. NPDeviceContext3DError_OutOfBounds, + + // A command was not recognized. NPDeviceContext3DError_UnknownCommand, + + // The arguments to a command were invalid. NPDeviceContext3DError_InvalidArguments, + + // The 3D context was lost, for example due to a power management event. The + // context must be destroyed and a new one created. + NPDeviceContext3DError_LostContext, + + // Any other error. NPDeviceContext3DError_GenericError } NPDeviceContext3DError; diff --git a/webkit/tools/pepper_test_plugin/plugin_object.cc b/webkit/tools/pepper_test_plugin/plugin_object.cc index 013702b..6880099 100644 --- a/webkit/tools/pepper_test_plugin/plugin_object.cc +++ b/webkit/tools/pepper_test_plugin/plugin_object.cc @@ -309,6 +309,11 @@ PluginObject::PluginObject(NPP npp) } PluginObject::~PluginObject() { +#if !defined(INDEPENDENT_PLUGIN) + if (pgl_context_) + Destroy3D(); +#endif + // TODO(kbr): add audio portion of test #if !defined(OS_MACOSX) deviceaudio_->destroyContext(npp_, &context_audio_); @@ -359,10 +364,10 @@ void PluginObject::New(NPMIMEType pluginType, } void PluginObject::SetWindow(const NPWindow& window) { - if (dimensions_ == 2) { - width_ = window.width; - height_ = window.height; + width_ = window.width; + height_ = window.height; + if (dimensions_ == 2) { NPDeviceContext2DConfig config; NPDeviceContext2D context; device2d_->initializeContext(npp_, &config, &context); @@ -376,20 +381,8 @@ void PluginObject::SetWindow(const NPWindow& window) { device2d_->flushContext(npp_, &context, callback, NULL); } else { #if !defined(INDEPENDENT_PLUGIN) - if (!pgl_context_) { - // Initialize a 3D context. - NPDeviceContext3DConfig config; - config.commandBufferSize = kCommandBufferSize; - device3d_->initializeContext(npp_, &config, &context3d_); - - // Create a PGL context. - pgl_context_ = pglCreateContext(npp_, device3d_, &context3d_); - } - - // Reset the viewport to new window size. - pglMakeCurrent(pgl_context_); - glViewport(0, 0, window.width, window.height); - pglMakeCurrent(NULL); + if (!pgl_context_) + Initialize3D(); // Schedule the first call to Draw. browser->pluginthreadasynccall(npp_, Draw3DCallback, this); @@ -413,15 +406,52 @@ void PluginObject::SetWindow(const NPWindow& window) { #endif } -void PluginObject::Draw3D() { +void PluginObject::Initialize3D() { #if !defined(INDEPENDENT_PLUGIN) - // Render some stuff. + DCHECK(!pgl_context_); + + // Initialize a 3D context. + NPDeviceContext3DConfig config; + config.commandBufferSize = kCommandBufferSize; + device3d_->initializeContext(npp_, &config, &context3d_); + + // Create a PGL context. + pgl_context_ = pglCreateContext(npp_, device3d_, &context3d_); + + // Initialize the demo GL state. pglMakeCurrent(pgl_context_); - GLFromCPPTestFunction(); + GLFromCPPInit(); + pglMakeCurrent(NULL); +#endif // INDEPENDENT_PLUGIN +} + +void PluginObject::Destroy3D() { +#if !defined(INDEPENDENT_PLUGIN) + DCHECK(pgl_context_); + + // Destroy the PGL context. + pglDestroyContext(pgl_context_); + pgl_context_ = NULL; + + // Destroy the Device3D context. + device3d_->destroyContext(npp_, &context3d_); +#endif // INDEPENDENT_PLUGIN +} + +void PluginObject::Draw3D() { +#if !defined(INDEPENDENT_PLUGIN) + if (!pglMakeCurrent(pgl_context_) && pglGetError() == PGL_CONTEXT_LOST) { + Destroy3D(); + Initialize3D(); + pglMakeCurrent(pgl_context_); + } + + glViewport(0, 0, width_, height_); + GLFromCPPDraw(); pglSwapBuffers(); pglMakeCurrent(NULL); // Schedule another call to Draw. browser->pluginthreadasynccall(npp_, Draw3DCallback, this); -#endif +#endif // INDEPENDENT_PLUGIN } diff --git a/webkit/tools/pepper_test_plugin/plugin_object.h b/webkit/tools/pepper_test_plugin/plugin_object.h index 1d9970d..73a3277 100644 --- a/webkit/tools/pepper_test_plugin/plugin_object.h +++ b/webkit/tools/pepper_test_plugin/plugin_object.h @@ -47,6 +47,8 @@ class PluginObject { void New(NPMIMEType pluginType, int16 argc, char* argn[], char* argv[]); void SetWindow(const NPWindow& window); + void Initialize3D(); + void Destroy3D(); void Draw3D(); private: |