Skip to content

Commit c810ea4

Browse files
committed
Reduce shader permutations in the compatibility backend
1 parent 6c05ec3 commit c810ea4

File tree

4 files changed

+27
-26
lines changed

4 files changed

+27
-26
lines changed

drivers/gles3/rasterizer_canvas_gles3.cpp

+19-13
Original file line numberDiff line numberDiff line change
@@ -687,6 +687,8 @@ void RasterizerCanvasGLES3::_render_items(RID p_to_render_target, int p_item_cou
687687

688688
state.current_tex = RID();
689689

690+
const uint64_t base_specialization = GLES3::Config::get_singleton()->float_texture_supported ? 0 : CanvasShaderGLES3::USE_RGBA_SHADOWS;
691+
690692
for (uint32_t i = 0; i <= state.current_batch_index; i++) {
691693
// Skipping when there is no instances.
692694
if (state.canvas_instance_batches[i].instance_count == 0) {
@@ -705,10 +707,9 @@ void RasterizerCanvasGLES3::_render_items(RID p_to_render_target, int p_item_cou
705707
}
706708

707709
GLES3::CanvasMaterialData *material_data = state.canvas_instance_batches[i].material_data;
708-
CanvasShaderGLES3::ShaderVariant variant = state.canvas_instance_batches[i].shader_variant;
709-
uint64_t specialization = 0;
710-
specialization |= uint64_t(state.canvas_instance_batches[i].lights_disabled);
711-
specialization |= uint64_t(!GLES3::Config::get_singleton()->float_texture_supported) << 1;
710+
CanvasShaderGLES3::ShaderVariant variant = CanvasShaderGLES3::MODE_DEFAULT;
711+
uint64_t specialization = state.canvas_instance_batches[i].specialization;
712+
specialization |= base_specialization;
712713
RID shader_version = data.canvas_shader_default_version;
713714

714715
if (material_data) {
@@ -810,6 +811,7 @@ void RasterizerCanvasGLES3::_render_items(RID p_to_render_target, int p_item_cou
810811

811812
void RasterizerCanvasGLES3::_record_item_commands(const Item *p_item, RID p_render_target, const Transform2D &p_canvas_transform_inverse, Item *&current_clip, GLES3::CanvasShaderData::BlendMode p_blend_mode, Light *p_lights, uint32_t &r_index, bool &r_batch_broken, bool &r_sdf_used, const Point2 &p_repeat_offset) {
812813
RenderingServer::CanvasItemTextureFilter texture_filter = p_item->texture_filter == RS::CANVAS_ITEM_TEXTURE_FILTER_DEFAULT ? state.default_filter : p_item->texture_filter;
814+
const uint64_t specialization_command_mask = ~(CanvasShaderGLES3::USE_NINEPATCH | CanvasShaderGLES3::USE_PRIMITIVE | CanvasShaderGLES3::USE_ATTRIBUTES | CanvasShaderGLES3::USE_INSTANCING);
813815

814816
if (texture_filter != state.canvas_instance_batches[state.current_batch_index].filter) {
815817
_new_batch(r_batch_broken);
@@ -868,9 +870,9 @@ void RasterizerCanvasGLES3::_record_item_commands(const Item *p_item, RID p_rend
868870

869871
bool lights_disabled = light_count == 0 && !state.using_directional_lights;
870872

871-
if (lights_disabled != state.canvas_instance_batches[state.current_batch_index].lights_disabled) {
873+
if (lights_disabled != bool(state.canvas_instance_batches[state.current_batch_index].specialization & CanvasShaderGLES3::DISABLE_LIGHTING)) {
872874
_new_batch(r_batch_broken);
873-
state.canvas_instance_batches[state.current_batch_index].lights_disabled = lights_disabled;
875+
state.canvas_instance_batches[state.current_batch_index].specialization ^= CanvasShaderGLES3::DISABLE_LIGHTING;
874876
}
875877

876878
const Item::Command *c = p_item->commands;
@@ -936,7 +938,7 @@ void RasterizerCanvasGLES3::_record_item_commands(const Item *p_item, RID p_rend
936938
state.canvas_instance_batches[state.current_batch_index].tex = rect->texture;
937939
state.canvas_instance_batches[state.current_batch_index].command_type = Item::Command::TYPE_RECT;
938940
state.canvas_instance_batches[state.current_batch_index].command = c;
939-
state.canvas_instance_batches[state.current_batch_index].shader_variant = CanvasShaderGLES3::MODE_QUAD;
941+
state.canvas_instance_batches[state.current_batch_index].specialization &= specialization_command_mask;
940942
}
941943

942944
_prepare_canvas_texture(rect->texture, state.canvas_instance_batches[state.current_batch_index].filter, state.canvas_instance_batches[state.current_batch_index].repeat, r_index, texpixel_size);
@@ -1026,7 +1028,8 @@ void RasterizerCanvasGLES3::_record_item_commands(const Item *p_item, RID p_rend
10261028
state.canvas_instance_batches[state.current_batch_index].tex = np->texture;
10271029
state.canvas_instance_batches[state.current_batch_index].command_type = Item::Command::TYPE_NINEPATCH;
10281030
state.canvas_instance_batches[state.current_batch_index].command = c;
1029-
state.canvas_instance_batches[state.current_batch_index].shader_variant = CanvasShaderGLES3::MODE_NINEPATCH;
1031+
state.canvas_instance_batches[state.current_batch_index].specialization &= specialization_command_mask;
1032+
state.canvas_instance_batches[state.current_batch_index].specialization |= CanvasShaderGLES3::USE_NINEPATCH;
10301033
}
10311034

10321035
_prepare_canvas_texture(np->texture, state.canvas_instance_batches[state.current_batch_index].filter, state.canvas_instance_batches[state.current_batch_index].repeat, r_index, texpixel_size);
@@ -1092,7 +1095,8 @@ void RasterizerCanvasGLES3::_record_item_commands(const Item *p_item, RID p_rend
10921095
state.canvas_instance_batches[state.current_batch_index].tex = polygon->texture;
10931096
state.canvas_instance_batches[state.current_batch_index].command_type = Item::Command::TYPE_POLYGON;
10941097
state.canvas_instance_batches[state.current_batch_index].command = c;
1095-
state.canvas_instance_batches[state.current_batch_index].shader_variant = CanvasShaderGLES3::MODE_ATTRIBUTES;
1098+
state.canvas_instance_batches[state.current_batch_index].specialization &= specialization_command_mask;
1099+
state.canvas_instance_batches[state.current_batch_index].specialization |= CanvasShaderGLES3::USE_ATTRIBUTES;
10961100

10971101
_prepare_canvas_texture(polygon->texture, state.canvas_instance_batches[state.current_batch_index].filter, state.canvas_instance_batches[state.current_batch_index].repeat, r_index, texpixel_size);
10981102

@@ -1119,7 +1123,8 @@ void RasterizerCanvasGLES3::_record_item_commands(const Item *p_item, RID p_rend
11191123
state.canvas_instance_batches[state.current_batch_index].primitive_points = primitive->point_count;
11201124
state.canvas_instance_batches[state.current_batch_index].command_type = Item::Command::TYPE_PRIMITIVE;
11211125
state.canvas_instance_batches[state.current_batch_index].command = c;
1122-
state.canvas_instance_batches[state.current_batch_index].shader_variant = CanvasShaderGLES3::MODE_PRIMITIVE;
1126+
state.canvas_instance_batches[state.current_batch_index].specialization &= specialization_command_mask;
1127+
state.canvas_instance_batches[state.current_batch_index].specialization |= CanvasShaderGLES3::USE_PRIMITIVE;
11231128
}
11241129

11251130
_prepare_canvas_texture(state.canvas_instance_batches[state.current_batch_index].tex, state.canvas_instance_batches[state.current_batch_index].filter, state.canvas_instance_batches[state.current_batch_index].repeat, r_index, texpixel_size);
@@ -1164,7 +1169,8 @@ void RasterizerCanvasGLES3::_record_item_commands(const Item *p_item, RID p_rend
11641169
_new_batch(r_batch_broken);
11651170

11661171
Color modulate(1, 1, 1, 1);
1167-
state.canvas_instance_batches[state.current_batch_index].shader_variant = CanvasShaderGLES3::MODE_ATTRIBUTES;
1172+
state.canvas_instance_batches[state.current_batch_index].specialization &= specialization_command_mask;
1173+
state.canvas_instance_batches[state.current_batch_index].specialization |= CanvasShaderGLES3::USE_ATTRIBUTES;
11681174
if (c->type == Item::Command::TYPE_MESH) {
11691175
const Item::CommandMesh *m = static_cast<const Item::CommandMesh *>(c);
11701176
state.canvas_instance_batches[state.current_batch_index].tex = m->texture;
@@ -1174,7 +1180,7 @@ void RasterizerCanvasGLES3::_record_item_commands(const Item *p_item, RID p_rend
11741180
} else if (c->type == Item::Command::TYPE_MULTIMESH) {
11751181
const Item::CommandMultiMesh *mm = static_cast<const Item::CommandMultiMesh *>(c);
11761182
state.canvas_instance_batches[state.current_batch_index].tex = mm->texture;
1177-
state.canvas_instance_batches[state.current_batch_index].shader_variant = CanvasShaderGLES3::MODE_INSTANCED;
1183+
state.canvas_instance_batches[state.current_batch_index].specialization |= CanvasShaderGLES3::USE_INSTANCING;
11781184

11791185
if (GLES3::MeshStorage::get_singleton()->multimesh_uses_colors(mm->multimesh)) {
11801186
state.instance_data_array[r_index].flags |= FLAGS_INSTANCING_HAS_COLORS;
@@ -1189,7 +1195,7 @@ void RasterizerCanvasGLES3::_record_item_commands(const Item *p_item, RID p_rend
11891195
const Item::CommandParticles *pt = static_cast<const Item::CommandParticles *>(c);
11901196
RID particles = pt->particles;
11911197
state.canvas_instance_batches[state.current_batch_index].tex = pt->texture;
1192-
state.canvas_instance_batches[state.current_batch_index].shader_variant = CanvasShaderGLES3::MODE_INSTANCED;
1198+
state.canvas_instance_batches[state.current_batch_index].specialization |= CanvasShaderGLES3::USE_INSTANCING;
11931199
state.instance_data_array[r_index].flags |= FLAGS_INSTANCING_HAS_COLORS;
11941200
state.instance_data_array[r_index].flags |= FLAGS_INSTANCING_HAS_CUSTOM_DATA;
11951201

drivers/gles3/rasterizer_canvas_gles3.h

+1-3
Original file line numberDiff line numberDiff line change
@@ -273,14 +273,12 @@ class RasterizerCanvasGLES3 : public RendererCanvasRender {
273273

274274
RID material;
275275
GLES3::CanvasMaterialData *material_data = nullptr;
276-
CanvasShaderGLES3::ShaderVariant shader_variant = CanvasShaderGLES3::MODE_QUAD;
277276
uint64_t vertex_input_mask = RS::ARRAY_FORMAT_VERTEX | RS::ARRAY_FORMAT_COLOR | RS::ARRAY_FORMAT_TEX_UV;
277+
uint64_t specialization = 0;
278278

279279
const Item::Command *command = nullptr;
280280
Item::Command::Type command_type = Item::Command::TYPE_ANIMATION_SLICE; // Can default to any type that doesn't form a batch.
281281
uint32_t primitive_points = 0;
282-
283-
bool lights_disabled = false;
284282
};
285283

286284
// DataBuffer contains our per-frame data. I.e. the resources that are updated each frame.

drivers/gles3/shaders/canvas.glsl

+5-6
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,16 @@
11
/* clang-format off */
22
#[modes]
33

4-
mode_quad =
5-
mode_ninepatch = #define USE_NINEPATCH
6-
mode_primitive = #define USE_PRIMITIVE
7-
mode_attributes = #define USE_ATTRIBUTES
8-
mode_instanced = #define USE_ATTRIBUTES \n#define USE_INSTANCING
4+
mode_default =
95

106
#[specializations]
117

128
DISABLE_LIGHTING = true
139
USE_RGBA_SHADOWS = false
14-
SINGLE_INSTANCE = false
10+
USE_NINEPATCH = false
11+
USE_PRIMITIVE = false
12+
USE_ATTRIBUTES = false
13+
USE_INSTANCING = false
1514

1615
#[vertex]
1716

drivers/gles3/shaders/sky.glsl

+2-4
Original file line numberDiff line numberDiff line change
@@ -2,17 +2,15 @@
22
#[modes]
33

44
mode_background =
5-
mode_half_res = #define USE_HALF_RES_PASS
6-
mode_quarter_res = #define USE_QUARTER_RES_PASS
75
mode_cubemap = #define USE_CUBEMAP_PASS
8-
mode_cubemap_half_res = #define USE_CUBEMAP_PASS \n#define USE_HALF_RES_PASS
9-
mode_cubemap_quarter_res = #define USE_CUBEMAP_PASS \n#define USE_QUARTER_RES_PASS
106

117
#[specializations]
128

139
USE_MULTIVIEW = false
1410
USE_INVERTED_Y = true
1511
APPLY_TONEMAPPING = true
12+
USE_QUARTER_RES_PASS = false
13+
USE_HALF_RES_PASS = false
1614

1715
#[vertex]
1816

0 commit comments

Comments
 (0)