-
Notifications
You must be signed in to change notification settings - Fork 25
Expand file tree
/
Copy pathOffscreen.java
More file actions
122 lines (104 loc) · 3.8 KB
/
Copy pathOffscreen.java
File metadata and controls
122 lines (104 loc) · 3.8 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
package javaforce.gl;
import java.awt.Image;
import javaforce.*;
import javaforce.awt.*;
import static javaforce.gl.GL.*;
/**
* GL Offscreen rendering buffer.
*/
public class Offscreen {
//offscreen data
private int os_fb, os_clr_rb, os_depth_rb;
private int os_width, os_height;
private int[] os_px; //pixels
private int[] os_fpx; //flipped pixels
private JFImage os_img; //basically a BufferedImage
/** Get offscreen buffer in a java.awt.Image */
public Image getOffscreen() {
GL gl = GL.getInstance();
//TODO : the image is trippled here - need to optimize!!!
gl.glReadPixels(0, 0, os_width, os_height, GL_BGRA, GL_UNSIGNED_BYTE, os_px);
//invert and fix alpha (pixel by pixel - slow - OUCH!)
//OpenGL makes black pixels transparent which causes unwanted trailing effects
int src = (os_height - 1) * os_width;
int dst = 0;
for(int y=0;y<os_height;y++) {
for(int x=0;x<os_width;x++) {
os_fpx[dst++] = os_px[src++] | 0xff000000;
}
src -= os_width * 2;
}
os_img.putPixels(os_fpx, 0, 0, os_width, os_height, 0);
return os_img.getImage();
}
/** Get offscreen buffer pixels (leaving alpha channel as is)
* Pixels that are not rendered to are usually transparent.
*/
public int[] getOffscreenPixels() {
GL gl = GL.getInstance();
gl.glReadPixels(0, 0, os_width, os_height, GL_BGRA, GL_UNSIGNED_BYTE, os_px);
//invert and fix alpha (pixel by pixel - slow - OUCH!)
//OpenGL makes black pixels transparent which causes unwanted trailing effects
int src = (os_height - 1) * os_width;
int dst = 0;
for(int y=0;y<os_height;y++) {
System.arraycopy(os_px, src, os_fpx, dst, os_width);
src -= os_width;
dst += os_width;
}
return os_fpx;
}
private void createBuffers(int width, int height) {
GL gl = GL.getInstance();
int[] ids = new int[1];
gl.glGenRenderbuffers(1, ids);
os_clr_rb = ids[0];
if (debug) {
JFLog.log("GLOffscreen:os_clr_rb=" + os_clr_rb);
}
gl.glBindRenderbuffer(GL_RENDERBUFFER, os_clr_rb);
gl.glRenderbufferStorage(GL_RENDERBUFFER, GL_RGBA, width, height);
gl.glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, os_clr_rb);
gl.glGenRenderbuffers(1, ids);
os_depth_rb = ids[0];
if (debug) {
JFLog.log("GLOffscreen:os_depth_rb=" + os_depth_rb);
}
gl.glBindRenderbuffer(GL_RENDERBUFFER, os_depth_rb);
gl.glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT32, width, height);
gl.glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, os_depth_rb);
}
/** Resize offscreen buffer dimensions. */
public void resizeOffscreen(int width, int height) {
GL gl = GL.getInstance();
os_width = width;
os_height = height;
os_px = new int[os_width * os_height];
os_fpx = new int[os_width * os_height];
os_img = new JFImage(os_width, os_height);
gl.glBindFramebuffer(GL_FRAMEBUFFER, os_fb);
int[] ids = {os_clr_rb, os_depth_rb};
gl.glDeleteRenderbuffers(2, ids);
createBuffers(width, height);
}
/** Creates an offscreen buffer to where rendering is directly to. */
public void createOffscreen(int width, int height) {
GL gl = GL.getInstance();
if (os_fb != 0) return; //already done
int[] ids = new int[1];
gl.glGenFramebuffers(1, ids);
os_fb = ids[0];
gl.glBindFramebuffer(GL_FRAMEBUFFER, os_fb);
createBuffers(width, height);
gl.glBindFramebuffer(GL_FRAMEBUFFER, os_fb);
os_width = width;
os_height = height;
os_px = new int[os_width * os_height];
os_fpx = new int[os_width * os_height];
os_img = new JFImage(os_width, os_height);
}
public void setRenderToOffscreen(boolean state) {
GL gl = GL.getInstance();
gl.glBindFramebuffer(GL_FRAMEBUFFER, state ? os_fb : 0);
}
}