mirror of
https://github.com/flutter/flutter.git
synced 2026-02-20 02:29:02 +08:00
[Impeller] Downsample gaussian blur passes bidirectionally (flutter/engine#35561)
This commit is contained in:
parent
379215c159
commit
a645e493ec
@ -79,6 +79,7 @@ std::shared_ptr<FilterContents> FilterContents::MakeDirectionalGaussianBlur(
|
||||
BlurStyle blur_style,
|
||||
Entity::TileMode tile_mode,
|
||||
FilterInput::Ref source_override,
|
||||
Sigma secondary_sigma,
|
||||
const Matrix& effect_transform) {
|
||||
auto blur = std::make_shared<DirectionalGaussianBlurFilterContents>();
|
||||
blur->SetInputs({input});
|
||||
@ -87,6 +88,7 @@ std::shared_ptr<FilterContents> FilterContents::MakeDirectionalGaussianBlur(
|
||||
blur->SetBlurStyle(blur_style);
|
||||
blur->SetTileMode(tile_mode);
|
||||
blur->SetSourceOverride(source_override);
|
||||
blur->SetSecondarySigma(secondary_sigma);
|
||||
blur->SetEffectTransform(effect_transform);
|
||||
return blur;
|
||||
}
|
||||
@ -100,10 +102,10 @@ std::shared_ptr<FilterContents> FilterContents::MakeGaussianBlur(
|
||||
const Matrix& effect_transform) {
|
||||
auto x_blur = MakeDirectionalGaussianBlur(input, sigma_x, Point(1, 0),
|
||||
BlurStyle::kNormal, tile_mode,
|
||||
nullptr, effect_transform);
|
||||
nullptr, {}, effect_transform);
|
||||
auto y_blur = MakeDirectionalGaussianBlur(FilterInput::Make(x_blur), sigma_y,
|
||||
Point(0, 1), blur_style, tile_mode,
|
||||
input, effect_transform);
|
||||
input, sigma_x, effect_transform);
|
||||
return y_blur;
|
||||
}
|
||||
|
||||
|
||||
@ -48,6 +48,7 @@ class FilterContents : public Contents {
|
||||
BlurStyle blur_style = BlurStyle::kNormal,
|
||||
Entity::TileMode tile_mode = Entity::TileMode::kDecal,
|
||||
FilterInput::Ref alpha_mask = nullptr,
|
||||
Sigma secondary_sigma = {},
|
||||
const Matrix& effect_transform = Matrix());
|
||||
|
||||
static std::shared_ptr<FilterContents> MakeGaussianBlur(
|
||||
|
||||
@ -32,6 +32,10 @@ void DirectionalGaussianBlurFilterContents::SetSigma(Sigma sigma) {
|
||||
blur_sigma_ = sigma;
|
||||
}
|
||||
|
||||
void DirectionalGaussianBlurFilterContents::SetSecondarySigma(Sigma sigma) {
|
||||
secondary_blur_sigma_ = sigma;
|
||||
}
|
||||
|
||||
void DirectionalGaussianBlurFilterContents::SetDirection(Vector2 direction) {
|
||||
blur_direction_ = direction.Normalize();
|
||||
if (blur_direction_.IsZero()) {
|
||||
@ -221,12 +225,22 @@ std::optional<Snapshot> DirectionalGaussianBlurFilterContents::RenderFilter(
|
||||
return pass.AddCommand(cmd);
|
||||
};
|
||||
|
||||
Scalar x_scale =
|
||||
1.0 /
|
||||
std::ceil(std::log2(std::max(2.0f, transformed_blur_radius_length)));
|
||||
auto scaled_texture_width = pass_texture_rect.size.width * x_scale;
|
||||
auto out_texture = renderer.MakeSubpass(
|
||||
ISize(scaled_texture_width, pass_texture_rect.size.height), callback);
|
||||
Vector2 scale;
|
||||
{
|
||||
scale.x =
|
||||
1.0 /
|
||||
std::ceil(std::log2(std::max(2.0f, transformed_blur_radius_length)));
|
||||
|
||||
Scalar y_radius = std::abs(pass_transform.GetDirectionScale(Vector2(
|
||||
0, source_override_ ? Radius{secondary_blur_sigma_}.radius : 1)));
|
||||
scale.y = 1.0 / std::ceil(std::log2(std::max(2.0f, y_radius)));
|
||||
}
|
||||
|
||||
Vector2 scaled_size = pass_texture_rect.size * scale;
|
||||
ISize floored_size = ISize(scaled_size.x, scaled_size.y);
|
||||
|
||||
auto out_texture = renderer.MakeSubpass(floored_size, callback);
|
||||
|
||||
if (!out_texture) {
|
||||
return std::nullopt;
|
||||
}
|
||||
@ -238,12 +252,10 @@ std::optional<Snapshot> DirectionalGaussianBlurFilterContents::RenderFilter(
|
||||
|
||||
return Snapshot{
|
||||
.texture = out_texture,
|
||||
.transform = texture_rotate.Invert() *
|
||||
Matrix::MakeTranslation(pass_texture_rect.origin) *
|
||||
Matrix::MakeScale(Vector2(
|
||||
(1 / x_scale) * (scaled_texture_width /
|
||||
std::floor(scaled_texture_width)),
|
||||
1)),
|
||||
.transform =
|
||||
texture_rotate.Invert() *
|
||||
Matrix::MakeTranslation(pass_texture_rect.origin) *
|
||||
Matrix::MakeScale((1 / scale) * (scaled_size / floored_size)),
|
||||
.sampler_descriptor = sampler_desc};
|
||||
}
|
||||
|
||||
|
||||
@ -19,6 +19,8 @@ class DirectionalGaussianBlurFilterContents final : public FilterContents {
|
||||
|
||||
void SetSigma(Sigma sigma);
|
||||
|
||||
void SetSecondarySigma(Sigma sigma);
|
||||
|
||||
void SetDirection(Vector2 direction);
|
||||
|
||||
void SetBlurStyle(BlurStyle blur_style);
|
||||
@ -42,6 +44,7 @@ class DirectionalGaussianBlurFilterContents final : public FilterContents {
|
||||
const Matrix& effect_transform,
|
||||
const Rect& coverage) const override;
|
||||
Sigma blur_sigma_;
|
||||
Sigma secondary_blur_sigma_;
|
||||
Vector2 blur_direction_;
|
||||
BlurStyle blur_style_ = BlurStyle::kNormal;
|
||||
Entity::TileMode tile_mode_ = Entity::TileMode::kDecal;
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user