modusa 0.4.28__py3-none-any.whl → 0.4.30__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- modusa/__init__.py +9 -8
- modusa/tools/__init__.py +7 -2
- modusa/tools/ann_saver.py +30 -0
- modusa/tools/audio_recorder.py +0 -1
- modusa/tools/synth.py +2 -0
- modusa/tools/youtube_downloader.py +1 -4
- {modusa-0.4.28.dist-info → modusa-0.4.30.dist-info}/METADATA +2 -2
- modusa-0.4.30.dist-info/RECORD +21 -0
- pyproject.toml +2 -2
- modusa/config.py +0 -18
- modusa/decorators.py +0 -176
- modusa/devtools/generate_docs_source.py +0 -92
- modusa/devtools/generate_template.py +0 -144
- modusa/devtools/list_authors.py +0 -2
- modusa/devtools/list_plugins.py +0 -60
- modusa/devtools/main.py +0 -45
- modusa/devtools/templates/generator.py +0 -24
- modusa/devtools/templates/io.py +0 -24
- modusa/devtools/templates/model.py +0 -47
- modusa/devtools/templates/plugin.py +0 -41
- modusa/devtools/templates/test.py +0 -10
- modusa/devtools/templates/tool.py +0 -24
- modusa/generators/__init__.py +0 -13
- modusa/generators/audio.py +0 -188
- modusa/generators/audio_waveforms.py +0 -236
- modusa/generators/base.py +0 -29
- modusa/generators/ftds.py +0 -298
- modusa/generators/s1d.py +0 -270
- modusa/generators/s2d.py +0 -300
- modusa/generators/s_ax.py +0 -102
- modusa/generators/t_ax.py +0 -64
- modusa/generators/tds.py +0 -267
- modusa/models/__init__.py +0 -14
- modusa/models/audio.py +0 -90
- modusa/models/base.py +0 -70
- modusa/models/data.py +0 -457
- modusa/models/ftds.py +0 -584
- modusa/models/s1d.py +0 -578
- modusa/models/s2d.py +0 -619
- modusa/models/s_ax.py +0 -448
- modusa/models/t_ax.py +0 -335
- modusa/models/tds.py +0 -465
- modusa/plugins/__init__.py +0 -3
- modusa/plugins/base.py +0 -100
- modusa/tools/_plotter_old.py +0 -629
- modusa/tools/audio_saver.py +0 -30
- modusa/tools/base.py +0 -43
- modusa/tools/math_ops.py +0 -335
- modusa/utils/__init__.py +0 -1
- modusa/utils/config.py +0 -25
- modusa/utils/excp.py +0 -49
- modusa/utils/logger.py +0 -18
- modusa/utils/np_func_cat.py +0 -44
- modusa/utils/plot.py +0 -142
- modusa-0.4.28.dist-info/RECORD +0 -65
- {modusa-0.4.28.dist-info → modusa-0.4.30.dist-info}/WHEEL +0 -0
- {modusa-0.4.28.dist-info → modusa-0.4.30.dist-info}/entry_points.txt +0 -0
- {modusa-0.4.28.dist-info → modusa-0.4.30.dist-info}/licenses/LICENSE.md +0 -0
modusa/tools/math_ops.py
DELETED
@@ -1,335 +0,0 @@
|
|
1
|
-
#!/usr/bin/env python3
|
2
|
-
|
3
|
-
from modusa import excp
|
4
|
-
from modusa.tools.base import ModusaTool
|
5
|
-
from typing import Any
|
6
|
-
import numpy as np
|
7
|
-
|
8
|
-
class MathOps(ModusaTool):
|
9
|
-
"""
|
10
|
-
Performs arithmetic and NumPy-style ops.
|
11
|
-
|
12
|
-
Note
|
13
|
-
----
|
14
|
-
- Shape-changing operations like reshape, transpose, etc. are not yet supported. Use only element-wise or aggregation ops for now.
|
15
|
-
- Index alignment must be handled carefully in future extensions.
|
16
|
-
"""
|
17
|
-
|
18
|
-
def _axes_match(a1: tuple[np.ndarray, ...], a2: tuple[np.ndarray, ...]) -> bool:
|
19
|
-
"""
|
20
|
-
To check if two axes are same.
|
21
|
-
|
22
|
-
It checks the length of the axes and the corresponding values.
|
23
|
-
"""
|
24
|
-
if len(a1) != len(a2):
|
25
|
-
return False
|
26
|
-
return all(np.allclose(x, y, atol=1e-8) for x, y in zip(a1, a2))
|
27
|
-
|
28
|
-
|
29
|
-
#----------------------------------
|
30
|
-
# To handle basic element wise
|
31
|
-
# math operations like
|
32
|
-
# +, -, *, **, / ...
|
33
|
-
#----------------------------------
|
34
|
-
|
35
|
-
@staticmethod
|
36
|
-
def add(a: Any, b: Any) -> np.generic | np.ndarray:
|
37
|
-
try:
|
38
|
-
result = np.add(a, b)
|
39
|
-
except Exception as e:
|
40
|
-
raise excp.InputError(f"`a` and `b` can't be added") from e
|
41
|
-
|
42
|
-
if isinstance(a, str) and isinstance(b, str): # numpy actually concatenates, we do not want that
|
43
|
-
raise excp.InputError(f"`a` and `b` can't be added")
|
44
|
-
return result
|
45
|
-
|
46
|
-
@staticmethod
|
47
|
-
def subtract(a: Any, b: Any) -> np.generic | np.ndarray:
|
48
|
-
try:
|
49
|
-
result = np.subtract(a, b)
|
50
|
-
except Exception as e:
|
51
|
-
raise excp.InputError(f"`a` and `b` can't be subtracted") from e
|
52
|
-
return result
|
53
|
-
|
54
|
-
@staticmethod
|
55
|
-
def multiply(a: Any, b: Any) -> np.generic | np.ndarray:
|
56
|
-
try:
|
57
|
-
result = np.multiply(a, b)
|
58
|
-
except Exception as e:
|
59
|
-
raise excp.InputError(f"`a` and `b` can't be multiplied") from e
|
60
|
-
|
61
|
-
if isinstance(a, str) and isinstance(b, str): # numpy actually concatenates, we do not want that
|
62
|
-
raise excp.InputError(f"`a` and `b` can't be multiplied")
|
63
|
-
return result
|
64
|
-
|
65
|
-
@staticmethod
|
66
|
-
def divide(a: Any, b: Any) -> np.generic | np.ndarray:
|
67
|
-
try:
|
68
|
-
result = np.divide(a, b)
|
69
|
-
except Exception as e:
|
70
|
-
raise excp.InputError(f"`a` and `b` can't be divided") from e
|
71
|
-
return result
|
72
|
-
|
73
|
-
@staticmethod
|
74
|
-
def power(a: Any, b: Any) -> np.generic | np.ndarray:
|
75
|
-
try:
|
76
|
-
result = np.power(a, b)
|
77
|
-
except Exception as e:
|
78
|
-
raise excp.InputError(f"`a` can't be exponentiated with `b`") from e
|
79
|
-
return result
|
80
|
-
|
81
|
-
@staticmethod
|
82
|
-
def floor_divide(a: Any, b: Any) -> np.generic | np.ndarray:
|
83
|
-
try:
|
84
|
-
result = np.floor_divide(a, b)
|
85
|
-
except Exception as e:
|
86
|
-
raise excp.InputError(f"`a` can't be floor divided by `b`") from e
|
87
|
-
return result
|
88
|
-
|
89
|
-
#----------------------------------
|
90
|
-
# To handle numpy aggregator ops
|
91
|
-
#----------------------------------
|
92
|
-
@staticmethod
|
93
|
-
def mean(a: Any, axis: int | None = None) -> np.generic | np.ndarray:
|
94
|
-
try:
|
95
|
-
result = np.mean(a, axis=axis)
|
96
|
-
except Exception as e:
|
97
|
-
raise excp.InputError(f"can't find mean for `a`") from e
|
98
|
-
return result
|
99
|
-
|
100
|
-
@staticmethod
|
101
|
-
def std(a: Any, axis: int | None = None) -> np.generic | np.ndarray:
|
102
|
-
""""""
|
103
|
-
try:
|
104
|
-
result = np.std(a, axis=axis)
|
105
|
-
except Exception as e:
|
106
|
-
raise excp.InputError(f"can't find std for `a`") from e
|
107
|
-
return result
|
108
|
-
|
109
|
-
@staticmethod
|
110
|
-
def min(a: Any, axis: int | None = None) -> np.generic | np.ndarray:
|
111
|
-
try:
|
112
|
-
result = np.min(a, axis=axis)
|
113
|
-
except Exception as e:
|
114
|
-
raise excp.InputError(f"can't find min for `a`") from e
|
115
|
-
return result
|
116
|
-
|
117
|
-
@staticmethod
|
118
|
-
def max(a: Any, axis: int | None = None) -> np.generic | np.ndarray:
|
119
|
-
try:
|
120
|
-
result = np.max(a, axis=axis)
|
121
|
-
except Exception as e:
|
122
|
-
raise excp.InputError(f"can't find max for `a`") from e
|
123
|
-
return result
|
124
|
-
|
125
|
-
@staticmethod
|
126
|
-
def sum(a: Any, axis: int | None = None) -> np.generic | np.ndarray:
|
127
|
-
try:
|
128
|
-
result = np.sum(a, axis=axis)
|
129
|
-
except Exception as e:
|
130
|
-
raise excp.InputError(f"can't find sum for `a`") from e
|
131
|
-
return result
|
132
|
-
|
133
|
-
#----------------------------------
|
134
|
-
# To handle numpy ops where the
|
135
|
-
# shapes are unaltered
|
136
|
-
# sin, cos, exp, log, ...
|
137
|
-
#----------------------------------
|
138
|
-
|
139
|
-
@staticmethod
|
140
|
-
def sin(a: Any) -> np.generic | np.ndarray:
|
141
|
-
try:
|
142
|
-
result = np.sin(a)
|
143
|
-
except Exception as e:
|
144
|
-
raise excp.InputError(f"can't find sin for `a`") from e
|
145
|
-
return result
|
146
|
-
|
147
|
-
@staticmethod
|
148
|
-
def cos(a: Any) -> np.generic | np.ndarray:
|
149
|
-
try:
|
150
|
-
result = np.cos(a)
|
151
|
-
except Exception as e:
|
152
|
-
raise excp.InputError(f"can't find cos for `a`") from e
|
153
|
-
return result
|
154
|
-
|
155
|
-
@staticmethod
|
156
|
-
def tanh(a: Any) -> np.generic | np.ndarray:
|
157
|
-
try:
|
158
|
-
result = np.tanh(a)
|
159
|
-
except Exception as e:
|
160
|
-
raise excp.InputError(f"can't find tanh for `a`") from e
|
161
|
-
return result
|
162
|
-
|
163
|
-
@staticmethod
|
164
|
-
def exp(a: Any) -> np.generic | np.ndarray:
|
165
|
-
try:
|
166
|
-
result = np.exp(a)
|
167
|
-
except Exception as e:
|
168
|
-
raise excp.InputError(f"can't find exp for `a`") from e
|
169
|
-
return result
|
170
|
-
|
171
|
-
@staticmethod
|
172
|
-
def log(a: Any) -> np.generic | np.ndarray:
|
173
|
-
try:
|
174
|
-
result = np.log(a)
|
175
|
-
except Exception as e:
|
176
|
-
raise excp.InputError(f"can't find log for `a`") from e
|
177
|
-
return result
|
178
|
-
|
179
|
-
@staticmethod
|
180
|
-
def log10(a: Any) -> np.generic | np.ndarray:
|
181
|
-
try:
|
182
|
-
result = np.log10(a)
|
183
|
-
except Exception as e:
|
184
|
-
raise excp.InputError(f"can't find log10 for `a`") from e
|
185
|
-
return result
|
186
|
-
|
187
|
-
@staticmethod
|
188
|
-
def log2(a: Any) -> np.generic | np.ndarray:
|
189
|
-
try:
|
190
|
-
result = np.log2(a)
|
191
|
-
except Exception as e:
|
192
|
-
raise excp.InputError(f"can't find log2 for `a`") from e
|
193
|
-
return result
|
194
|
-
|
195
|
-
@staticmethod
|
196
|
-
def log1p(a: Any) -> np.generic | np.ndarray:
|
197
|
-
try:
|
198
|
-
result = np.log1p(a)
|
199
|
-
except Exception as e:
|
200
|
-
raise excp.InputError(f"can't find log1p for `a`") from e
|
201
|
-
return result
|
202
|
-
|
203
|
-
|
204
|
-
@staticmethod
|
205
|
-
def sqrt(a: Any) -> np.generic | np.ndarray:
|
206
|
-
try:
|
207
|
-
result = np.sqrt(a)
|
208
|
-
except Exception as e:
|
209
|
-
raise excp.InputError(f"can't find sqrt for `a`") from e
|
210
|
-
return result
|
211
|
-
|
212
|
-
@staticmethod
|
213
|
-
def abs(a: Any) -> np.generic | np.ndarray:
|
214
|
-
try:
|
215
|
-
result = np.abs(a)
|
216
|
-
except Exception as e:
|
217
|
-
raise excp.InputError(f"can't find abs for `a`") from e
|
218
|
-
return result
|
219
|
-
|
220
|
-
@staticmethod
|
221
|
-
def floor(a: Any) -> np.generic | np.ndarray:
|
222
|
-
try:
|
223
|
-
result = np.floor(a)
|
224
|
-
except Exception as e:
|
225
|
-
raise excp.InputError(f"can't find floor for `a`") from e
|
226
|
-
return result
|
227
|
-
|
228
|
-
@staticmethod
|
229
|
-
def ceil(a: Any) -> np.generic | np.ndarray:
|
230
|
-
try:
|
231
|
-
result = np.ceil(a)
|
232
|
-
except Exception as e:
|
233
|
-
raise excp.InputError(f"can't find ceil for `a`") from e
|
234
|
-
return result
|
235
|
-
|
236
|
-
@staticmethod
|
237
|
-
def round(a: Any) -> np.generic | np.ndarray:
|
238
|
-
try:
|
239
|
-
result = np.round(a)
|
240
|
-
except Exception as e:
|
241
|
-
raise excp.InputError(f"can't find round for `a`") from e
|
242
|
-
return result
|
243
|
-
|
244
|
-
#------------------------------------
|
245
|
-
# TODO: Add shape-changing ops like
|
246
|
-
# reshape, transpose, squeeze later
|
247
|
-
#------------------------------------
|
248
|
-
|
249
|
-
@staticmethod
|
250
|
-
def reshape(a: Any, shape: int | tuple[int, ...]) -> np.ndarray:
|
251
|
-
try:
|
252
|
-
result = np.reshape(a, shape=shape)
|
253
|
-
except Exception as e:
|
254
|
-
raise excp.InputError(f"can't reshape `a`") from e
|
255
|
-
return result
|
256
|
-
|
257
|
-
#------------------------------------
|
258
|
-
# Complex numbers operations
|
259
|
-
#------------------------------------
|
260
|
-
|
261
|
-
@staticmethod
|
262
|
-
def real(a: Any) -> np.ndarray:
|
263
|
-
try:
|
264
|
-
result = np.real(a)
|
265
|
-
except Exception as e:
|
266
|
-
raise excp.InputError(f"can't find real for `a`") from e
|
267
|
-
return result
|
268
|
-
|
269
|
-
@staticmethod
|
270
|
-
def imag(a: Any) -> np.ndarray:
|
271
|
-
try:
|
272
|
-
result = np.imag(a)
|
273
|
-
except Exception as e:
|
274
|
-
raise excp.InputError(f"can't find imag for `a`") from e
|
275
|
-
return result
|
276
|
-
|
277
|
-
@staticmethod
|
278
|
-
def angle(a: Any) -> np.ndarray:
|
279
|
-
try:
|
280
|
-
result = np.angle(a)
|
281
|
-
except Exception as e:
|
282
|
-
raise excp.InputError(f"can't find angle for `a`") from e
|
283
|
-
return result
|
284
|
-
|
285
|
-
#------------------------------------
|
286
|
-
# Comparison
|
287
|
-
#------------------------------------
|
288
|
-
|
289
|
-
@staticmethod
|
290
|
-
def lt(a: Any, b: Any) -> np.ndarray:
|
291
|
-
try:
|
292
|
-
mask = a < b
|
293
|
-
except Exception as e:
|
294
|
-
raise excp.InputError(f"`a` and `b` can't be compared") from e
|
295
|
-
return mask
|
296
|
-
|
297
|
-
@staticmethod
|
298
|
-
def le(a: Any, b: Any) -> np.ndarray:
|
299
|
-
try:
|
300
|
-
mask = a <= b
|
301
|
-
except Exception as e:
|
302
|
-
raise excp.InputError(f"`a` and `b` can't be compared") from e
|
303
|
-
return mask
|
304
|
-
|
305
|
-
@staticmethod
|
306
|
-
def gt(a: Any, b: Any) -> np.ndarray:
|
307
|
-
try:
|
308
|
-
mask = a > b
|
309
|
-
except Exception as e:
|
310
|
-
raise excp.InputError(f"`a` and `b` can't be compared") from e
|
311
|
-
return mask
|
312
|
-
|
313
|
-
@staticmethod
|
314
|
-
def ge(a: Any, b: Any) -> np.ndarray:
|
315
|
-
try:
|
316
|
-
mask = a >= b
|
317
|
-
except Exception as e:
|
318
|
-
raise excp.InputError(f"`a` and `b` can't be compared") from e
|
319
|
-
return mask
|
320
|
-
|
321
|
-
@staticmethod
|
322
|
-
def eq(a: Any, b: Any) -> np.ndarray:
|
323
|
-
try:
|
324
|
-
mask = a == b
|
325
|
-
except Exception as e:
|
326
|
-
raise excp.InputError(f"`a` and `b` can't be compared") from e
|
327
|
-
return mask
|
328
|
-
|
329
|
-
@staticmethod
|
330
|
-
def ne(a: Any, b: Any) -> np.ndarray:
|
331
|
-
try:
|
332
|
-
mask = a != b
|
333
|
-
except Exception as e:
|
334
|
-
raise excp.InputError(f"`a` and `b` can't be compared") from e
|
335
|
-
return mask
|
modusa/utils/__init__.py
DELETED
@@ -1 +0,0 @@
|
|
1
|
-
#!/usr/bin/env python3
|
modusa/utils/config.py
DELETED
@@ -1,25 +0,0 @@
|
|
1
|
-
#!/usr/bin/env python3
|
2
|
-
|
3
|
-
import logging
|
4
|
-
|
5
|
-
class PATHS:
|
6
|
-
from pathlib import Path
|
7
|
-
ROOT_DP: Path = Path(__file__).parents[2].resolve()
|
8
|
-
AUDIO_DP: Path = ROOT_DP / "data" / "audio"
|
9
|
-
EXAMPLE_AUDIO_FP: Path = AUDIO_DP / "Arko - Nazm Nazm.mp3"
|
10
|
-
LABELS_CSV_FP: Path = ROOT_DP / "data" / "label_data.csv"
|
11
|
-
REPORTS_DP: Path = ROOT_DP / "data" / "reports"
|
12
|
-
|
13
|
-
class DEFAULT_SETTINGS:
|
14
|
-
SR: int = 44100
|
15
|
-
LOG_LEVEL = logging.WARNING
|
16
|
-
|
17
|
-
class STFT:
|
18
|
-
N_FFT: int = 2048
|
19
|
-
WIN_SIZE: int = 2048
|
20
|
-
HOP_SIZE: int = 512
|
21
|
-
WINDOW: str = "hann"
|
22
|
-
|
23
|
-
class NOVELTY:
|
24
|
-
GAMMA: int = 10
|
25
|
-
LOCAL_AVG: int = 40
|
modusa/utils/excp.py
DELETED
@@ -1,49 +0,0 @@
|
|
1
|
-
#!/usr/bin/env python3
|
2
|
-
|
3
|
-
|
4
|
-
#----------------------------------------
|
5
|
-
# Base class errors
|
6
|
-
#----------------------------------------
|
7
|
-
class ModusaBaseError(Exception):
|
8
|
-
"""
|
9
|
-
Ultimate base class for any kind of custom errors.
|
10
|
-
"""
|
11
|
-
pass
|
12
|
-
|
13
|
-
class TypeError(ModusaBaseError):
|
14
|
-
pass
|
15
|
-
|
16
|
-
class InputError(ModusaBaseError):
|
17
|
-
"""
|
18
|
-
Any Input type error.
|
19
|
-
"""
|
20
|
-
|
21
|
-
class InputTypeError(ModusaBaseError):
|
22
|
-
"""
|
23
|
-
Any Input type error.
|
24
|
-
"""
|
25
|
-
|
26
|
-
class InputValueError(ModusaBaseError):
|
27
|
-
"""
|
28
|
-
Any Input type error.
|
29
|
-
"""
|
30
|
-
|
31
|
-
class OperationNotPossibleError(ModusaBaseError):
|
32
|
-
"""
|
33
|
-
Any errors if there is an operations
|
34
|
-
failure.
|
35
|
-
"""
|
36
|
-
|
37
|
-
class ImmutableAttributeError(ModusaBaseError):
|
38
|
-
"""Raised when attempting to modify an immutable attribute."""
|
39
|
-
pass
|
40
|
-
|
41
|
-
class FileNotFoundError(ModusaBaseError):
|
42
|
-
"""Raised when file does not exist."""
|
43
|
-
pass
|
44
|
-
|
45
|
-
class PluginInputError(ModusaBaseError):
|
46
|
-
pass
|
47
|
-
|
48
|
-
class PluginOutputError(ModusaBaseError):
|
49
|
-
pass
|
modusa/utils/logger.py
DELETED
@@ -1,18 +0,0 @@
|
|
1
|
-
#!/usr/bin/env python3
|
2
|
-
|
3
|
-
import logging
|
4
|
-
|
5
|
-
def setup_logging(log_level: int | None = logging.WARNING):
|
6
|
-
logging.basicConfig(
|
7
|
-
level=log_level,
|
8
|
-
format="%(asctime)s | %(levelname)s | %(name)s | %(funcName)s():%(lineno)d\n> %(message)s\n",
|
9
|
-
datefmt='%Y-%m-%d %H:%M:%S'
|
10
|
-
)
|
11
|
-
# Silence 3rd-party spam
|
12
|
-
logging.getLogger("matplotlib").setLevel(logging.WARNING)
|
13
|
-
logging.getLogger("PIL").setLevel(logging.WARNING)
|
14
|
-
logging.getLogger("numba").setLevel(logging.WARNING)
|
15
|
-
logging.getLogger("py").setLevel(logging.ERROR)
|
16
|
-
|
17
|
-
def get_logger(name=None):
|
18
|
-
return logging.getLogger(name)
|
modusa/utils/np_func_cat.py
DELETED
@@ -1,44 +0,0 @@
|
|
1
|
-
#!/usr/bin/env python3
|
2
|
-
|
3
|
-
# This contains categorised NumPy functions
|
4
|
-
# This is useful while handling np operations on modusa signals
|
5
|
-
|
6
|
-
import numpy as np
|
7
|
-
|
8
|
-
SHAPE_PRESERVING_FUNCS = {
|
9
|
-
np.sin, np.cos, np.tan,
|
10
|
-
np.sinh, np.cosh, np.tanh,
|
11
|
-
np.arcsin, np.arccos, np.arctan,
|
12
|
-
np.exp, np.expm1, np.log, np.log2, np.log10, np.log1p,
|
13
|
-
np.abs, np.negative, np.positive,
|
14
|
-
np.square, np.sqrt, np.cbrt,
|
15
|
-
np.floor, np.ceil, np.round, np.rint, np.trunc,
|
16
|
-
np.clip, np.sign,
|
17
|
-
np.add, np.subtract, np.multiply, np.true_divide, np.floor_divide
|
18
|
-
}
|
19
|
-
|
20
|
-
REDUCTION_FUNCS = {
|
21
|
-
np.sum, np.prod,
|
22
|
-
np.mean, np.std, np.var,
|
23
|
-
np.min, np.max,
|
24
|
-
np.argmin, np.argmax,
|
25
|
-
np.median, np.percentile,
|
26
|
-
np.all, np.any,
|
27
|
-
np.nanmean, np.nanstd, np.nanvar, np.nansum
|
28
|
-
}
|
29
|
-
|
30
|
-
CONCAT_FUNCS = {
|
31
|
-
np.concatenate, np.stack, np.hstack, np.vstack, np.dstack,
|
32
|
-
np.column_stack, np.row_stack
|
33
|
-
}
|
34
|
-
|
35
|
-
X_NEEDS_ADJUSTMENT_FUNCS = {
|
36
|
-
np.diff,
|
37
|
-
np.gradient,
|
38
|
-
np.trim_zeros,
|
39
|
-
np.unwrap,
|
40
|
-
np.fft.fft, np.fft.ifft, np.fft.fftshift, np.fft.ifftshift,
|
41
|
-
np.correlate, np.convolve
|
42
|
-
}
|
43
|
-
|
44
|
-
|
modusa/utils/plot.py
DELETED
@@ -1,142 +0,0 @@
|
|
1
|
-
#!/usr/bin/env python3
|
2
|
-
|
3
|
-
from modusa.models.s1d import S1D
|
4
|
-
from modusa.models.s2d import S2D
|
5
|
-
import matplotlib.pyplot as plt
|
6
|
-
import numpy as np
|
7
|
-
from collections import defaultdict
|
8
|
-
import itertools
|
9
|
-
|
10
|
-
def _in_notebook() -> bool:
|
11
|
-
"""
|
12
|
-
To check if we are in jupyter notebook environment.
|
13
|
-
"""
|
14
|
-
try:
|
15
|
-
from IPython import get_ipython
|
16
|
-
shell = get_ipython()
|
17
|
-
return shell and shell.__class__.__name__ == "ZMQInteractiveShell"
|
18
|
-
except ImportError:
|
19
|
-
return False
|
20
|
-
|
21
|
-
def plot_multiple_signals(
|
22
|
-
*args,
|
23
|
-
loc = None,
|
24
|
-
x_lim: tuple[float, float] | None = None,
|
25
|
-
highlight_regions: list[tuple[float, float, str]] | None = None,
|
26
|
-
vlines: list[float, ...] | None = None,
|
27
|
-
) -> plt.Figure:
|
28
|
-
"""
|
29
|
-
Plots multiple instances of uniform `Signal1D` and `Signal2D`
|
30
|
-
with proper formatting and time aligned.
|
31
|
-
|
32
|
-
Parameters
|
33
|
-
----------
|
34
|
-
loc: tuple[int]
|
35
|
-
- The len should match the number of signals sent as args.
|
36
|
-
- e.g. (0, 1, 1) => First plot at ax 0, second and third plot at ax 1
|
37
|
-
- Default: None => (0, 1, 2, ...) all plots on a new ax.
|
38
|
-
highlight_regions: list[tuple[float, float, str]]
|
39
|
-
-
|
40
|
-
|
41
|
-
"""
|
42
|
-
|
43
|
-
assert len(args) >= 1, "No signal provided to plot"
|
44
|
-
signals = args
|
45
|
-
|
46
|
-
for signal in signals:
|
47
|
-
if not isinstance(signal, (S1D, S2D)):
|
48
|
-
raise TypeError(f"Invalid signal type {type(signal)}")
|
49
|
-
|
50
|
-
if loc is None: # => We will plot all the signals on different subplots
|
51
|
-
loc = tuple([i for i in range(len(args))]) # Create (0, 1, 2, ...) that serves as ax number for plots
|
52
|
-
else: # Incase loc is provided, we make sure that we do it for each of the signals
|
53
|
-
assert len(args) == len(loc)
|
54
|
-
|
55
|
-
# Make sure that all the elements in loc do not miss any number in between (0, 1, 1, 2, 4) -> Not allowed
|
56
|
-
assert min(loc) == 0
|
57
|
-
max_loc = max(loc)
|
58
|
-
for i in range(max_loc):
|
59
|
-
if i not in loc:
|
60
|
-
raise ValueError(f"Invalid `loc` values, it should not have any missing integer in between.")
|
61
|
-
|
62
|
-
# Create a dict that maps subplot to signals that need to be plotted on that subplot e.g. {0: [signal1, signal3], ...}
|
63
|
-
subplot_signal_map = defaultdict(list)
|
64
|
-
for signal, i in zip(args, loc):
|
65
|
-
subplot_signal_map[i].append(signal)
|
66
|
-
|
67
|
-
# We need to create a figure with right configurations
|
68
|
-
height_ratios = []
|
69
|
-
height_1d_subplot = 0.4
|
70
|
-
height_2d_subplot = 1
|
71
|
-
n_1d_subplots = 0
|
72
|
-
n_2d_subplots = 0
|
73
|
-
for l, signals in subplot_signal_map.items():
|
74
|
-
|
75
|
-
# If there is any 2D signal, the subplot will be 2D
|
76
|
-
if any(isinstance(s, S2D) for s in signals):
|
77
|
-
n_2d_subplots += 1
|
78
|
-
height_ratios.append(height_2d_subplot)
|
79
|
-
|
80
|
-
# If all are 1D signal, the subplot will be 1D
|
81
|
-
elif all(isinstance(s, S1D) for s in signals):
|
82
|
-
n_1d_subplots += 1
|
83
|
-
height_ratios.append(height_1d_subplot)
|
84
|
-
|
85
|
-
|
86
|
-
n_subplots = n_1d_subplots + n_2d_subplots
|
87
|
-
fig_width = 15
|
88
|
-
fig_height = n_1d_subplots * 2 + n_2d_subplots * 4 # This is as per the figsize height set in the plotter tool
|
89
|
-
fig, axs = plt.subplots(n_subplots, 2, figsize=(fig_width, fig_height), width_ratios=[1, 0.01], height_ratios=height_ratios) # 2nd column for cbar
|
90
|
-
|
91
|
-
if n_subplots == 1:
|
92
|
-
axs = [axs] # axs becomes list of one pair [ (ax, cbar_ax) ]
|
93
|
-
|
94
|
-
# We find the x axis limits as per the max limit for all the signals combined, so that all the signals can be seen.
|
95
|
-
if x_lim is None:
|
96
|
-
x_min = min(np.min(signal.x.values) for signal in args)
|
97
|
-
x_max = max(np.max(signal.x.values) for signal in args)
|
98
|
-
x_lim = (x_min, x_max)
|
99
|
-
|
100
|
-
for l, signals in subplot_signal_map.items():
|
101
|
-
# Incase we have plot multiple signals in the same subplot, we change the color
|
102
|
-
fmt_cycle = itertools.cycle(['k-', 'r-', 'g-', 'b-', 'm-', 'c-', 'y-'])
|
103
|
-
|
104
|
-
# For each subplot, we want to know if it is 2D or 1D
|
105
|
-
if any(isinstance(s, S2D) for s in signals): is_1d_subplot = False
|
106
|
-
else: is_1d_subplot = True
|
107
|
-
|
108
|
-
if is_1d_subplot: # All the signals are 1D
|
109
|
-
for signal in signals:
|
110
|
-
fmt = next(fmt_cycle)
|
111
|
-
if len(signals) == 1: # highlight region works properly only if there is one signal for a subplot
|
112
|
-
signal.plot(axs[l][0], x_lim=x_lim, highlight_regions=highlight_regions, show_grid=True, vlines=vlines, fmt=fmt, legend=signal._title)
|
113
|
-
else:
|
114
|
-
y, x = signal._x._values, signal._y._values
|
115
|
-
signal.plot(axs[l][0], x_lim=x_lim, show_grid=True, vlines=vlines, fmt=fmt, legend=signal.title, y_label=signal.y.label, x_label=signal.x.label, title="")
|
116
|
-
|
117
|
-
# Remove the colorbar column (if the subplot is 1d)
|
118
|
-
axs[l][1].remove()
|
119
|
-
|
120
|
-
if not is_1d_subplot: # Atleast 1 signal is 2D, we we have a 2D subplot
|
121
|
-
for signal in signals:
|
122
|
-
if len(signals) == 1: # Only one 2D signal is to be plotted
|
123
|
-
signal.plot(axs[l][0], x_lim=x_lim, show_colorbar=True, cax=axs[l][1], highlight_regions=highlight_regions, vlines=vlines)
|
124
|
-
else:
|
125
|
-
if isinstance(signal, S1D):
|
126
|
-
fmt = next(fmt_cycle)
|
127
|
-
signal.plot(axs[l][0], x_lim=x_lim, show_grid=True, vlines=vlines, fmt=fmt, legend=signal.title, y_label=signal.y.label, x_label=signal.x.label, title="")
|
128
|
-
elif isinstance(signal, S2D):
|
129
|
-
signal.plot(axs[l][0], x_lim=x_lim, show_colorbar=True, cax=axs[l][1], vlines=vlines, x_label=signal.x.label, y_label=signal.y.label, title="")
|
130
|
-
|
131
|
-
# We set the xlim, this will align all the signals automatically as they are on the same row
|
132
|
-
for l in range(n_subplots):
|
133
|
-
axs[l][0].set_xlim(x_lim)
|
134
|
-
|
135
|
-
if _in_notebook():
|
136
|
-
plt.tight_layout()
|
137
|
-
plt.close(fig)
|
138
|
-
return fig
|
139
|
-
else:
|
140
|
-
plt.tight_layout()
|
141
|
-
plt.show()
|
142
|
-
return fig
|
modusa-0.4.28.dist-info/RECORD
DELETED
@@ -1,65 +0,0 @@
|
|
1
|
-
LICENSE.md,sha256=JTaXAjx5awk76VArKCx5dUW8vmLEWsL_ZlR7-umaHbA,1078
|
2
|
-
README.md,sha256=Ybe2rcDecfSCiUpec2n7btQvgyi4R9JG0bfdwSWijWk,981
|
3
|
-
modusa-0.4.28.dist-info/METADATA,sha256=SbjrOO2aDmiL4sber_0ROvDBgfc54nFeN11oa_Up76w,1442
|
4
|
-
modusa-0.4.28.dist-info/WHEEL,sha256=9P2ygRxDrTJz3gsagc0Z96ukrxjr-LFBGOgv3AuKlCA,90
|
5
|
-
modusa-0.4.28.dist-info/entry_points.txt,sha256=fmKpleVXj6CdaBVL14WoEy6xx7JQCs85jvzwTi3lePM,73
|
6
|
-
modusa-0.4.28.dist-info/licenses/LICENSE.md,sha256=JTaXAjx5awk76VArKCx5dUW8vmLEWsL_ZlR7-umaHbA,1078
|
7
|
-
modusa/__init__.py,sha256=m0Vh3SouHLacDwiiEV8oJ2ehpbETV8J6u-CqYAJws5E,359
|
8
|
-
modusa/config.py,sha256=bTqK4t00FZqERVITrxW_q284aDDJAa9aMSfFknfR-oU,280
|
9
|
-
modusa/decorators.py,sha256=8zeNX_wE37O6Vp0ysR4-WCZaEL8mq8dyCF_I5DHOzks,5905
|
10
|
-
modusa/devtools/generate_docs_source.py,sha256=UDflHsk-Yh9-3YJTVBzKL32y8hcxiRgAlFEBTMiDqwM,3301
|
11
|
-
modusa/devtools/generate_template.py,sha256=0sT_5-SjMLXyvePRDaIxr1RCz_9v6zFH9OoJqpuD2zI,5204
|
12
|
-
modusa/devtools/list_authors.py,sha256=FWBQKOLznVthvMYMASrx2Gw5lqKHEOccQpBisDZ53Dw,24
|
13
|
-
modusa/devtools/list_plugins.py,sha256=g-R5hoaCzHfClY_Sfa788IQ9CAKzQGTfyqmthXDZQqw,1729
|
14
|
-
modusa/devtools/main.py,sha256=zIB7x6km4RkV3A9P26NWpQberLn_3PWKbABxqAmzlzI,1993
|
15
|
-
modusa/devtools/templates/generator.py,sha256=ATEEgf0UtQ_eM_iA7colVBrlilIqViYC1CzNVUlXzRM,449
|
16
|
-
modusa/devtools/templates/io.py,sha256=yYU41zMpE204xRsqBxsRqLs3sH1LF6KgtJvzCNKNbhY,388
|
17
|
-
modusa/devtools/templates/model.py,sha256=iwmXadLMA4IAMgOEktdCWKZsceLgaaZkTWcJHqjQZzI,954
|
18
|
-
modusa/devtools/templates/plugin.py,sha256=MWqrxBxfRKVw2zjEgfAG0RYUAMjuazhqC5PXIb0gJi4,868
|
19
|
-
modusa/devtools/templates/test.py,sha256=CjZ_oqwJFhltNYzqfK1pcz1ShgeJXZLOnYpmOawfASs,244
|
20
|
-
modusa/devtools/templates/tool.py,sha256=2iQfHbFKtTELPvNoX42rHr9_5lXRrXpwxb9z5OL96Xc,435
|
21
|
-
modusa/fonts/NotoSansDevanagari-Regular.ttf,sha256=CEqU2J61Sq-5OgVuFUJcNP2Fn2NCh1Fl0wSDezvPwtI,221084
|
22
|
-
modusa/generators/__init__.py,sha256=xQUsOObRhTEPzdZsBGd4nT_9AWaL8uE_bisFAN_Wp9Q,236
|
23
|
-
modusa/generators/audio.py,sha256=91CnBDPZhagfJOx-cDoBBj3NrE92m70PmFmv7T8aQco,4477
|
24
|
-
modusa/generators/audio_waveforms.py,sha256=x-r4_kDi2xieQNBCo11qY2uk2bFcvzeNOppfJnj2oYs,6105
|
25
|
-
modusa/generators/base.py,sha256=Kd3eAYOU8PDE28hz0uXfnrmgYSK2lGgHcr5NqeExxbE,938
|
26
|
-
modusa/generators/ftds.py,sha256=BkELukm5zbDwUxQVoylrlT9irIUUB2ZGfBc5pH5LUDc,6704
|
27
|
-
modusa/generators/s1d.py,sha256=M05oU22qkuLd9ycTSoOyfDtC4w2DEBebRZ4VTkUJRQo,5756
|
28
|
-
modusa/generators/s2d.py,sha256=kU67dZj4tdIDSUFJeheXm_JKbyHpZZOGmW5jya6w0wo,6874
|
29
|
-
modusa/generators/s_ax.py,sha256=4CTFp_KwYnl4HDno-ATpTXOfKR9WEVOV45nwuk2OoVk,2221
|
30
|
-
modusa/generators/t_ax.py,sha256=X-XOJuGWw99dPAVsCVzNTfBFr81Vw56aZlGDmcl5q3k,1478
|
31
|
-
modusa/generators/tds.py,sha256=eGvzcjXyWaw5NVzM3D098r3xkoMcX8Ma9YoDUdL30Mo,5960
|
32
|
-
modusa/images/icon.png,sha256=UgGXlL4xjdIYxqO1en3iQfNN1BFsazxpT7NiPZSDu70,13321
|
33
|
-
modusa/models/__init__.py,sha256=G8sNOnBnTKqPmC4Z46ximBhc_pfBOF_G6AIfxT8DFzw,271
|
34
|
-
modusa/models/audio.py,sha256=IcNx3h8tb5Jt6KZug_TQKM5iufVk3i7Ug37iKG4gsJ0,2411
|
35
|
-
modusa/models/base.py,sha256=1qAXj69VsmrjGqShl5b27Jvt7OADHmPY0L9fBtpB_1E,1621
|
36
|
-
modusa/models/data.py,sha256=ds5zM0NOCwGImdxNdx27OnVpgKZ6kXUJMYBUqFWshXY,11368
|
37
|
-
modusa/models/ftds.py,sha256=5rd-3h1tzuy3OdD-pb66T0trPo77AvseZt3dy1zdZpg,16182
|
38
|
-
modusa/models/s1d.py,sha256=Hm2woUn9wcuwq1RYuEwlAWQPOLoRtnJoFD0mofW67mo,15550
|
39
|
-
modusa/models/s2d.py,sha256=10XXpZveFW6OY-v7O3xRy6xDNS5lzJi9UjJMqywyuYE,16782
|
40
|
-
modusa/models/s_ax.py,sha256=kKUOwZU9wV-w1ZJyOmdkcLMGtSOXA2gYzZ5f1FsHSEg,10793
|
41
|
-
modusa/models/t_ax.py,sha256=ZUhvZPUW1TkdZYuUd6Ucm-vsv0JqtZ9yEe3ab67Ma6w,8022
|
42
|
-
modusa/models/tds.py,sha256=FAGfibjyyE_lkEuQp-vSCuqQnopOjmy_IXqUjRlg9kc,11677
|
43
|
-
modusa/plugins/__init__.py,sha256=r1Bf5mnrVKRIwxboutY1iGzDy4EPQhqpk1kSW7iJj_Q,54
|
44
|
-
modusa/plugins/base.py,sha256=Bh_1Bja7fOymFsCgwhXDbV6ys3D8muNrPwrfDrG_G_A,2382
|
45
|
-
modusa/tools/__init__.py,sha256=YWbsQ40Pcu3Md2lNoKe4JnFtvpMGUVEwE92PoDkc6v4,371
|
46
|
-
modusa/tools/_plotter_old.py,sha256=KGow7mihA2H1WNq7s5bpivhCgGo2qVIeDaO6iabpsrg,19294
|
47
|
-
modusa/tools/ann_loader.py,sha256=m6Qu6jXnQ8LfUhKItoHSaHlGxUyzUJlGEyu4_50qJ8w,3099
|
48
|
-
modusa/tools/audio_converter.py,sha256=415qBoPm2sBIuBSI7m1XBKm0AbmVmPydIPPr-uO8D3c,1778
|
49
|
-
modusa/tools/audio_loader.py,sha256=xmeodrJqJV5j9-lrUPk3W9-bdEA4-6RvTAn8pIErUN0,4084
|
50
|
-
modusa/tools/audio_player.py,sha256=kyBUnodkOE9Ox-hKHkfPeGAQ1RPTddbZYXO1ezz6-9w,2494
|
51
|
-
modusa/tools/audio_recorder.py,sha256=K_LGqsPdjTdf3figEZTSQLmgMzYWgz18HTO8C1j5fE4,2788
|
52
|
-
modusa/tools/audio_saver.py,sha256=ldzfr_AydsHTnKbxmBLJblN-hLzTmOlppOm306xI4Ug,510
|
53
|
-
modusa/tools/base.py,sha256=C0ESJ0mIfjjRlAkRbSetNtMoOfS6IrHBjexRp3l_Mh4,1293
|
54
|
-
modusa/tools/math_ops.py,sha256=ZZ7U4DgqT7cOeE7_Lzi_Qq-48WYfwR9_osbZwTmE9eg,8690
|
55
|
-
modusa/tools/plotter.py,sha256=QfF8kCi79nS-J5lQyEuH_BbAmTo-PdfjDbnK9yTAmRE,30863
|
56
|
-
modusa/tools/synth.py,sha256=-oaCQbz21ZaleIxJ4uZP-c8b9Wjrwhi33STDKu9uLDg,1202
|
57
|
-
modusa/tools/youtube_downloader.py,sha256=hB_X8-7nOHXOlxg6vv3wyhBLoAsWyomrULP6_uCQL7s,1698
|
58
|
-
modusa/utils/__init__.py,sha256=1oLL20yLB1GL9IbFiZD8OReDqiCpFr-yetIR6x1cNkI,23
|
59
|
-
modusa/utils/config.py,sha256=cuGbqbovx5WDQq5rw3hIKcv3CnE5NttjacSOWnP1yu4,576
|
60
|
-
modusa/utils/excp.py,sha256=L9vhaGjKpv9viJYdmC9n5ndmk2GVbUBuFyZyhAQZmWY,906
|
61
|
-
modusa/utils/logger.py,sha256=K0rsnObeNKCxlNeSnVnJeRhgfmob6riB2uyU7h3dDmA,571
|
62
|
-
modusa/utils/np_func_cat.py,sha256=TyIFgRc6bARRMDnZxlVURO5Z0I-GWhxRONYyIv-Vwxs,1007
|
63
|
-
modusa/utils/plot.py,sha256=s_vNdxvKfwxEngvJPgrF1PcmxZNnNaaXPViHWjyjJ-c,5335
|
64
|
-
pyproject.toml,sha256=jsT7XGIUHSiP4RZosRROYMuLhngW6uHfTcwYtAgAZNw,1413
|
65
|
-
modusa-0.4.28.dist-info/RECORD,,
|
File without changes
|
File without changes
|
File without changes
|