|
30 | 30 | #include "shared-bindings/bleio/ScanEntry.h" |
31 | 31 | #include "shared-bindings/bleio/Scanner.h" |
32 | 32 |
|
33 | | -#define DEFAULT_INTERVAL 100 |
34 | | -#define DEFAULT_WINDOW 100 |
| 33 | +#define INTERVAL_DEFAULT (0.1f) |
| 34 | +#define INTERVAL_MIN (0.0025f) |
| 35 | +#define INTERVAL_MIN_STRING "0.0025" |
| 36 | +#define INTERVAL_MAX (40.959375f) |
| 37 | +#define INTERVAL_MAX_STRING "40.959375" |
| 38 | +#define WINDOW_DEFAULT (0.1f) |
35 | 39 |
|
36 | 40 | //| .. currentmodule:: bleio |
37 | 41 | //| |
|
45 | 49 | //| import bleio |
46 | 50 | //| scanner = bleio.Scanner() |
47 | 51 | //| entries = scanner.scan(2.5) # Scan for 2.5 seconds |
48 | | -//| print(entries) |
49 | 52 | //| |
50 | 53 |
|
51 | 54 | //| .. class:: Scanner() |
52 | 55 | //| |
53 | 56 | //| Create a new Scanner object. |
54 | 57 | //| |
| 58 | +STATIC mp_obj_t bleio_scanner_make_new(const mp_obj_type_t *type, size_t n_args, const mp_obj_t *all_args, mp_map_t *kw_args) { |
| 59 | + mp_arg_check_num(n_args, kw_args, 0, 0, false); |
55 | 60 |
|
56 | | -//| .. attribute:: interval |
57 | | -//| |
58 | | -//| The interval (in seconds) between the start of two consecutive scan windows. |
59 | | -//| Allowed values are between 0.010 and 10.24 sec. |
60 | | -//| |
| 61 | + bleio_scanner_obj_t *self = m_new_obj(bleio_scanner_obj_t); |
| 62 | + self->base.type = type; |
61 | 63 |
|
62 | | -//| .. attribute:: window |
63 | | -//| |
64 | | -//| The duration (in seconds) in which a single BLE channel is scanned. |
65 | | -//| Allowed values are between 0.010 and 10.24 sec. |
66 | | -//| |
| 64 | + return MP_OBJ_FROM_PTR(self); |
| 65 | +} |
67 | 66 |
|
68 | | -//| .. method:: scan(timeout) |
| 67 | +//| .. method:: scan(timeout, \*, interval=0.1, window=0.1) |
69 | 68 | //| |
70 | 69 | //| Performs a BLE scan. |
71 | 70 | //| |
72 | 71 | //| :param float timeout: the scan timeout in seconds |
| 72 | +//| :param float interval: the interval (in seconds) between the start of two consecutive scan windows |
| 73 | +//| Must be in the range 0.0025 - 40.959375 seconds. |
| 74 | +//| :param float window: the duration (in seconds) to scan a single BLE channel |
| 75 | +//| `window` must be <= `interval`. |
73 | 76 | //| :returns: advertising packets found |
74 | 77 | //| :rtype: list of :py:class:`bleio.ScanEntry` |
75 | 78 | //| |
76 | | -STATIC mp_obj_t bleio_scanner_make_new(const mp_obj_type_t *type, size_t n_args, const mp_obj_t *all_args, mp_map_t *kw_args) { |
77 | | - mp_arg_check_num(n_args, kw_args, 0, 0, false); |
78 | | - |
79 | | - |
80 | | - bleio_scanner_obj_t *self = m_new_obj(bleio_scanner_obj_t); |
81 | | - self->base.type = type; |
82 | | - |
83 | | - self->interval = DEFAULT_INTERVAL; |
84 | | - self->window = DEFAULT_WINDOW; |
85 | | - |
86 | | - return MP_OBJ_FROM_PTR(self); |
87 | | -} |
88 | | - |
89 | | -STATIC mp_obj_t bleio_scanner_get_interval(mp_obj_t self_in) { |
90 | | - bleio_scanner_obj_t *self = MP_OBJ_TO_PTR(self_in); |
91 | | - |
92 | | - return mp_obj_new_int(self->interval); |
93 | | -} |
94 | | -MP_DEFINE_CONST_FUN_OBJ_1(bleio_scanner_get_interval_obj, bleio_scanner_get_interval); |
95 | | - |
96 | | -static mp_obj_t bleio_scanner_set_interval(mp_obj_t self_in, mp_obj_t value) { |
97 | | - bleio_scanner_obj_t *self = MP_OBJ_TO_PTR(self_in); |
98 | | - |
99 | | - self->interval = mp_obj_get_int(value); |
100 | | - |
101 | | - return mp_const_none; |
102 | | -} |
103 | | -STATIC MP_DEFINE_CONST_FUN_OBJ_2(bleio_scanner_set_interval_obj, bleio_scanner_set_interval); |
104 | | - |
105 | | -const mp_obj_property_t bleio_scanner_interval_obj = { |
106 | | - .base.type = &mp_type_property, |
107 | | - .proxy = { (mp_obj_t)&bleio_scanner_get_interval_obj, |
108 | | - (mp_obj_t)&bleio_scanner_set_interval_obj, |
109 | | - (mp_obj_t)&mp_const_none_obj }, |
110 | | -}; |
111 | | - |
112 | | -STATIC mp_obj_t scanner_scan(mp_obj_t self_in, mp_obj_t timeout_in) { |
113 | | - bleio_scanner_obj_t *self = MP_OBJ_TO_PTR(self_in); |
114 | | - const mp_int_t timeout = mp_obj_get_int(timeout_in); |
| 79 | +STATIC mp_obj_t bleio_scanner_scan(size_t n_args, const mp_obj_t *pos_args, mp_map_t *kw_args) { |
| 80 | + enum { ARG_timeout, ARG_interval, ARG_window }; |
| 81 | + static const mp_arg_t allowed_args[] = { |
| 82 | + { MP_QSTR_timeout, MP_ARG_REQUIRED | MP_ARG_OBJ }, |
| 83 | + { MP_QSTR_interval, MP_ARG_KW_ONLY | MP_ARG_INT, {.u_obj = MP_OBJ_NULL} }, |
| 84 | + { MP_QSTR_window, MP_ARG_KW_ONLY | MP_ARG_INT, {.u_obj = MP_OBJ_NULL} }, |
| 85 | + }; |
| 86 | + |
| 87 | + bleio_scanner_obj_t *self = MP_OBJ_TO_PTR(pos_args[0]); |
| 88 | + mp_arg_val_t args[MP_ARRAY_SIZE(allowed_args)]; |
| 89 | + mp_arg_parse_all(n_args - 1, pos_args + 1, kw_args, MP_ARRAY_SIZE(allowed_args), allowed_args, args); |
| 90 | + |
| 91 | + const mp_float_t timeout = mp_obj_get_float(args[ARG_timeout].u_obj); |
| 92 | + |
| 93 | + if (args[ARG_interval].u_obj == MP_OBJ_NULL) { |
| 94 | + args[ARG_interval].u_obj = mp_obj_new_float(INTERVAL_DEFAULT); |
| 95 | + } |
| 96 | + |
| 97 | + if (args[ARG_window].u_obj == MP_OBJ_NULL) { |
| 98 | + args[ARG_window].u_obj = mp_obj_new_float(WINDOW_DEFAULT); |
| 99 | + } |
| 100 | + |
| 101 | + const mp_float_t interval = mp_obj_float_get(args[ARG_interval].u_obj); |
| 102 | + if (interval < INTERVAL_MIN || interval > INTERVAL_MAX) { |
| 103 | + mp_raise_ValueError_varg(translate("interval must be in range %s-%s"), INTERVAL_MIN_STRING, INTERVAL_MAX_STRING); |
| 104 | + } |
| 105 | + |
| 106 | + const mp_float_t window = mp_obj_float_get(args[ARG_window].u_obj); |
| 107 | + if (window > interval) { |
| 108 | + mp_raise_ValueError(translate("window must be <= interval")); |
| 109 | + } |
115 | 110 |
|
116 | 111 | self->adv_reports = mp_obj_new_list(0, NULL); |
117 | 112 |
|
118 | | - common_hal_bleio_scanner_scan(self, timeout); |
| 113 | + common_hal_bleio_scanner_scan(self, timeout, interval, window); |
119 | 114 |
|
120 | 115 | return self->adv_reports; |
121 | 116 | } |
122 | | -STATIC MP_DEFINE_CONST_FUN_OBJ_2(bleio_scanner_scan_obj, scanner_scan); |
123 | | - |
124 | | -STATIC mp_obj_t bleio_scanner_get_window(mp_obj_t self_in) { |
125 | | - bleio_scanner_obj_t *self = MP_OBJ_TO_PTR(self_in); |
126 | | - |
127 | | - return mp_obj_new_int(self->window); |
128 | | -} |
129 | | -MP_DEFINE_CONST_FUN_OBJ_1(bleio_scanner_get_window_obj, bleio_scanner_get_window); |
130 | | - |
131 | | -static mp_obj_t bleio_scanner_set_window(mp_obj_t self_in, mp_obj_t value) { |
132 | | - bleio_scanner_obj_t *self = MP_OBJ_TO_PTR(self_in); |
| 117 | +STATIC MP_DEFINE_CONST_FUN_OBJ_KW(bleio_scanner_scan_obj, 2, bleio_scanner_scan); |
133 | 118 |
|
134 | | - self->window = mp_obj_get_int(value); |
135 | | - |
136 | | - return mp_const_none; |
137 | | -} |
138 | | -STATIC MP_DEFINE_CONST_FUN_OBJ_2(bleio_scanner_set_window_obj, bleio_scanner_set_window); |
139 | | - |
140 | | -const mp_obj_property_t bleio_scanner_window_obj = { |
141 | | - .base.type = &mp_type_property, |
142 | | - .proxy = { (mp_obj_t)&bleio_scanner_get_window_obj, |
143 | | - (mp_obj_t)&bleio_scanner_set_window_obj, |
144 | | - (mp_obj_t)&mp_const_none_obj }, |
145 | | -}; |
146 | 119 |
|
147 | 120 | STATIC const mp_rom_map_elem_t bleio_scanner_locals_dict_table[] = { |
148 | | - { MP_ROM_QSTR(MP_QSTR_interval), MP_ROM_PTR(&bleio_scanner_interval_obj) }, |
149 | 121 | { MP_ROM_QSTR(MP_QSTR_scan), MP_ROM_PTR(&bleio_scanner_scan_obj) }, |
150 | | - { MP_ROM_QSTR(MP_QSTR_window), MP_ROM_PTR(&bleio_scanner_window_obj) }, |
151 | 122 | }; |
152 | 123 |
|
153 | 124 | STATIC MP_DEFINE_CONST_DICT(bleio_scanner_locals_dict, bleio_scanner_locals_dict_table); |
154 | 125 |
|
155 | 126 | const mp_obj_type_t bleio_scanner_type = { |
156 | 127 | { &mp_type_type }, |
157 | 128 | .name = MP_QSTR_Scanner, |
158 | | - .print = bleio_scanner_print, |
159 | 129 | .make_new = bleio_scanner_make_new, |
160 | 130 | .locals_dict = (mp_obj_dict_t*)&bleio_scanner_locals_dict |
161 | 131 | }; |
0 commit comments