Spaces:
Sleeping
Sleeping
nahue-passano
commited on
Commit
•
ab70807
1
Parent(s):
358ef2a
update: new streamlit layout and fixed processing
Browse files- README.md +1 -1
- aira/__pycache__/__init__.cpython-38.pyc +0 -0
- aira/__pycache__/core.cpython-38.pyc +0 -0
- aira/core.py +13 -14
- aira/engine/__pycache__/__init__.cpython-38.pyc +0 -0
- aira/engine/__pycache__/filtering.cpython-38.pyc +0 -0
- aira/engine/__pycache__/input.cpython-38.pyc +0 -0
- aira/engine/__pycache__/intensity.cpython-38.pyc +0 -0
- aira/engine/__pycache__/plot.cpython-38.pyc +0 -0
- aira/engine/__pycache__/pressure.cpython-38.pyc +0 -0
- aira/engine/__pycache__/reflections.cpython-38.pyc +0 -0
- aira/engine/plot.py +2 -0
- aira/{gui.py → pyqt_gui.py} +82 -40
- app.py → aira/streamlit_app.py +42 -37
- aira/utils/__pycache__/__init__.cpython-38.pyc +0 -0
- aira/utils/__pycache__/formatter.cpython-38.pyc +0 -0
- aira/utils/__pycache__/utils.cpython-38.pyc +0 -0
README.md
CHANGED
@@ -5,7 +5,7 @@ colorFrom: indigo
|
|
5 |
colorTo: gray
|
6 |
sdk: streamlit
|
7 |
sdk_version: 1.21.0
|
8 |
-
app_file:
|
9 |
pinned: false
|
10 |
license: gpl-2.0
|
11 |
---
|
|
|
5 |
colorTo: gray
|
6 |
sdk: streamlit
|
7 |
sdk_version: 1.21.0
|
8 |
+
app_file: aira/streamlit_app.py
|
9 |
pinned: false
|
10 |
license: gpl-2.0
|
11 |
---
|
aira/__pycache__/__init__.cpython-38.pyc
CHANGED
Binary files a/aira/__pycache__/__init__.cpython-38.pyc and b/aira/__pycache__/__init__.cpython-38.pyc differ
|
|
aira/__pycache__/core.cpython-38.pyc
CHANGED
Binary files a/aira/__pycache__/core.cpython-38.pyc and b/aira/__pycache__/core.cpython-38.pyc differ
|
|
aira/core.py
CHANGED
@@ -16,27 +16,18 @@ from aira.engine.reflections import detect_reflections
|
|
16 |
from aira.utils import read_signals_dict, cartesian_to_spherical
|
17 |
|
18 |
|
19 |
-
INTEGRATION_TIME = 0.005
|
20 |
-
INTENSITY_THRESHOLD = -60
|
21 |
-
ANALYSIS_LENGTH = 1
|
22 |
-
|
23 |
-
|
24 |
@dataclass
|
25 |
class AmbisonicsImpulseResponseAnalyzer:
|
26 |
"""Main class for analyzing Ambisonics impulse responses"""
|
27 |
|
28 |
-
integration_time: float = INTEGRATION_TIME
|
29 |
-
intensity_threshold: float = INTENSITY_THRESHOLD
|
30 |
-
analysis_length: float = ANALYSIS_LENGTH
|
31 |
-
bformat_frequency_correction: bool = True
|
32 |
input_builder = InputProcessorChain()
|
33 |
|
34 |
def analyze(
|
35 |
self,
|
36 |
input_dict: dict,
|
37 |
-
integration_time: float
|
38 |
-
intensity_threshold: float
|
39 |
-
analysis_length: float
|
40 |
show: bool = False,
|
41 |
) -> go.Figure:
|
42 |
"""Analyzes a set of measurements in Ambisonics format and plots a hedgehog
|
@@ -150,7 +141,15 @@ if __name__ == "__main__":
|
|
150 |
# "channels_per_file": 4,
|
151 |
# "frequency_correction": False,
|
152 |
# }
|
153 |
-
|
|
|
|
|
154 |
analyzer = AmbisonicsImpulseResponseAnalyzer()
|
155 |
-
fig = analyzer.analyze(
|
|
|
|
|
|
|
|
|
|
|
|
|
156 |
analyzer.export_xy_projection(fig, "projection.png")
|
|
|
16 |
from aira.utils import read_signals_dict, cartesian_to_spherical
|
17 |
|
18 |
|
|
|
|
|
|
|
|
|
|
|
19 |
@dataclass
|
20 |
class AmbisonicsImpulseResponseAnalyzer:
|
21 |
"""Main class for analyzing Ambisonics impulse responses"""
|
22 |
|
|
|
|
|
|
|
|
|
23 |
input_builder = InputProcessorChain()
|
24 |
|
25 |
def analyze(
|
26 |
self,
|
27 |
input_dict: dict,
|
28 |
+
integration_time: float,
|
29 |
+
intensity_threshold: float,
|
30 |
+
analysis_length: float,
|
31 |
show: bool = False,
|
32 |
) -> go.Figure:
|
33 |
"""Analyzes a set of measurements in Ambisonics format and plots a hedgehog
|
|
|
141 |
# "channels_per_file": 4,
|
142 |
# "frequency_correction": False,
|
143 |
# }
|
144 |
+
integration_time = 0.01
|
145 |
+
intensity_threshold = -50
|
146 |
+
analysis_length = 0.3
|
147 |
analyzer = AmbisonicsImpulseResponseAnalyzer()
|
148 |
+
fig = analyzer.analyze(
|
149 |
+
input_dict=data,
|
150 |
+
integration_time=integration_time,
|
151 |
+
intensity_threshold=intensity_threshold,
|
152 |
+
analysis_length=analysis_length,
|
153 |
+
show=True,
|
154 |
+
)
|
155 |
analyzer.export_xy_projection(fig, "projection.png")
|
aira/engine/__pycache__/__init__.cpython-38.pyc
CHANGED
Binary files a/aira/engine/__pycache__/__init__.cpython-38.pyc and b/aira/engine/__pycache__/__init__.cpython-38.pyc differ
|
|
aira/engine/__pycache__/filtering.cpython-38.pyc
CHANGED
Binary files a/aira/engine/__pycache__/filtering.cpython-38.pyc and b/aira/engine/__pycache__/filtering.cpython-38.pyc differ
|
|
aira/engine/__pycache__/input.cpython-38.pyc
CHANGED
Binary files a/aira/engine/__pycache__/input.cpython-38.pyc and b/aira/engine/__pycache__/input.cpython-38.pyc differ
|
|
aira/engine/__pycache__/intensity.cpython-38.pyc
CHANGED
Binary files a/aira/engine/__pycache__/intensity.cpython-38.pyc and b/aira/engine/__pycache__/intensity.cpython-38.pyc differ
|
|
aira/engine/__pycache__/plot.cpython-38.pyc
CHANGED
Binary files a/aira/engine/__pycache__/plot.cpython-38.pyc and b/aira/engine/__pycache__/plot.cpython-38.pyc differ
|
|
aira/engine/__pycache__/pressure.cpython-38.pyc
CHANGED
Binary files a/aira/engine/__pycache__/pressure.cpython-38.pyc and b/aira/engine/__pycache__/pressure.cpython-38.pyc differ
|
|
aira/engine/__pycache__/reflections.cpython-38.pyc
CHANGED
Binary files a/aira/engine/__pycache__/reflections.cpython-38.pyc and b/aira/engine/__pycache__/reflections.cpython-38.pyc differ
|
|
aira/engine/plot.py
CHANGED
@@ -145,6 +145,7 @@ def setup_plotly_layout() -> go.Figure:
|
|
145 |
_type_
|
146 |
_description_
|
147 |
"""
|
|
|
148 |
fig = make_subplots(
|
149 |
rows=2,
|
150 |
cols=1,
|
@@ -152,6 +153,7 @@ def setup_plotly_layout() -> go.Figure:
|
|
152 |
vertical_spacing=0.05,
|
153 |
specs=[[{"type": "scene"}], [{"type": "xy"}]],
|
154 |
subplot_titles=("<b>Hedgehog</b>", "<b>Omnidirectional channel</b>"),
|
|
|
155 |
)
|
156 |
|
157 |
camera, buttons = get_plotly_scenes()
|
|
|
145 |
_type_
|
146 |
_description_
|
147 |
"""
|
148 |
+
initial_fig = go.Figure()
|
149 |
fig = make_subplots(
|
150 |
rows=2,
|
151 |
cols=1,
|
|
|
153 |
vertical_spacing=0.05,
|
154 |
specs=[[{"type": "scene"}], [{"type": "xy"}]],
|
155 |
subplot_titles=("<b>Hedgehog</b>", "<b>Omnidirectional channel</b>"),
|
156 |
+
figure=initial_fig,
|
157 |
)
|
158 |
|
159 |
camera, buttons = get_plotly_scenes()
|
aira/{gui.py → pyqt_gui.py}
RENAMED
@@ -12,26 +12,21 @@ from PyQt5 import QtCore, QtGui, QtWidgets, QtWebEngineWidgets
|
|
12 |
from PyQt5.QtWidgets import (
|
13 |
QLabel,
|
14 |
QFileDialog,
|
15 |
-
QMessageBox,
|
16 |
)
|
17 |
-
from PyQt5.QtGui import QPixmap
|
18 |
-
from PyQt5.QtCore import Qt
|
19 |
-
|
20 |
from pathlib import Path
|
21 |
|
22 |
from aira.core import AmbisonicsImpulseResponseAnalyzer
|
23 |
from aira.engine.input import InputMode
|
24 |
|
25 |
-
INTEGRATION_TIME = 0.01
|
26 |
-
|
27 |
-
analyzer = AmbisonicsImpulseResponseAnalyzer(integration_time=INTEGRATION_TIME)
|
28 |
-
|
29 |
|
30 |
class Ui_MainWindow(object):
|
31 |
def setupUi(self, MainWindow):
|
32 |
MainWindow.setObjectName("MainWindow")
|
33 |
MainWindow.resize(1350, 727)
|
34 |
-
MainWindow.setMinimumSize(QtCore.QSize(
|
35 |
MainWindow.setWindowIcon(QtGui.QIcon(str(Path("docs/images/aira-icon.png"))))
|
36 |
self.centralwidget = QtWidgets.QWidget(MainWindow)
|
37 |
self.centralwidget.setStyleSheet("background-color:#313438 ; ")
|
@@ -258,7 +253,6 @@ class Ui_MainWindow(object):
|
|
258 |
font.setPointSize(12)
|
259 |
self.rB_1ms.setFont(font)
|
260 |
self.rB_1ms.setObjectName("rB_1ms")
|
261 |
-
self.rB_1ms.setChecked(True)
|
262 |
self.verticalLayout_6.addWidget(self.rB_1ms)
|
263 |
self.rB_5ms = QtWidgets.QRadioButton(self.frame_analyze)
|
264 |
palette = QtGui.QPalette()
|
@@ -304,6 +298,7 @@ class Ui_MainWindow(object):
|
|
304 |
font.setPointSize(12)
|
305 |
self.rB_5ms.setFont(font)
|
306 |
self.rB_5ms.setObjectName("rB_5ms")
|
|
|
307 |
self.verticalLayout_6.addWidget(self.rB_5ms)
|
308 |
self.rB_10ms = QtWidgets.QRadioButton(self.frame_analyze)
|
309 |
palette = QtGui.QPalette()
|
@@ -427,7 +422,7 @@ class Ui_MainWindow(object):
|
|
427 |
self.label_analysis_length.setObjectName("label_analysis_length")
|
428 |
self.verticalLayout_6.addWidget(self.label_analysis_length)
|
429 |
self.lineEdit_aLength = QtWidgets.QLineEdit(self.frame_analyze)
|
430 |
-
self.lineEdit_aLength.setText("
|
431 |
font = QtGui.QFont()
|
432 |
font.setFamily("Lato")
|
433 |
font.setPointSize(10)
|
@@ -494,7 +489,7 @@ class Ui_MainWindow(object):
|
|
494 |
self.lineEdit_threshold.setStyleSheet(
|
495 |
"background-color: rgb(255, 255, 255);\n" "\n" ""
|
496 |
)
|
497 |
-
self.lineEdit_threshold.setText("60")
|
498 |
self.lineEdit_threshold.setObjectName("lineEdit_threshold")
|
499 |
self.verticalLayout_6.addWidget(self.lineEdit_threshold)
|
500 |
spacerItem5 = QtWidgets.QSpacerItem(
|
@@ -559,19 +554,9 @@ class Ui_MainWindow(object):
|
|
559 |
self.verticalLayout_8 = QtWidgets.QVBoxLayout(self.frame_hedgehog)
|
560 |
self.verticalLayout_8.setContentsMargins(0, 0, 0, 0)
|
561 |
self.verticalLayout_8.setObjectName("verticalLayout_8")
|
562 |
-
self.frame_hedgehog_label = QtWidgets.QFrame(self.frame_hedgehog)
|
563 |
-
self.frame_hedgehog_label.setMaximumSize(QtCore.QSize(16777215, 42))
|
564 |
-
self.frame_hedgehog_label.setFrameShape(QtWidgets.QFrame.StyledPanel)
|
565 |
-
self.frame_hedgehog_label.setFrameShadow(QtWidgets.QFrame.Raised)
|
566 |
-
self.frame_hedgehog_label.setObjectName("frame_hedgehog_label")
|
567 |
-
self.horizontalLayout_2 = QtWidgets.QHBoxLayout(self.frame_hedgehog_label)
|
568 |
-
self.horizontalLayout_2.setContentsMargins(0, 0, 0, 0)
|
569 |
-
self.horizontalLayout_2.setObjectName("horizontalLayout_2")
|
570 |
spacerItem11 = QtWidgets.QSpacerItem(
|
571 |
430, 20, QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Minimum
|
572 |
)
|
573 |
-
self.horizontalLayout_2.addItem(spacerItem11)
|
574 |
-
self.label_hedgehog = QtWidgets.QLabel(self.frame_hedgehog_label)
|
575 |
palette = QtGui.QPalette()
|
576 |
brush = QtGui.QBrush(QtGui.QColor(69, 113, 213))
|
577 |
brush.setStyle(QtCore.Qt.SolidPattern)
|
@@ -609,19 +594,12 @@ class Ui_MainWindow(object):
|
|
609 |
brush = QtGui.QBrush(QtGui.QColor(49, 52, 56))
|
610 |
brush.setStyle(QtCore.Qt.SolidPattern)
|
611 |
palette.setBrush(QtGui.QPalette.Disabled, QtGui.QPalette.Window, brush)
|
612 |
-
self.label_hedgehog.setPalette(palette)
|
613 |
font = QtGui.QFont()
|
614 |
font.setFamily("Lato")
|
615 |
font.setPointSize(15)
|
616 |
-
self.label_hedgehog.setFont(font)
|
617 |
-
self.label_hedgehog.setAlignment(QtCore.Qt.AlignCenter)
|
618 |
-
self.label_hedgehog.setObjectName("label_hedgehog")
|
619 |
-
self.horizontalLayout_2.addWidget(self.label_hedgehog)
|
620 |
spacerItem12 = QtWidgets.QSpacerItem(
|
621 |
429, 20, QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Minimum
|
622 |
)
|
623 |
-
self.horizontalLayout_2.addItem(spacerItem12)
|
624 |
-
self.verticalLayout_8.addWidget(self.frame_hedgehog_label)
|
625 |
self.frame_hedgehog_plot = QtWidgets.QFrame(self.frame_hedgehog)
|
626 |
self.frame_hedgehog_plot.setFrameShape(QtWidgets.QFrame.StyledPanel)
|
627 |
self.frame_hedgehog_plot.setFrameShadow(QtWidgets.QFrame.Raised)
|
@@ -646,6 +624,7 @@ class Ui_MainWindow(object):
|
|
646 |
self.verticalLayout_10.setObjectName("verticalLayout_10")
|
647 |
self.frame_plan_header = QtWidgets.QFrame(self.frame_tab_plan)
|
648 |
self.frame_plan_header.setMaximumSize(QtCore.QSize(16777215, 60))
|
|
|
649 |
self.frame_plan_header.setFrameShape(QtWidgets.QFrame.StyledPanel)
|
650 |
self.frame_plan_header.setFrameShadow(QtWidgets.QFrame.Raised)
|
651 |
self.frame_plan_header.setObjectName("frame_plan_header")
|
@@ -683,7 +662,6 @@ class Ui_MainWindow(object):
|
|
683 |
self.label_plan_view.setPixmap(
|
684 |
pixmap.scaled(750, 3000, aspectRatioMode=Qt.KeepAspectRatio)
|
685 |
)
|
686 |
-
# self.label_plan_view.addWidget(self.label_plan_view)
|
687 |
self.horizontalLayout_6.addWidget(self.label_plan_view)
|
688 |
self.horizontalLayout_5.addWidget(self.frame_plan_view)
|
689 |
self.verticalLayout_10.addWidget(self.frame_view)
|
@@ -812,7 +790,7 @@ class Ui_MainWindow(object):
|
|
812 |
|
813 |
# CONEXIONES DE GUI CON ACCIONES
|
814 |
|
815 |
-
#
|
816 |
self.path_1 = QLabel()
|
817 |
self.path_2 = QLabel()
|
818 |
self.path_3 = QLabel()
|
@@ -834,10 +812,11 @@ class Ui_MainWindow(object):
|
|
834 |
self.actionImport_Bformat_4channels.triggered.connect(
|
835 |
self.import_Bformat_4channels
|
836 |
)
|
837 |
-
|
838 |
self.pb_analyze.clicked.connect(self.analyze)
|
839 |
self.pB_load_plan.clicked.connect(self.load_plan)
|
840 |
self.pB_export_plan.clicked.connect(self.export_plan)
|
|
|
841 |
|
842 |
def retranslateUi(self, MainWindow):
|
843 |
_translate = QtCore.QCoreApplication.translate
|
@@ -855,7 +834,7 @@ class Ui_MainWindow(object):
|
|
855 |
)
|
856 |
self.label_threshold.setText(_translate("MainWindow", "Threshold [dB]"))
|
857 |
self.pb_analyze.setText(_translate("MainWindow", "Analyze"))
|
858 |
-
|
859 |
self.tabWidget.setTabText(
|
860 |
self.tabWidget.indexOf(self.tab_main), _translate("MainWindow", "Main")
|
861 |
)
|
@@ -950,7 +929,7 @@ class Ui_MainWindow(object):
|
|
950 |
"channel_Z": Z_path,
|
951 |
"input_mode": input_mode,
|
952 |
"channels_per_file": channels_per_file,
|
953 |
-
"frequency_correction":
|
954 |
}
|
955 |
else:
|
956 |
B4_path = self.path_1.text()
|
@@ -959,11 +938,31 @@ class Ui_MainWindow(object):
|
|
959 |
"stacked_signals": B4_path,
|
960 |
"input_mode": input_mode,
|
961 |
"channels_per_file": channels_per_file,
|
962 |
-
"frequency_correction":
|
963 |
}
|
964 |
|
965 |
-
|
966 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
967 |
|
968 |
def load_plan(self):
|
969 |
file_dialog = QFileDialog()
|
@@ -971,12 +970,52 @@ class Ui_MainWindow(object):
|
|
971 |
MainWindow, "Select image", "", "Image file (*.png *.jpg *.jpeg)"
|
972 |
)
|
973 |
if file_path:
|
974 |
-
|
975 |
-
self.
|
976 |
-
|
|
|
977 |
)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
978 |
self.enable_export()
|
979 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
980 |
def enable_export(self):
|
981 |
self.pB_export_plan.setEnabled(True)
|
982 |
self.pB_export_plan.setStyleSheet(
|
@@ -999,6 +1038,8 @@ class Ui_MainWindow(object):
|
|
999 |
save_path, _ = file_dialog.getSaveFileName(
|
1000 |
MainWindow, "Export image", "", "Image file (*.png *.jpg *.jpeg)"
|
1001 |
)
|
|
|
|
|
1002 |
|
1003 |
def import_Aformat_1channel(self):
|
1004 |
file_dialog = QFileDialog()
|
@@ -1090,6 +1131,7 @@ class Ui_MainWindow(object):
|
|
1090 |
save_path, _ = file_dialog.getSaveFileName(
|
1091 |
MainWindow, "Export image", "", "Image file (*.png *.jpg *.jpeg)"
|
1092 |
)
|
|
|
1093 |
|
1094 |
|
1095 |
if __name__ == "__main__":
|
|
|
12 |
from PyQt5.QtWidgets import (
|
13 |
QLabel,
|
14 |
QFileDialog,
|
|
|
15 |
)
|
16 |
+
from PyQt5.QtGui import QPixmap, QPainter, QImage
|
17 |
+
from PyQt5.QtCore import Qt, QPoint
|
18 |
+
|
19 |
from pathlib import Path
|
20 |
|
21 |
from aira.core import AmbisonicsImpulseResponseAnalyzer
|
22 |
from aira.engine.input import InputMode
|
23 |
|
|
|
|
|
|
|
|
|
24 |
|
25 |
class Ui_MainWindow(object):
|
26 |
def setupUi(self, MainWindow):
|
27 |
MainWindow.setObjectName("MainWindow")
|
28 |
MainWindow.resize(1350, 727)
|
29 |
+
MainWindow.setMinimumSize(QtCore.QSize(1200, 900))
|
30 |
MainWindow.setWindowIcon(QtGui.QIcon(str(Path("docs/images/aira-icon.png"))))
|
31 |
self.centralwidget = QtWidgets.QWidget(MainWindow)
|
32 |
self.centralwidget.setStyleSheet("background-color:#313438 ; ")
|
|
|
253 |
font.setPointSize(12)
|
254 |
self.rB_1ms.setFont(font)
|
255 |
self.rB_1ms.setObjectName("rB_1ms")
|
|
|
256 |
self.verticalLayout_6.addWidget(self.rB_1ms)
|
257 |
self.rB_5ms = QtWidgets.QRadioButton(self.frame_analyze)
|
258 |
palette = QtGui.QPalette()
|
|
|
298 |
font.setPointSize(12)
|
299 |
self.rB_5ms.setFont(font)
|
300 |
self.rB_5ms.setObjectName("rB_5ms")
|
301 |
+
self.rB_5ms.setChecked(True)
|
302 |
self.verticalLayout_6.addWidget(self.rB_5ms)
|
303 |
self.rB_10ms = QtWidgets.QRadioButton(self.frame_analyze)
|
304 |
palette = QtGui.QPalette()
|
|
|
422 |
self.label_analysis_length.setObjectName("label_analysis_length")
|
423 |
self.verticalLayout_6.addWidget(self.label_analysis_length)
|
424 |
self.lineEdit_aLength = QtWidgets.QLineEdit(self.frame_analyze)
|
425 |
+
self.lineEdit_aLength.setText("500")
|
426 |
font = QtGui.QFont()
|
427 |
font.setFamily("Lato")
|
428 |
font.setPointSize(10)
|
|
|
489 |
self.lineEdit_threshold.setStyleSheet(
|
490 |
"background-color: rgb(255, 255, 255);\n" "\n" ""
|
491 |
)
|
492 |
+
self.lineEdit_threshold.setText("-60")
|
493 |
self.lineEdit_threshold.setObjectName("lineEdit_threshold")
|
494 |
self.verticalLayout_6.addWidget(self.lineEdit_threshold)
|
495 |
spacerItem5 = QtWidgets.QSpacerItem(
|
|
|
554 |
self.verticalLayout_8 = QtWidgets.QVBoxLayout(self.frame_hedgehog)
|
555 |
self.verticalLayout_8.setContentsMargins(0, 0, 0, 0)
|
556 |
self.verticalLayout_8.setObjectName("verticalLayout_8")
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
557 |
spacerItem11 = QtWidgets.QSpacerItem(
|
558 |
430, 20, QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Minimum
|
559 |
)
|
|
|
|
|
560 |
palette = QtGui.QPalette()
|
561 |
brush = QtGui.QBrush(QtGui.QColor(69, 113, 213))
|
562 |
brush.setStyle(QtCore.Qt.SolidPattern)
|
|
|
594 |
brush = QtGui.QBrush(QtGui.QColor(49, 52, 56))
|
595 |
brush.setStyle(QtCore.Qt.SolidPattern)
|
596 |
palette.setBrush(QtGui.QPalette.Disabled, QtGui.QPalette.Window, brush)
|
|
|
597 |
font = QtGui.QFont()
|
598 |
font.setFamily("Lato")
|
599 |
font.setPointSize(15)
|
|
|
|
|
|
|
|
|
600 |
spacerItem12 = QtWidgets.QSpacerItem(
|
601 |
429, 20, QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Minimum
|
602 |
)
|
|
|
|
|
603 |
self.frame_hedgehog_plot = QtWidgets.QFrame(self.frame_hedgehog)
|
604 |
self.frame_hedgehog_plot.setFrameShape(QtWidgets.QFrame.StyledPanel)
|
605 |
self.frame_hedgehog_plot.setFrameShadow(QtWidgets.QFrame.Raised)
|
|
|
624 |
self.verticalLayout_10.setObjectName("verticalLayout_10")
|
625 |
self.frame_plan_header = QtWidgets.QFrame(self.frame_tab_plan)
|
626 |
self.frame_plan_header.setMaximumSize(QtCore.QSize(16777215, 60))
|
627 |
+
self.frame_plan_header.setMinimumSize(QtCore.QSize(0, 60))
|
628 |
self.frame_plan_header.setFrameShape(QtWidgets.QFrame.StyledPanel)
|
629 |
self.frame_plan_header.setFrameShadow(QtWidgets.QFrame.Raised)
|
630 |
self.frame_plan_header.setObjectName("frame_plan_header")
|
|
|
662 |
self.label_plan_view.setPixmap(
|
663 |
pixmap.scaled(750, 3000, aspectRatioMode=Qt.KeepAspectRatio)
|
664 |
)
|
|
|
665 |
self.horizontalLayout_6.addWidget(self.label_plan_view)
|
666 |
self.horizontalLayout_5.addWidget(self.frame_plan_view)
|
667 |
self.verticalLayout_10.addWidget(self.frame_view)
|
|
|
790 |
|
791 |
# CONEXIONES DE GUI CON ACCIONES
|
792 |
|
793 |
+
# Labels para guardar la data que devuelven las funciones de import triggereadas
|
794 |
self.path_1 = QLabel()
|
795 |
self.path_2 = QLabel()
|
796 |
self.path_3 = QLabel()
|
|
|
812 |
self.actionImport_Bformat_4channels.triggered.connect(
|
813 |
self.import_Bformat_4channels
|
814 |
)
|
815 |
+
self.actionExport_hedgehog_plot.triggered.connect(self.export_hedgehog)
|
816 |
self.pb_analyze.clicked.connect(self.analyze)
|
817 |
self.pB_load_plan.clicked.connect(self.load_plan)
|
818 |
self.pB_export_plan.clicked.connect(self.export_plan)
|
819 |
+
self.label_plan_view.mousePressEvent = lambda event: self.mousePressEvent(event)
|
820 |
|
821 |
def retranslateUi(self, MainWindow):
|
822 |
_translate = QtCore.QCoreApplication.translate
|
|
|
834 |
)
|
835 |
self.label_threshold.setText(_translate("MainWindow", "Threshold [dB]"))
|
836 |
self.pb_analyze.setText(_translate("MainWindow", "Analyze"))
|
837 |
+
|
838 |
self.tabWidget.setTabText(
|
839 |
self.tabWidget.indexOf(self.tab_main), _translate("MainWindow", "Main")
|
840 |
)
|
|
|
929 |
"channel_Z": Z_path,
|
930 |
"input_mode": input_mode,
|
931 |
"channels_per_file": channels_per_file,
|
932 |
+
"frequency_correction": False,
|
933 |
}
|
934 |
else:
|
935 |
B4_path = self.path_1.text()
|
|
|
938 |
"stacked_signals": B4_path,
|
939 |
"input_mode": input_mode,
|
940 |
"channels_per_file": channels_per_file,
|
941 |
+
"frequency_correction": False,
|
942 |
}
|
943 |
|
944 |
+
if self.rB_1ms.isChecked():
|
945 |
+
integration_time = 0.001
|
946 |
+
elif self.rB_5ms.isChecked():
|
947 |
+
integration_time = 0.005
|
948 |
+
else:
|
949 |
+
integration_time = 0.01
|
950 |
+
|
951 |
+
intensity_threshold = float(self.lineEdit_threshold.text())
|
952 |
+
analysis_length = float(self.lineEdit_aLength.text()) / 1000
|
953 |
+
|
954 |
+
analyzer = AmbisonicsImpulseResponseAnalyzer()
|
955 |
+
fig = analyzer.analyze(
|
956 |
+
input_dict=data,
|
957 |
+
integration_time=integration_time,
|
958 |
+
intensity_threshold=intensity_threshold,
|
959 |
+
analysis_length=analysis_length,
|
960 |
+
)
|
961 |
+
analyzer.export_xy_projection(fig, "projection.png")
|
962 |
+
fig.write_html("out.html")
|
963 |
+
url = QtCore.QUrl.fromLocalFile(str(Path("out.html").resolve()))
|
964 |
+
self.gV_hedgehog.load(url)
|
965 |
+
self.plotly_fig = fig
|
966 |
|
967 |
def load_plan(self):
|
968 |
file_dialog = QFileDialog()
|
|
|
970 |
MainWindow, "Select image", "", "Image file (*.png *.jpg *.jpeg)"
|
971 |
)
|
972 |
if file_path:
|
973 |
+
# Cargar la imagen base
|
974 |
+
self.base_image = QImage(file_path)
|
975 |
+
scaled_image = self.base_image.scaled(
|
976 |
+
1000, 800, Qt.AspectRatioMode.KeepAspectRatio
|
977 |
)
|
978 |
+
|
979 |
+
# Crear una imagen resultante del mismo tamaño que la imagen base
|
980 |
+
self.result_image = QImage(scaled_image.size(), QImage.Format_ARGB32)
|
981 |
+
self.result_image.fill(0) # Rellenar con transparencia
|
982 |
+
|
983 |
+
# Mostrar la imagen base en un QLabel
|
984 |
+
self.label_plan_view.setPixmap(QPixmap.fromImage(scaled_image))
|
985 |
+
|
986 |
+
# Ajustar el tamaño del QLabel al tamaño de la imagen base escalada
|
987 |
+
self.label_plan_view.resize(scaled_image.size())
|
988 |
+
|
989 |
self.enable_export()
|
990 |
|
991 |
+
def mousePressEvent(self, event):
|
992 |
+
if event.button() == Qt.LeftButton:
|
993 |
+
# Verificar si el clic ocurrió dentro de los límites de la imagen base
|
994 |
+
if (
|
995 |
+
event.x() < self.base_image.width()
|
996 |
+
and event.y() < self.base_image.height()
|
997 |
+
):
|
998 |
+
# Cargar la imagen superpuesta
|
999 |
+
overlay_image = QImage("projection.png")
|
1000 |
+
overlay_position = QPoint(event.x() - 787, event.y() - 350)
|
1001 |
+
|
1002 |
+
# Dibujar la imagen base en la imagen resultante
|
1003 |
+
painter = QPainter(self.result_image)
|
1004 |
+
painter.drawImage(
|
1005 |
+
0,
|
1006 |
+
0,
|
1007 |
+
self.base_image.scaled(
|
1008 |
+
1000, 800, Qt.AspectRatioMode.KeepAspectRatio
|
1009 |
+
),
|
1010 |
+
)
|
1011 |
+
|
1012 |
+
# Dibujar la imagen superpuesta en la imagen resultante
|
1013 |
+
painter.drawImage(overlay_position, overlay_image)
|
1014 |
+
painter.end()
|
1015 |
+
|
1016 |
+
# Mostrar la imagen resultante en el QLabel
|
1017 |
+
self.label_plan_view.setPixmap(QPixmap.fromImage(self.result_image))
|
1018 |
+
|
1019 |
def enable_export(self):
|
1020 |
self.pB_export_plan.setEnabled(True)
|
1021 |
self.pB_export_plan.setStyleSheet(
|
|
|
1038 |
save_path, _ = file_dialog.getSaveFileName(
|
1039 |
MainWindow, "Export image", "", "Image file (*.png *.jpg *.jpeg)"
|
1040 |
)
|
1041 |
+
if save_path:
|
1042 |
+
self.result_image.save(save_path)
|
1043 |
|
1044 |
def import_Aformat_1channel(self):
|
1045 |
file_dialog = QFileDialog()
|
|
|
1131 |
save_path, _ = file_dialog.getSaveFileName(
|
1132 |
MainWindow, "Export image", "", "Image file (*.png *.jpg *.jpeg)"
|
1133 |
)
|
1134 |
+
self.plotly_fig.write_image(save_path, "png", width=1366, height=768, scale=1.0)
|
1135 |
|
1136 |
|
1137 |
if __name__ == "__main__":
|
app.py → aira/streamlit_app.py
RENAMED
@@ -1,9 +1,9 @@
|
|
|
|
|
|
1 |
import streamlit as st
|
2 |
-
|
3 |
from aira.core import AmbisonicsImpulseResponseAnalyzer
|
4 |
from aira.engine.input import InputMode
|
5 |
-
import os
|
6 |
-
import tempfile
|
7 |
|
8 |
|
9 |
def save_temp_file(file):
|
@@ -23,14 +23,24 @@ def run_streamlit_app():
|
|
23 |
logo_path = "docs/images/aira-banner.png"
|
24 |
personal_logo_path = "docs/images/nahue-passano.png"
|
25 |
st.columns(11)[10].image(personal_logo_path, use_column_width=True)
|
26 |
-
st.columns(3)[1].image(logo_path, use_column_width=True)
|
27 |
|
28 |
# Audio loading and settings
|
29 |
|
30 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
31 |
|
32 |
with audio_files:
|
33 |
-
st.
|
34 |
up_files, down_files = st.columns(2)
|
35 |
|
36 |
with up_files:
|
@@ -45,37 +55,32 @@ def run_streamlit_app():
|
|
45 |
"Inverse filter", type=["mp3", "wav"]
|
46 |
)
|
47 |
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
63 |
-
|
64 |
-
|
65 |
-
|
66 |
-
|
67 |
-
|
68 |
-
|
69 |
-
|
70 |
-
|
71 |
-
)
|
72 |
-
|
73 |
-
|
74 |
-
st.plotly_chart(fig, use_container_width=True, height=1080)
|
75 |
-
|
76 |
-
# Generar un gráfico genérico con Plotly
|
77 |
-
fig = go.Figure(data=go.Scatter(x=[1, 2, 3, 4], y=[10, 5, 7, 2]))
|
78 |
-
st.plotly_chart(fig)
|
79 |
|
80 |
|
81 |
if __name__ == "__main__":
|
|
|
1 |
+
import os
|
2 |
+
import tempfile
|
3 |
import streamlit as st
|
4 |
+
|
5 |
from aira.core import AmbisonicsImpulseResponseAnalyzer
|
6 |
from aira.engine.input import InputMode
|
|
|
|
|
7 |
|
8 |
|
9 |
def save_temp_file(file):
|
|
|
23 |
logo_path = "docs/images/aira-banner.png"
|
24 |
personal_logo_path = "docs/images/nahue-passano.png"
|
25 |
st.columns(11)[10].image(personal_logo_path, use_column_width=True)
|
|
|
26 |
|
27 |
# Audio loading and settings
|
28 |
|
29 |
+
settings, audio_files = st.columns(2)
|
30 |
+
|
31 |
+
with settings:
|
32 |
+
st.image(logo_path, use_column_width=True)
|
33 |
+
st.subheader("⚙️ Settings")
|
34 |
+
col1, col2, col3 = st.columns(3)
|
35 |
+
with col1:
|
36 |
+
integration_time = st.selectbox("Integration time [ms]", [1, 5, 10])
|
37 |
+
with col2:
|
38 |
+
analysis_length = st.text_input("Analysis length [ms]", value="500")
|
39 |
+
with col3:
|
40 |
+
intensity_threshold = st.text_input("Intensity threshold [dB]", value=-60)
|
41 |
|
42 |
with audio_files:
|
43 |
+
st.subheader("🔉 LSS room responses in A-Format")
|
44 |
up_files, down_files = st.columns(2)
|
45 |
|
46 |
with up_files:
|
|
|
55 |
"Inverse filter", type=["mp3", "wav"]
|
56 |
)
|
57 |
|
58 |
+
# "Analyze" button
|
59 |
+
if st.button("Analyze", use_container_width=True):
|
60 |
+
data = {
|
61 |
+
"front_left_up": save_temp_file(audio_file_flu),
|
62 |
+
"front_right_down": save_temp_file(audio_file_frd),
|
63 |
+
"back_right_up": save_temp_file(audio_file_bru),
|
64 |
+
"back_left_down": save_temp_file(audio_file_bld),
|
65 |
+
"inverse_filter": save_temp_file(audio_file_inverse_filter),
|
66 |
+
"input_mode": InputMode.LSS,
|
67 |
+
"channels_per_file": 1,
|
68 |
+
"frequency_correction": True,
|
69 |
+
}
|
70 |
+
analyzer = AmbisonicsImpulseResponseAnalyzer()
|
71 |
+
fig = analyzer.analyze(
|
72 |
+
input_dict=data,
|
73 |
+
integration_time=float(integration_time) / 1000,
|
74 |
+
intensity_threshold=float(intensity_threshold),
|
75 |
+
analysis_length=float(analysis_length) / 1000,
|
76 |
+
show=False,
|
77 |
+
)
|
78 |
+
fig.update_layout(
|
79 |
+
height=1080,
|
80 |
+
paper_bgcolor="rgb(14,17,23)",
|
81 |
+
plot_bgcolor="rgb(14,17,23)",
|
82 |
+
)
|
83 |
+
st.plotly_chart(fig, use_container_width=True, height=1080)
|
|
|
|
|
|
|
|
|
|
|
84 |
|
85 |
|
86 |
if __name__ == "__main__":
|
aira/utils/__pycache__/__init__.cpython-38.pyc
CHANGED
Binary files a/aira/utils/__pycache__/__init__.cpython-38.pyc and b/aira/utils/__pycache__/__init__.cpython-38.pyc differ
|
|
aira/utils/__pycache__/formatter.cpython-38.pyc
CHANGED
Binary files a/aira/utils/__pycache__/formatter.cpython-38.pyc and b/aira/utils/__pycache__/formatter.cpython-38.pyc differ
|
|
aira/utils/__pycache__/utils.cpython-38.pyc
CHANGED
Binary files a/aira/utils/__pycache__/utils.cpython-38.pyc and b/aira/utils/__pycache__/utils.cpython-38.pyc differ
|
|