mirror of
https://github.com/hyprwm/wlroots-hyprland.git
synced 2024-11-22 21:05:58 +01:00
wlr_scene: Handle fractional scaling better
Try to alleviate scaling inaccuracies by implementing a fudge factor.
This commit is contained in:
parent
6d90518c97
commit
c2d2773df5
1 changed files with 26 additions and 4 deletions
|
@ -270,6 +270,14 @@ static uint32_t region_area(pixman_region32_t *region) {
|
||||||
return area;
|
return area;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void scale_output_damage(pixman_region32_t *damage, float scale) {
|
||||||
|
wlr_region_scale(damage, damage, scale);
|
||||||
|
|
||||||
|
if (floor(scale) != scale) {
|
||||||
|
wlr_region_expand(damage, damage, 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static void scene_damage_outputs(struct wlr_scene *scene, pixman_region32_t *damage) {
|
static void scene_damage_outputs(struct wlr_scene *scene, pixman_region32_t *damage) {
|
||||||
if (!pixman_region32_not_empty(damage)) {
|
if (!pixman_region32_not_empty(damage)) {
|
||||||
return;
|
return;
|
||||||
|
@ -282,8 +290,7 @@ static void scene_damage_outputs(struct wlr_scene *scene, pixman_region32_t *dam
|
||||||
pixman_region32_copy(&output_damage, damage);
|
pixman_region32_copy(&output_damage, damage);
|
||||||
pixman_region32_translate(&output_damage,
|
pixman_region32_translate(&output_damage,
|
||||||
-scene_output->x, -scene_output->y);
|
-scene_output->x, -scene_output->y);
|
||||||
wlr_region_scale(&output_damage, &output_damage,
|
scale_output_damage(&output_damage, scene_output->output->scale);
|
||||||
scene_output->output->scale);
|
|
||||||
if (wlr_damage_ring_add(&scene_output->damage_ring, &output_damage)) {
|
if (wlr_damage_ring_add(&scene_output->damage_ring, &output_damage)) {
|
||||||
wlr_output_schedule_frame(scene_output->output);
|
wlr_output_schedule_frame(scene_output->output);
|
||||||
}
|
}
|
||||||
|
@ -649,6 +656,11 @@ void wlr_scene_buffer_set_buffer_with_damage(struct wlr_scene_buffer *scene_buff
|
||||||
pixman_region32_intersect(&output_damage, &output_damage, &cull_region);
|
pixman_region32_intersect(&output_damage, &output_damage, &cull_region);
|
||||||
pixman_region32_fini(&cull_region);
|
pixman_region32_fini(&cull_region);
|
||||||
|
|
||||||
|
// if we are using fractional scaling add a 1px margin.
|
||||||
|
if (floor(output_scale) != output_scale) {
|
||||||
|
wlr_region_expand(&output_damage, &output_damage, 1);
|
||||||
|
}
|
||||||
|
|
||||||
pixman_region32_translate(&output_damage,
|
pixman_region32_translate(&output_damage,
|
||||||
(lx - scene_output->x) * output_scale,
|
(lx - scene_output->x) * output_scale,
|
||||||
(ly - scene_output->y) * output_scale);
|
(ly - scene_output->y) * output_scale);
|
||||||
|
@ -1055,7 +1067,7 @@ static void scene_node_render(struct wlr_scene_node *node,
|
||||||
pixman_region32_init(&render_region);
|
pixman_region32_init(&render_region);
|
||||||
pixman_region32_copy(&render_region, &node->visible);
|
pixman_region32_copy(&render_region, &node->visible);
|
||||||
pixman_region32_translate(&render_region, -scene_output->x, -scene_output->y);
|
pixman_region32_translate(&render_region, -scene_output->x, -scene_output->y);
|
||||||
wlr_region_scale(&render_region, &render_region, output->scale);
|
scale_output_damage(&render_region, output->scale);
|
||||||
pixman_region32_intersect(&render_region, &render_region, damage);
|
pixman_region32_intersect(&render_region, &render_region, damage);
|
||||||
if (!pixman_region32_not_empty(&render_region)) {
|
if (!pixman_region32_not_empty(&render_region)) {
|
||||||
pixman_region32_fini(&render_region);
|
pixman_region32_fini(&render_region);
|
||||||
|
@ -1534,6 +1546,8 @@ bool wlr_scene_output_commit(struct wlr_scene_output *scene_output) {
|
||||||
// scene nodes above. Those scene nodes will just render atop having us
|
// scene nodes above. Those scene nodes will just render atop having us
|
||||||
// never see the background.
|
// never see the background.
|
||||||
if (scene_output->scene->calculate_visibility) {
|
if (scene_output->scene->calculate_visibility) {
|
||||||
|
float output_scale = scene_output->output->scale;
|
||||||
|
|
||||||
for (int i = list_len - 1; i >= 0; i--) {
|
for (int i = list_len - 1; i >= 0; i--) {
|
||||||
struct wlr_scene_node *node = list_data[i];
|
struct wlr_scene_node *node = list_data[i];
|
||||||
int x, y;
|
int x, y;
|
||||||
|
@ -1550,10 +1564,18 @@ bool wlr_scene_output_commit(struct wlr_scene_output *scene_output) {
|
||||||
pixman_region32_intersect(&opaque, &opaque, &node->visible);
|
pixman_region32_intersect(&opaque, &opaque, &node->visible);
|
||||||
|
|
||||||
pixman_region32_translate(&opaque, -scene_output->x, -scene_output->y);
|
pixman_region32_translate(&opaque, -scene_output->x, -scene_output->y);
|
||||||
wlr_region_scale(&opaque, &opaque, scene_output->output->scale);
|
wlr_region_scale(&opaque, &opaque, output_scale);
|
||||||
pixman_region32_subtract(&background, &background, &opaque);
|
pixman_region32_subtract(&background, &background, &opaque);
|
||||||
pixman_region32_fini(&opaque);
|
pixman_region32_fini(&opaque);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (floor(output_scale) != output_scale) {
|
||||||
|
wlr_region_expand(&background, &background, 1);
|
||||||
|
|
||||||
|
// reintersect with the damage because we never want to render
|
||||||
|
// outside of the damage region
|
||||||
|
pixman_region32_intersect(&background, &background, &damage);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int nrects;
|
int nrects;
|
||||||
|
|
Loading…
Reference in a new issue