summaryrefslogtreecommitdiffstats
path: root/content/browser/renderer_host/compositing_iosurface_context_mac.mm
diff options
context:
space:
mode:
Diffstat (limited to 'content/browser/renderer_host/compositing_iosurface_context_mac.mm')
-rw-r--r--content/browser/renderer_host/compositing_iosurface_context_mac.mm107
1 files changed, 107 insertions, 0 deletions
diff --git a/content/browser/renderer_host/compositing_iosurface_context_mac.mm b/content/browser/renderer_host/compositing_iosurface_context_mac.mm
new file mode 100644
index 0000000..ede46b4
--- /dev/null
+++ b/content/browser/renderer_host/compositing_iosurface_context_mac.mm
@@ -0,0 +1,107 @@
+// Copyright (c) 2013 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.
+
+#include "content/browser/renderer_host/compositing_iosurface_context_mac.h"
+
+#include <OpenGL/gl.h>
+#include <OpenGL/OpenGL.h>
+#include <vector>
+
+#include "base/command_line.h"
+#include "base/logging.h"
+#include "content/browser/renderer_host/compositing_iosurface_shader_programs_mac.h"
+#include "ui/gl/gl_switches.h"
+#include "ui/gl/gpu_switching_manager.h"
+
+namespace content {
+
+scoped_refptr<CompositingIOSurfaceContext>
+ CompositingIOSurfaceContext::Get(
+ CompositingIOSurfaceMac::SurfaceOrder surface_order) {
+ std::vector<NSOpenGLPixelFormatAttribute> attributes;
+ attributes.push_back(NSOpenGLPFADoubleBuffer);
+ // We don't need a depth buffer - try setting its size to 0...
+ attributes.push_back(NSOpenGLPFADepthSize); attributes.push_back(0);
+ if (ui::GpuSwitchingManager::GetInstance()->SupportsDualGpus())
+ attributes.push_back(NSOpenGLPFAAllowOfflineRenderers);
+ attributes.push_back(0);
+
+ scoped_nsobject<NSOpenGLPixelFormat> glPixelFormat(
+ [[NSOpenGLPixelFormat alloc] initWithAttributes:&attributes.front()]);
+ if (!glPixelFormat) {
+ LOG(ERROR) << "NSOpenGLPixelFormat initWithAttributes failed";
+ return NULL;
+ }
+
+ scoped_nsobject<NSOpenGLContext> nsgl_context(
+ [[NSOpenGLContext alloc] initWithFormat:glPixelFormat
+ shareContext:nil]);
+ if (!nsgl_context) {
+ LOG(ERROR) << "NSOpenGLContext initWithFormat failed";
+ return NULL;
+ }
+
+ // If requested, ask the WindowServer to render the OpenGL surface underneath
+ // the window. This, combined with a hole punched in the window, will allow
+ // for views to "overlap" the GL surface from the user's point of view.
+ if (surface_order == CompositingIOSurfaceMac::SURFACE_ORDER_BELOW_WINDOW) {
+ GLint gl_surface_order = -1;
+ [nsgl_context setValues:&gl_surface_order
+ forParameter:NSOpenGLCPSurfaceOrder];
+ }
+
+ CGLContextObj cgl_context = (CGLContextObj)[nsgl_context CGLContextObj];
+ if (!cgl_context) {
+ LOG(ERROR) << "CGLContextObj failed";
+ return NULL;
+ }
+
+ // Draw at beam vsync.
+ bool is_vsync_disabled =
+ CommandLine::ForCurrentProcess()->HasSwitch(switches::kDisableGpuVsync);
+ GLint swapInterval = is_vsync_disabled ? 0 : 1;
+ [nsgl_context setValues:&swapInterval forParameter:NSOpenGLCPSwapInterval];
+
+ // Prepare the shader program cache. Precompile only the shader programs
+ // needed to draw the IO Surface.
+ CGLSetCurrentContext(cgl_context);
+ scoped_ptr<CompositingIOSurfaceShaderPrograms> shader_program_cache(
+ new CompositingIOSurfaceShaderPrograms());
+ const bool prepared = (
+ shader_program_cache->UseBlitProgram() &&
+ shader_program_cache->UseSolidWhiteProgram());
+ glUseProgram(0u);
+ CGLSetCurrentContext(0);
+ if (!prepared) {
+ LOG(ERROR) << "IOSurface failed to compile/link required shader programs.";
+ return NULL;
+ }
+
+ return new CompositingIOSurfaceContext(
+ surface_order,
+ nsgl_context.release(),
+ cgl_context,
+ is_vsync_disabled,
+ shader_program_cache.Pass());
+}
+
+CompositingIOSurfaceContext::CompositingIOSurfaceContext(
+ CompositingIOSurfaceMac::SurfaceOrder surface_order,
+ NSOpenGLContext* nsgl_context,
+ CGLContextObj cgl_context,
+ bool is_vsync_disabled,
+ scoped_ptr<CompositingIOSurfaceShaderPrograms> shader_program_cache)
+ : surface_order_(surface_order),
+ nsgl_context_(nsgl_context),
+ cgl_context_(cgl_context),
+ shader_program_cache_(shader_program_cache.Pass()) {
+}
+
+CompositingIOSurfaceContext::~CompositingIOSurfaceContext() {
+ CGLSetCurrentContext(cgl_context_);
+ shader_program_cache_->Reset();
+ CGLSetCurrentContext(0);
+}
+
+} // namespace content