diff options
Diffstat (limited to 'libs/hwui/PixelBuffer.h')
-rw-r--r-- | libs/hwui/PixelBuffer.h | 180 |
1 files changed, 180 insertions, 0 deletions
diff --git a/libs/hwui/PixelBuffer.h b/libs/hwui/PixelBuffer.h new file mode 100644 index 0000000..32d5417 --- /dev/null +++ b/libs/hwui/PixelBuffer.h @@ -0,0 +1,180 @@ +/* + * Copyright (C) 2013 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef ANDROID_HWUI_PIXEL_BUFFER_H +#define ANDROID_HWUI_PIXEL_BUFFER_H + +#include <GLES3/gl3.h> + +namespace android { +namespace uirenderer { + +/** + * Represents a pixel buffer. A pixel buffer will be backed either by a + * PBO on OpenGL ES 3.0 and higher or by an array of uint8_t on other + * versions. If the buffer is backed by a PBO it will of type + * GL_PIXEL_UNPACK_BUFFER. + * + * To read from or write into a PixelBuffer you must first map the + * buffer using the map(AccessMode) method. This method returns a + * pointer to the beginning of the buffer. + * + * Before the buffer can be used by the GPU, for instance to upload + * a texture, you must first unmap the buffer. To do so, call the + * unmap() method. + * + * Mapping and unmapping a PixelBuffer can have the side effect of + * changing the currently active GL_PIXEL_UNPACK_BUFFER. It is + * therefore recommended to call Caches::unbindPixelbuffer() after + * using a PixelBuffer to upload to a texture. + */ +class PixelBuffer { +public: + enum BufferType { + kBufferType_Auto, + kBufferType_CPU + }; + + enum AccessMode { + kAccessMode_None = 0, + kAccessMode_Read = GL_MAP_READ_BIT, + kAccessMode_Write = GL_MAP_WRITE_BIT, + kAccessMode_ReadWrite = GL_MAP_READ_BIT | GL_MAP_WRITE_BIT + }; + + /** + * Creates a new PixelBuffer object with the specified format and + * dimensions. The buffer is immediately allocated. + * + * The buffer type specifies how the buffer should be allocated. + * By default this method will automatically choose whether to allocate + * a CPU or GPU buffer. + */ + static PixelBuffer* create(GLenum format, uint32_t width, uint32_t height, + BufferType type = kBufferType_Auto); + + virtual ~PixelBuffer() { + } + + /** + * Returns the format of this render buffer. + */ + GLenum getFormat() const { + return mFormat; + } + + /** + * Maps this before with the specified access mode. This method + * returns a pointer to the region of memory where the buffer was + * mapped. + * + * If the buffer is already mapped when this method is invoked, + * this method will return the previously mapped pointer. The + * access mode can only be changed by calling unmap() first. + * + * The specified access mode cannot be kAccessMode_None. + */ + virtual uint8_t* map(AccessMode mode = kAccessMode_ReadWrite) = 0; + + /** + * Unmaps this buffer, if needed. After the buffer is unmapped, + * the pointer previously returned by map() becomes invalid and + * should not be used. After calling this method, getMappedPointer() + * will always return NULL. + */ + virtual void unmap() = 0; + + /** + * Returns the current access mode for this buffer. If the buffer + * is not mapped, this method returns kAccessMode_None. + */ + AccessMode getAccessMode() const { + return mAccessMode; + } + + /** + * Returns the currently mapped pointer. Returns NULL if the buffer + * is not mapped. + */ + virtual uint8_t* getMappedPointer() const = 0; + + /** + * Upload the specified rectangle of this pixe buffer as a + * GL_TEXTURE_2D texture. Calling this method will trigger + * an unmap() if necessary. + */ + virtual void upload(uint32_t x, uint32_t y, uint32_t width, uint32_t height, int offset) = 0; + + /** + * Returns the width of the render buffer in pixels. + */ + uint32_t getWidth() const { + return mWidth; + } + + /** + * Returns the height of the render buffer in pixels. + */ + uint32_t getHeight() const { + return mHeight; + } + + /** + * Returns the size of this pixel buffer in bytes. + */ + uint32_t getSize() const { + return mWidth * mHeight * formatSize(mFormat); + } + + /** + * Returns the number of bytes per pixel in the specified format. + * + * Supported formats: + * GL_ALPHA + * GL_RGBA + */ + static uint32_t formatSize(GLenum format) { + switch (format) { + case GL_ALPHA: + return 1; + case GL_RGBA: + return 4; + } + return 0; + } + +protected: + /** + * Creates a new render buffer in the specified format and dimensions. + * The format must be GL_ALPHA or GL_RGBA. + */ + PixelBuffer(GLenum format, uint32_t width, uint32_t height): + mFormat(format), mWidth(width), mHeight(height), mAccessMode(kAccessMode_None) { + } + + GLenum mFormat; + + uint32_t mWidth; + uint32_t mHeight; + + AccessMode mAccessMode; + +}; // class PixelBuffer + +}; // namespace uirenderer +}; // namespace android + +#endif // ANDROID_HWUI_PIXEL_BUFFER_H |