[Impeller] remove usage of VBB when allocating vertices of a fixed size. (flutter/engine#55235)
The VertexBufferBuilder (VBB) always does a heap allocation of its vertices before copying them into the host buffer. This is unecessary when uploading a fixed set of vertices, like many filters do. Instead create a helper function that uploads from a std::array. In most cases this is the same or less code. We could go template madness to emplace directly but that doesnt seem necessary.
This commit is contained in:
@@ -7,6 +7,7 @@
|
||||
|
||||
#include "fml/logging.h"
|
||||
#include "impeller/core/formats.h"
|
||||
#include "impeller/core/vertex_buffer.h"
|
||||
#include "impeller/entity/contents/clip_contents.h"
|
||||
#include "impeller/entity/contents/content_context.h"
|
||||
#include "impeller/entity/entity.h"
|
||||
@@ -160,11 +161,8 @@ bool ClipContents::Render(const ContentContext& renderer,
|
||||
break;
|
||||
}
|
||||
auto points = cover_area.GetPoints();
|
||||
auto vertices =
|
||||
VertexBufferBuilder<VS::PerVertexData>{}
|
||||
.AddVertices({{points[0]}, {points[1]}, {points[2]}, {points[3]}})
|
||||
.CreateVertexBuffer(renderer.GetTransientsBuffer());
|
||||
pass.SetVertexBuffer(std::move(vertices));
|
||||
pass.SetVertexBuffer(
|
||||
CreateVertexBuffer(points, renderer.GetTransientsBuffer()));
|
||||
|
||||
pass.SetPipeline(renderer.GetClipPipeline(options));
|
||||
|
||||
@@ -237,15 +235,15 @@ bool ClipRestoreContents::Render(const ContentContext& renderer,
|
||||
auto ltrb =
|
||||
restore_coverage_.value_or(Rect::MakeSize(pass.GetRenderTargetSize()))
|
||||
.GetLTRB();
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{Point(ltrb[0], ltrb[1])},
|
||||
{Point(ltrb[2], ltrb[1])},
|
||||
{Point(ltrb[0], ltrb[3])},
|
||||
{Point(ltrb[2], ltrb[3])},
|
||||
});
|
||||
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(ltrb[0], ltrb[1])},
|
||||
VS::PerVertexData{Point(ltrb[2], ltrb[1])},
|
||||
VS::PerVertexData{Point(ltrb[0], ltrb[3])},
|
||||
VS::PerVertexData{Point(ltrb[2], ltrb[3])},
|
||||
};
|
||||
pass.SetVertexBuffer(
|
||||
vtx_builder.CreateVertexBuffer(renderer.GetTransientsBuffer()));
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer()));
|
||||
|
||||
VS::FrameInfo info;
|
||||
info.depth = GetShaderClipDepth(entity);
|
||||
|
||||
@@ -13,6 +13,7 @@
|
||||
#include "impeller/core/formats.h"
|
||||
#include "impeller/core/sampler_descriptor.h"
|
||||
#include "impeller/core/texture_descriptor.h"
|
||||
#include "impeller/core/vertex_buffer.h"
|
||||
#include "impeller/entity/contents/anonymous_contents.h"
|
||||
#include "impeller/entity/contents/content_context.h"
|
||||
#include "impeller/entity/contents/contents.h"
|
||||
@@ -152,14 +153,18 @@ static std::optional<Entity> AdvancedBlend(
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
|
||||
auto size = pass.GetRenderTargetSize();
|
||||
VertexBufferBuilder<typename VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{Point(0, 0), dst_uvs[0], src_uvs[0]},
|
||||
{Point(size.width, 0), dst_uvs[1], src_uvs[1]},
|
||||
{Point(0, size.height), dst_uvs[2], src_uvs[2]},
|
||||
{Point(size.width, size.height), dst_uvs[3], src_uvs[3]},
|
||||
});
|
||||
auto vtx_buffer = vtx_builder.CreateVertexBuffer(host_buffer);
|
||||
|
||||
std::array<typename VS::PerVertexData, 4> vertices = {
|
||||
typename VS::PerVertexData{Point(0, 0), dst_uvs[0], src_uvs[0]},
|
||||
typename VS::PerVertexData{Point(size.width, 0), dst_uvs[1],
|
||||
src_uvs[1]},
|
||||
typename VS::PerVertexData{Point(0, size.height), dst_uvs[2],
|
||||
src_uvs[2]},
|
||||
typename VS::PerVertexData{Point(size.width, size.height), dst_uvs[3],
|
||||
src_uvs[3]},
|
||||
};
|
||||
auto vtx_buffer =
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer());
|
||||
|
||||
auto options = OptionsFromPass(pass);
|
||||
options.primitive_type = PrimitiveType::kTriangleStrip;
|
||||
@@ -282,16 +287,16 @@ std::optional<Entity> BlendFilterContents::CreateForegroundAdvancedBlend(
|
||||
using FS = BlendScreenPipeline::FragmentShader;
|
||||
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
|
||||
auto size = dst_snapshot->texture->GetSize();
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{{0, 0}, {0, 0}, {0, 0}},
|
||||
{Point(size.width, 0), {1, 0}, {1, 0}},
|
||||
{Point(0, size.height), {0, 1}, {0, 1}},
|
||||
{Point(size.width, size.height), {1, 1}, {1, 1}},
|
||||
});
|
||||
auto vtx_buffer = vtx_builder.CreateVertexBuffer(host_buffer);
|
||||
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{{0, 0}, {0, 0}, {0, 0}},
|
||||
VS::PerVertexData{Point(size.width, 0), {1, 0}, {1, 0}},
|
||||
VS::PerVertexData{Point(0, size.height), {0, 1}, {0, 1}},
|
||||
VS::PerVertexData{Point(size.width, size.height), {1, 1}, {1, 1}},
|
||||
};
|
||||
auto vtx_buffer =
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer());
|
||||
|
||||
#ifdef IMPELLER_DEBUG
|
||||
pass.SetCommandLabel(SPrintF("Foreground Advanced Blend Filter (%s)",
|
||||
@@ -434,14 +439,15 @@ std::optional<Entity> BlendFilterContents::CreateForegroundPorterDuffBlend(
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
auto size = dst_snapshot->texture->GetSize();
|
||||
auto color = foreground_color.Premultiply();
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{{0, 0}, {0, 0}, color},
|
||||
{Point(size.width, 0), {1, 0}, color},
|
||||
{Point(0, size.height), {0, 1}, color},
|
||||
{Point(size.width, size.height), {1, 1}, color},
|
||||
});
|
||||
auto vtx_buffer = vtx_builder.CreateVertexBuffer(host_buffer);
|
||||
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{{0, 0}, {0, 0}, color},
|
||||
VS::PerVertexData{Point(size.width, 0), {1, 0}, color},
|
||||
VS::PerVertexData{Point(0, size.height), {0, 1}, color},
|
||||
VS::PerVertexData{Point(size.width, size.height), {1, 1}, color},
|
||||
};
|
||||
auto vtx_buffer =
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer());
|
||||
|
||||
#ifdef IMPELLER_DEBUG
|
||||
pass.SetCommandLabel(SPrintF("Foreground PorterDuff Blend Filter (%s)",
|
||||
@@ -562,14 +568,14 @@ static std::optional<Entity> PipelineBlend(
|
||||
FS::BindTextureSampler(pass, input->texture, sampler);
|
||||
|
||||
auto size = input->texture->GetSize();
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{Point(0, 0), Point(0, 0)},
|
||||
{Point(size.width, 0), Point(1, 0)},
|
||||
{Point(0, size.height), Point(0, 1)},
|
||||
{Point(size.width, size.height), Point(1, 1)},
|
||||
});
|
||||
pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(0, 0), Point(0, 0)},
|
||||
VS::PerVertexData{Point(size.width, 0), Point(1, 0)},
|
||||
VS::PerVertexData{Point(0, size.height), Point(0, 1)},
|
||||
VS::PerVertexData{Point(size.width, size.height), Point(1, 1)},
|
||||
};
|
||||
pass.SetVertexBuffer(
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer()));
|
||||
|
||||
VS::FrameInfo frame_info;
|
||||
frame_info.mvp = pass.GetOrthographicTransform() *
|
||||
@@ -711,15 +717,14 @@ std::optional<Entity> BlendFilterContents::CreateFramebufferAdvancedBlend(
|
||||
FS::FragInfo frag_info;
|
||||
frag_info.alpha = 1.0;
|
||||
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{{0, 0}, {0, 0}},
|
||||
{Point(1, 0), {1, 0}},
|
||||
{Point(0, 1), {0, 1}},
|
||||
{Point(1, 1), {1, 1}},
|
||||
});
|
||||
auto vtx_buffer = vtx_builder.CreateVertexBuffer(host_buffer);
|
||||
pass.SetVertexBuffer(std::move(vtx_buffer));
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{{0, 0}, {0, 0}},
|
||||
VS::PerVertexData{Point(1, 0), {1, 0}},
|
||||
VS::PerVertexData{Point(0, 1), {0, 1}},
|
||||
VS::PerVertexData{Point(1, 1), {1, 1}},
|
||||
};
|
||||
pass.SetVertexBuffer(
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer()));
|
||||
|
||||
VS::BindFrameInfo(pass, host_buffer.EmplaceUniform(frame_info));
|
||||
FS::BindFragInfo(pass, host_buffer.EmplaceUniform(frag_info));
|
||||
@@ -753,20 +758,20 @@ std::optional<Entity> BlendFilterContents::CreateFramebufferAdvancedBlend(
|
||||
src_texture = src_snapshot->texture;
|
||||
}
|
||||
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{Point(0, 0), Point(0, 0)},
|
||||
{Point(1, 0), Point(1, 0)},
|
||||
{Point(0, 1), Point(0, 1)},
|
||||
{Point(1, 1), Point(1, 1)},
|
||||
});
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(0, 0), Point(0, 0)},
|
||||
VS::PerVertexData{Point(1, 0), Point(1, 0)},
|
||||
VS::PerVertexData{Point(0, 1), Point(0, 1)},
|
||||
VS::PerVertexData{Point(1, 1), Point(1, 1)},
|
||||
};
|
||||
|
||||
auto options = OptionsFromPass(pass);
|
||||
options.blend_mode = BlendMode::kSource;
|
||||
options.primitive_type = PrimitiveType::kTriangleStrip;
|
||||
|
||||
pass.SetCommandLabel("Framebuffer Advanced Blend Filter");
|
||||
pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
|
||||
pass.SetVertexBuffer(
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer()));
|
||||
|
||||
switch (blend_mode) {
|
||||
case BlendMode::kScreen:
|
||||
|
||||
@@ -91,15 +91,15 @@ std::optional<Entity> BorderMaskBlurFilterContents::RenderFilter(
|
||||
const Entity& entity, RenderPass& pass) -> bool {
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
auto origin = coverage.GetOrigin();
|
||||
auto size = coverage.GetSize();
|
||||
vtx_builder.AddVertices({
|
||||
{origin, input_uvs[0]},
|
||||
{{origin.x + size.width, origin.y}, input_uvs[1]},
|
||||
{{origin.x, origin.y + size.height}, input_uvs[2]},
|
||||
{{origin.x + size.width, origin.y + size.height}, input_uvs[3]},
|
||||
});
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{origin, input_uvs[0]},
|
||||
VS::PerVertexData{{origin.x + size.width, origin.y}, input_uvs[1]},
|
||||
VS::PerVertexData{{origin.x, origin.y + size.height}, input_uvs[2]},
|
||||
VS::PerVertexData{{origin.x + size.width, origin.y + size.height},
|
||||
input_uvs[3]},
|
||||
};
|
||||
|
||||
auto options = OptionsFromPassAndEntity(pass, entity);
|
||||
options.primitive_type = PrimitiveType::kTriangleStrip;
|
||||
@@ -117,7 +117,7 @@ std::optional<Entity> BorderMaskBlurFilterContents::RenderFilter(
|
||||
|
||||
pass.SetCommandLabel("Border Mask Blur Filter");
|
||||
pass.SetPipeline(renderer.GetBorderMaskBlurPipeline(options));
|
||||
pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
|
||||
pass.SetVertexBuffer(CreateVertexBuffer(vertices, host_buffer));
|
||||
|
||||
FS::BindFragInfo(pass, host_buffer.EmplaceUniform(frag_info));
|
||||
VS::BindFrameInfo(pass, host_buffer.EmplaceUniform(frame_info));
|
||||
|
||||
@@ -63,15 +63,15 @@ std::optional<Entity> ColorMatrixFilterContents::RenderFilter(
|
||||
|
||||
auto size = input_snapshot->texture->GetSize();
|
||||
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{Point(0, 0)},
|
||||
{Point(1, 0)},
|
||||
{Point(0, 1)},
|
||||
{Point(1, 1)},
|
||||
});
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(0, 0)},
|
||||
VS::PerVertexData{Point(1, 0)},
|
||||
VS::PerVertexData{Point(0, 1)},
|
||||
VS::PerVertexData{Point(1, 1)},
|
||||
};
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
|
||||
pass.SetVertexBuffer(
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer()));
|
||||
|
||||
VS::FrameInfo frame_info;
|
||||
frame_info.mvp = Entity::GetShaderTransform(
|
||||
|
||||
@@ -34,15 +34,6 @@ SamplerDescriptor MakeSamplerDescriptor(MinMagFilter filter,
|
||||
return sampler_desc;
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
void BindVertices(RenderPass& pass,
|
||||
HostBuffer& host_buffer,
|
||||
std::initializer_list<typename T::PerVertexData>&& vertices) {
|
||||
VertexBufferBuilder<typename T::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices(vertices);
|
||||
pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
|
||||
}
|
||||
|
||||
void SetTileMode(SamplerDescriptor* descriptor,
|
||||
const ContentContext& renderer,
|
||||
Entity::TileMode tile_mode) {
|
||||
@@ -329,6 +320,8 @@ fml::StatusOr<RenderTarget> MakeDownsampleSubpass(
|
||||
const SamplerDescriptor& sampler_descriptor,
|
||||
const DownsamplePassArgs& pass_args,
|
||||
Entity::TileMode tile_mode) {
|
||||
using VS = TextureFillVertexShader;
|
||||
|
||||
// If the texture already had mip levels generated, then we can use the
|
||||
// original downsample shader.
|
||||
if (pass_args.effective_scalar.x >= 0.5f ||
|
||||
@@ -351,13 +344,13 @@ fml::StatusOr<RenderTarget> MakeDownsampleSubpass(
|
||||
frag_info.alpha = 1.0;
|
||||
|
||||
const Quad& uvs = pass_args.uvs;
|
||||
BindVertices<TextureFillVertexShader>(pass, host_buffer,
|
||||
{
|
||||
{Point(0, 0), uvs[0]},
|
||||
{Point(1, 0), uvs[1]},
|
||||
{Point(0, 1), uvs[2]},
|
||||
{Point(1, 1), uvs[3]},
|
||||
});
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(0, 0), uvs[0]},
|
||||
VS::PerVertexData{Point(1, 0), uvs[1]},
|
||||
VS::PerVertexData{Point(0, 1), uvs[2]},
|
||||
VS::PerVertexData{Point(1, 1), uvs[3]},
|
||||
};
|
||||
pass.SetVertexBuffer(CreateVertexBuffer(vertices, host_buffer));
|
||||
|
||||
SamplerDescriptor linear_sampler_descriptor = sampler_descriptor;
|
||||
SetTileMode(&linear_sampler_descriptor, renderer, tile_mode);
|
||||
@@ -406,13 +399,13 @@ fml::StatusOr<RenderTarget> MakeDownsampleSubpass(
|
||||
frag_info.pixel_size = Vector2(1.0f / Size(input_texture->GetSize()));
|
||||
|
||||
const Quad& uvs = pass_args.uvs;
|
||||
BindVertices<TextureFillVertexShader>(pass, host_buffer,
|
||||
{
|
||||
{Point(0, 0), uvs[0]},
|
||||
{Point(1, 0), uvs[1]},
|
||||
{Point(0, 1), uvs[2]},
|
||||
{Point(1, 1), uvs[3]},
|
||||
});
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(0, 0), uvs[0]},
|
||||
VS::PerVertexData{Point(1, 0), uvs[1]},
|
||||
VS::PerVertexData{Point(0, 1), uvs[2]},
|
||||
VS::PerVertexData{Point(1, 1), uvs[3]},
|
||||
};
|
||||
pass.SetVertexBuffer(CreateVertexBuffer(vertices, host_buffer));
|
||||
|
||||
SamplerDescriptor linear_sampler_descriptor = sampler_descriptor;
|
||||
SetTileMode(&linear_sampler_descriptor, renderer, tile_mode);
|
||||
@@ -443,6 +436,8 @@ fml::StatusOr<RenderTarget> MakeBlurSubpass(
|
||||
const BlurParameters& blur_info,
|
||||
std::optional<RenderTarget> destination_target,
|
||||
const Quad& blur_uvs) {
|
||||
using VS = GaussianBlurVertexShader;
|
||||
|
||||
if (blur_info.blur_sigma < kEhCloseEnough) {
|
||||
return input_pass;
|
||||
}
|
||||
@@ -464,13 +459,13 @@ fml::StatusOr<RenderTarget> MakeBlurSubpass(
|
||||
options.primitive_type = PrimitiveType::kTriangleStrip;
|
||||
pass.SetPipeline(renderer.GetGaussianBlurPipeline(options));
|
||||
|
||||
BindVertices<GaussianBlurVertexShader>(pass, host_buffer,
|
||||
{
|
||||
{blur_uvs[0], blur_uvs[0]},
|
||||
{blur_uvs[1], blur_uvs[1]},
|
||||
{blur_uvs[2], blur_uvs[2]},
|
||||
{blur_uvs[3], blur_uvs[3]},
|
||||
});
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{blur_uvs[0], blur_uvs[0]},
|
||||
VS::PerVertexData{blur_uvs[1], blur_uvs[1]},
|
||||
VS::PerVertexData{blur_uvs[2], blur_uvs[2]},
|
||||
VS::PerVertexData{blur_uvs[3], blur_uvs[3]},
|
||||
};
|
||||
pass.SetVertexBuffer(CreateVertexBuffer(vertices, host_buffer));
|
||||
|
||||
SamplerDescriptor linear_sampler_descriptor = sampler_descriptor;
|
||||
linear_sampler_descriptor.mag_filter = MinMagFilter::kLinear;
|
||||
|
||||
@@ -51,17 +51,15 @@ std::optional<Entity> LinearToSrgbFilterContents::RenderFilter(
|
||||
pass.SetPipeline(renderer.GetLinearToSrgbFilterPipeline(options));
|
||||
|
||||
auto size = input_snapshot->texture->GetSize();
|
||||
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{Point(0, 0)},
|
||||
{Point(1, 0)},
|
||||
{Point(0, 1)},
|
||||
{Point(1, 1)},
|
||||
});
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(0, 0)},
|
||||
VS::PerVertexData{Point(1, 0)},
|
||||
VS::PerVertexData{Point(0, 1)},
|
||||
VS::PerVertexData{Point(1, 1)},
|
||||
};
|
||||
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
|
||||
pass.SetVertexBuffer(CreateVertexBuffer(vertices, host_buffer));
|
||||
|
||||
VS::FrameInfo frame_info;
|
||||
frame_info.mvp = Entity::GetShaderTransform(
|
||||
|
||||
@@ -76,13 +76,12 @@ std::optional<Entity> DirectionalMorphologyFilterContents::RenderFilter(
|
||||
RenderPass& pass) {
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{Point(0, 0), input_uvs[0]},
|
||||
{Point(1, 0), input_uvs[1]},
|
||||
{Point(0, 1), input_uvs[2]},
|
||||
{Point(1, 1), input_uvs[3]},
|
||||
});
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(0, 0), input_uvs[0]},
|
||||
VS::PerVertexData{Point(1, 0), input_uvs[1]},
|
||||
VS::PerVertexData{Point(0, 1), input_uvs[2]},
|
||||
VS::PerVertexData{Point(1, 1), input_uvs[3]},
|
||||
};
|
||||
|
||||
VS::FrameInfo frame_info;
|
||||
frame_info.mvp = Matrix::MakeOrthographic(ISize(1, 1));
|
||||
@@ -116,7 +115,7 @@ std::optional<Entity> DirectionalMorphologyFilterContents::RenderFilter(
|
||||
options.primitive_type = PrimitiveType::kTriangleStrip;
|
||||
options.blend_mode = BlendMode::kSource;
|
||||
pass.SetPipeline(renderer.GetMorphologyFilterPipeline(options));
|
||||
pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
|
||||
pass.SetVertexBuffer(CreateVertexBuffer(vertices, host_buffer));
|
||||
|
||||
auto sampler_descriptor = input_snapshot->sampler_descriptor;
|
||||
if (renderer.GetDeviceCapabilities().SupportsDecalSamplerAddressMode()) {
|
||||
|
||||
@@ -52,16 +52,16 @@ std::optional<Entity> SrgbToLinearFilterContents::RenderFilter(
|
||||
|
||||
auto size = input_snapshot->texture->GetSize();
|
||||
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{Point(0, 0)},
|
||||
{Point(1, 0)},
|
||||
{Point(0, 1)},
|
||||
{Point(1, 1)},
|
||||
});
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(0, 0)},
|
||||
VS::PerVertexData{Point(1, 0)},
|
||||
VS::PerVertexData{Point(0, 1)},
|
||||
VS::PerVertexData{Point(1, 1)},
|
||||
};
|
||||
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
|
||||
pass.SetVertexBuffer(
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer()));
|
||||
|
||||
VS::FrameInfo frame_info;
|
||||
frame_info.mvp = Entity::GetShaderTransform(
|
||||
|
||||
@@ -81,16 +81,16 @@ std::optional<Entity> YUVToRGBFilterContents::RenderFilter(
|
||||
|
||||
auto size = y_input_snapshot->texture->GetSize();
|
||||
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{Point(0, 0)},
|
||||
{Point(1, 0)},
|
||||
{Point(0, 1)},
|
||||
{Point(1, 1)},
|
||||
});
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(0, 0)},
|
||||
VS::PerVertexData{Point(1, 0)},
|
||||
VS::PerVertexData{Point(0, 1)},
|
||||
VS::PerVertexData{Point(1, 1)},
|
||||
};
|
||||
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
|
||||
pass.SetVertexBuffer(
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer()));
|
||||
|
||||
VS::FrameInfo frame_info;
|
||||
frame_info.mvp = Entity::GetShaderTransform(
|
||||
|
||||
@@ -54,20 +54,21 @@ bool FramebufferBlendContents::Render(const ContentContext& renderer,
|
||||
}
|
||||
|
||||
auto size = src_snapshot->texture->GetSize();
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
vtx_builder.AddVertices({
|
||||
{Point(0, 0), Point(0, 0)},
|
||||
{Point(size.width, 0), Point(1, 0)},
|
||||
{Point(0, size.height), Point(0, 1)},
|
||||
{Point(size.width, size.height), Point(1, 1)},
|
||||
});
|
||||
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(0, 0), Point(0, 0)},
|
||||
VS::PerVertexData{Point(size.width, 0), Point(1, 0)},
|
||||
VS::PerVertexData{Point(0, size.height), Point(0, 1)},
|
||||
VS::PerVertexData{Point(size.width, size.height), Point(1, 1)},
|
||||
};
|
||||
|
||||
auto options = OptionsFromPass(pass);
|
||||
options.blend_mode = BlendMode::kSource;
|
||||
options.primitive_type = PrimitiveType::kTriangleStrip;
|
||||
|
||||
pass.SetCommandLabel("Framebuffer Advanced Blend Filter");
|
||||
pass.SetVertexBuffer(vtx_builder.CreateVertexBuffer(host_buffer));
|
||||
pass.SetVertexBuffer(
|
||||
CreateVertexBuffer(vertices, renderer.GetTransientsBuffer()));
|
||||
|
||||
switch (blend_mode_) {
|
||||
case BlendMode::kScreen:
|
||||
|
||||
@@ -69,8 +69,6 @@ bool SolidRRectBlurContents::Render(const ContentContext& renderer,
|
||||
using VS = RRectBlurPipeline::VertexShader;
|
||||
using FS = RRectBlurPipeline::FragmentShader;
|
||||
|
||||
VertexBufferBuilder<VS::PerVertexData> vtx_builder;
|
||||
|
||||
// Clamp the max kernel width/height to 1000 to limit the extent
|
||||
// of the blur and to kEhCloseEnough to prevent NaN calculations
|
||||
// trying to evaluate a Guassian distribution with a sigma of 0.
|
||||
@@ -79,19 +77,17 @@ bool SolidRRectBlurContents::Render(const ContentContext& renderer,
|
||||
// sigma->radius conversion we use for slower blurs.
|
||||
auto blur_radius = PadForSigma(blur_sigma);
|
||||
auto positive_rect = rect_->GetPositive();
|
||||
{
|
||||
auto left = -blur_radius;
|
||||
auto top = -blur_radius;
|
||||
auto right = positive_rect.GetWidth() + blur_radius;
|
||||
auto bottom = positive_rect.GetHeight() + blur_radius;
|
||||
auto left = -blur_radius;
|
||||
auto top = -blur_radius;
|
||||
auto right = positive_rect.GetWidth() + blur_radius;
|
||||
auto bottom = positive_rect.GetHeight() + blur_radius;
|
||||
|
||||
vtx_builder.AddVertices({
|
||||
{Point(left, top)},
|
||||
{Point(right, top)},
|
||||
{Point(left, bottom)},
|
||||
{Point(right, bottom)},
|
||||
});
|
||||
}
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{Point(left, top)},
|
||||
VS::PerVertexData{Point(right, top)},
|
||||
VS::PerVertexData{Point(left, bottom)},
|
||||
VS::PerVertexData{Point(right, bottom)},
|
||||
};
|
||||
|
||||
ContentContextOptions opts = OptionsFromPassAndEntity(pass, entity);
|
||||
opts.primitive_type = PrimitiveType::kTriangleStrip;
|
||||
@@ -115,15 +111,13 @@ bool SolidRRectBlurContents::Render(const ContentContext& renderer,
|
||||
positive_rect.GetWidth() * 0.5f),
|
||||
std::clamp(corner_radii_.height, kEhCloseEnough,
|
||||
positive_rect.GetHeight() * 0.5f)};
|
||||
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
pass.SetCommandLabel("RRect Shadow");
|
||||
pass.SetPipeline(renderer.GetRRectBlurPipeline(opts));
|
||||
pass.SetVertexBuffer(
|
||||
vtx_builder.CreateVertexBuffer(renderer.GetTransientsBuffer()));
|
||||
VS::BindFrameInfo(pass,
|
||||
renderer.GetTransientsBuffer().EmplaceUniform(frame_info));
|
||||
FS::BindFragInfo(pass,
|
||||
renderer.GetTransientsBuffer().EmplaceUniform(frag_info));
|
||||
pass.SetVertexBuffer(CreateVertexBuffer(vertices, host_buffer));
|
||||
|
||||
VS::BindFrameInfo(pass, host_buffer.EmplaceUniform(frame_info));
|
||||
FS::BindFragInfo(pass, host_buffer.EmplaceUniform(frag_info));
|
||||
|
||||
if (!pass.Draw().ok()) {
|
||||
return false;
|
||||
|
||||
@@ -124,17 +124,20 @@ bool TextureContents::Render(const ContentContext& renderer,
|
||||
|
||||
auto texture_coords =
|
||||
Rect::MakeSize(texture_->GetSize()).Project(source_rect_);
|
||||
|
||||
VertexBufferBuilder<VS::PerVertexData> vertex_builder;
|
||||
vertex_builder.AddVertices({
|
||||
{destination_rect_.GetLeftTop(), texture_coords.GetLeftTop()},
|
||||
{destination_rect_.GetRightTop(), texture_coords.GetRightTop()},
|
||||
{destination_rect_.GetLeftBottom(), texture_coords.GetLeftBottom()},
|
||||
{destination_rect_.GetRightBottom(), texture_coords.GetRightBottom()},
|
||||
});
|
||||
|
||||
auto& host_buffer = renderer.GetTransientsBuffer();
|
||||
|
||||
std::array<VS::PerVertexData, 4> vertices = {
|
||||
VS::PerVertexData{destination_rect_.GetLeftTop(),
|
||||
texture_coords.GetLeftTop()},
|
||||
VS::PerVertexData{destination_rect_.GetRightTop(),
|
||||
texture_coords.GetRightTop()},
|
||||
VS::PerVertexData{destination_rect_.GetLeftBottom(),
|
||||
texture_coords.GetLeftBottom()},
|
||||
VS::PerVertexData{destination_rect_.GetRightBottom(),
|
||||
texture_coords.GetRightBottom()},
|
||||
};
|
||||
auto vertex_buffer = CreateVertexBuffer(vertices, host_buffer);
|
||||
|
||||
VS::FrameInfo frame_info;
|
||||
frame_info.mvp = entity.GetShaderTransform(pass);
|
||||
frame_info.texture_sampler_y_coord_scale = texture_->GetYCoordScale();
|
||||
@@ -160,7 +163,7 @@ bool TextureContents::Render(const ContentContext& renderer,
|
||||
? renderer.GetTextureStrictSrcPipeline(pipeline_options)
|
||||
: renderer.GetTexturePipeline(pipeline_options));
|
||||
|
||||
pass.SetVertexBuffer(vertex_builder.CreateVertexBuffer(host_buffer));
|
||||
pass.SetVertexBuffer(vertex_buffer);
|
||||
VS::BindFrameInfo(pass, host_buffer.EmplaceUniform(frame_info));
|
||||
|
||||
if (strict_source_rect_enabled_) {
|
||||
|
||||
@@ -6,6 +6,8 @@
|
||||
#define FLUTTER_IMPELLER_RENDERER_VERTEX_BUFFER_BUILDER_H_
|
||||
|
||||
#include <initializer_list>
|
||||
#include <memory>
|
||||
#include <type_traits>
|
||||
#include <vector>
|
||||
|
||||
#include "impeller/base/strings.h"
|
||||
@@ -17,6 +19,19 @@
|
||||
|
||||
namespace impeller {
|
||||
|
||||
/// @brief Create an index-less vertex buffer from a fixed size array.
|
||||
template <class VertexType, size_t size>
|
||||
VertexBuffer CreateVertexBuffer(std::array<VertexType, size> input,
|
||||
HostBuffer& host_buffer) {
|
||||
return VertexBuffer{
|
||||
.vertex_buffer =
|
||||
host_buffer.Emplace(input.data(), sizeof(VertexType) * size,
|
||||
alignof(VertexType)), //
|
||||
.vertex_count = size, //
|
||||
.index_type = IndexType::kNone, //
|
||||
};
|
||||
}
|
||||
|
||||
template <class VertexType_, class IndexType_ = uint16_t>
|
||||
class VertexBufferBuilder {
|
||||
public:
|
||||
|
||||
Reference in New Issue
Block a user