Skip to content
This repository was archived by the owner on Feb 25, 2025. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions ci/licenses_golden/licenses_flutter
Original file line number Diff line number Diff line change
Expand Up @@ -589,6 +589,8 @@ FILE: ../../../flutter/impeller/entity/contents/text_contents.cc
FILE: ../../../flutter/impeller/entity/contents/text_contents.h
FILE: ../../../flutter/impeller/entity/contents/texture_contents.cc
FILE: ../../../flutter/impeller/entity/contents/texture_contents.h
FILE: ../../../flutter/impeller/entity/contents/tiled_texture_contents.cc
FILE: ../../../flutter/impeller/entity/contents/tiled_texture_contents.h
FILE: ../../../flutter/impeller/entity/contents/vertices_contents.cc
FILE: ../../../flutter/impeller/entity/contents/vertices_contents.h
FILE: ../../../flutter/impeller/entity/entity.cc
Expand Down Expand Up @@ -645,6 +647,8 @@ FILE: ../../../flutter/impeller/entity/shaders/sweep_gradient_fill.frag
FILE: ../../../flutter/impeller/entity/shaders/sweep_gradient_fill.vert
FILE: ../../../flutter/impeller/entity/shaders/texture_fill.frag
FILE: ../../../flutter/impeller/entity/shaders/texture_fill.vert
FILE: ../../../flutter/impeller/entity/shaders/tiled_texture_fill.frag
FILE: ../../../flutter/impeller/entity/shaders/tiled_texture_fill.vert
FILE: ../../../flutter/impeller/entity/shaders/vertices.frag
FILE: ../../../flutter/impeller/entity/shaders/vertices.vert
FILE: ../../../flutter/impeller/geometry/color.cc
Expand Down
78 changes: 78 additions & 0 deletions impeller/aiks/aiks_unittests.cc
Original file line number Diff line number Diff line change
Expand Up @@ -10,10 +10,12 @@
#include "impeller/aiks/aiks_playground.h"
#include "impeller/aiks/canvas.h"
#include "impeller/aiks/image.h"
#include "impeller/entity/contents/tiled_texture_contents.h"
#include "impeller/geometry/color.h"
#include "impeller/geometry/geometry_unittests.h"
#include "impeller/geometry/path_builder.h"
#include "impeller/playground/widgets.h"
#include "impeller/renderer/command_buffer.h"
#include "impeller/renderer/snapshot.h"
#include "impeller/typographer/backends/skia/text_frame_skia.h"
#include "impeller/typographer/backends/skia/text_render_context_skia.h"
Expand Down Expand Up @@ -70,6 +72,82 @@ TEST_P(AiksTest, CanRenderImage) {
ASSERT_TRUE(OpenPlaygroundHere(canvas.EndRecordingAsPicture()));
}

bool GenerateMipmap(std::shared_ptr<Context> context,
std::shared_ptr<Texture> texture,
std::string label) {
auto buffer = context->CreateCommandBuffer();
if (!buffer) {
return false;
}
auto pass = buffer->CreateBlitPass();
if (!pass) {
return false;
}
pass->GenerateMipmap(texture, label);
pass->EncodeCommands(context->GetResourceAllocator());
return true;
}

TEST_P(AiksTest, CanRenderTiledTexture) {
auto context = GetContext();
ASSERT_TRUE(context);
bool first_frame = true;
auto texture = CreateTextureForFixture("table_mountain_nx.png");
auto callback = [&](AiksContext& renderer, RenderTarget& render_target) {
if (first_frame) {
first_frame = false;
GenerateMipmap(context, texture, "table_mountain_nx");
ImGui::SetNextWindowSize({480, 100});
ImGui::SetNextWindowPos({100, 550});
}

const char* tile_mode_names[] = {"Clamp", "Repeat", "Mirror", "Decal"};
const Entity::TileMode tile_modes[] = {
Entity::TileMode::kClamp, Entity::TileMode::kRepeat,
Entity::TileMode::kMirror, Entity::TileMode::kDecal};
const char* mip_filter_names[] = {"None", "Nearest", "Linear"};
const MipFilter mip_filters[] = {MipFilter::kNone, MipFilter::kNearest,
MipFilter::kLinear};
const char* min_mag_filter_names[] = {"Nearest", "Linear"};
const MinMagFilter min_mag_filters[] = {MinMagFilter::kNearest,
MinMagFilter::kLinear};
static int selected_x_tile_mode = 0;
static int selected_y_tile_mode = 0;
static int selected_mip_filter = 0;
static int selected_min_mag_filter = 0;
ImGui::Begin("Controls", nullptr, ImGuiWindowFlags_AlwaysAutoResize);
ImGui::Combo("X tile mode", &selected_x_tile_mode, tile_mode_names,
sizeof(tile_mode_names) / sizeof(char*));
ImGui::Combo("Y tile mode", &selected_y_tile_mode, tile_mode_names,
sizeof(tile_mode_names) / sizeof(char*));
ImGui::Combo("Mip filter", &selected_mip_filter, mip_filter_names,
sizeof(mip_filter_names) / sizeof(char*));
ImGui::Combo("Min Mag filter", &selected_min_mag_filter,
min_mag_filter_names,
sizeof(min_mag_filter_names) / sizeof(char*));
ImGui::End();
Canvas canvas;
Paint paint;
canvas.Translate({100.0, 100.0, 0});
auto x_tile_mode = tile_modes[selected_x_tile_mode];
auto y_tile_mode = tile_modes[selected_y_tile_mode];
SamplerDescriptor descriptor;
descriptor.mip_filter = mip_filters[selected_mip_filter];
descriptor.min_filter = min_mag_filters[selected_min_mag_filter];
descriptor.mag_filter = min_mag_filters[selected_min_mag_filter];
paint.color_source = [texture, x_tile_mode, y_tile_mode, descriptor]() {
auto contents = std::make_shared<TiledTextureContents>();
contents->SetTexture(texture);
contents->SetTileModes(x_tile_mode, y_tile_mode);
contents->SetSamplerDescriptor(descriptor);
return contents;
};
canvas.DrawRect({0, 0, 600, 600}, paint);
return renderer.Render(canvas.EndRecordingAsPicture(), render_target);
};
ASSERT_TRUE(OpenPlaygroundHere(callback));
}

TEST_P(AiksTest, CanRenderImageRect) {
Canvas canvas;
Paint paint;
Expand Down
26 changes: 19 additions & 7 deletions impeller/compiler/shader_lib/impeller/texture.glsl
Original file line number Diff line number Diff line change
Expand Up @@ -48,9 +48,9 @@ float IPFloatTile(float t, float tile_mode) {
/// Remap a vec2 using a tiling mode.
///
/// Runs each component of the vec2 through `IPFloatTile`.
vec2 IPVec2Tile(vec2 coords, float tile_mode) {
return vec2(IPFloatTile(coords.x, tile_mode),
IPFloatTile(coords.y, tile_mode));
vec2 IPVec2Tile(vec2 coords, float x_tile_mode, float y_tile_mode) {
return vec2(IPFloatTile(coords.x, x_tile_mode),
IPFloatTile(coords.y, y_tile_mode));
}

/// Sample a texture, emulating a specific tile mode.
Expand All @@ -60,13 +60,25 @@ vec2 IPVec2Tile(vec2 coords, float tile_mode) {
vec4 IPSampleWithTileMode(sampler2D tex,
vec2 coords,
float y_coord_scale,
float tile_mode) {
if (tile_mode == kTileModeDecal &&
(coords.x < 0 || coords.y < 0 || coords.x >= 1 || coords.y >= 1)) {
float x_tile_mode,
float y_tile_mode) {
if (x_tile_mode == kTileModeDecal && (coords.x < 0 || coords.x >= 1) ||
y_tile_mode == kTileModeDecal && (coords.y < 0 || coords.y >= 1)) {
return vec4(0);
}

return IPSample(tex, IPVec2Tile(coords, tile_mode), y_coord_scale);
return IPSample(tex, IPVec2Tile(coords, x_tile_mode, y_tile_mode), y_coord_scale);
}

/// Sample a texture, emulating a specific tile mode.
///
/// This is useful for Impeller graphics backend that don't have native support
/// for Decal.
vec4 IPSampleWithTileMode(sampler2D tex,
vec2 coords,
float y_coord_scale,
float tile_mode) {
return IPSampleWithTileMode(tex, coords, y_coord_scale, tile_mode, tile_mode);
}

#endif
102 changes: 60 additions & 42 deletions impeller/display_list/display_list_dispatcher.cc
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
#include "impeller/entity/contents/radial_gradient_contents.h"
#include "impeller/entity/contents/solid_stroke_contents.h"
#include "impeller/entity/contents/sweep_gradient_contents.h"
#include "impeller/entity/contents/tiled_texture_contents.h"
#include "impeller/entity/entity.h"
#include "impeller/geometry/path.h"
#include "impeller/geometry/path_builder.h"
Expand Down Expand Up @@ -118,6 +119,47 @@ static Entity::TileMode ToTileMode(flutter::DlTileMode tile_mode) {
}
}

static impeller::SamplerDescriptor ToSamplerDescriptor(
const flutter::DlImageSampling options) {
impeller::SamplerDescriptor desc;
switch (options) {
case flutter::DlImageSampling::kNearestNeighbor:
desc.min_filter = desc.mag_filter = impeller::MinMagFilter::kNearest;
desc.label = "Nearest Sampler";
break;
case flutter::DlImageSampling::kLinear:
desc.min_filter = desc.mag_filter = impeller::MinMagFilter::kLinear;
desc.label = "Linear Sampler";
break;
case flutter::DlImageSampling::kMipmapLinear:
desc.min_filter = desc.mag_filter = impeller::MinMagFilter::kLinear;
desc.mip_filter = impeller::MipFilter::kLinear;
desc.label = "Mipmap Linear Sampler";
break;
default:
break;
}
return desc;
}

static impeller::SamplerDescriptor ToSamplerDescriptor(
const flutter::DlFilterMode options) {
impeller::SamplerDescriptor desc;
switch (options) {
case flutter::DlFilterMode::kNearest:
desc.min_filter = desc.mag_filter = impeller::MinMagFilter::kNearest;
desc.label = "Nearest Sampler";
break;
case flutter::DlFilterMode::kLinear:
desc.min_filter = desc.mag_filter = impeller::MinMagFilter::kLinear;
desc.label = "Linear Sampler";
break;
default:
break;
}
return desc;
}

// |flutter::Dispatcher|
void DisplayListDispatcher::setAntiAlias(bool aa) {
// Nothing to do because AA is implicit.
Expand Down Expand Up @@ -316,7 +358,24 @@ void DisplayListDispatcher::setColorSource(
};
return;
}
case flutter::DlColorSourceType::kImage:
case flutter::DlColorSourceType::kImage: {
const flutter::DlImageColorSource* image_color_source = source->asImage();
FML_DCHECK(image_color_source &&
image_color_source->image()->impeller_texture());
auto texture = image_color_source->image()->impeller_texture();
auto x_tile_mode = ToTileMode(image_color_source->horizontal_tile_mode());
auto y_tile_mode = ToTileMode(image_color_source->vertical_tile_mode());
auto desc = ToSamplerDescriptor(image_color_source->sampling());
paint_.color_source = [texture, x_tile_mode, y_tile_mode, desc]() {
auto contents = std::make_shared<TiledTextureContents>();
contents->SetTexture(texture);
contents->SetTileModes(x_tile_mode, y_tile_mode);
contents->SetSamplerDescriptor(desc);
// TODO(109384) Support 'matrix' parameter for all color sources.
return contents;
};
return;
}
case flutter::DlColorSourceType::kConicalGradient:
case flutter::DlColorSourceType::kUnknown:
UNIMPLEMENTED;
Expand Down Expand Up @@ -908,47 +967,6 @@ void DisplayListDispatcher::drawImage(const sk_sp<flutter::DlImage> image,
);
}

static impeller::SamplerDescriptor ToSamplerDescriptor(
const flutter::DlImageSampling options) {
impeller::SamplerDescriptor desc;
switch (options) {
case flutter::DlImageSampling::kNearestNeighbor:
desc.min_filter = desc.mag_filter = impeller::MinMagFilter::kNearest;
desc.label = "Nearest Sampler";
break;
case flutter::DlImageSampling::kLinear:
desc.min_filter = desc.mag_filter = impeller::MinMagFilter::kLinear;
desc.label = "Linear Sampler";
break;
case flutter::DlImageSampling::kMipmapLinear:
desc.min_filter = desc.mag_filter = impeller::MinMagFilter::kLinear;
desc.mip_filter = impeller::MipFilter::kLinear;
desc.label = "Mipmap Linear Sampler";
break;
default:
break;
}
return desc;
}

static impeller::SamplerDescriptor ToSamplerDescriptor(
const flutter::DlFilterMode options) {
impeller::SamplerDescriptor desc;
switch (options) {
case flutter::DlFilterMode::kNearest:
desc.min_filter = desc.mag_filter = impeller::MinMagFilter::kNearest;
desc.label = "Nearest Sampler";
break;
case flutter::DlFilterMode::kLinear:
desc.min_filter = desc.mag_filter = impeller::MinMagFilter::kLinear;
desc.label = "Linear Sampler";
break;
default:
break;
}
return desc;
}

// |flutter::Dispatcher|
void DisplayListDispatcher::drawImageRect(
const sk_sp<flutter::DlImage> image,
Expand Down
4 changes: 4 additions & 0 deletions impeller/entity/BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,8 @@ impeller_shaders("entity_shaders") {
"shaders/sweep_gradient_fill.vert",
"shaders/texture_fill.frag",
"shaders/texture_fill.vert",
"shaders/tiled_texture_fill.frag",
"shaders/tiled_texture_fill.vert",
"shaders/vertices.frag",
"shaders/vertices.vert",
]
Expand Down Expand Up @@ -101,6 +103,8 @@ impeller_component("entity") {
"contents/text_contents.h",
"contents/texture_contents.cc",
"contents/texture_contents.h",
"contents/tiled_texture_contents.cc",
"contents/tiled_texture_contents.h",
"contents/vertices_contents.cc",
"contents/vertices_contents.h",
"entity.cc",
Expand Down
2 changes: 2 additions & 0 deletions impeller/entity/contents/content_context.cc
Original file line number Diff line number Diff line change
Expand Up @@ -191,6 +191,8 @@ ContentContext::ContentContext(std::shared_ptr<Context> context)
blend_softlight_pipelines_[{}] =
CreateDefaultPipeline<BlendSoftLightPipeline>(*context_);
texture_pipelines_[{}] = CreateDefaultPipeline<TexturePipeline>(*context_);
tiled_texture_pipelines_[{}] =
CreateDefaultPipeline<TiledTexturePipeline>(*context_);
gaussian_blur_pipelines_[{}] =
CreateDefaultPipeline<GaussianBlurPipeline>(*context_);
border_mask_blur_pipelines_[{}] =
Expand Down
10 changes: 10 additions & 0 deletions impeller/entity/contents/content_context.h
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,8 @@
#include "impeller/entity/sweep_gradient_fill.vert.h"
#include "impeller/entity/texture_fill.frag.h"
#include "impeller/entity/texture_fill.vert.h"
#include "impeller/entity/tiled_texture_fill.frag.h"
#include "impeller/entity/tiled_texture_fill.vert.h"
#include "impeller/entity/vertices.frag.h"
#include "impeller/entity/vertices.vert.h"
#include "impeller/renderer/formats.h"
Expand Down Expand Up @@ -104,6 +106,8 @@ using BlendSoftLightPipeline =
PipelineT<AdvancedBlendVertexShader, AdvancedBlendSoftlightFragmentShader>;
using TexturePipeline =
PipelineT<TextureFillVertexShader, TextureFillFragmentShader>;
using TiledTexturePipeline =
PipelineT<TiledTextureFillVertexShader, TiledTextureFillFragmentShader>;
using GaussianBlurPipeline =
PipelineT<GaussianBlurVertexShader, GaussianBlurFragmentShader>;
using BorderMaskBlurPipeline =
Expand Down Expand Up @@ -189,6 +193,11 @@ class ContentContext {
return GetPipeline(texture_pipelines_, opts);
}

std::shared_ptr<Pipeline> GetTiledTexturePipeline(
ContentContextOptions opts) const {
return GetPipeline(tiled_texture_pipelines_, opts);
}

std::shared_ptr<Pipeline> GetGaussianBlurPipeline(
ContentContextOptions opts) const {
return GetPipeline(gaussian_blur_pipelines_, opts);
Expand Down Expand Up @@ -333,6 +342,7 @@ class ContentContext {
mutable Variants<RRectBlurPipeline> rrect_blur_pipelines_;
mutable Variants<BlendPipeline> texture_blend_pipelines_;
mutable Variants<TexturePipeline> texture_pipelines_;
mutable Variants<TiledTexturePipeline> tiled_texture_pipelines_;
mutable Variants<GaussianBlurPipeline> gaussian_blur_pipelines_;
mutable Variants<BorderMaskBlurPipeline> border_mask_blur_pipelines_;
mutable Variants<ColorMatrixColorFilterPipeline>
Expand Down
Loading