PicoVector: Improve transform handling.

* Store a reference to transform, so `set_transform(Transform())` is not GC'd until it is replaced
* Transformations return the transform, allowing chaining: `transform.rotate().scale().translate()`
* A new `get_transform` method for getting the currently set transform.
pull/1019/head
Phil Howard 2025-02-27 16:22:19 +00:00
rodzic a2b91340e2
commit fbe2851eaf
3 zmienionych plików z 27 dodań i 15 usunięć

Wyświetl plik

@ -96,6 +96,7 @@ static MP_DEFINE_CONST_FUN_OBJ_2(VECTOR_set_font_align_obj, VECTOR_set_font_alig
static MP_DEFINE_CONST_FUN_OBJ_2(VECTOR_set_antialiasing_obj, VECTOR_set_antialiasing);
static MP_DEFINE_CONST_FUN_OBJ_2(VECTOR_set_transform_obj, VECTOR_set_transform);
static MP_DEFINE_CONST_FUN_OBJ_2(VECTOR_set_clip_obj, VECTOR_set_clip);
static MP_DEFINE_CONST_FUN_OBJ_1(VECTOR_get_transform_obj, VECTOR_get_transform);
static MP_DEFINE_CONST_FUN_OBJ_2(VECTOR_draw_obj, VECTOR_draw);
@ -112,6 +113,7 @@ static const mp_rom_map_elem_t VECTOR_locals_dict_table[] = {
{ MP_ROM_QSTR(MP_QSTR_set_antialiasing), MP_ROM_PTR(&VECTOR_set_antialiasing_obj) },
{ MP_ROM_QSTR(MP_QSTR_set_transform), MP_ROM_PTR(&VECTOR_set_transform_obj) },
{ MP_ROM_QSTR(MP_QSTR_set_clip), MP_ROM_PTR(&VECTOR_set_clip_obj) },
{ MP_ROM_QSTR(MP_QSTR_get_transform), MP_ROM_PTR(&VECTOR_get_transform_obj) },
{ MP_ROM_QSTR(MP_QSTR_draw), MP_ROM_PTR(&VECTOR_draw_obj) },
};

Wyświetl plik

@ -23,16 +23,17 @@ typedef struct _ModPicoGraphics_obj_t {
bool blocking = true;
} ModPicoGraphics_obj_t;
typedef struct _VECTOR_obj_t {
mp_obj_base_t base;
PicoVector *vector;
} _VECTOR_obj_t;
typedef struct _TRANSFORM_obj_t {
mp_obj_base_t base;
pp_mat3_t transform;
} _TRANSFORM_obj_t;
typedef struct _VECTOR_obj_t {
mp_obj_base_t base;
PicoVector *vector;
_TRANSFORM_obj_t *transform;
} _VECTOR_obj_t;
typedef struct _POLY_obj_t {
mp_obj_base_t base;
pp_poly_t *poly;
@ -566,7 +567,7 @@ mp_obj_t TRANSFORM_custom(mp_obj_t self_in, mp_obj_t custom_in) {
pp_mat3_mul(&transform->transform, &t);
return mp_const_none;
return transform;
}
mp_obj_t TRANSFORM_rotate(mp_obj_t self_in, mp_obj_t angle_in, mp_obj_t origin_in) {
@ -589,7 +590,7 @@ mp_obj_t TRANSFORM_rotate(mp_obj_t self_in, mp_obj_t angle_in, mp_obj_t origin_i
pp_mat3_rotate(&transform->transform, angle);
}
return mp_const_none;
return transform;
}
mp_obj_t TRANSFORM_translate(mp_obj_t self_in, mp_obj_t x_in, mp_obj_t y_in) {
@ -600,7 +601,7 @@ mp_obj_t TRANSFORM_translate(mp_obj_t self_in, mp_obj_t x_in, mp_obj_t y_in) {
pp_mat3_translate(&transform->transform, o_x, o_y);
return mp_const_none;
return transform;
}
mp_obj_t TRANSFORM_scale(mp_obj_t self_in, mp_obj_t x_in, mp_obj_t y_in) {
@ -611,7 +612,7 @@ mp_obj_t TRANSFORM_scale(mp_obj_t self_in, mp_obj_t x_in, mp_obj_t y_in) {
pp_mat3_scale(&transform->transform, o_x, o_y);
return mp_const_none;
return transform;
}
mp_obj_t TRANSFORM_reset(mp_obj_t self_in) {
@ -645,22 +646,30 @@ mp_obj_t VECTOR_make_new(const mp_obj_type_t *type, size_t n_args, size_t n_kw,
mp_obj_t VECTOR_set_transform(mp_obj_t self_in, mp_obj_t transform_in) {
_VECTOR_obj_t *self = MP_OBJ_TO_PTR2(self_in, _VECTOR_obj_t);
(void)self;
if(transform_in == mp_const_none) {
pp_mat3_t* old = pp_transform(NULL);
(void)old; // TODO: Return old transform?
pp_transform(NULL);
self->transform = NULL;
} else if MP_OBJ_IS_TYPE(transform_in, &TRANSFORM_type) {
_TRANSFORM_obj_t *transform = (_TRANSFORM_obj_t *)MP_OBJ_TO_PTR(transform_in);
pp_mat3_t* old = pp_transform(&transform->transform);
(void)old;
pp_transform(&transform->transform);
// Store a reference to the transform so `set_transform(Transform())`
// doesn't break when GC runs.
self->transform = transform;
} else {
// TODO: ValueError?
mp_raise_ValueError("Must set a valid transform or None.");
}
return mp_const_none;
}
mp_obj_t VECTOR_get_transform(mp_obj_t self_in) {
_VECTOR_obj_t *self = MP_OBJ_TO_PTR2(self_in, _VECTOR_obj_t);
return self->transform ? self->transform : mp_const_none;
}
mp_obj_t VECTOR_set_font(mp_obj_t self_in, mp_obj_t font, mp_obj_t size) {
_VECTOR_obj_t *self = MP_OBJ_TO_PTR2(self_in, _VECTOR_obj_t);

Wyświetl plik

@ -47,6 +47,7 @@ extern mp_obj_t VECTOR_set_font_align(mp_obj_t self_in, mp_obj_t align);
extern mp_obj_t VECTOR_set_antialiasing(mp_obj_t self_in, mp_obj_t aa);
extern mp_obj_t VECTOR_set_transform(mp_obj_t self_in, mp_obj_t transform_in);
extern mp_obj_t VECTOR_set_clip(mp_obj_t self_in, mp_obj_t clip_in);
extern mp_obj_t VECTOR_get_transform(mp_obj_t self_in);
extern mp_obj_t VECTOR_draw(mp_obj_t self_in, mp_obj_t poly_in);
extern mp_obj_t VECTOR_rotate(size_t n_args, const mp_obj_t *pos_args, mp_map_t *kw_args);