summaryrefslogtreecommitdiff
path: root/include/render/fx_renderer/fx_renderer.h
blob: ffd31da9e42d40b54b469cfbdc0a2b99c28ee4b0 (plain)
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
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
#ifndef _FX_OPENGL_H
#define _FX_OPENGL_H

#include <GLES2/gl2.h>
#include <GLES2/gl2ext.h>
#include <stdbool.h>
#include <wlr/render/egl.h>
#include <wlr/render/gles2.h>
#include <wlr/render/wlr_texture.h>
#include <wlr/util/addon.h>
#include <wlr/util/box.h>
#include "render/fx_renderer/fx_stencilbuffer.h"
#include "types/fx/shadow_data.h"

enum fx_tex_shader_source {
	SHADER_SOURCE_TEXTURE_RGBA = 1,
	SHADER_SOURCE_TEXTURE_RGBX = 2,
	SHADER_SOURCE_TEXTURE_EXTERNAL = 3,
};

struct quad_shader {
	GLuint program;
	GLint proj;
	GLint color;
	GLint pos_attrib;
};

struct tex_shader {
	GLuint program;
	GLint proj;
	GLint tex;
	GLint alpha;
	GLint pos_attrib;
	GLint tex_attrib;
	GLint size;
	GLint position;
	GLint radius;
};

struct stencil_mask_shader {
	GLuint program;
	GLint proj;
	GLint color;
	GLint pos_attrib;
	GLint half_size;
	GLint position;
	GLint radius;
};

struct box_shadow_shader {
	GLuint program;
	GLint proj;
	GLint color;
	GLint pos_attrib;
	GLint position;
	GLint size;
	GLint blur_sigma;
	GLint corner_radius;
};

struct fx_framebuffer {
	bool initialized;

	GLuint fbo;
	GLuint rbo;

	struct wlr_buffer *wlr_buffer;
	struct fx_renderer *renderer;
	struct wl_list link; // fx_renderer.buffers
	struct wlr_addon addon;

	EGLImageKHR image;
};

struct fx_texture {
	struct wlr_texture wlr_texture;
	struct fx_renderer *fx_renderer;
	struct wl_list link; // fx_renderer.textures

	// Basically:
	//   GL_TEXTURE_2D == mutable
	//   GL_TEXTURE_EXTERNAL_OES == immutable
	GLuint target;
	GLuint tex;

	EGLImageKHR image;

	bool has_alpha;

	// Only affects target == GL_TEXTURE_2D
	uint32_t drm_format; // used to interpret upload data
	// If imported from a wlr_buffer
	struct wlr_buffer *buffer;
	struct wlr_addon buffer_addon;
};

struct fx_renderer {
	float projection[9];

	int viewport_width, viewport_height;

	struct wlr_output *wlr_output;

	struct wlr_egl *egl;

	struct fx_stencilbuffer stencil_buffer;

	struct wl_list textures; // fx_texture.link
	struct wl_list buffers; // fx_framebuffer.link

	// The FBO and texture used by wlroots
	GLuint wlr_main_buffer_fbo;
	struct wlr_gles2_texture_attribs wlr_main_texture_attribs;

	struct wlr_addon addon;

	struct {
		bool OES_egl_image_external;
		bool OES_egl_image;
	} exts;

	struct {
		PFNGLEGLIMAGETARGETTEXTURE2DOESPROC glEGLImageTargetTexture2DOES;
		PFNGLEGLIMAGETARGETRENDERBUFFERSTORAGEOESPROC glEGLImageTargetRenderbufferStorageOES;
	} procs;

	struct {
		struct quad_shader quad;
		struct tex_shader tex_rgba;
		struct tex_shader tex_rgbx;
		struct tex_shader tex_ext;
		struct box_shadow_shader box_shadow;
		struct stencil_mask_shader stencil_mask;
	} shaders;
};

///
/// fx_framebuffer
///

struct fx_framebuffer fx_framebuffer_create(void);

void fx_framebuffer_bind(struct fx_framebuffer *buffer);

void fx_framebuffer_bind_wlr_fbo(struct fx_renderer *renderer);

void fx_framebuffer_update(struct fx_renderer *fx_renderer, struct fx_framebuffer *fx_buffer,
		int width, int height);

void fx_framebuffer_add_stencil_buffer(struct fx_framebuffer *buffer, int width, int height);

void fx_framebuffer_release(struct fx_framebuffer *buffer);

///
/// fx_texture
///

struct fx_texture *fx_get_texture(struct wlr_texture *wlr_texture);

struct fx_texture *fx_texture_from_buffer(struct fx_renderer *fx_renderer,
	struct wlr_buffer *buffer);

void fx_texture_destroy(struct fx_texture *texture);

bool wlr_texture_is_fx(struct wlr_texture *wlr_texture);

void wlr_gles2_texture_get_fx_attribs(struct fx_texture *texture,
		struct wlr_gles2_texture_attribs *attribs);

///
/// fx_renderer
///

void fx_renderer_init_addon(struct wlr_egl *egl, struct wlr_output *output,
		struct wlr_addon_set *addons, const void * owner);

struct fx_renderer *fx_renderer_addon_find(struct wlr_addon_set *addons,
		const void * owner);

struct fx_renderer *fx_renderer_create(struct wlr_egl *egl, struct wlr_output *output);

void fx_renderer_begin(struct fx_renderer *renderer, int width, int height);

void fx_renderer_end(struct fx_renderer *renderer);

void fx_renderer_clear(const float color[static 4]);

void fx_renderer_scissor(struct wlr_box *box);

// Initialize the stenciling work
void fx_renderer_stencil_mask_init(void);

// Close the mask
void fx_renderer_stencil_mask_close(bool draw_inside_mask);

// Finish stenciling and clear the buffer
void fx_renderer_stencil_mask_fini(void);

void fx_renderer_stencil_enable(void);

void fx_renderer_stencil_disable(void);

bool fx_render_subtexture_with_matrix(struct fx_renderer *renderer,
		struct wlr_texture *wlr_texture, const struct wlr_fbox *src_box,
		const struct wlr_box *dst_box, const float matrix[static 9],
		float opacity, int corner_radius);

void fx_render_rect(struct fx_renderer *renderer, const struct wlr_box *box,
		const float color[static 4], const float projection[static 9]);

void fx_render_box_shadow(struct fx_renderer *renderer,
		const struct wlr_box *box, const struct wlr_box *stencil_box,
		const float matrix[static 9], int corner_radius,
		struct shadow_data *shadow_data);

#endif