| Index: chrome/browser/renderer_host/accelerated_surface_container_mac.cc
|
| ===================================================================
|
| --- chrome/browser/renderer_host/accelerated_surface_container_mac.cc (revision 75488)
|
| +++ chrome/browser/renderer_host/accelerated_surface_container_mac.cc (working copy)
|
| @@ -1,233 +0,0 @@
|
| -// Copyright (c) 2010 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 "chrome/browser/renderer_host/accelerated_surface_container_mac.h"
|
| -
|
| -#include "app/surface/io_surface_support_mac.h"
|
| -#include "base/logging.h"
|
| -#include "chrome/browser/renderer_host/accelerated_surface_container_manager_mac.h"
|
| -#include "webkit/plugins/npapi/webplugin.h"
|
| -
|
| -AcceleratedSurfaceContainerMac::AcceleratedSurfaceContainerMac(
|
| - AcceleratedSurfaceContainerManagerMac* manager,
|
| - bool opaque)
|
| - : manager_(manager),
|
| - opaque_(opaque),
|
| - surface_id_(0),
|
| - width_(0),
|
| - height_(0),
|
| - texture_(0),
|
| - texture_needs_upload_(true),
|
| - texture_pending_deletion_(0),
|
| - visible_(false),
|
| - was_painted_to_(false) {
|
| -}
|
| -
|
| -AcceleratedSurfaceContainerMac::~AcceleratedSurfaceContainerMac() {
|
| -}
|
| -
|
| -void AcceleratedSurfaceContainerMac::SetSizeAndIOSurface(
|
| - int32 width,
|
| - int32 height,
|
| - uint64 io_surface_identifier) {
|
| - // Ignore |io_surface_identifier|: The surface hasn't been painted to and
|
| - // only contains garbage data. Update the surface in |set_was_painted_to()|
|
| - // instead.
|
| - width_ = width;
|
| - height_ = height;
|
| -}
|
| -
|
| -void AcceleratedSurfaceContainerMac::SetSizeAndTransportDIB(
|
| - int32 width,
|
| - int32 height,
|
| - TransportDIB::Handle transport_dib) {
|
| - if (TransportDIB::is_valid(transport_dib)) {
|
| - transport_dib_.reset(TransportDIB::Map(transport_dib));
|
| - EnqueueTextureForDeletion();
|
| - width_ = width;
|
| - height_ = height;
|
| - }
|
| -}
|
| -
|
| -void AcceleratedSurfaceContainerMac::SetGeometry(
|
| - const webkit::npapi::WebPluginGeometry& geom) {
|
| - visible_ = geom.visible;
|
| - if (geom.rects_valid)
|
| - clip_rect_ = geom.clip_rect;
|
| -}
|
| -
|
| -void AcceleratedSurfaceContainerMac::Draw(CGLContextObj context) {
|
| - IOSurfaceSupport* io_surface_support = IOSurfaceSupport::Initialize();
|
| - GLenum target = GL_TEXTURE_RECTANGLE_ARB;
|
| - if (texture_pending_deletion_) {
|
| - // Clean up an old texture object. This is essentially a pre-emptive
|
| - // cleanup, as the resources will be released when the OpenGL context
|
| - // associated with our containing NSView is destroyed. However, if we
|
| - // resize a plugin often, we might generate a lot of textures, so we
|
| - // should try to eagerly reclaim their resources. Note also that the
|
| - // OpenGL context must be current when performing the deletion, and it
|
| - // seems risky to make the OpenGL context current at an arbitrary point
|
| - // in time, which is why the deletion does not occur in the container's
|
| - // destructor.
|
| - glDeleteTextures(1, &texture_pending_deletion_);
|
| - texture_pending_deletion_ = 0;
|
| - }
|
| - if (!texture_) {
|
| - if ((io_surface_support && !surface_.get()) ||
|
| - (!io_surface_support && !transport_dib_.get()))
|
| - return;
|
| - glGenTextures(1, &texture_);
|
| - glBindTexture(target, texture_);
|
| - glTexParameterf(target, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
| - glTexParameterf(target, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
| - if (io_surface_support) {
|
| - texture_needs_upload_ = true;
|
| - } else {
|
| - // Reserve space on the card for the actual texture upload, done with the
|
| - // glTexSubImage2D() call, below.
|
| - glTexImage2D(target,
|
| - 0, // mipmap level 0
|
| - GL_RGBA, // internal format
|
| - width_,
|
| - height_,
|
| - 0, // no border
|
| - GL_BGRA, // The GPU plugin read BGRA pixels
|
| - GL_UNSIGNED_INT_8_8_8_8_REV,
|
| - NULL); // No data, this call just reserves room.
|
| - }
|
| - }
|
| -
|
| - // When using an IOSurface, the texture does not need to be repeatedly
|
| - // uploaded, just when we've been told we have to.
|
| - if (io_surface_support && texture_needs_upload_) {
|
| - DCHECK(surface_.get());
|
| - glBindTexture(target, texture_);
|
| - // Don't think we need to identify a plane.
|
| - GLuint plane = 0;
|
| - io_surface_support->CGLTexImageIOSurface2D(context,
|
| - target,
|
| - GL_RGBA,
|
| - surface_width_,
|
| - surface_height_,
|
| - GL_BGRA,
|
| - GL_UNSIGNED_INT_8_8_8_8_REV,
|
| - surface_.get(),
|
| - plane);
|
| - texture_needs_upload_ = false;
|
| - }
|
| - // If using TransportDIBs, the texture needs to be uploaded every frame.
|
| - if (transport_dib_.get() != NULL) {
|
| - void* pixel_memory = transport_dib_->memory();
|
| - if (pixel_memory) {
|
| - glBindTexture(target, texture_);
|
| - glPixelStorei(GL_UNPACK_ALIGNMENT, 1); // Needed for NPOT textures.
|
| - glTexSubImage2D(target,
|
| - 0, // mipmap level 0
|
| - 0, // x-offset
|
| - 0, // y-offset
|
| - width_,
|
| - height_,
|
| - GL_BGRA, // The GPU plugin gave us BGRA pixels
|
| - GL_UNSIGNED_INT_8_8_8_8_REV,
|
| - pixel_memory);
|
| - }
|
| - }
|
| -
|
| - if (texture_) {
|
| - int texture_width = io_surface_support ? surface_width_ : width_;
|
| - int texture_height = io_surface_support ? surface_height_ : height_;
|
| -
|
| - // TODO(kbr): convert this to use only OpenGL ES 2.0 functionality.
|
| -
|
| - // TODO(kbr): may need to pay attention to cutout rects.
|
| - int clipX = clip_rect_.x();
|
| - int clipY = clip_rect_.y();
|
| - int clipWidth = clip_rect_.width();
|
| - int clipHeight = clip_rect_.height();
|
| -
|
| - if (clipX + clipWidth > texture_width)
|
| - clipWidth = texture_width - clipX;
|
| - if (clipY + clipHeight > texture_height)
|
| - clipHeight = texture_height - clipY;
|
| -
|
| - if (opaque_) {
|
| - // Pepper 3D's output is currently considered opaque even if the
|
| - // program draws pixels with alpha less than 1. In order to have
|
| - // this effect, we need to drop the alpha channel of the input,
|
| - // replacing it with alpha = 1.
|
| -
|
| - // First fill the rectangle with alpha=1.
|
| - glColorMask(false, false, false, true);
|
| - glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
| - glBegin(GL_TRIANGLE_STRIP);
|
| - glVertex3f(0, 0, 0);
|
| - glVertex3f(clipWidth, 0, 0);
|
| - glVertex3f(0, clipHeight, 0);
|
| - glVertex3f(clipWidth, clipHeight, 0);
|
| - glEnd();
|
| -
|
| - // Now draw the color channels from the incoming texture.
|
| - glColorMask(true, true, true, false);
|
| - // This call shouldn't be necessary -- we are using the GL_REPLACE
|
| - // texture environment mode -- but it appears to be.
|
| - glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
|
| - } else {
|
| - glColorMask(true, true, true, true);
|
| - }
|
| -
|
| - // Draw the color channels from the incoming texture.
|
| - glBindTexture(target, texture_);
|
| - glEnable(target);
|
| - glBegin(GL_TRIANGLE_STRIP);
|
| -
|
| - glTexCoord2f(clipX, texture_height - clipY);
|
| - glVertex3f(0, 0, 0);
|
| -
|
| - glTexCoord2f(clipX + clipWidth, texture_height - clipY);
|
| - glVertex3f(clipWidth, 0, 0);
|
| -
|
| - glTexCoord2f(clipX, texture_height - clipY - clipHeight);
|
| - glVertex3f(0, clipHeight, 0);
|
| -
|
| - glTexCoord2f(clipX + clipWidth, texture_height - clipY - clipHeight);
|
| - glVertex3f(clipWidth, clipHeight, 0);
|
| -
|
| - glEnd();
|
| - glDisable(target);
|
| - }
|
| -}
|
| -
|
| -bool AcceleratedSurfaceContainerMac::ShouldBeVisible() const {
|
| - return visible_ && was_painted_to_ && !clip_rect_.IsEmpty();
|
| -}
|
| -
|
| -void AcceleratedSurfaceContainerMac::set_was_painted_to(uint64 surface_id) {
|
| - if (surface_id && (!surface_ || surface_id != surface_id_)) {
|
| - // Keep the surface that was most recently painted to around.
|
| - if (IOSurfaceSupport* io_surface_support = IOSurfaceSupport::Initialize()) {
|
| - CFTypeRef surface = io_surface_support->IOSurfaceLookup(
|
| - static_cast<uint32>(surface_id));
|
| - // Can fail if IOSurface with that ID was already released by the
|
| - // gpu process or the plugin process. We will get a |set_was_painted_to()|
|
| - // message with a new surface soon in that case.
|
| - if (surface) {
|
| - surface_.reset(surface);
|
| - surface_id_ = surface_id;
|
| - surface_width_ = io_surface_support->IOSurfaceGetWidth(surface_);
|
| - surface_height_ = io_surface_support->IOSurfaceGetHeight(surface_);
|
| - EnqueueTextureForDeletion();
|
| - }
|
| - }
|
| - }
|
| - was_painted_to_ = true;
|
| -}
|
| -
|
| -void AcceleratedSurfaceContainerMac::EnqueueTextureForDeletion() {
|
| - if (texture_) {
|
| - DCHECK(texture_pending_deletion_ == 0);
|
| - texture_pending_deletion_ = texture_;
|
| - texture_ = 0;
|
| - }
|
| -}
|
| -
|
|
|