gfx/wr/webrender/res/clip_shared.glsl
author Kartikaya Gupta <kgupta@mozilla.com>
Thu, 22 Nov 2018 21:47:48 +0000
changeset 447760 89caaea53d18aaf2d4b90b98a2f989a8cdc7062b
parent 440971 gfx/webrender/res/clip_shared.glsl@2cd2f8f1bc806c45b5d797809abcec8688b1ab65
child 449407 c67f67bb48d5594fba32666623cc7563aabcb08f
permissions -rw-r--r--
Bug 1507524 - Move webrender to gfx/wr. r=jrmuizel This patch copies the webrender repository contents into gfx/wr. The existing files from gfx/webrender, gfx/webrender_api, and gfx/wrench are moved, and the remaining files are added. The revision being used is the same as before. In addition, the mozilla-central top-level Cargo.toml and the gfx/webrender_bindings/Cargo.toml files are updated to reflect the new structure. Differential Revision: https://phabricator.services.mozilla.com/D12059

/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

#include rect,render_task,gpu_cache,snap,transform

#ifdef WR_VERTEX_SHADER

#define SEGMENT_ALL         0
#define SEGMENT_CORNER_TL   1
#define SEGMENT_CORNER_TR   2
#define SEGMENT_CORNER_BL   3
#define SEGMENT_CORNER_BR   4

in int aClipRenderTaskAddress;
in int aClipTransformId;
in int aPrimTransformId;
in int aClipSegment;
in ivec4 aClipDataResourceAddress;

struct ClipMaskInstance {
    int render_task_address;
    int clip_transform_id;
    int prim_transform_id;
    int segment;
    ivec2 clip_data_address;
    ivec2 resource_address;
};

ClipMaskInstance fetch_clip_item() {
    ClipMaskInstance cmi;

    cmi.render_task_address = aClipRenderTaskAddress;
    cmi.clip_transform_id = aClipTransformId;
    cmi.prim_transform_id = aPrimTransformId;
    cmi.segment = aClipSegment;
    cmi.clip_data_address = aClipDataResourceAddress.xy;
    cmi.resource_address = aClipDataResourceAddress.zw;

    return cmi;
}

struct ClipVertexInfo {
    vec3 local_pos;
    RectWithSize clipped_local_rect;
};

RectWithSize intersect_rect(RectWithSize a, RectWithSize b) {
    vec4 p = clamp(vec4(a.p0, a.p0 + a.size), b.p0.xyxy, b.p0.xyxy + b.size.xyxy);
    return RectWithSize(p.xy, max(vec2(0.0), p.zw - p.xy));
}

// The transformed vertex function that always covers the whole clip area,
// which is the intersection of all clip instances of a given primitive
ClipVertexInfo write_clip_tile_vertex(RectWithSize local_clip_rect,
                                      Transform prim_transform,
                                      Transform clip_transform,
                                      ClipArea area) {
    vec2 device_pos = area.screen_origin +
                      aPosition.xy * area.common_data.task_rect.size;

    if (clip_transform.is_axis_aligned && prim_transform.is_axis_aligned) {
        mat4 snap_mat = clip_transform.m * prim_transform.inv_m;
        vec4 snap_positions = compute_snap_positions(
            snap_mat,
            local_clip_rect,
            area.common_data.device_pixel_scale
        );

        vec2 snap_offsets = compute_snap_offset_impl(
            device_pos,
            RectWithSize(snap_positions.xy, snap_positions.zw - snap_positions.xy),
            snap_positions
        );

        device_pos -= snap_offsets;
    }

    vec2 world_pos = device_pos / area.common_data.device_pixel_scale;

    vec4 pos = prim_transform.m * vec4(world_pos, 0.0, 1.0);
    pos.xyz /= pos.w;

    vec4 p = get_node_pos(pos.xy, clip_transform);
    vec3 local_pos = p.xyw * pos.w;

    vec4 vertex_pos = vec4(
        area.common_data.task_rect.p0 + aPosition.xy * area.common_data.task_rect.size,
        0.0,
        1.0
    );

    gl_Position = uTransform * vertex_pos;

    init_transform_vs(vec4(local_clip_rect.p0, local_clip_rect.p0 + local_clip_rect.size));

    ClipVertexInfo vi = ClipVertexInfo(local_pos, local_clip_rect);
    return vi;
}

#endif //WR_VERTEX_SHADER