Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Sync changes from mozilla-central gfx/wr #3841

Merged
merged 7 commits into from Jan 23, 2020

Bug 1606771 - Fix border image repetition computation. r=gw

The computation of the repetition depends on the aspect ratio of the segment's uv rectangle, which was previously represented by the dx/dy variables in the shader. These were mistakenly computing the ratio of the normalized uvs within the primitive's total uv rect, which was incorrect since the normalization introduces a non-uniform scale.
This patch fixes it by taking the uv size in device pixels instead of the the normalized textel rect. dx and dy are also renamed into segment_uv_size which is a more informative name.

Differential Revision: https://phabricator.services.mozilla.com/D60768

[ghsync] From https://hg.mozilla.org/mozilla-central/rev/b77165c764503ccf3b0f52b60fff265d4048ba6e
  • Loading branch information
nical authored and moz-gfx committed Jan 23, 2020
commit 39c6ce217e6988ad303843431e26e7769ff31240
@@ -93,57 +93,57 @@ void image_brush_vs(
local_rect = segment_rect;
stretch_size = local_rect.size;

float dx = segment_data.z - segment_data.x;
float dy = segment_data.w - segment_data.y;

// If the extra data is a texel rect, modify the UVs.
if ((brush_flags & BRUSH_FLAG_TEXEL_RECT) != 0) {

vec2 uv_size = res.uv_rect.p1 - res.uv_rect.p0;
uv0 = res.uv_rect.p0 + segment_data.xy * uv_size;
uv1 = res.uv_rect.p0 + segment_data.zw * uv_size;

// Size of the uv rect of the segment we are considering when computing
// the repetitions. In most case it is the current segment, but for the
// middle area we look at the border size instead.
vec2 segment_uv_size = uv1 - uv0;

#ifdef WR_FEATURE_REPETITION
// The repetition parameters for the middle area of a nine-patch are based
// on the size of the border segments rather than the middle segment itself,
// taking top and left by default, falling back to bottom and right when a
// size is empty.
// TODO(bug 1609893): Move this logic of the CPU as well as other sources of
// TODO(bug 1609893): Move this logic to the CPU as well as other sources of
// branchiness in this shader.
if ((brush_flags & BRUSH_FLAG_SEGMENT_NINEPATCH_MIDDLE) != 0) {
dx = segment_data.x;
dy = segment_data.y;
segment_uv_size = uv0 - res.uv_rect.p0;
stretch_size.x = segment_rect.p0.x - prim_rect.p0.x;
stretch_size.y = segment_rect.p0.y - prim_rect.p0.y;
float epsilon = 0.001;
if (dx < epsilon || stretch_size.x < epsilon) {
dx = 1.0 - segment_data.z;
if (segment_uv_size.x < epsilon || stretch_size.x < epsilon) {
segment_uv_size.x = res.uv_rect.p1.x - uv1.x;
stretch_size.x = prim_rect.p0.x + prim_rect.size.x
- segment_rect.p0.x - segment_rect.size.x;
}
if (dy < epsilon || stretch_size.y < epsilon) {
dy = 1.0 - segment_data.w;
if (segment_uv_size.y < epsilon || stretch_size.y < epsilon) {
segment_uv_size.y = res.uv_rect.p1.y - uv1.y;
stretch_size.y = prim_rect.p0.y + prim_rect.size.y
- segment_rect.p0.y - segment_rect.size.y;
}
}

vec2 original_stretch_size = stretch_size;
if ((brush_flags & BRUSH_FLAG_SEGMENT_REPEAT_X) != 0) {
stretch_size.x = original_stretch_size.y / dy * dx;
stretch_size.x = original_stretch_size.y / segment_uv_size.y * segment_uv_size.x;
}
if ((brush_flags & BRUSH_FLAG_SEGMENT_REPEAT_Y) != 0) {
stretch_size.y = original_stretch_size.x / dx * dy;
stretch_size.y = original_stretch_size.x / segment_uv_size.x * segment_uv_size.y;
}
#endif

} else {
#ifdef WR_FEATURE_REPETITION
if ((brush_flags & BRUSH_FLAG_SEGMENT_REPEAT_X) != 0) {
stretch_size.x = dx;
stretch_size.x = segment_data.z - segment_data.x;
}
if ((brush_flags & BRUSH_FLAG_SEGMENT_REPEAT_Y) != 0) {
stretch_size.y = dy;
stretch_size.y = segment_data.w - segment_data.y;
}
#endif
}
ProTip! Use n and p to navigate between commits in a pull request.
You can’t perform that action at this time.