blob: b3a8f74b26e670e15a6e394a4b5a3132b0da5545 [file] [log] [blame]
// Copyright (c) 2012 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// This API is consistent with other OpenGL setup APIs like window's WGL
// and pepper's PGL. This API is used to manage OpenGL RendererGLContexts in the
// Chrome renderer process in a way that is consistent with other platforms.
#ifndef CONTENT_RENDERER_GPU_RENDERER_GL_CONTEXT_H_
#define CONTENT_RENDERER_GPU_RENDERER_GL_CONTEXT_H_
#pragma once
#include "base/callback.h"
#include "base/memory/ref_counted.h"
#include "base/memory/scoped_ptr.h"
#include "base/memory/weak_ptr.h"
#include "base/threading/non_thread_safe.h"
#include "build/build_config.h"
#include "ui/gfx/gl/gpu_preference.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/size.h"
class GpuChannelHost;
class CommandBufferProxy;
class GURL;
namespace gpu {
namespace gles2 {
class GLES2CmdHelper;
class GLES2Implementation;
}
}
class RendererGLContext : public base::SupportsWeakPtr<RendererGLContext>,
public base::NonThreadSafe {
public:
// These are the same error codes as used by EGL.
enum Error {
SUCCESS = 0x3000,
NOT_INITIALIZED = 0x3001,
BAD_ATTRIBUTE = 0x3004,
BAD_RendererGLContext = 0x3006,
CONTEXT_LOST = 0x300E
};
// RendererGLContext configuration attributes. Those in the 16-bit range are
// the same as used by EGL. Those outside the 16-bit range are unique to
// Chromium. Attributes are matched using a closest fit algorithm.
enum Attribute {
ALPHA_SIZE = 0x3021,
BLUE_SIZE = 0x3022,
GREEN_SIZE = 0x3023,
RED_SIZE = 0x3024,
DEPTH_SIZE = 0x3025,
STENCIL_SIZE = 0x3026,
SAMPLES = 0x3031,
SAMPLE_BUFFERS = 0x3032,
HEIGHT = 0x3056,
WIDTH = 0x3057,
NONE = 0x3038, // Attrib list = terminator
SHARE_RESOURCES = 0x10000,
BIND_GENERATES_RESOURCES = 0x10001
};
// Reasons that a lost context might have been provoked.
enum ContextLostReason {
// This context definitely provoked the loss of context.
kGuilty,
// This context definitely did not provoke the loss of context.
kInnocent,
// It is unknown whether this context provoked the loss of context.
kUnknown
};
// Initialize the library. This must have completed before any other
// functions are invoked.
static bool Initialize();
// Terminate the library. This must be called after any other functions
// have completed.
static bool Terminate();
~RendererGLContext();
// Create a RendererGLContext that renders directly to a view. The view and
// the associated window must not be destroyed until the returned
// RendererGLContext has been destroyed, otherwise the GPU process might
// attempt to render to an invalid window handle.
//
// NOTE: on Mac OS X, this entry point is only used to set up the
// accelerated compositor's output. On this platform, we actually pass
// a gfx::PluginWindowHandle in place of the gfx::NativeViewId,
// because the facility to allocate a fake PluginWindowHandle is
// already in place. We could add more entry points and messages to
// allocate both fake PluginWindowHandles and NativeViewIds and map
// from fake NativeViewIds to PluginWindowHandles, but this seems like
// unnecessary complexity at the moment.
//
// The render_view_id is currently also only used on Mac OS X.
// TODO(kbr): clean up the arguments to this function and make them
// more cross-platform.
static RendererGLContext* CreateViewContext(
GpuChannelHost* channel,
int32 surface_id,
RendererGLContext* share_group,
const char* allowed_extensions,
const int32* attrib_list,
const GURL& active_url,
gfx::GpuPreference gpu_preference);
// Create a RendererGLContext that renders to an offscreen frame buffer. If
// parent is not NULL, that RendererGLContext can access a copy of the created
// RendererGLContext's frame buffer that is updated every time SwapBuffers is
// called. It is not as general as shared RendererGLContexts in other
// implementations of OpenGL. If parent is not NULL, it must be used on the
// same thread as the parent. A child RendererGLContext may not outlive its
// parent. attrib_list must be NULL or a NONE-terminated list of
// attribute/value pairs.
static RendererGLContext* CreateOffscreenContext(
GpuChannelHost* channel,
const gfx::Size& size,
RendererGLContext* share_group,
const char* allowed_extensions,
const int32* attrib_list,
const GURL& active_url,
gfx::GpuPreference gpu_preference);
// Sets the parent context. If any parent textures have been created for
// another parent, it is important to delete them before changing the parent.
bool SetParent(RendererGLContext* parent);
// For an offscreen frame buffer RendererGLContext, return the texture ID with
// respect to the parent RendererGLContext. Returns zero if RendererGLContext
// does not have a parent.
uint32 GetParentTextureId();
// Create a new texture in the parent's RendererGLContext. Returns zero if
// RendererGLContext does not have a parent.
uint32 CreateParentTexture(const gfx::Size& size);
// Deletes a texture in the parent's RendererGLContext.
void DeleteParentTexture(uint32 texture);
void SetContextLostCallback(
const base::Callback<void(ContextLostReason)>& callback);
// Set the current RendererGLContext for the calling thread.
static bool MakeCurrent(RendererGLContext* context);
// For a view RendererGLContext, display everything that has been rendered
// since the last call. For an offscreen RendererGLContext, resolve everything
// that has been rendered since the last call to a copy that can be accessed
// by the parent RendererGLContext.
bool SwapBuffers();
// Run the task once the channel has been flushed. Takes care of deleting the
// task whether the echo succeeds or not.
bool Echo(const base::Closure& task);
// Sends an IPC message with the new state of surface visibility
bool SetSurfaceVisible(bool visibility);
// TODO(gman): Remove this
void DisableShaderTranslation();
// Allows direct access to the GLES2 implementation so a RendererGLContext
// can be used without making it current.
gpu::gles2::GLES2Implementation* GetImplementation();
// Return the current error.
Error GetError();
// Return true if GPU process reported RendererGLContext lost or there was a
// problem communicating with the GPU process.
bool IsCommandBufferContextLost();
CommandBufferProxy* GetCommandBufferProxy();
private:
explicit RendererGLContext(GpuChannelHost* channel);
bool Initialize(bool onscreen,
int32 surface_id,
const gfx::Size& size,
RendererGLContext* share_group,
const char* allowed_extensions,
const int32* attrib_list,
const GURL& active_url,
gfx::GpuPreference gpu_preference);
void Destroy();
void OnContextLost();
scoped_refptr<GpuChannelHost> channel_;
base::WeakPtr<RendererGLContext> parent_;
base::Callback<void(ContextLostReason)> context_lost_callback_;
uint32 parent_texture_id_;
CommandBufferProxy* command_buffer_;
gpu::gles2::GLES2CmdHelper* gles2_helper_;
int32 transfer_buffer_id_;
gpu::gles2::GLES2Implementation* gles2_implementation_;
Error last_error_;
int frame_number_;
DISALLOW_COPY_AND_ASSIGN(RendererGLContext);
};
#endif // CONTENT_RENDERER_GPU_RENDERER_GL_CONTEXT_H_