blob: 191a66a6d7414b526925523622b9e8abf8cf76d9 [file] [log] [blame]
Romain Guy3bbacf22013-02-06 16:51:04 -08001/*
2 * Copyright (C) 2013 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#ifndef ANDROID_HWUI_RENDER_BUFFER_H
18#define ANDROID_HWUI_RENDER_BUFFER_H
19
20#include <GLES2/gl2.h>
21#include <GLES2/gl2ext.h>
22
23namespace android {
24namespace uirenderer {
25
26/**
27 * Represents an OpenGL render buffer. Render buffers are attached
28 * to layers to perform stencil work.
29 */
30struct RenderBuffer {
31 /**
32 * Creates a new render buffer in the specified format and dimensions.
33 * The format must be one of the formats allowed by glRenderbufferStorage().
34 */
John Reck1bcacfd2017-11-03 10:12:19 -070035 RenderBuffer(GLenum format, uint32_t width, uint32_t height)
36 : mFormat(format), mWidth(width), mHeight(height), mAllocated(false) {
Romain Guy3bbacf22013-02-06 16:51:04 -080037 glGenRenderbuffers(1, &mName);
38 }
39
40 ~RenderBuffer() {
Romain Guy8d4aeb72013-02-12 16:08:55 -080041 if (mName) {
Romain Guy3bbacf22013-02-06 16:51:04 -080042 glDeleteRenderbuffers(1, &mName);
43 }
44 }
45
46 /**
47 * Returns the GL name of this render buffer.
48 */
John Reck1bcacfd2017-11-03 10:12:19 -070049 GLuint getName() const { return mName; }
Romain Guy3bbacf22013-02-06 16:51:04 -080050
51 /**
52 * Returns the format of this render buffer.
53 */
John Reck1bcacfd2017-11-03 10:12:19 -070054 GLenum getFormat() const { return mFormat; }
Romain Guy3bbacf22013-02-06 16:51:04 -080055
56 /**
57 * Binds this render buffer to the current GL context.
58 */
John Reck1bcacfd2017-11-03 10:12:19 -070059 void bind() const { glBindRenderbuffer(GL_RENDERBUFFER, mName); }
Romain Guy3bbacf22013-02-06 16:51:04 -080060
61 /**
62 * Indicates whether this render buffer has allocated its
63 * storage. See allocate() and resize().
64 */
John Reck1bcacfd2017-11-03 10:12:19 -070065 bool isAllocated() const { return mAllocated; }
Romain Guy3bbacf22013-02-06 16:51:04 -080066
67 /**
68 * Allocates this render buffer's storage if needed.
69 * This method doesn't do anything if isAllocated() returns true.
70 */
71 void allocate() {
72 if (!mAllocated) {
73 glRenderbufferStorage(GL_RENDERBUFFER, mFormat, mWidth, mHeight);
74 mAllocated = true;
75 }
76 }
77
78 /**
79 * Resizes this render buffer. If the buffer was previously allocated,
80 * the storage is re-allocated wit the new specified dimensions. If the
81 * buffer wasn't previously allocated, the buffer remains unallocated.
82 */
83 void resize(uint32_t width, uint32_t height) {
84 if (isAllocated() && (width != mWidth || height != mHeight)) {
85 glRenderbufferStorage(GL_RENDERBUFFER, mFormat, width, height);
86 }
87
88 mWidth = width;
89 mHeight = height;
90 }
91
92 /**
93 * Returns the width of the render buffer in pixels.
94 */
John Reck1bcacfd2017-11-03 10:12:19 -070095 uint32_t getWidth() const { return mWidth; }
Romain Guy3bbacf22013-02-06 16:51:04 -080096
97 /**
98 * Returns the height of the render buffer in pixels.
99 */
John Reck1bcacfd2017-11-03 10:12:19 -0700100 uint32_t getHeight() const { return mHeight; }
Romain Guy3bbacf22013-02-06 16:51:04 -0800101
102 /**
103 * Returns the size of this render buffer in bytes.
104 */
105 uint32_t getSize() const {
106 // Round to the nearest byte
John Reck1bcacfd2017-11-03 10:12:19 -0700107 return (uint32_t)((mWidth * mHeight * formatSize(mFormat)) / 8.0f + 0.5f);
Romain Guy3bbacf22013-02-06 16:51:04 -0800108 }
109
110 /**
111 * Returns the number of bits per component in the specified format.
112 * The format must be one of the formats allowed by glRenderbufferStorage().
113 */
114 static uint32_t formatSize(GLenum format) {
115 switch (format) {
116 case GL_STENCIL_INDEX8:
117 return 8;
118 case GL_STENCIL_INDEX1_OES:
119 return 1;
120 case GL_STENCIL_INDEX4_OES:
121 return 4;
122 case GL_DEPTH_COMPONENT16:
123 case GL_RGBA4:
124 case GL_RGB565:
125 case GL_RGB5_A1:
126 return 16;
127 }
128 return 0;
129 }
130
131 /**
132 * Indicates whether the specified format represents a stencil buffer.
133 */
134 static bool isStencilBuffer(GLenum format) {
135 switch (format) {
136 case GL_STENCIL_INDEX8:
137 case GL_STENCIL_INDEX1_OES:
138 case GL_STENCIL_INDEX4_OES:
139 return true;
140 }
141 return false;
142 }
143
Romain Guy8d4aeb72013-02-12 16:08:55 -0800144 /**
145 * Returns the name of the specified render buffer format.
146 */
147 static const char* formatName(GLenum format) {
148 switch (format) {
149 case GL_STENCIL_INDEX8:
150 return "STENCIL_8";
151 case GL_STENCIL_INDEX1_OES:
152 return "STENCIL_1";
153 case GL_STENCIL_INDEX4_OES:
154 return "STENCIL_4";
155 case GL_DEPTH_COMPONENT16:
156 return "DEPTH_16";
157 case GL_RGBA4:
Romain Guy2b44eb72013-02-13 11:33:26 -0800158 return "RGBA_4444";
Romain Guy8d4aeb72013-02-12 16:08:55 -0800159 case GL_RGB565:
160 return "RGB_565";
161 case GL_RGB5_A1:
162 return "RGBA_5551";
163 }
164 return "Unknown";
165 }
166
Romain Guy3bbacf22013-02-06 16:51:04 -0800167private:
168 GLenum mFormat;
169
170 uint32_t mWidth;
171 uint32_t mHeight;
172
173 bool mAllocated;
174
175 GLuint mName;
John Reck1bcacfd2017-11-03 10:12:19 -0700176}; // struct RenderBuffer
Romain Guy3bbacf22013-02-06 16:51:04 -0800177
John Reck1bcacfd2017-11-03 10:12:19 -0700178}; // namespace uirenderer
179}; // namespace android
Romain Guy3bbacf22013-02-06 16:51:04 -0800180
John Reck1bcacfd2017-11-03 10:12:19 -0700181#endif // ANDROID_HWUI_RENDER_BUFFER_H