Move the mask enable flag to the tile to reduce drawcall count

This commit is contained in:
Patrick Walton 2020-04-22 11:04:16 -07:00
parent a9003fe69b
commit 104869a6e9
12 changed files with 114 additions and 100 deletions

View File

@ -12,8 +12,10 @@
use crate::concurrent::executor::Executor; use crate::concurrent::executor::Executor;
use crate::gpu::renderer::{BlendModeExt, MASK_TILES_ACROSS, MASK_TILES_DOWN}; use crate::gpu::renderer::{BlendModeExt, MASK_TILES_ACROSS, MASK_TILES_DOWN};
use crate::gpu_data::{AlphaTileId, Clip, ClipBatch, ClipBatchKey, ClipBatchKind, Fill, FillBatchEntry, RenderCommand}; use crate::gpu_data::{AlphaTileId, Clip, ClipBatch, ClipBatchKey, ClipBatchKind, Fill};
use crate::gpu_data::{Tile, TileBatch, TileBatchTexture, TileObjectPrimitive}; use crate::gpu_data::{FillBatchEntry, RenderCommand, TILE_CTRL_MASK_0_SHIFT};
use crate::gpu_data::{TILE_CTRL_MASK_EVEN_ODD, TILE_CTRL_MASK_WINDING, Tile, TileBatch};
use crate::gpu_data::{TileBatchTexture, TileObjectPrimitive};
use crate::options::{PreparedBuildOptions, PreparedRenderTransform, RenderCommandListener}; use crate::options::{PreparedBuildOptions, PreparedRenderTransform, RenderCommandListener};
use crate::paint::{PaintInfo, PaintMetadata}; use crate::paint::{PaintInfo, PaintMetadata};
use crate::scene::{DisplayItem, Scene}; use crate::scene::{DisplayItem, Scene};
@ -213,6 +215,7 @@ impl<'a, 'b> SceneBuilder<'a, 'b> {
paint_metadata, paint_metadata,
blend_mode: path_object.blend_mode(), blend_mode: path_object.blend_mode(),
built_clip_path, built_clip_path,
fill_rule: path_object.fill_rule(),
})); }));
tiler.generate_tiles(); tiler.generate_tiles();
@ -309,8 +312,7 @@ impl<'a, 'b> SceneBuilder<'a, 'b> {
current_depth, current_depth,
None, None,
built_draw_path.blend_mode, built_draw_path.blend_mode,
built_draw_path.filter, built_draw_path.filter);
None);
self.add_alpha_tiles(&mut culled_tiles, self.add_alpha_tiles(&mut culled_tiles,
layer_z_buffer, layer_z_buffer,
@ -318,8 +320,7 @@ impl<'a, 'b> SceneBuilder<'a, 'b> {
current_depth, current_depth,
color_texture, color_texture,
built_draw_path.blend_mode, built_draw_path.blend_mode,
built_draw_path.filter, built_draw_path.filter);
Some(built_draw_path.mask_0_fill_rule));
match built_draw_path.path.solid_tiles { match built_draw_path.path.solid_tiles {
SolidTiles::Regular(ref tiles) => { SolidTiles::Regular(ref tiles) => {
@ -329,8 +330,7 @@ impl<'a, 'b> SceneBuilder<'a, 'b> {
current_depth, current_depth,
color_texture, color_texture,
built_draw_path.blend_mode, built_draw_path.blend_mode,
built_draw_path.filter, built_draw_path.filter);
None);
} }
SolidTiles::Occluders(_) => {} SolidTiles::Occluders(_) => {}
} }
@ -393,8 +393,7 @@ impl<'a, 'b> SceneBuilder<'a, 'b> {
current_depth: u32, current_depth: u32,
color_texture: Option<TileBatchTexture>, color_texture: Option<TileBatchTexture>,
blend_mode: BlendMode, blend_mode: BlendMode,
filter: Filter, filter: Filter) {
mask_0_fill_rule: Option<FillRule>) {
let mut batch_indices: Vec<BatchIndex> = vec![]; let mut batch_indices: Vec<BatchIndex> = vec![];
for built_alpha_tile in built_alpha_tiles { for built_alpha_tile in built_alpha_tiles {
// Early cull if possible. // Early cull if possible.
@ -419,12 +418,10 @@ impl<'a, 'b> SceneBuilder<'a, 'b> {
color_texture: ref batch_color_texture, color_texture: ref batch_color_texture,
blend_mode: batch_blend_mode, blend_mode: batch_blend_mode,
filter: batch_filter, filter: batch_filter,
mask_0_fill_rule: batch_mask_0_fill_rule,
tile_page: batch_tile_page tile_page: batch_tile_page
})) if *batch_color_texture == color_texture && })) if *batch_color_texture == color_texture &&
batch_blend_mode == blend_mode && batch_blend_mode == blend_mode &&
batch_filter == filter && batch_filter == filter &&
batch_mask_0_fill_rule == mask_0_fill_rule &&
!batch_blend_mode.needs_readable_framebuffer() && !batch_blend_mode.needs_readable_framebuffer() &&
batch_tile_page == built_alpha_tile.page => { batch_tile_page == built_alpha_tile.page => {
dest_batch_index = Some(BatchIndex { dest_batch_index = Some(BatchIndex {
@ -449,7 +446,6 @@ impl<'a, 'b> SceneBuilder<'a, 'b> {
color_texture, color_texture,
blend_mode, blend_mode,
filter, filter,
mask_0_fill_rule,
tile_page: built_alpha_tile.page, tile_page: built_alpha_tile.page,
})); }));
} }
@ -871,13 +867,20 @@ impl Tile {
draw_tiling_path_info: &DrawTilingPathInfo) draw_tiling_path_info: &DrawTilingPathInfo)
-> Tile { -> Tile {
let mask_0_uv = calculate_mask_uv(draw_tile_index); let mask_0_uv = calculate_mask_uv(draw_tile_index);
let mut ctrl = 0;
match draw_tiling_path_info.fill_rule {
FillRule::EvenOdd => ctrl |= TILE_CTRL_MASK_EVEN_ODD << TILE_CTRL_MASK_0_SHIFT,
FillRule::Winding => ctrl |= TILE_CTRL_MASK_WINDING << TILE_CTRL_MASK_0_SHIFT,
}
Tile { Tile {
tile_x: tile_origin.x() as i16, tile_x: tile_origin.x() as i16,
tile_y: tile_origin.y() as i16, tile_y: tile_origin.y() as i16,
mask_0_u: mask_0_uv.x() as u8, mask_0_u: mask_0_uv.x() as u8,
mask_0_v: mask_0_uv.y() as u8, mask_0_v: mask_0_uv.y() as u8,
mask_0_backdrop: draw_tile_backdrop, mask_0_backdrop: draw_tile_backdrop,
flags: 0, ctrl: ctrl as u16,
pad: 0, pad: 0,
color: draw_tiling_path_info.paint_id.0, color: draw_tiling_path_info.paint_id.0,
} }

View File

@ -25,7 +25,6 @@ use half::f16;
use pathfinder_color::{self as color, ColorF, ColorU}; use pathfinder_color::{self as color, ColorF, ColorU};
use pathfinder_content::effects::{BlendMode, BlurDirection, DefringingKernel}; use pathfinder_content::effects::{BlendMode, BlurDirection, DefringingKernel};
use pathfinder_content::effects::{Filter, PatternFilter}; use pathfinder_content::effects::{Filter, PatternFilter};
use pathfinder_content::fill::FillRule;
use pathfinder_content::render_target::RenderTargetId; use pathfinder_content::render_target::RenderTargetId;
use pathfinder_geometry::line_segment::LineSegment2F; use pathfinder_geometry::line_segment::LineSegment2F;
use pathfinder_geometry::rect::RectI; use pathfinder_geometry::rect::RectI;
@ -65,9 +64,6 @@ const TEXTURE_METADATA_TEXTURE_HEIGHT: i32 = 65536 / TEXTURE_METADATA_ENTRIES_P
const MASK_FRAMEBUFFER_WIDTH: i32 = TILE_WIDTH as i32 * MASK_TILES_ACROSS as i32; const MASK_FRAMEBUFFER_WIDTH: i32 = TILE_WIDTH as i32 * MASK_TILES_ACROSS as i32;
const MASK_FRAMEBUFFER_HEIGHT: i32 = TILE_HEIGHT as i32 * MASK_TILES_DOWN as i32; const MASK_FRAMEBUFFER_HEIGHT: i32 = TILE_HEIGHT as i32 * MASK_TILES_DOWN as i32;
const COMBINER_CTRL_MASK_WINDING: i32 = 0x1;
const COMBINER_CTRL_MASK_EVEN_ODD: i32 = 0x2;
const COMBINER_CTRL_COLOR_COMBINE_SRC_IN: i32 = 0x1; const COMBINER_CTRL_COLOR_COMBINE_SRC_IN: i32 = 0x1;
const COMBINER_CTRL_COLOR_COMBINE_DEST_IN: i32 = 0x2; const COMBINER_CTRL_COLOR_COMBINE_DEST_IN: i32 = 0x2;
@ -92,7 +88,6 @@ const COMBINER_CTRL_COMPOSITE_SATURATION: i32 = 0xd;
const COMBINER_CTRL_COMPOSITE_COLOR: i32 = 0xe; const COMBINER_CTRL_COMPOSITE_COLOR: i32 = 0xe;
const COMBINER_CTRL_COMPOSITE_LUMINOSITY: i32 = 0xf; const COMBINER_CTRL_COMPOSITE_LUMINOSITY: i32 = 0xf;
const COMBINER_CTRL_MASK_0_SHIFT: i32 = 0;
const COMBINER_CTRL_COLOR_FILTER_SHIFT: i32 = 4; const COMBINER_CTRL_COLOR_FILTER_SHIFT: i32 = 4;
const COMBINER_CTRL_COLOR_COMBINE_SHIFT: i32 = 6; const COMBINER_CTRL_COLOR_COMBINE_SHIFT: i32 = 6;
const COMBINER_CTRL_COMPOSITE_SHIFT: i32 = 8; const COMBINER_CTRL_COMPOSITE_SHIFT: i32 = 8;
@ -311,6 +306,7 @@ where
} }
pub fn render_command(&mut self, command: &RenderCommand) { pub fn render_command(&mut self, command: &RenderCommand) {
debug!("render command: {:?}", command);
match *command { match *command {
RenderCommand::Start { bounding_quad, path_count, needs_readable_framebuffer } => { RenderCommand::Start { bounding_quad, path_count, needs_readable_framebuffer } => {
self.start_rendering(bounding_quad, path_count, needs_readable_framebuffer); self.start_rendering(bounding_quad, path_count, needs_readable_framebuffer);
@ -349,7 +345,6 @@ where
self.draw_tiles(batch.tile_page, self.draw_tiles(batch.tile_page,
count as u32, count as u32,
batch.color_texture, batch.color_texture,
batch.mask_0_fill_rule,
batch.blend_mode, batch.blend_mode,
batch.filter) batch.filter)
} }
@ -726,7 +721,6 @@ where
tile_page: u16, tile_page: u16,
tile_count: u32, tile_count: u32,
color_texture_0: Option<TileBatchTexture>, color_texture_0: Option<TileBatchTexture>,
mask_0_fill_rule: Option<FillRule>,
blend_mode: BlendMode, blend_mode: BlendMode,
filter: Filter) { filter: Filter) {
// TODO(pcwalton): Disable blend for solid tiles. // TODO(pcwalton): Disable blend for solid tiles.
@ -739,17 +733,6 @@ where
let clear_color = self.clear_color_for_draw_operation(); let clear_color = self.clear_color_for_draw_operation();
let draw_viewport = self.draw_viewport(); let draw_viewport = self.draw_viewport();
let mut ctrl = 0;
match mask_0_fill_rule {
None => {}
Some(FillRule::Winding) => {
ctrl |= COMBINER_CTRL_MASK_WINDING << COMBINER_CTRL_MASK_0_SHIFT
}
Some(FillRule::EvenOdd) => {
ctrl |= COMBINER_CTRL_MASK_EVEN_ODD << COMBINER_CTRL_MASK_0_SHIFT
}
}
let mut textures = vec![&self.texture_metadata_texture]; let mut textures = vec![&self.texture_metadata_texture];
let mut uniforms = vec![ let mut uniforms = vec![
(&self.tile_program.transform_uniform, (&self.tile_program.transform_uniform,
@ -770,14 +753,14 @@ where
textures.push(self.device.framebuffer_texture(&self.dest_blend_framebuffer)); textures.push(self.device.framebuffer_texture(&self.dest_blend_framebuffer));
} }
if mask_0_fill_rule.is_some() { if let Some(alpha_tile_page) = self.alpha_tile_pages.get(&tile_page) {
uniforms.push((&self.tile_program.mask_texture_0_uniform, uniforms.push((&self.tile_program.mask_texture_0_uniform,
UniformData::TextureUnit(textures.len() as u32))); UniformData::TextureUnit(textures.len() as u32)));
textures.push(self.device.framebuffer_texture( textures.push(self.device.framebuffer_texture(&alpha_tile_page.framebuffer));
&self.alpha_tile_pages[&tile_page].framebuffer));
} }
// TODO(pcwalton): Refactor. // TODO(pcwalton): Refactor.
let mut ctrl = 0;
if let Some(color_texture) = color_texture_0 { if let Some(color_texture) = color_texture_0 {
let color_texture_page = self.texture_page(color_texture.page); let color_texture_page = self.texture_page(color_texture.page);
let color_texture_size = self.device.texture_size(color_texture_page).to_f32(); let color_texture_size = self.device.texture_size(color_texture_page).to_f32();

View File

@ -169,6 +169,7 @@ impl<D> TileVertexArray<D> where D: Device {
let mask_backdrop_attr = let mask_backdrop_attr =
device.get_vertex_attr(&tile_program.program, "MaskBackdrop").unwrap(); device.get_vertex_attr(&tile_program.program, "MaskBackdrop").unwrap();
let color_attr = device.get_vertex_attr(&tile_program.program, "Color").unwrap(); let color_attr = device.get_vertex_attr(&tile_program.program, "Color").unwrap();
let tile_ctrl_attr = device.get_vertex_attr(&tile_program.program, "TileCtrl").unwrap();
device.bind_buffer(&vertex_array, quad_vertex_positions_buffer, BufferTarget::Vertex); device.bind_buffer(&vertex_array, quad_vertex_positions_buffer, BufferTarget::Vertex);
device.configure_vertex_attr(&vertex_array, &tile_offset_attr, &VertexAttrDescriptor { device.configure_vertex_attr(&vertex_array, &tile_offset_attr, &VertexAttrDescriptor {
@ -217,6 +218,15 @@ impl<D> TileVertexArray<D> where D: Device {
divisor: 1, divisor: 1,
buffer_index: 1, buffer_index: 1,
}); });
device.configure_vertex_attr(&vertex_array, &tile_ctrl_attr, &VertexAttrDescriptor {
size: 1,
class: VertexAttrClass::Int,
attr_type: VertexAttrType::I16,
stride: TILE_INSTANCE_SIZE,
offset: 10,
divisor: 1,
buffer_index: 1,
});
device.bind_buffer(&vertex_array, quad_vertex_indices_buffer, BufferTarget::Index); device.bind_buffer(&vertex_array, quad_vertex_indices_buffer, BufferTarget::Index);
TileVertexArray { vertex_array } TileVertexArray { vertex_array }

View File

@ -15,7 +15,6 @@ use crate::options::BoundingQuad;
use crate::paint::PaintCompositeOp; use crate::paint::PaintCompositeOp;
use pathfinder_color::ColorU; use pathfinder_color::ColorU;
use pathfinder_content::effects::{BlendMode, Filter}; use pathfinder_content::effects::{BlendMode, Filter};
use pathfinder_content::fill::FillRule;
use pathfinder_content::render_target::RenderTargetId; use pathfinder_content::render_target::RenderTargetId;
use pathfinder_geometry::line_segment::{LineSegmentU4, LineSegmentU8}; use pathfinder_geometry::line_segment::{LineSegmentU4, LineSegmentU8};
use pathfinder_geometry::rect::RectI; use pathfinder_geometry::rect::RectI;
@ -28,6 +27,12 @@ use std::sync::atomic::{AtomicUsize, Ordering};
use std::time::Duration; use std::time::Duration;
use std::u32; use std::u32;
pub const TILE_CTRL_MASK_MASK: i32 = 0x3;
pub const TILE_CTRL_MASK_WINDING: i32 = 0x1;
pub const TILE_CTRL_MASK_EVEN_ODD: i32 = 0x2;
pub const TILE_CTRL_MASK_0_SHIFT: i32 = 0;
pub enum RenderCommand { pub enum RenderCommand {
// Starts rendering a frame. // Starts rendering a frame.
Start { Start {
@ -102,7 +107,6 @@ pub struct TextureLocation {
pub struct TileBatch { pub struct TileBatch {
pub tiles: Vec<Tile>, pub tiles: Vec<Tile>,
pub color_texture: Option<TileBatchTexture>, pub color_texture: Option<TileBatchTexture>,
pub mask_0_fill_rule: Option<FillRule>,
pub filter: Filter, pub filter: Filter,
pub blend_mode: BlendMode, pub blend_mode: BlendMode,
pub tile_page: u16, pub tile_page: u16,
@ -194,7 +198,7 @@ pub struct Tile {
pub mask_0_backdrop: i8, pub mask_0_backdrop: i8,
pub pad: u8, pub pad: u8,
pub color: u16, pub color: u16,
pub flags: u16, pub ctrl: u16,
} }
#[derive(Clone, Copy, PartialEq, Debug)] #[derive(Clone, Copy, PartialEq, Debug)]
@ -260,10 +264,9 @@ impl Debug for RenderCommand {
RenderCommand::BeginTileDrawing => write!(formatter, "BeginTileDrawing"), RenderCommand::BeginTileDrawing => write!(formatter, "BeginTileDrawing"),
RenderCommand::DrawTiles(ref batch) => { RenderCommand::DrawTiles(ref batch) => {
write!(formatter, write!(formatter,
"DrawTiles(x{}, C0 {:?}, M0 {:?}, {:?})", "DrawTiles(x{}, C0 {:?}, {:?})",
batch.tiles.len(), batch.tiles.len(),
batch.color_texture, batch.color_texture,
batch.mask_0_fill_rule,
batch.blend_mode) batch.blend_mode)
} }
RenderCommand::Finish { cpu_build_time } => { RenderCommand::Finish { cpu_build_time } => {

View File

@ -51,6 +51,7 @@ pub(crate) struct DrawTilingPathInfo<'a> {
pub(crate) paint_metadata: &'a PaintMetadata, pub(crate) paint_metadata: &'a PaintMetadata,
pub(crate) blend_mode: BlendMode, pub(crate) blend_mode: BlendMode,
pub(crate) built_clip_path: Option<&'a BuiltPath>, pub(crate) built_clip_path: Option<&'a BuiltPath>,
pub(crate) fill_rule: FillRule,
} }
impl<'a, 'b> Tiler<'a, 'b> { impl<'a, 'b> Tiler<'a, 'b> {

View File

@ -91,7 +91,6 @@ impl ZBuffer {
tiles: vec![], tiles: vec![],
filter: Filter::None, filter: Filter::None,
blend_mode: BlendMode::default(), blend_mode: BlendMode::default(),
mask_0_fill_rule: None,
tile_page: !0, tile_page: !0,
}); });
} }
@ -113,7 +112,7 @@ impl Tile {
mask_0_backdrop: 0, mask_0_backdrop: 0,
mask_0_u: 0, mask_0_u: 0,
mask_0_v: 0, mask_0_v: 0,
flags: 0, ctrl: 0,
pad: 0, pad: 0,
color: paint_id.0, color: paint_id.0,
} }

View File

@ -77,6 +77,7 @@ precision highp sampler2D;
uniform sampler2D uColorTexture0; uniform sampler2D uColorTexture0;
@ -93,6 +94,7 @@ uniform int uCtrl;
in vec3 vMaskTexCoord0; in vec3 vMaskTexCoord0;
in vec2 vColorTexCoord0; in vec2 vColorTexCoord0;
in vec4 vBaseColor; in vec4 vBaseColor;
in float vTileCtrl;
out vec4 oFragColor; out vec4 oFragColor;
@ -556,9 +558,9 @@ float sampleMask(float maskAlpha,
void calculateColor(int ctrl){ void calculateColor(int tileCtrl, int ctrl){
int maskCtrl0 =(ctrl >> 0)& 0x3; int maskCtrl0 =(tileCtrl >> 0)& 0x3;
float maskAlpha = 1.0; float maskAlpha = 1.0;
maskAlpha = sampleMask(maskAlpha, uMaskTexture0, vMaskTexCoord0, maskCtrl0); maskAlpha = sampleMask(maskAlpha, uMaskTexture0, vMaskTexCoord0, maskCtrl0);
@ -598,6 +600,6 @@ void calculateColor(int ctrl){
void main(){ void main(){
calculateColor(uCtrl); calculateColor(int(vTileCtrl), uCtrl);
} }

View File

@ -25,10 +25,12 @@ in ivec2 aTileOrigin;
in uvec2 aMaskTexCoord0; in uvec2 aMaskTexCoord0;
in ivec2 aMaskBackdrop; in ivec2 aMaskBackdrop;
in int aColor; in int aColor;
in int aTileCtrl;
out vec3 vMaskTexCoord0; out vec3 vMaskTexCoord0;
out vec2 vColorTexCoord0; out vec2 vColorTexCoord0;
out vec4 vBaseColor; out vec4 vBaseColor;
out float vTileCtrl;
void main(){ void main(){
vec2 tileOrigin = vec2(aTileOrigin), tileOffset = vec2(aTileOffset); vec2 tileOrigin = vec2(aTileOrigin), tileOffset = vec2(aTileOffset);
@ -48,6 +50,7 @@ void main(){
vColorTexCoord0 = mat2(colorTexMatrix0)* position + colorTexOffsets . xy; vColorTexCoord0 = mat2(colorTexMatrix0)* position + colorTexOffsets . xy;
vMaskTexCoord0 = vec3(maskTexCoord0, float(aMaskBackdrop . x)); vMaskTexCoord0 = vec3(maskTexCoord0, float(aMaskBackdrop . x));
vBaseColor = baseColor; vBaseColor = baseColor;
vTileCtrl = float(aTileCtrl);
gl_Position = uTransform * vec4(position, 0.0, 1.0); gl_Position = uTransform * vec4(position, 0.0, 1.0);
} }

View File

@ -24,7 +24,7 @@ struct spvDescriptorSetBuffer0
constant int* uCtrl [[id(13)]]; constant int* uCtrl [[id(13)]];
}; };
constant float3 _1040 = {}; constant float3 _1041 = {};
struct main0_out struct main0_out
{ {
@ -36,6 +36,7 @@ struct main0_in
float3 vMaskTexCoord0 [[user(locn0)]]; float3 vMaskTexCoord0 [[user(locn0)]];
float2 vColorTexCoord0 [[user(locn1)]]; float2 vColorTexCoord0 [[user(locn1)]];
float4 vBaseColor [[user(locn2)]]; float4 vBaseColor [[user(locn2)]];
float vTileCtrl [[user(locn3)]];
}; };
// Implementation of the GLSL mod() function, which is slightly different than Metal fmod() // Implementation of the GLSL mod() function, which is slightly different than Metal fmod()
@ -84,16 +85,16 @@ float4 filterRadialGradient(thread const float2& colorTexCoord, thread const tex
{ {
ts = ts.yx; ts = ts.yx;
} }
float _553; float _554;
if (ts.x >= 0.0) if (ts.x >= 0.0)
{ {
_553 = ts.x; _554 = ts.x;
} }
else else
{ {
_553 = ts.y; _554 = ts.y;
} }
float t = _553; float t = _554;
color = colorTexture.sample(colorTextureSmplr, (uvOrigin + float2(fast::clamp(t, 0.0, 1.0), 0.0))); color = colorTexture.sample(colorTextureSmplr, (uvOrigin + float2(fast::clamp(t, 0.0, 1.0), 0.0)));
} }
return color; return color;
@ -106,19 +107,19 @@ float4 filterBlur(thread const float2& colorTexCoord, thread const texture2d<flo
float3 gaussCoeff = filterParams1.xyz; float3 gaussCoeff = filterParams1.xyz;
float gaussSum = gaussCoeff.x; float gaussSum = gaussCoeff.x;
float4 color = colorTexture.sample(colorTextureSmplr, colorTexCoord) * gaussCoeff.x; float4 color = colorTexture.sample(colorTextureSmplr, colorTexCoord) * gaussCoeff.x;
float2 _598 = gaussCoeff.xy * gaussCoeff.yz; float2 _599 = gaussCoeff.xy * gaussCoeff.yz;
gaussCoeff = float3(_598.x, _598.y, gaussCoeff.z); gaussCoeff = float3(_599.x, _599.y, gaussCoeff.z);
for (int i = 1; i <= support; i += 2) for (int i = 1; i <= support; i += 2)
{ {
float gaussPartialSum = gaussCoeff.x; float gaussPartialSum = gaussCoeff.x;
float2 _618 = gaussCoeff.xy * gaussCoeff.yz; float2 _619 = gaussCoeff.xy * gaussCoeff.yz;
gaussCoeff = float3(_618.x, _618.y, gaussCoeff.z); gaussCoeff = float3(_619.x, _619.y, gaussCoeff.z);
gaussPartialSum += gaussCoeff.x; gaussPartialSum += gaussCoeff.x;
float2 srcOffset = srcOffsetScale * (float(i) + (gaussCoeff.x / gaussPartialSum)); float2 srcOffset = srcOffsetScale * (float(i) + (gaussCoeff.x / gaussPartialSum));
color += ((colorTexture.sample(colorTextureSmplr, (colorTexCoord - srcOffset)) + colorTexture.sample(colorTextureSmplr, (colorTexCoord + srcOffset))) * gaussPartialSum); color += ((colorTexture.sample(colorTextureSmplr, (colorTexCoord - srcOffset)) + colorTexture.sample(colorTextureSmplr, (colorTexCoord + srcOffset))) * gaussPartialSum);
gaussSum += (2.0 * gaussPartialSum); gaussSum += (2.0 * gaussPartialSum);
float2 _658 = gaussCoeff.xy * gaussCoeff.yz; float2 _659 = gaussCoeff.xy * gaussCoeff.yz;
gaussCoeff = float3(_658.x, _658.y, gaussCoeff.z); gaussCoeff = float3(_659.x, _659.y, gaussCoeff.z);
} }
return color / float4(gaussSum); return color / float4(gaussSum);
} }
@ -131,16 +132,16 @@ float filterTextSample1Tap(thread const float& offset, thread const texture2d<fl
void filterTextSample9Tap(thread float4& outAlphaLeft, thread float& outAlphaCenter, thread float4& outAlphaRight, thread const texture2d<float> colorTexture, thread const sampler colorTextureSmplr, thread const float2& colorTexCoord, thread const float4& kernel0, thread const float& onePixel) void filterTextSample9Tap(thread float4& outAlphaLeft, thread float& outAlphaCenter, thread float4& outAlphaRight, thread const texture2d<float> colorTexture, thread const sampler colorTextureSmplr, thread const float2& colorTexCoord, thread const float4& kernel0, thread const float& onePixel)
{ {
bool wide = kernel0.x > 0.0; bool wide = kernel0.x > 0.0;
float _234; float _235;
if (wide) if (wide)
{ {
float param = (-4.0) * onePixel; float param = (-4.0) * onePixel;
float2 param_1 = colorTexCoord; float2 param_1 = colorTexCoord;
_234 = filterTextSample1Tap(param, colorTexture, colorTextureSmplr, param_1); _235 = filterTextSample1Tap(param, colorTexture, colorTextureSmplr, param_1);
} }
else else
{ {
_234 = 0.0; _235 = 0.0;
} }
float param_2 = (-3.0) * onePixel; float param_2 = (-3.0) * onePixel;
float2 param_3 = colorTexCoord; float2 param_3 = colorTexCoord;
@ -148,7 +149,7 @@ void filterTextSample9Tap(thread float4& outAlphaLeft, thread float& outAlphaCen
float2 param_5 = colorTexCoord; float2 param_5 = colorTexCoord;
float param_6 = (-1.0) * onePixel; float param_6 = (-1.0) * onePixel;
float2 param_7 = colorTexCoord; float2 param_7 = colorTexCoord;
outAlphaLeft = float4(_234, filterTextSample1Tap(param_2, colorTexture, colorTextureSmplr, param_3), filterTextSample1Tap(param_4, colorTexture, colorTextureSmplr, param_5), filterTextSample1Tap(param_6, colorTexture, colorTextureSmplr, param_7)); outAlphaLeft = float4(_235, filterTextSample1Tap(param_2, colorTexture, colorTextureSmplr, param_3), filterTextSample1Tap(param_4, colorTexture, colorTextureSmplr, param_5), filterTextSample1Tap(param_6, colorTexture, colorTextureSmplr, param_7));
float param_8 = 0.0; float param_8 = 0.0;
float2 param_9 = colorTexCoord; float2 param_9 = colorTexCoord;
outAlphaCenter = filterTextSample1Tap(param_8, colorTexture, colorTextureSmplr, param_9); outAlphaCenter = filterTextSample1Tap(param_8, colorTexture, colorTextureSmplr, param_9);
@ -158,18 +159,18 @@ void filterTextSample9Tap(thread float4& outAlphaLeft, thread float& outAlphaCen
float2 param_13 = colorTexCoord; float2 param_13 = colorTexCoord;
float param_14 = 3.0 * onePixel; float param_14 = 3.0 * onePixel;
float2 param_15 = colorTexCoord; float2 param_15 = colorTexCoord;
float _294; float _295;
if (wide) if (wide)
{ {
float param_16 = 4.0 * onePixel; float param_16 = 4.0 * onePixel;
float2 param_17 = colorTexCoord; float2 param_17 = colorTexCoord;
_294 = filterTextSample1Tap(param_16, colorTexture, colorTextureSmplr, param_17); _295 = filterTextSample1Tap(param_16, colorTexture, colorTextureSmplr, param_17);
} }
else else
{ {
_294 = 0.0; _295 = 0.0;
} }
outAlphaRight = float4(filterTextSample1Tap(param_10, colorTexture, colorTextureSmplr, param_11), filterTextSample1Tap(param_12, colorTexture, colorTextureSmplr, param_13), filterTextSample1Tap(param_14, colorTexture, colorTextureSmplr, param_15), _294); outAlphaRight = float4(filterTextSample1Tap(param_10, colorTexture, colorTextureSmplr, param_11), filterTextSample1Tap(param_12, colorTexture, colorTextureSmplr, param_13), filterTextSample1Tap(param_14, colorTexture, colorTextureSmplr, param_15), _295);
} }
float filterTextConvolve7Tap(thread const float4& alpha0, thread const float3& alpha1, thread const float4& kernel0) float filterTextConvolve7Tap(thread const float4& alpha0, thread const float3& alpha1, thread const float4& kernel0)
@ -309,34 +310,34 @@ float3 compositeScreen(thread const float3& destColor, thread const float3& srcC
float3 compositeSelect(thread const bool3& cond, thread const float3& ifTrue, thread const float3& ifFalse) float3 compositeSelect(thread const bool3& cond, thread const float3& ifTrue, thread const float3& ifFalse)
{ {
float _724; float _725;
if (cond.x) if (cond.x)
{ {
_724 = ifTrue.x; _725 = ifTrue.x;
} }
else else
{ {
_724 = ifFalse.x; _725 = ifFalse.x;
} }
float _735; float _736;
if (cond.y) if (cond.y)
{ {
_735 = ifTrue.y; _736 = ifTrue.y;
} }
else else
{ {
_735 = ifFalse.y; _736 = ifFalse.y;
} }
float _746; float _747;
if (cond.z) if (cond.z)
{ {
_746 = ifTrue.z; _747 = ifTrue.z;
} }
else else
{ {
_746 = ifFalse.z; _747 = ifFalse.z;
} }
return float3(_724, _735, _746); return float3(_725, _736, _747);
} }
float3 compositeHardLight(thread const float3& destColor, thread const float3& srcColor) float3 compositeHardLight(thread const float3& destColor, thread const float3& srcColor)
@ -377,16 +378,16 @@ float3 compositeSoftLight(thread const float3& destColor, thread const float3& s
float compositeDivide(thread const float& num, thread const float& denom) float compositeDivide(thread const float& num, thread const float& denom)
{ {
float _760; float _761;
if (denom != 0.0) if (denom != 0.0)
{ {
_760 = num / denom; _761 = num / denom;
} }
else else
{ {
_760 = 0.0; _761 = 0.0;
} }
return _760; return _761;
} }
float3 compositeRGBToHSL(thread const float3& rgb) float3 compositeRGBToHSL(thread const float3& rgb)
@ -395,25 +396,25 @@ float3 compositeRGBToHSL(thread const float3& rgb)
float xMin = fast::min(fast::min(rgb.x, rgb.y), rgb.z); float xMin = fast::min(fast::min(rgb.x, rgb.y), rgb.z);
float c = v - xMin; float c = v - xMin;
float l = mix(xMin, v, 0.5); float l = mix(xMin, v, 0.5);
float3 _866; float3 _867;
if (rgb.x == v) if (rgb.x == v)
{ {
_866 = float3(0.0, rgb.yz); _867 = float3(0.0, rgb.yz);
} }
else else
{ {
float3 _879; float3 _880;
if (rgb.y == v) if (rgb.y == v)
{ {
_879 = float3(2.0, rgb.zx); _880 = float3(2.0, rgb.zx);
} }
else else
{ {
_879 = float3(4.0, rgb.xy); _880 = float3(4.0, rgb.xy);
} }
_866 = _879; _867 = _880;
} }
float3 terms = _866; float3 terms = _867;
float param = ((terms.x * c) + terms.y) - terms.z; float param = ((terms.x * c) + terms.y) - terms.z;
float param_1 = c; float param_1 = c;
float h = 1.0471975803375244140625 * compositeDivide(param, param_1); float h = 1.0471975803375244140625 * compositeDivide(param, param_1);
@ -545,9 +546,9 @@ float4 composite(thread const float4& srcColor, thread const texture2d<float> de
return float4(((srcColor.xyz * (srcColor.w * (1.0 - destColor.w))) + (blendedRGB * (srcColor.w * destColor.w))) + (destColor.xyz * (1.0 - srcColor.w)), 1.0); return float4(((srcColor.xyz * (srcColor.w * (1.0 - destColor.w))) + (blendedRGB * (srcColor.w * destColor.w))) + (destColor.xyz * (1.0 - srcColor.w)), 1.0);
} }
void calculateColor(thread const int& ctrl, thread texture2d<float> uMaskTexture0, thread const sampler uMaskTexture0Smplr, thread float3& vMaskTexCoord0, thread float4& vBaseColor, thread float2& vColorTexCoord0, thread texture2d<float> uColorTexture0, thread const sampler uColorTexture0Smplr, thread texture2d<float> uGammaLUT, thread const sampler uGammaLUTSmplr, thread float2 uColorTexture0Size, thread float4& gl_FragCoord, thread float2 uFramebufferSize, thread float4 uFilterParams0, thread float4 uFilterParams1, thread float4 uFilterParams2, thread texture2d<float> uDestTexture, thread const sampler uDestTextureSmplr, thread float4& oFragColor) void calculateColor(thread const int& tileCtrl, thread const int& ctrl, thread texture2d<float> uMaskTexture0, thread const sampler uMaskTexture0Smplr, thread float3& vMaskTexCoord0, thread float4& vBaseColor, thread float2& vColorTexCoord0, thread texture2d<float> uColorTexture0, thread const sampler uColorTexture0Smplr, thread texture2d<float> uGammaLUT, thread const sampler uGammaLUTSmplr, thread float2 uColorTexture0Size, thread float4& gl_FragCoord, thread float2 uFramebufferSize, thread float4 uFilterParams0, thread float4 uFilterParams1, thread float4 uFilterParams2, thread texture2d<float> uDestTexture, thread const sampler uDestTextureSmplr, thread float4& oFragColor)
{ {
int maskCtrl0 = (ctrl >> 0) & 3; int maskCtrl0 = (tileCtrl >> 0) & 3;
float maskAlpha = 1.0; float maskAlpha = 1.0;
float param = maskAlpha; float param = maskAlpha;
float3 param_1 = vMaskTexCoord0; float3 param_1 = vMaskTexCoord0;
@ -579,16 +580,17 @@ void calculateColor(thread const int& ctrl, thread texture2d<float> uMaskTexture
float2 param_16 = gl_FragCoord.xy; float2 param_16 = gl_FragCoord.xy;
int param_17 = compositeOp; int param_17 = compositeOp;
color = composite(param_14, uDestTexture, uDestTextureSmplr, param_15, param_16, param_17); color = composite(param_14, uDestTexture, uDestTextureSmplr, param_15, param_16, param_17);
float3 _1324 = color.xyz * color.w; float3 _1325 = color.xyz * color.w;
color = float4(_1324.x, _1324.y, _1324.z, color.w); color = float4(_1325.x, _1325.y, _1325.z, color.w);
oFragColor = color; oFragColor = color;
} }
fragment main0_out main0(main0_in in [[stage_in]], constant spvDescriptorSetBuffer0& spvDescriptorSet0 [[buffer(0)]], float4 gl_FragCoord [[position]]) fragment main0_out main0(main0_in in [[stage_in]], constant spvDescriptorSetBuffer0& spvDescriptorSet0 [[buffer(0)]], float4 gl_FragCoord [[position]])
{ {
main0_out out = {}; main0_out out = {};
int param = (*spvDescriptorSet0.uCtrl); int param = int(in.vTileCtrl);
calculateColor(param, spvDescriptorSet0.uMaskTexture0, spvDescriptorSet0.uMaskTexture0Smplr, in.vMaskTexCoord0, in.vBaseColor, in.vColorTexCoord0, spvDescriptorSet0.uColorTexture0, spvDescriptorSet0.uColorTexture0Smplr, spvDescriptorSet0.uGammaLUT, spvDescriptorSet0.uGammaLUTSmplr, (*spvDescriptorSet0.uColorTexture0Size), gl_FragCoord, (*spvDescriptorSet0.uFramebufferSize), (*spvDescriptorSet0.uFilterParams0), (*spvDescriptorSet0.uFilterParams1), (*spvDescriptorSet0.uFilterParams2), spvDescriptorSet0.uDestTexture, spvDescriptorSet0.uDestTextureSmplr, out.oFragColor); int param_1 = (*spvDescriptorSet0.uCtrl);
calculateColor(param, param_1, spvDescriptorSet0.uMaskTexture0, spvDescriptorSet0.uMaskTexture0Smplr, in.vMaskTexCoord0, in.vBaseColor, in.vColorTexCoord0, spvDescriptorSet0.uColorTexture0, spvDescriptorSet0.uColorTexture0Smplr, spvDescriptorSet0.uGammaLUT, spvDescriptorSet0.uGammaLUTSmplr, (*spvDescriptorSet0.uColorTexture0Size), gl_FragCoord, (*spvDescriptorSet0.uFramebufferSize), (*spvDescriptorSet0.uFilterParams0), (*spvDescriptorSet0.uFilterParams1), (*spvDescriptorSet0.uFilterParams2), spvDescriptorSet0.uDestTexture, spvDescriptorSet0.uDestTextureSmplr, out.oFragColor);
return out; return out;
} }

View File

@ -18,6 +18,7 @@ struct main0_out
float3 vMaskTexCoord0 [[user(locn0)]]; float3 vMaskTexCoord0 [[user(locn0)]];
float2 vColorTexCoord0 [[user(locn1)]]; float2 vColorTexCoord0 [[user(locn1)]];
float4 vBaseColor [[user(locn2)]]; float4 vBaseColor [[user(locn2)]];
float vTileCtrl [[user(locn3)]];
float4 gl_Position [[position]]; float4 gl_Position [[position]];
}; };
@ -28,6 +29,7 @@ struct main0_in
uint2 aMaskTexCoord0 [[attribute(2)]]; uint2 aMaskTexCoord0 [[attribute(2)]];
int2 aMaskBackdrop [[attribute(3)]]; int2 aMaskBackdrop [[attribute(3)]];
int aColor [[attribute(4)]]; int aColor [[attribute(4)]];
int aTileCtrl [[attribute(5)]];
}; };
vertex main0_out main0(main0_in in [[stage_in]], constant spvDescriptorSetBuffer0& spvDescriptorSet0 [[buffer(0)]]) vertex main0_out main0(main0_in in [[stage_in]], constant spvDescriptorSetBuffer0& spvDescriptorSet0 [[buffer(0)]])
@ -48,6 +50,7 @@ vertex main0_out main0(main0_in in [[stage_in]], constant spvDescriptorSetBuffer
out.vColorTexCoord0 = (float2x2(float2(colorTexMatrix0.xy), float2(colorTexMatrix0.zw)) * position) + colorTexOffsets.xy; out.vColorTexCoord0 = (float2x2(float2(colorTexMatrix0.xy), float2(colorTexMatrix0.zw)) * position) + colorTexOffsets.xy;
out.vMaskTexCoord0 = float3(maskTexCoord0, float(in.aMaskBackdrop.x)); out.vMaskTexCoord0 = float3(maskTexCoord0, float(in.aMaskBackdrop.x));
out.vBaseColor = baseColor; out.vBaseColor = baseColor;
out.vTileCtrl = float(in.aTileCtrl);
out.gl_Position = (*spvDescriptorSet0.uTransform) * float4(position, 0.0, 1.0); out.gl_Position = (*spvDescriptorSet0.uTransform) * float4(position, 0.0, 1.0);
return out; return out;
} }

View File

@ -41,9 +41,11 @@ precision highp sampler2D;
#define FRAC_6_PI 1.9098593171027443 #define FRAC_6_PI 1.9098593171027443
#define FRAC_PI_3 1.0471975511965976 #define FRAC_PI_3 1.0471975511965976
#define COMBINER_CTRL_MASK_MASK 0x3 #define TILE_CTRL_MASK_MASK 0x3
#define COMBINER_CTRL_MASK_WINDING 0x1 #define TILE_CTRL_MASK_WINDING 0x1
#define COMBINER_CTRL_MASK_EVEN_ODD 0x2 #define TILE_CTRL_MASK_EVEN_ODD 0x2
#define TILE_CTRL_MASK_0_SHIFT 0
#define COMBINER_CTRL_COLOR_COMBINE_MASK 0x3 #define COMBINER_CTRL_COLOR_COMBINE_MASK 0x3
#define COMBINER_CTRL_COLOR_COMBINE_SRC_IN 0x1 #define COMBINER_CTRL_COLOR_COMBINE_SRC_IN 0x1
@ -72,7 +74,6 @@ precision highp sampler2D;
#define COMBINER_CTRL_COMPOSITE_COLOR 0xe #define COMBINER_CTRL_COMPOSITE_COLOR 0xe
#define COMBINER_CTRL_COMPOSITE_LUMINOSITY 0xf #define COMBINER_CTRL_COMPOSITE_LUMINOSITY 0xf
#define COMBINER_CTRL_MASK_0_SHIFT 0
#define COMBINER_CTRL_COLOR_FILTER_SHIFT 4 #define COMBINER_CTRL_COLOR_FILTER_SHIFT 4
#define COMBINER_CTRL_COLOR_COMBINE_SHIFT 6 #define COMBINER_CTRL_COLOR_COMBINE_SHIFT 6
#define COMBINER_CTRL_COMPOSITE_SHIFT 8 #define COMBINER_CTRL_COMPOSITE_SHIFT 8
@ -91,6 +92,7 @@ uniform int uCtrl;
in vec3 vMaskTexCoord0; in vec3 vMaskTexCoord0;
in vec2 vColorTexCoord0; in vec2 vColorTexCoord0;
in vec4 vBaseColor; in vec4 vBaseColor;
in float vTileCtrl;
out vec4 oFragColor; out vec4 oFragColor;
@ -545,7 +547,7 @@ float sampleMask(float maskAlpha,
if (maskCtrl == 0) if (maskCtrl == 0)
return maskAlpha; return maskAlpha;
float coverage = texture(maskTexture, maskTexCoord.xy).r + maskTexCoord.z; float coverage = texture(maskTexture, maskTexCoord.xy).r + maskTexCoord.z;
if ((maskCtrl & COMBINER_CTRL_MASK_WINDING) != 0) if ((maskCtrl & TILE_CTRL_MASK_WINDING) != 0)
coverage = abs(coverage); coverage = abs(coverage);
else else
coverage = 1.0 - abs(1.0 - mod(coverage, 2.0)); coverage = 1.0 - abs(1.0 - mod(coverage, 2.0));
@ -554,9 +556,9 @@ float sampleMask(float maskAlpha,
// Main function // Main function
void calculateColor(int ctrl) { void calculateColor(int tileCtrl, int ctrl) {
// Sample mask. // Sample mask.
int maskCtrl0 = (ctrl >> COMBINER_CTRL_MASK_0_SHIFT) & COMBINER_CTRL_MASK_MASK; int maskCtrl0 = (tileCtrl >> TILE_CTRL_MASK_0_SHIFT) & TILE_CTRL_MASK_MASK;
float maskAlpha = 1.0; float maskAlpha = 1.0;
maskAlpha = sampleMask(maskAlpha, uMaskTexture0, vMaskTexCoord0, maskCtrl0); maskAlpha = sampleMask(maskAlpha, uMaskTexture0, vMaskTexCoord0, maskCtrl0);
@ -596,5 +598,5 @@ void calculateColor(int ctrl) {
// TODO(pcwalton): Generate this dynamically. // TODO(pcwalton): Generate this dynamically.
void main() { void main() {
calculateColor(uCtrl); calculateColor(int(vTileCtrl), uCtrl);
} }

View File

@ -23,10 +23,12 @@ in ivec2 aTileOrigin;
in uvec2 aMaskTexCoord0; in uvec2 aMaskTexCoord0;
in ivec2 aMaskBackdrop; in ivec2 aMaskBackdrop;
in int aColor; in int aColor;
in int aTileCtrl;
out vec3 vMaskTexCoord0; out vec3 vMaskTexCoord0;
out vec2 vColorTexCoord0; out vec2 vColorTexCoord0;
out vec4 vBaseColor; out vec4 vBaseColor;
out float vTileCtrl;
void main() { void main() {
vec2 tileOrigin = vec2(aTileOrigin), tileOffset = vec2(aTileOffset); vec2 tileOrigin = vec2(aTileOrigin), tileOffset = vec2(aTileOffset);
@ -46,5 +48,6 @@ void main() {
vColorTexCoord0 = mat2(colorTexMatrix0) * position + colorTexOffsets.xy; vColorTexCoord0 = mat2(colorTexMatrix0) * position + colorTexOffsets.xy;
vMaskTexCoord0 = vec3(maskTexCoord0, float(aMaskBackdrop.x)); vMaskTexCoord0 = vec3(maskTexCoord0, float(aMaskBackdrop.x));
vBaseColor = baseColor; vBaseColor = baseColor;
vTileCtrl = float(aTileCtrl);
gl_Position = uTransform * vec4(position, 0.0, 1.0); gl_Position = uTransform * vec4(position, 0.0, 1.0);
} }