Skip to content

Vectorio Rectangle leaves behind graphical debris when moved #4478

@kmatch98

Description

@kmatch98

This was raised by user "cake" on the discord chat on 24 March 2021 at 1:43 pm central.

@WarriorOfWire your insights are appreciated on this one.

Firmware

Adafruit CircuitPython 6.2.0-beta.4-84-gc81007afb-dirty on 2021-03-24; Adafruit PyPortal with samd51j20

Code/REPL

import board
import displayio
import vectorio

import time

display = board.DISPLAY


rect_palette = displayio.Palette(color_count = 2)
rect_palette[0] = 0xffffff
rect_palette[1] = 0x00ff00
rect_palette.make_transparent(0)

HEIGHT = 40
WIDTH = 60
rectangle = vectorio.VectorShape(
    shape = vectorio.Rectangle(WIDTH, HEIGHT),
    pixel_shader = rect_palette,
    x = 120,
    y = 120
)


group = displayio.Group()
group.append(rectangle)


dx = 7
dy = 3

display.show(group)
count=0
while True:

    rectangle.x -= dy
    if rectangle.x < -WIDTH:
        rectangle.x += 240+WIDTH

    rectangle.y += dx
    if rectangle.y > 240:
        rectangle.y -= 240 + HEIGHT

    if count < 1:
        time.sleep(0.1)
    else:
        time.sleep(10000)
    count +=1

Behavior

Leaves behind extra lines when the rectangle is moved.

Description

It looks like an off-by-one error in the dirty-rectangle tracking. The dirty rectangle tracking is "exclusive" so whatever dirty rectangle must be larger than the rectangle pixel dimensions by +1 in both x and y.

I hacked the vectorio _get_screen_area and this solved the issue, but I'm unsure if it's the correct approach. The last two lines were added to expand the dirty rectangle.

static void _get_screen_area(vectorio_vector_shape_t *self, displayio_area_t *out_area) {
    VECTORIO_SHAPE_DEBUG("%p get_screen_area tform:{x:%d y:%d dx:%d dy:%d scl:%d w:%d h:%d mx:%d my:%d tr:%d}", self,
        self->absolute_transform->x, self->absolute_transform->y, self->absolute_transform->dx, self->absolute_transform->dy, self->absolute_transform->scale,
        self->absolute_transform->width, self->absolute_transform->height, self->absolute_transform->mirror_x, self->absolute_transform->mirror_y, self->absolute_transform->transpose_xy
        );
    self->ishape.get_area(self->ishape.shape, out_area);
    VECTORIO_SHAPE_DEBUG(" in:{(%5d,%5d), (%5d,%5d)}", out_area->x1, out_area->y1, out_area->x2, out_area->y2);
    if (self->absolute_transform->transpose_xy) {
        int16_t swap = out_area->x1;
        out_area->x1 = (out_area->y1 + self->y) * self->absolute_transform->dx + self->absolute_transform->x;
        out_area->y1 = (swap + self->x) * self->absolute_transform->dy + self->absolute_transform->y;
        swap = out_area->x2;
        out_area->x2 = (out_area->y2 + self->y) * self->absolute_transform->dx + self->absolute_transform->x;
        out_area->y2 = (swap + self->x) * self->absolute_transform->dy + self->absolute_transform->y;
    } else {
        out_area->x1 = (out_area->x1 + self->x) * self->absolute_transform->dx + self->absolute_transform->x;
        out_area->y1 = (out_area->y1 + self->y) * self->absolute_transform->dy + self->absolute_transform->y;
        out_area->x2 = (out_area->x2 + self->x) * self->absolute_transform->dx + self->absolute_transform->x;
        out_area->y2 = (out_area->y2 + self->y) * self->absolute_transform->dy + self->absolute_transform->y;
    }
    // We might have mirrored due to dx
    if (out_area->x2 < out_area->x1) {
        int16_t swap = out_area->x1;
        out_area->x1 = out_area->x2;
        out_area->x2 = swap;
    }
    if (out_area->y2 < out_area->y1) {
        int16_t swap = out_area->y1;
        out_area->y1 = out_area->y2;
        out_area->y2 = swap;
    }
    out_area->x2 = out_area->x2 + 1;
    out_area->y2 = out_area->y2 + 1;

    VECTORIO_SHAPE_DEBUG(" out:{(%5d,%5d), (%5d,%5d)}\n", out_area->x1, out_area->y1, out_area->x2, out_area->y2);
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions