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
15 changes: 1 addition & 14 deletions impeller/compiler/shader_lib/impeller/texture.glsl
Original file line number Diff line number Diff line change
Expand Up @@ -82,27 +82,14 @@ vec2 IPVec2Tile(vec2 coords, float x_tile_mode, float y_tile_mode) {
/// for Decal.
vec4 IPSampleWithTileMode(sampler2D tex,
vec2 coords,
float y_coord_scale,
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, 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);
return texture(tex, coords);
}

/// Sample a texture, emulating a specific tile mode.
Expand Down
44 changes: 38 additions & 6 deletions impeller/entity/contents/tiled_texture_contents.cc
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,23 @@

namespace impeller {

static std::optional<SamplerAddressMode> TileModeToAddressMode(
Entity::TileMode tile_mode) {
switch (tile_mode) {
case Entity::TileMode::kClamp:
return SamplerAddressMode::kClampToEdge;
break;
case Entity::TileMode::kMirror:
return SamplerAddressMode::kMirror;
break;
case Entity::TileMode::kRepeat:
return SamplerAddressMode::kRepeat;
break;
case Entity::TileMode::kDecal:
return std::nullopt;
}
}

TiledTextureContents::TiledTextureContents() = default;

TiledTextureContents::~TiledTextureContents() = default;
Expand Down Expand Up @@ -50,6 +67,19 @@ TiledTextureContents::CreateFilterTexture(
return std::nullopt;
}

SamplerDescriptor TiledTextureContents::CreateDescriptor() const {
SamplerDescriptor descriptor = sampler_descriptor_;
auto width_mode = TileModeToAddressMode(x_tile_mode_);
auto height_mode = TileModeToAddressMode(y_tile_mode_);
if (width_mode.has_value()) {
descriptor.width_address_mode = width_mode.value();
}
if (height_mode.has_value()) {
descriptor.height_address_mode = height_mode.value();
}
return descriptor;
}

bool TiledTextureContents::Render(const ContentContext& renderer,
const Entity& entity,
RenderPass& pass) const {
Expand Down Expand Up @@ -84,13 +114,13 @@ bool TiledTextureContents::Render(const ContentContext& renderer,

VS::FrameInfo frame_info;
frame_info.mvp = geometry_result.transform;
frame_info.texture_sampler_y_coord_scale = texture_->GetYCoordScale();
frame_info.effect_transform = GetInverseMatrix();
frame_info.bounds_origin = geometry->GetCoverage(Matrix())->origin;
frame_info.texture_size = Vector2(static_cast<Scalar>(texture_size.width),
static_cast<Scalar>(texture_size.height));

FS::FragInfo frag_info;
frag_info.texture_sampler_y_coord_scale = texture_->GetYCoordScale();
frag_info.x_tile_mode = static_cast<Scalar>(x_tile_mode_);
frag_info.y_tile_mode = static_cast<Scalar>(y_tile_mode_);
frag_info.alpha = GetAlpha();
Expand All @@ -110,6 +140,7 @@ bool TiledTextureContents::Render(const ContentContext& renderer,
cmd.BindVertices(geometry_result.vertex_buffer);
VS::BindFrameInfo(cmd, host_buffer.EmplaceUniform(frame_info));
FS::BindFragInfo(cmd, host_buffer.EmplaceUniform(frag_info));

if (color_filter_.has_value()) {
auto filtered_texture = CreateFilterTexture(renderer);
if (!filtered_texture.has_value()) {
Expand All @@ -118,12 +149,12 @@ bool TiledTextureContents::Render(const ContentContext& renderer,
FS::BindTextureSampler(
cmd, filtered_texture.value(),
renderer.GetContext()->GetSamplerLibrary()->GetSampler(
sampler_descriptor_));
CreateDescriptor()));
} else {
FS::BindTextureSampler(
cmd, texture_,
renderer.GetContext()->GetSamplerLibrary()->GetSampler(
sampler_descriptor_));
CreateDescriptor()));
}

if (!pass.AddCommand(std::move(cmd))) {
Expand Down Expand Up @@ -156,9 +187,9 @@ bool TiledTextureContents::RenderVertices(const ContentContext& renderer,

VS::FrameInfo frame_info;
frame_info.mvp = geometry_result.transform;
frame_info.texture_sampler_y_coord_scale = texture_->GetYCoordScale();

FS::FragInfo frag_info;
frag_info.texture_sampler_y_coord_scale = texture_->GetYCoordScale();
frag_info.x_tile_mode = static_cast<Scalar>(x_tile_mode_);
frag_info.y_tile_mode = static_cast<Scalar>(y_tile_mode_);
frag_info.alpha = GetAlpha();
Expand All @@ -178,6 +209,7 @@ bool TiledTextureContents::RenderVertices(const ContentContext& renderer,
cmd.BindVertices(geometry_result.vertex_buffer);
VS::BindFrameInfo(cmd, host_buffer.EmplaceUniform(frame_info));
FS::BindFragInfo(cmd, host_buffer.EmplaceUniform(frag_info));

if (color_filter_.has_value()) {
auto filtered_texture = CreateFilterTexture(renderer);
if (!filtered_texture.has_value()) {
Expand All @@ -186,12 +218,12 @@ bool TiledTextureContents::RenderVertices(const ContentContext& renderer,
FS::BindTextureSampler(
cmd, filtered_texture.value(),
renderer.GetContext()->GetSamplerLibrary()->GetSampler(
sampler_descriptor_));
CreateDescriptor()));
} else {
FS::BindTextureSampler(
cmd, texture_,
renderer.GetContext()->GetSamplerLibrary()->GetSampler(
sampler_descriptor_));
CreateDescriptor()));
}

if (!pass.AddCommand(std::move(cmd))) {
Expand Down
2 changes: 2 additions & 0 deletions impeller/entity/contents/tiled_texture_contents.h
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,8 @@ class TiledTextureContents final : public ColorSourceContents {
const Entity& entity,
RenderPass& pass) const;

SamplerDescriptor CreateDescriptor() const;

std::shared_ptr<Texture> texture_;
SamplerDescriptor sampler_descriptor_ = {};
Entity::TileMode x_tile_mode_ = Entity::TileMode::kClamp;
Expand Down
16 changes: 6 additions & 10 deletions impeller/entity/shaders/tiled_texture_fill.frag
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@
uniform sampler2D texture_sampler;

uniform FragInfo {
float texture_sampler_y_coord_scale;
float x_tile_mode;
float y_tile_mode;
float alpha;
Expand All @@ -20,13 +19,10 @@ in vec2 v_texture_coords;
out vec4 frag_color;

void main() {
frag_color =
IPSampleWithTileMode(
texture_sampler, // sampler
v_texture_coords, // texture coordinates
frag_info.texture_sampler_y_coord_scale, // y coordinate scale
frag_info.x_tile_mode, // x tile mode
frag_info.y_tile_mode // y tile mode
) *
frag_info.alpha;
frag_color = IPSampleWithTileMode(texture_sampler, // sampler
v_texture_coords, // texture coordinates
frag_info.x_tile_mode, // x tile mode
frag_info.y_tile_mode // y tile mode
) *
frag_info.alpha;
}
10 changes: 7 additions & 3 deletions impeller/entity/shaders/tiled_texture_fill.vert
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <impeller/texture.glsl>
#include <impeller/transform.glsl>
#include <impeller/types.glsl>

Expand All @@ -10,6 +11,7 @@ uniform FrameInfo {
mat4 effect_transform;
vec2 bounds_origin;
vec2 texture_size;
float texture_sampler_y_coord_scale;
}
frame_info;

Expand All @@ -19,7 +21,9 @@ out vec2 v_texture_coords;

void main() {
gl_Position = frame_info.mvp * vec4(position, 0.0, 1.0);
v_texture_coords = IPVec2TransformPosition(
frame_info.effect_transform,
(position - frame_info.bounds_origin) / frame_info.texture_size);
v_texture_coords = IPRemapCoords(
IPVec2TransformPosition(
frame_info.effect_transform,
(position - frame_info.bounds_origin) / frame_info.texture_size),
frame_info.texture_sampler_y_coord_scale);
}
2 changes: 1 addition & 1 deletion impeller/tools/malioc.json

Large diffs are not rendered by default.