vrseasons

view src/rtarg.cc @ 0:393ef1143c9c

VR seasons
author John Tsiombikas <nuclear@member.fsf.org>
date Tue, 07 Apr 2015 11:16:56 +0300
parents
children eea1b91dc3d4
line source
1 #include "opengl.h"
2 #include "rtarg.h"
4 static int next_pow2(int x);
6 RenderTarget::RenderTarget()
7 {
8 xsz = ysz = 0;
9 fbo = color = depth = 0;
11 tex_fmt = 0;
12 tex_xsz = tex_ysz = 0;
13 }
15 RenderTarget::~RenderTarget()
16 {
17 destroy();
18 }
20 bool RenderTarget::create(int xsz, int ysz)
21 {
22 destroy();
24 this->xsz = xsz;
25 this->ysz = ysz;
27 tex_xsz = next_pow2(xsz);
28 tex_ysz = next_pow2(ysz);
29 tex_fmt = check_extension("GL_ARB_texture_float") ? GL_RGB16F : GL_RGB;
31 glGenFramebuffers(1, &fbo);
32 glBindFramebuffer(GL_FRAMEBUFFER, fbo);
34 glGenTextures(1, &color);
35 glBindTexture(GL_TEXTURE_2D, color);
36 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
37 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
38 glTexImage2D(GL_TEXTURE_2D, 0, tex_fmt, tex_xsz, tex_ysz, 0, GL_RGB, GL_UNSIGNED_BYTE, 0);
39 glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, color, 0);
41 glGenRenderbuffers(1, &depth);
42 glBindRenderbuffer(GL_RENDERBUFFER, depth);
43 glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, tex_xsz, tex_ysz);
44 glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, depth);
46 return true;
47 }
49 bool RenderTarget::resize(int xsz, int ysz)
50 {
51 if(!fbo) {
52 return create(xsz, ysz);
53 }
55 this->xsz = xsz;
56 this->ysz = ysz;
57 int new_tex_xsz = next_pow2(xsz);
58 int new_tex_ysz = next_pow2(ysz);
60 if(tex_xsz != new_tex_xsz || tex_ysz != new_tex_ysz) {
61 glBindTexture(GL_TEXTURE_2D, color);
62 glTexImage2D(GL_TEXTURE_2D, 0, tex_fmt, tex_xsz, tex_ysz, 0, GL_RGB, GL_UNSIGNED_BYTE, 0);
64 glBindRenderbuffer(GL_RENDERBUFFER, depth);
65 glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, tex_xsz, tex_ysz);
67 tex_xsz = new_tex_xsz;
68 tex_ysz = new_tex_ysz;
69 }
70 return true;
71 }
73 void RenderTarget::destroy()
74 {
75 if(fbo) {
76 glDeleteFramebuffers(1, &fbo);
77 }
78 if(color) {
79 glDeleteTextures(1, &color);
80 }
81 if(depth) {
82 glDeleteRenderbuffers(1, &depth);
83 }
84 fbo = color = depth = 0;
85 }
87 bool RenderTarget::is_valid() const
88 {
89 return fbo != 0;
90 }
92 unsigned int RenderTarget::get_texture() const
93 {
94 return color;
95 }
97 int RenderTarget::get_width() const
98 {
99 return xsz;
100 }
102 int RenderTarget::get_height() const
103 {
104 return ysz;
105 }
107 int RenderTarget::get_tex_width() const
108 {
109 return tex_xsz;
110 }
112 int RenderTarget::get_tex_height() const
113 {
114 return tex_ysz;
115 }
117 void set_render_target(const RenderTarget *rtarg)
118 {
119 if(rtarg) {
120 glBindFramebuffer(GL_FRAMEBUFFER, rtarg->color);
121 } else {
122 glBindFramebuffer(GL_FRAMEBUFFER, 0);
123 }
124 }
126 static int next_pow2(int x)
127 {
128 x--;
129 x = (x >> 1) | x;
130 x = (x >> 2) | x;
131 x = (x >> 4) | x;
132 x = (x >> 8) | x;
133 x = (x >> 16) | x;
134 return x + 1;
135 }