|
37 | 37 | #include "shared-bindings/synthio/MidiTrack.h"
|
38 | 38 | #include "shared-bindings/synthio/Synthesizer.h"
|
39 | 39 |
|
| 40 | +#define default_attack_time (MICROPY_FLOAT_CONST(0.1)) |
| 41 | +#define default_decay_time (MICROPY_FLOAT_CONST(0.05)) |
| 42 | +#define default_release_time (MICROPY_FLOAT_CONST(0.2)) |
| 43 | +#define default_attack_level (MICROPY_FLOAT_CONST(1.)) |
| 44 | +#define default_sustain_level (MICROPY_FLOAT_CONST(0.8)) |
| 45 | + |
| 46 | +static const mp_arg_t envelope_properties[] = { |
| 47 | + { MP_QSTR_attack_time, MP_ARG_OBJ | MP_ARG_KW_ONLY, {.u_obj = MP_OBJ_NULL } }, |
| 48 | + { MP_QSTR_decay_time, MP_ARG_OBJ | MP_ARG_KW_ONLY, {.u_obj = MP_OBJ_NULL } }, |
| 49 | + { MP_QSTR_release_time, MP_ARG_OBJ | MP_ARG_KW_ONLY, {.u_obj = MP_OBJ_NULL } }, |
| 50 | + { MP_QSTR_attack_level, MP_ARG_OBJ | MP_ARG_KW_ONLY, {.u_obj = MP_OBJ_NULL } }, |
| 51 | + { MP_QSTR_sustain_level, MP_ARG_OBJ | MP_ARG_KW_ONLY, {.u_obj = MP_OBJ_NULL } }, |
| 52 | +}; |
| 53 | + |
40 | 54 | //| """Support for multi-channel audio synthesis
|
41 | 55 | //|
|
42 | 56 | //| At least 2 simultaneous notes are supported. samd5x, mimxrt10xx and rp2040 platforms support up to 12 notes.
|
|
46 | 60 | //| class Envelope:
|
47 | 61 | //| def __init__(
|
48 | 62 | //| self,
|
49 |
| -//| attack_time: float, |
50 |
| -//| decay_time: float, |
51 |
| -//| release_time: float, |
52 |
| -//| attack_level: float, |
53 |
| -//| sustain_level: float, |
| 63 | +//| *, |
| 64 | +//| attack_time: Optional[float] = 0.1, |
| 65 | +//| decay_time: Optional[float] = 0.05, |
| 66 | +//| release_time: Optional[float] = 0.2, |
| 67 | +//| attack_level: Optional[float] = 1.0, |
| 68 | +//| sustain_level: Optional[float] = 0.8, |
54 | 69 | //| ) -> None:
|
55 | 70 | //| """Construct an Envelope object
|
56 | 71 | //|
|
|
82 | 97 | //| """The relative level, in the range ``0.0`` to ``1.0`` of the volume of the sustain phase"""
|
83 | 98 | //|
|
84 | 99 |
|
85 |
| -STATIC mp_obj_t synthio_envelope_make_new(const mp_obj_type_t *type_in, size_t n_args, size_t n_kw, const mp_obj_t *args) { |
86 |
| - mp_obj_t new_obj = namedtuple_make_new(type_in, n_args, n_kw, args); |
87 |
| - mp_obj_t *fields; |
88 |
| - size_t len; |
89 |
| - mp_obj_tuple_get(new_obj, &len, &fields); |
| 100 | +STATIC mp_obj_t synthio_envelope_make_new(const mp_obj_type_t *type_in, size_t n_args, size_t n_kw, const mp_obj_t *all_args) { |
| 101 | + mp_arg_val_t args[MP_ARRAY_SIZE(envelope_properties)]; |
| 102 | + enum { ARG_attack_time, ARG_decay_time, ARG_release_time, ARG_attack_level, ARG_sustain_level }; |
| 103 | + mp_arg_parse_all_kw_array(n_args, n_kw, all_args, MP_ARRAY_SIZE(envelope_properties), envelope_properties, args); |
| 104 | + |
| 105 | + if (args[ARG_attack_time].u_obj == MP_OBJ_NULL) { |
| 106 | + args[ARG_attack_time].u_obj = mp_obj_new_float(default_attack_time); |
| 107 | + } |
| 108 | + if (args[ARG_decay_time].u_obj == MP_OBJ_NULL) { |
| 109 | + args[ARG_decay_time].u_obj = mp_obj_new_float(default_decay_time); |
| 110 | + } |
| 111 | + if (args[ARG_release_time].u_obj == MP_OBJ_NULL) { |
| 112 | + args[ARG_release_time].u_obj = mp_obj_new_float(default_release_time); |
| 113 | + } |
| 114 | + if (args[ARG_attack_level].u_obj == MP_OBJ_NULL) { |
| 115 | + args[ARG_attack_level].u_obj = mp_obj_new_float(default_attack_level); |
| 116 | + } |
| 117 | + if (args[ARG_sustain_level].u_obj == MP_OBJ_NULL) { |
| 118 | + args[ARG_sustain_level].u_obj = mp_obj_new_float(default_sustain_level); |
| 119 | + } |
90 | 120 |
|
91 |
| - mp_arg_validate_obj_float_non_negative(fields[0], 0., MP_QSTR_attack_time); |
92 |
| - mp_arg_validate_obj_float_non_negative(fields[1], 0., MP_QSTR_decay_time); |
93 |
| - mp_arg_validate_obj_float_non_negative(fields[2], 0., MP_QSTR_release_time); |
| 121 | + mp_arg_validate_obj_float_non_negative(args[ARG_attack_time].u_obj, 0., MP_QSTR_attack_time); |
| 122 | + mp_arg_validate_obj_float_non_negative(args[ARG_decay_time].u_obj, 0., MP_QSTR_decay_time); |
| 123 | + mp_arg_validate_obj_float_non_negative(args[ARG_release_time].u_obj, 0., MP_QSTR_release_time); |
94 | 124 |
|
95 |
| - mp_arg_validate_obj_float_range(fields[3], 0, 1, MP_QSTR_attack_level); |
96 |
| - mp_arg_validate_obj_float_range(fields[4], 0, 1, MP_QSTR_sustain_level); |
| 125 | + mp_arg_validate_obj_float_range(args[ARG_attack_level].u_obj, 0, 1, MP_QSTR_attack_level); |
| 126 | + mp_arg_validate_obj_float_range(args[ARG_sustain_level].u_obj, 0, 1, MP_QSTR_sustain_level); |
97 | 127 |
|
98 |
| - return new_obj; |
| 128 | + MP_STATIC_ASSERT(sizeof(mp_arg_val_t) == sizeof(mp_obj_t)); |
| 129 | + return namedtuple_make_new(type_in, MP_ARRAY_SIZE(args), 0, &args[0].u_obj); |
99 | 130 | };
|
100 | 131 |
|
101 | 132 | const mp_obj_namedtuple_type_t synthio_envelope_type_obj = {
|
|
0 commit comments