| OLD | NEW |
| (Empty) |
| 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | |
| 2 // Use of this source code is governed by a BSD-style license that can be | |
| 3 // found in the LICENSE file. | |
| 4 | |
| 5 #include "webkit/glue/plugins/mac_accelerated_surface_container.h" | |
| 6 | |
| 7 #include "app/surface/io_surface_support_mac.h" | |
| 8 #include "base/logging.h" | |
| 9 #include "webkit/glue/plugins/mac_accelerated_surface_container_manager.h" | |
| 10 #include "webkit/glue/plugins/webplugin.h" | |
| 11 | |
| 12 MacAcceleratedSurfaceContainer::MacAcceleratedSurfaceContainer() | |
| 13 : x_(0), | |
| 14 y_(0), | |
| 15 surface_(NULL), | |
| 16 width_(0), | |
| 17 height_(0), | |
| 18 texture_(0) { | |
| 19 } | |
| 20 | |
| 21 MacAcceleratedSurfaceContainer::~MacAcceleratedSurfaceContainer() { | |
| 22 ReleaseIOSurface(); | |
| 23 } | |
| 24 | |
| 25 void MacAcceleratedSurfaceContainer::ReleaseIOSurface() { | |
| 26 if (surface_) { | |
| 27 CFRelease(surface_); | |
| 28 surface_ = NULL; | |
| 29 } | |
| 30 } | |
| 31 | |
| 32 void MacAcceleratedSurfaceContainer::SetSizeAndIOSurface( | |
| 33 int32 width, | |
| 34 int32 height, | |
| 35 uint64 io_surface_identifier, | |
| 36 MacAcceleratedSurfaceContainerManager* manager) { | |
| 37 ReleaseIOSurface(); | |
| 38 IOSurfaceSupport* io_surface_support = IOSurfaceSupport::Initialize(); | |
| 39 if (io_surface_support) { | |
| 40 surface_ = io_surface_support->IOSurfaceLookup( | |
| 41 static_cast<uint32>(io_surface_identifier)); | |
| 42 EnqueueTextureForDeletion(manager); | |
| 43 width_ = width; | |
| 44 height_ = height; | |
| 45 } | |
| 46 } | |
| 47 | |
| 48 void MacAcceleratedSurfaceContainer::SetSizeAndTransportDIB( | |
| 49 int32 width, | |
| 50 int32 height, | |
| 51 TransportDIB::Handle transport_dib, | |
| 52 MacAcceleratedSurfaceContainerManager* manager) { | |
| 53 if (TransportDIB::is_valid(transport_dib)) { | |
| 54 transport_dib_.reset(TransportDIB::Map(transport_dib)); | |
| 55 EnqueueTextureForDeletion(manager); | |
| 56 width_ = width; | |
| 57 height_ = height; | |
| 58 } | |
| 59 } | |
| 60 | |
| 61 void MacAcceleratedSurfaceContainer::MoveTo( | |
| 62 const webkit_glue::WebPluginGeometry& geom) { | |
| 63 x_ = geom.window_rect.x(); | |
| 64 y_ = geom.window_rect.y(); | |
| 65 // TODO(kbr): may need to pay attention to cutout rects. | |
| 66 clipRect_ = geom.clip_rect; | |
| 67 } | |
| 68 | |
| 69 void MacAcceleratedSurfaceContainer::Draw(CGLContextObj context) { | |
| 70 IOSurfaceSupport* io_surface_support = IOSurfaceSupport::Initialize(); | |
| 71 GLenum target = GL_TEXTURE_RECTANGLE_ARB; | |
| 72 if (!texture_) { | |
| 73 if ((io_surface_support && !surface_) || | |
| 74 (!io_surface_support && !transport_dib_.get())) | |
| 75 return; | |
| 76 glGenTextures(1, &texture_); | |
| 77 glBindTexture(target, texture_); | |
| 78 glTexParameterf(target, GL_TEXTURE_MIN_FILTER, GL_NEAREST); | |
| 79 glTexParameterf(target, GL_TEXTURE_MAG_FILTER, GL_NEAREST); | |
| 80 // When using an IOSurface, the texture does not need to be repeatedly | |
| 81 // uploaded, so bind the IOSurface once during texture gen in this case. | |
| 82 if (io_surface_support) { | |
| 83 DCHECK(surface_); | |
| 84 // Don't think we need to identify a plane. | |
| 85 GLuint plane = 0; | |
| 86 io_surface_support->CGLTexImageIOSurface2D(context, | |
| 87 target, | |
| 88 GL_RGBA, | |
| 89 width_, | |
| 90 height_, | |
| 91 GL_BGRA, | |
| 92 GL_UNSIGNED_INT_8_8_8_8_REV, | |
| 93 surface_, | |
| 94 plane); | |
| 95 } else { | |
| 96 // Reserve space on the card for the actual texture upload, done with the | |
| 97 // glTexSubImage2D() call, below. | |
| 98 glTexImage2D(target, | |
| 99 0, // mipmap level 0 | |
| 100 GL_RGBA, // internal format | |
| 101 width_, | |
| 102 height_, | |
| 103 0, // no border | |
| 104 GL_BGRA, // The GPU plugin read BGRA pixels | |
| 105 GL_UNSIGNED_INT_8_8_8_8_REV, | |
| 106 NULL); // No data, this call just reserves room. | |
| 107 } | |
| 108 } | |
| 109 | |
| 110 // If using TransportDIBs, the texture needs to be uploaded every frame. | |
| 111 if (transport_dib_.get() != NULL) { | |
| 112 void* pixel_memory = transport_dib_->memory(); | |
| 113 if (pixel_memory) { | |
| 114 glBindTexture(target, texture_); | |
| 115 glPixelStorei(GL_UNPACK_ALIGNMENT, 1); // Needed for NPOT textures. | |
| 116 glTexSubImage2D(target, | |
| 117 0, // mipmap level 0 | |
| 118 0, // x-offset | |
| 119 0, // y-offset | |
| 120 width_, | |
| 121 height_, | |
| 122 GL_BGRA, // The GPU plugin gave us BGRA pixels | |
| 123 GL_UNSIGNED_INT_8_8_8_8_REV, | |
| 124 pixel_memory); | |
| 125 } | |
| 126 } | |
| 127 | |
| 128 if (texture_) { | |
| 129 // TODO(kbr): convert this to use only OpenGL ES 2.0 functionality | |
| 130 glBindTexture(target, texture_); | |
| 131 glEnable(target); | |
| 132 glBegin(GL_TRIANGLE_STRIP); | |
| 133 // TODO(kbr): may need to pay attention to cutout rects. | |
| 134 int clipX = clipRect_.x(); | |
| 135 int clipY = clipRect_.y(); | |
| 136 int clipWidth = clipRect_.width(); | |
| 137 int clipHeight = clipRect_.height(); | |
| 138 int x = x_ + clipX; | |
| 139 int y = y_ + clipY; | |
| 140 glTexCoord2f(clipX, height_ - clipY); | |
| 141 glVertex3f(x, y, 0); | |
| 142 glTexCoord2f(clipX + clipWidth, height_ - clipY); | |
| 143 glVertex3f(x + clipWidth, y, 0); | |
| 144 glTexCoord2f(clipX, height_ - clipY - clipHeight); | |
| 145 glVertex3f(x, y + clipHeight, 0); | |
| 146 glTexCoord2f(clipX + clipWidth, height_ - clipY - clipHeight); | |
| 147 glVertex3f(x + clipWidth, y + clipHeight, 0); | |
| 148 glEnd(); | |
| 149 glDisable(target); | |
| 150 } | |
| 151 } | |
| 152 | |
| 153 void MacAcceleratedSurfaceContainer::EnqueueTextureForDeletion( | |
| 154 MacAcceleratedSurfaceContainerManager* manager) { | |
| 155 manager->EnqueueTextureForDeletion(texture_); | |
| 156 texture_ = 0; | |
| 157 } | |
| 158 | |
| OLD | NEW |