Cleanup: misc spelling fixes
[blender.git] / source / blender / draw / intern / draw_manager.h
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  *
16  * Copyright 2016, Blender Foundation.
17  */
18
19 /** \file
20  * \ingroup draw
21  */
22
23 /* Private functions / structs of the draw manager */
24
25 #ifndef __DRAW_MANAGER_H__
26 #define __DRAW_MANAGER_H__
27
28 #include "DRW_engine.h"
29 #include "DRW_render.h"
30
31 #include "BLI_linklist.h"
32 #include "BLI_threads.h"
33
34 #include "GPU_batch.h"
35 #include "GPU_context.h"
36 #include "GPU_framebuffer.h"
37 #include "GPU_shader.h"
38 #include "GPU_uniformbuffer.h"
39 #include "GPU_viewport.h"
40
41 #include "draw_instance_data.h"
42
43 /* Use draw manager to call GPU_select, see: DRW_draw_select_loop */
44 #define USE_GPU_SELECT
45
46 // #define DRW_DEBUG_CULLING
47 #define DRW_DEBUG_USE_UNIFORM_NAME 0
48 #define DRW_UNIFORM_BUFFER_NAME 64
49
50 /* ------------ Profiling --------------- */
51
52 #define USE_PROFILE
53
54 #ifdef USE_PROFILE
55 #  include "PIL_time.h"
56
57 #  define PROFILE_TIMER_FALLOFF 0.04
58
59 #  define PROFILE_START(time_start) \
60     double time_start = PIL_check_seconds_timer(); \
61     ((void)0)
62
63 #  define PROFILE_END_ACCUM(time_accum, time_start) \
64     { \
65       time_accum += (PIL_check_seconds_timer() - time_start) * 1e3; \
66     } \
67     ((void)0)
68
69 /* exp average */
70 #  define PROFILE_END_UPDATE(time_update, time_start) \
71     { \
72       double _time_delta = (PIL_check_seconds_timer() - time_start) * 1e3; \
73       time_update = (time_update * (1.0 - PROFILE_TIMER_FALLOFF)) + \
74                     (_time_delta * PROFILE_TIMER_FALLOFF); \
75     } \
76     ((void)0)
77
78 #else /* USE_PROFILE */
79
80 #  define PROFILE_START(time_start) ((void)0)
81 #  define PROFILE_END_ACCUM(time_accum, time_start) ((void)0)
82 #  define PROFILE_END_UPDATE(time_update, time_start) ((void)0)
83
84 #endif /* USE_PROFILE */
85
86 /* ------------ Data Structure --------------- */
87 /**
88  * Data structure containing all drawcalls organized by passes and materials.
89  * DRWPass > DRWShadingGroup > DRWCall > DRWCallState
90  *                           > DRWUniform
91  */
92
93 /* Used by DRWCallState.flag */
94 enum {
95   DRW_CALL_NEGSCALE = (1 << 1),
96 };
97
98 /* Used by DRWCallState.matflag */
99 enum {
100   DRW_CALL_MODELINVERSE = (1 << 0),
101   DRW_CALL_MODELVIEWPROJECTION = (1 << 1),
102   DRW_CALL_ORCOTEXFAC = (1 << 2),
103   DRW_CALL_OBJECTINFO = (1 << 3),
104 };
105
106 typedef struct DRWCullingState {
107   uint32_t mask;
108   /* Culling: Using Bounding Sphere for now for faster culling.
109    * Not ideal for planes. Could be extended. */
110   BoundSphere bsphere;
111   /* Grrr only used by EEVEE. */
112   void *user_data;
113 } DRWCullingState;
114
115 typedef struct DRWCallState {
116   DRWCullingState *culling;
117   uchar flag;
118   uchar matflag; /* Which matrices to compute. */
119   short ob_index;
120   /* Matrices */
121   float model[4][4];
122   float modelinverse[4][4];
123   float orcotexfac[2][3];
124   float ob_random;
125 } DRWCallState;
126
127 typedef struct DRWCall {
128   struct DRWCall *next;
129   DRWCallState *state;
130
131   GPUBatch *batch;
132   uint vert_first;
133   uint vert_count;
134   uint inst_count;
135
136 #ifdef USE_GPU_SELECT
137   /* TODO(fclem) remove once we have a dedicated selection engine. */
138   int select_id;
139   GPUVertBuf *inst_selectid;
140 #endif
141 } DRWCall;
142
143 /* Used by DRWUniform.type */
144 typedef enum {
145   DRW_UNIFORM_INT,
146   DRW_UNIFORM_INT_COPY,
147   DRW_UNIFORM_FLOAT,
148   DRW_UNIFORM_FLOAT_COPY,
149   DRW_UNIFORM_TEXTURE,
150   DRW_UNIFORM_TEXTURE_PERSIST,
151   DRW_UNIFORM_TEXTURE_REF,
152   DRW_UNIFORM_BLOCK,
153   DRW_UNIFORM_BLOCK_PERSIST,
154 } DRWUniformType;
155
156 struct DRWUniform {
157   DRWUniform *next; /* single-linked list */
158   union {
159     /* For reference or array/vector types. */
160     const void *pvalue;
161     /* Single values. */
162     float fvalue[2];
163     int ivalue[2];
164   };
165   int name_ofs; /* name offset in name buffer. */
166   int location;
167   char type;      /* DRWUniformType */
168   char length;    /* cannot be more than 16 */
169   char arraysize; /* cannot be more than 16 too */
170 };
171
172 struct DRWShadingGroup {
173   DRWShadingGroup *next;
174
175   GPUShader *shader;    /* Shader to bind */
176   DRWUniform *uniforms; /* Uniforms pointers */
177
178   struct {
179     DRWCall *first, *last; /* Linked list of DRWCall */
180   } calls;
181
182   /** TODO Maybe remove from here */
183   struct GPUVertBuf *tfeedback_target;
184
185   /** State changes for this batch only (or'd with the pass's state) */
186   DRWState state_extra;
187   /** State changes for this batch only (and'd with the pass's state) */
188   DRWState state_extra_disable;
189   /** Stencil mask to use for stencil test / write operations */
190   uint stencil_mask;
191
192   /* Builtin matrices locations */
193   int model;
194   int modelinverse;
195   int modelviewprojection;
196   int orcotexfac;
197   int callid;
198   int objectinfo;
199   uchar matflag; /* Matrices needed, same as DRWCall.flag */
200
201   DRWPass *pass_parent; /* backlink to pass we're in */
202 };
203
204 #define MAX_PASS_NAME 32
205
206 struct DRWPass {
207   /* Linked list */
208   struct {
209     DRWShadingGroup *first;
210     DRWShadingGroup *last;
211   } shgroups;
212
213   DRWState state;
214   char name[MAX_PASS_NAME];
215 };
216
217 /* keep in sync with viewBlock */
218 typedef struct DRWViewUboStorage {
219   /* View matrices */
220   float persmat[4][4];
221   float persinv[4][4];
222   float viewmat[4][4];
223   float viewinv[4][4];
224   float winmat[4][4];
225   float wininv[4][4];
226
227   float clipplanes[6][4];
228   /* Should not be here. Not view dependent (only main view). */
229   float viewcamtexcofac[4];
230 } DRWViewUboStorage;
231
232 #define MAX_CULLED_VIEWS 32
233
234 struct DRWView {
235   /** Parent view if this is a sub view. NULL otherwise. */
236   struct DRWView *parent;
237
238   DRWViewUboStorage storage;
239   /** Number of active clipplanes. */
240   int clip_planes_len;
241   /** Does culling result needs to be updated. */
242   bool is_dirty;
243   /** Culling */
244   uint32_t culling_mask;
245   BoundBox frustum_corners;
246   BoundSphere frustum_bsphere;
247   float frustum_planes[6][4];
248   /** Custom visibility function. */
249   DRWCallVisibilityFn *visibility_fn;
250   void *user_data;
251 };
252
253 /* TODO(fclem): Future awaits */
254 #if 0
255 typedef struct ModelUboStorage {
256   float model[4][4];
257   float modelinverse[4][4];
258 } ModelUboStorage;
259 #endif
260
261 /* ------------- DRAW DEBUG ------------ */
262
263 typedef struct DRWDebugLine {
264   struct DRWDebugLine *next; /* linked list */
265   float pos[2][3];
266   float color[4];
267 } DRWDebugLine;
268
269 typedef struct DRWDebugSphere {
270   struct DRWDebugSphere *next; /* linked list */
271   float mat[4][4];
272   float color[4];
273 } DRWDebugSphere;
274
275 /* ------------- DRAW MANAGER ------------ */
276
277 #define DST_MAX_SLOTS 64  /* Cannot be changed without modifying RST.bound_tex_slots */
278 #define MAX_CLIP_PLANES 6 /* GL_MAX_CLIP_PLANES is at least 6 */
279 #define STENCIL_UNDEFINED 256
280 typedef struct DRWManager {
281   /* TODO clean up this struct a bit */
282   /* Cache generation */
283   ViewportMemoryPool *vmempool;
284   DRWInstanceDataList *idatalist;
285   DRWInstanceData *object_instance_data[MAX_INSTANCE_DATA_SIZE];
286   /* Default Unit model matrix state without culling. */
287   DRWCallState *unit_state;
288   /* State of the object being evaluated if already allocated. */
289   DRWCallState *ob_state;
290   struct DupliObject *dupli_source;
291   struct Object *dupli_parent;
292   struct Object *dupli_origin;
293   struct GHash *dupli_ghash;
294   void **dupli_datas; /* Array of dupli_data (one for each enabled engine) to handle duplis. */
295
296   /* Rendering state */
297   GPUShader *shader;
298   GPUBatch *batch;
299
300   /* Managed by `DRW_state_set`, `DRW_state_reset` */
301   DRWState state;
302   DRWState state_lock;
303   uint stencil_mask;
304
305   /* Per viewport */
306   GPUViewport *viewport;
307   struct GPUFrameBuffer *default_framebuffer;
308   float size[2];
309   float inv_size[2];
310   float screenvecs[2][3];
311   float pixsize;
312
313   struct {
314     uint is_select : 1;
315     uint is_depth : 1;
316     uint is_image_render : 1;
317     uint is_scene_render : 1;
318     uint do_color_management : 1;
319     uint draw_background : 1;
320     uint draw_text : 1;
321   } options;
322
323   /* Current rendering context */
324   DRWContextState draw_ctx;
325
326   /* Convenience pointer to text_store owned by the viewport */
327   struct DRWTextStore **text_store_p;
328
329   ListBase enabled_engines; /* RenderEngineType */
330   void **vedata_array;      /* ViewportEngineData */
331   int enabled_engine_count; /* Length of enabled_engines list. */
332
333   bool buffer_finish_called; /* Avoid bad usage of DRW_render_instance_buffer_finish */
334
335   DRWView *view_default;
336   DRWView *view_active;
337   DRWView *view_previous;
338   uint primary_view_ct;
339   /** TODO(fclem) Remove this. Only here to support
340    * shaders without common_view_lib.glsl */
341   DRWViewUboStorage view_storage_cpy;
342
343 #ifdef USE_GPU_SELECT
344   uint select_id;
345 #endif
346
347   /* ---------- Nothing after this point is cleared after use ----------- */
348
349   /* gl_context serves as the offset for clearing only
350    * the top portion of the struct so DO NOT MOVE IT! */
351   /** Unique ghost context used by the draw manager. */
352   void *gl_context;
353   GPUContext *gpu_context;
354   /** Mutex to lock the drw manager and avoid concurrent context usage. */
355   TicketMutex *gl_context_mutex;
356
357   /** GPU Resource State: Memory storage between drawing. */
358   struct {
359     /* High end GPUs supports up to 32 binds per shader stage.
360      * We only use textures during the vertex and fragment stage,
361      * so 2 * 32 slots is a nice limit. */
362     GPUTexture *bound_texs[DST_MAX_SLOTS];
363     uint64_t bound_tex_slots;
364     uint64_t bound_tex_slots_persist;
365
366     GPUUniformBuffer *bound_ubos[DST_MAX_SLOTS];
367     uint64_t bound_ubo_slots;
368     uint64_t bound_ubo_slots_persist;
369   } RST;
370
371   struct {
372     /* TODO(fclem) optimize: use chunks. */
373     DRWDebugLine *lines;
374     DRWDebugSphere *spheres;
375   } debug;
376
377   struct {
378     char *buffer;
379     uint buffer_len;
380     uint buffer_ofs;
381   } uniform_names;
382 } DRWManager;
383
384 extern DRWManager DST; /* TODO: get rid of this and allow multi-threaded rendering. */
385
386 /* --------------- FUNCTIONS ------------- */
387
388 void drw_texture_set_parameters(GPUTexture *tex, DRWTextureFlag flags);
389
390 void *drw_viewport_engine_data_ensure(void *engine_type);
391
392 void drw_state_set(DRWState state);
393
394 void drw_debug_draw(void);
395 void drw_debug_init(void);
396
397 void drw_batch_cache_validate(Object *ob);
398 void drw_batch_cache_generate_requested(struct Object *ob);
399
400 /* Procedural Drawing */
401 GPUBatch *drw_cache_procedural_points_get(void);
402 GPUBatch *drw_cache_procedural_lines_get(void);
403 GPUBatch *drw_cache_procedural_triangles_get(void);
404
405 #endif /* __DRAW_MANAGER_H__ */