in vec2 position;
out vec2 image_pos;
flat out vec2 flow_du;
+flat out float mean_diff;
uniform int width_patches;
uniform vec2 patch_size; // In 0..1 coordinates.
uniform vec2 patch_spacing; // In 0..1 coordinates.
uniform sampler2D flow_tex;
+uniform vec2 flow_size;
void main()
{
int patch_x = gl_InstanceID % width_patches;
int patch_y = gl_InstanceID / width_patches;
- // TODO: Lock the bottom left of the patch to an integer number of pixels?
+ // Convert the patch index to being the full 0..1 range, to match where
+ // the motion search puts the patches. We don't bother with the locking
+ // to texel centers, though.
+ vec2 patch_center = ivec2(patch_x, patch_y) / (flow_size - 1.0);
- image_pos = patch_spacing * ivec2(patch_x, patch_y) + patch_size * position;
+ // Increase the patch size a bit; since patch spacing is not necessarily
+ // an integer number of pixels, and we don't use conservative rasterization,
+ // we could be missing the outer edges of the patch. And it seemingly helps
+ // a little bit in general to have some more candidates as well -- although
+ // this is measured without variational refinement, so it might be moot
+ // with it.
+ //
+ // This maps [0.0,1.0] to [-0.25,1.25], ie. extends the patch by 25% in
+ // all directions.
+ vec2 grown_pos = (position * 1.5) - 0.25;
+
+ image_pos = patch_center + patch_size * (grown_pos - 0.5f);
// Find the flow value for this patch, and send it on to the fragment shader.
- flow_du = texelFetch(flow_tex, ivec2(patch_x, patch_y), 0).xy;
+ vec3 flow_du_and_mean_diff = texelFetch(flow_tex, ivec2(patch_x, patch_y), 0).xyz;
+ flow_du = flow_du_and_mean_diff.xy;
+ mean_diff = flow_du_and_mean_diff.z;
// The result of glOrtho(0.0, 1.0, 0.0, 1.0, 0.0, 1.0) is:
//