mirror of https://gitlab.com/pamhyr/pamhyr2
Compare commits
4 Commits
44a8be6be3
...
14549330b9
| Author | SHA1 | Date |
|---|---|---|
|
|
14549330b9 | |
|
|
2487bec6d6 | |
|
|
4e1acfecdc | |
|
|
c63c776989 |
|
|
@ -29,8 +29,133 @@ from Model.Results.River.River import River
|
||||||
logger = logging.getLogger()
|
logger = logging.getLogger()
|
||||||
|
|
||||||
|
|
||||||
|
class AdditionalData(SQLSubModel):
|
||||||
|
_sub_classes = []
|
||||||
|
|
||||||
|
def __init__(self, id=-1, study=None, data=None):
|
||||||
|
super(AdditionalData, self).__init__(
|
||||||
|
id=id, status=study.status,
|
||||||
|
owner_scenario=study.status.scenario.id
|
||||||
|
)
|
||||||
|
|
||||||
|
self._study = study
|
||||||
|
self._data = data
|
||||||
|
|
||||||
|
@property
|
||||||
|
def data(self):
|
||||||
|
return self._data
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def _db_create(cls, execute, ext=""):
|
||||||
|
execute(f"""
|
||||||
|
CREATE TABLE results_add_data{ext} (
|
||||||
|
{cls.create_db_add_pamhyr_id()},
|
||||||
|
result INTEGER NOT NULL,
|
||||||
|
type_x TEXT NOT NULL,
|
||||||
|
type_y TEXT NOT NULL,
|
||||||
|
legend TEXT NOT NULL,
|
||||||
|
unit TEXT NOT NULL,
|
||||||
|
data_len INTEGER NOT NULL,
|
||||||
|
x BLOB NOT NULL,
|
||||||
|
y BLOB NOT NULL,
|
||||||
|
{Scenario.create_db_add_scenario()},
|
||||||
|
{Scenario.create_db_add_scenario_fk()},
|
||||||
|
FOREIGN KEY(result) REFERENCES results(pamhyr_id),
|
||||||
|
PRIMARY KEY(pamhyr_id, result, scenario)
|
||||||
|
)
|
||||||
|
""")
|
||||||
|
|
||||||
|
if ext != "":
|
||||||
|
return True
|
||||||
|
|
||||||
|
return cls._create_submodel(execute)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def _db_update(cls, execute, version, data=None):
|
||||||
|
major, minor, release = version.strip().split(".")
|
||||||
|
|
||||||
|
if major == "0" and int(minor) == 2 and int(release) <= 1:
|
||||||
|
cls._db_create(execute)
|
||||||
|
|
||||||
|
return cls._update_submodel(execute, version, data)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def _db_load(cls, execute, data=None):
|
||||||
|
new = []
|
||||||
|
|
||||||
|
study = data['study']
|
||||||
|
status = data['status']
|
||||||
|
scenario = data["scenario"]
|
||||||
|
|
||||||
|
table = execute(
|
||||||
|
"SELECT pamhyr_id, type_x, type_y, " +
|
||||||
|
"legend, unit, data_len, x, y, " +
|
||||||
|
"scenario " +
|
||||||
|
"FROM results_add_data " +
|
||||||
|
f"WHERE scenario = {scenario.id}"
|
||||||
|
)
|
||||||
|
|
||||||
|
if table is None:
|
||||||
|
return new
|
||||||
|
|
||||||
|
for v in table:
|
||||||
|
it = iter(v)
|
||||||
|
|
||||||
|
pid = next(it)
|
||||||
|
type_x = next(it)
|
||||||
|
type_y = next(it)
|
||||||
|
legend = next(it)
|
||||||
|
unit = next(it)
|
||||||
|
data_len = next(it)
|
||||||
|
bx = next(it)
|
||||||
|
by = next(it)
|
||||||
|
owner_scenario = next(it)
|
||||||
|
|
||||||
|
data_format = ">" + ''.join(itertools.repeat("d", data_len))
|
||||||
|
x = struct.unpack(data_format, bx)
|
||||||
|
y = struct.unpack(data_format, by)
|
||||||
|
|
||||||
|
data = {
|
||||||
|
'type_x': tmp_dict[data_type[2]],
|
||||||
|
'type_y': tmp_dict[data_type[0]],
|
||||||
|
'legend': legend,
|
||||||
|
'unit': tmp_unit[data_type[0]],
|
||||||
|
'x': x, 'y': y
|
||||||
|
}
|
||||||
|
|
||||||
|
new_results = cls(study=study)
|
||||||
|
new.append(new_results)
|
||||||
|
|
||||||
|
return new
|
||||||
|
|
||||||
|
def _db_save(self, execute, data=None):
|
||||||
|
if self._status.scenario.id != self._owner_scenario:
|
||||||
|
return
|
||||||
|
|
||||||
|
pid = self._pamhyr_id
|
||||||
|
data_len = len(self._data["x"])
|
||||||
|
|
||||||
|
data_format = ">" + ''.join(itertools.repeat("d", data_len))
|
||||||
|
bx = struct.pack(data_format, *self._data["x"])
|
||||||
|
by = struct.pack(data_format, *self._data["y"])
|
||||||
|
|
||||||
|
execute(
|
||||||
|
"INSERT INTO " +
|
||||||
|
"results_add_data (pamhyr_id, result, " +
|
||||||
|
"type_x, type_y, " +
|
||||||
|
"legend, unit, data_len, x, y, " +
|
||||||
|
"scenario) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
|
||||||
|
self._pamhyr_id, data["result"],
|
||||||
|
self._data["type_x"], self._data["type_y"],
|
||||||
|
self._data["legend"], self._data["unit"],
|
||||||
|
data_len, bx, by, self._owner_scenario
|
||||||
|
)
|
||||||
|
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
class Results(SQLSubModel):
|
class Results(SQLSubModel):
|
||||||
_sub_classes = [River]
|
_sub_classes = [River, AdditionalData]
|
||||||
|
|
||||||
def __init__(self, id=-1, study=None, solver=None,
|
def __init__(self, id=-1, study=None, solver=None,
|
||||||
repertory="", name="0"):
|
repertory="", name="0"):
|
||||||
|
|
@ -50,6 +175,7 @@ class Results(SQLSubModel):
|
||||||
# Keep results creation date
|
# Keep results creation date
|
||||||
"creation_date": datetime.now(),
|
"creation_date": datetime.now(),
|
||||||
"study_revision": study.status.version,
|
"study_revision": study.status.version,
|
||||||
|
"additional_data": [],
|
||||||
}
|
}
|
||||||
|
|
||||||
if solver is not None:
|
if solver is not None:
|
||||||
|
|
@ -206,6 +332,11 @@ class Results(SQLSubModel):
|
||||||
f"WHERE scenario = {self._owner_scenario} " +
|
f"WHERE scenario = {self._owner_scenario} " +
|
||||||
f"AND result = {pid}"
|
f"AND result = {pid}"
|
||||||
)
|
)
|
||||||
|
execute(
|
||||||
|
"DELETE FROM results_add_data " +
|
||||||
|
f"WHERE scenario = {self._owner_scenario} " +
|
||||||
|
f"AND result = {pid}"
|
||||||
|
)
|
||||||
|
|
||||||
def _db_save(self, execute, data=None):
|
def _db_save(self, execute, data=None):
|
||||||
if self._status.scenario.id != self._owner_scenario:
|
if self._status.scenario.id != self._owner_scenario:
|
||||||
|
|
@ -238,4 +369,7 @@ class Results(SQLSubModel):
|
||||||
data["result"] = self._pamhyr_id
|
data["result"] = self._pamhyr_id
|
||||||
self._river._db_save(execute, data)
|
self._river._db_save(execute, data)
|
||||||
|
|
||||||
|
for add_data in self.get("additional_data"):
|
||||||
|
add_data._db_save(execute, data)
|
||||||
|
|
||||||
return True
|
return True
|
||||||
|
|
|
||||||
|
|
@ -37,7 +37,7 @@ logger = logging.getLogger()
|
||||||
|
|
||||||
|
|
||||||
class Study(SQLModel):
|
class Study(SQLModel):
|
||||||
_version = "0.2.1"
|
_version = "0.2.2"
|
||||||
|
|
||||||
_sub_classes = [
|
_sub_classes = [
|
||||||
Scenario,
|
Scenario,
|
||||||
|
|
|
||||||
|
|
@ -1569,10 +1569,12 @@ class ApplicationWindow(QMainWindow, ListedSubWindow, WindowToolKit):
|
||||||
|
|
||||||
# No results available
|
# No results available
|
||||||
if results is None:
|
if results is None:
|
||||||
|
self.msg_open_results_no_results()
|
||||||
return
|
return
|
||||||
|
|
||||||
# results does not have values, for example if geometry missmatch
|
# results does not have values, for example if geometry missmatch
|
||||||
if not results.is_valid:
|
if not results.is_valid:
|
||||||
|
self.msg_open_results_invalid_results()
|
||||||
return
|
return
|
||||||
|
|
||||||
if results.get('study_revision') != self._study.status.version:
|
if results.get('study_revision') != self._study.status.version:
|
||||||
|
|
@ -1598,6 +1600,20 @@ class ApplicationWindow(QMainWindow, ListedSubWindow, WindowToolKit):
|
||||||
)
|
)
|
||||||
res.show()
|
res.show()
|
||||||
|
|
||||||
|
def msg_open_results_no_results(self):
|
||||||
|
self.message_box(
|
||||||
|
window_title=self._trad["Warning"],
|
||||||
|
text=self._trad["mb_open_results_title"],
|
||||||
|
informative_text=self._trad["mb_open_results_no_results_msg"]
|
||||||
|
)
|
||||||
|
|
||||||
|
def msg_open_results_invalid_results(self):
|
||||||
|
self.message_box(
|
||||||
|
window_title=self._trad["Error"],
|
||||||
|
text=self._trad["mb_open_results_title"],
|
||||||
|
informative_text=self._trad["mb_open_results_invalid_results_msg"]
|
||||||
|
)
|
||||||
|
|
||||||
def open_solver_results_adists(self, solver, results=None):
|
def open_solver_results_adists(self, solver, results=None):
|
||||||
def reading_fn():
|
def reading_fn():
|
||||||
self._tmp_results = results
|
self._tmp_results = results
|
||||||
|
|
|
||||||
|
|
@ -59,6 +59,8 @@ from PyQt5.QtWidgets import (
|
||||||
QSlider, QLabel, QWidget, QGridLayout, QTabBar, QInputDialog
|
QSlider, QLabel, QWidget, QGridLayout, QTabBar, QInputDialog
|
||||||
)
|
)
|
||||||
|
|
||||||
|
from Model.Results.Results import AdditionalData
|
||||||
|
|
||||||
from View.Tools.Plot.PamhyrCanvas import MplCanvas
|
from View.Tools.Plot.PamhyrCanvas import MplCanvas
|
||||||
from View.Tools.Plot.PamhyrToolbar import PamhyrPlotToolbar
|
from View.Tools.Plot.PamhyrToolbar import PamhyrPlotToolbar
|
||||||
|
|
||||||
|
|
@ -1231,7 +1233,6 @@ class ResultsWindow(PamhyrWindow):
|
||||||
return
|
return
|
||||||
|
|
||||||
def import_data(self):
|
def import_data(self):
|
||||||
|
|
||||||
file_types = [
|
file_types = [
|
||||||
self._trad["file_csv"],
|
self._trad["file_csv"],
|
||||||
self._trad["file_all"],
|
self._trad["file_all"],
|
||||||
|
|
@ -1248,29 +1249,50 @@ class ResultsWindow(PamhyrWindow):
|
||||||
if filename == "":
|
if filename == "":
|
||||||
return
|
return
|
||||||
|
|
||||||
sep = " "
|
x, y = self.read_csv_file_data(filename)
|
||||||
|
data = self.read_csv_file_format(x, y)
|
||||||
|
|
||||||
def is_float(string):
|
results = self._results[self._current_results[0]]
|
||||||
if string.replace(".", "").isnumeric():
|
data_lst = results.get("additional_data")
|
||||||
return True
|
data_lst.append(
|
||||||
else:
|
AdditionalData(
|
||||||
return False
|
study=self._study,
|
||||||
|
data=data
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
self.update_plot_additional_data()
|
||||||
|
|
||||||
|
def read_csv_file_data(self, filename):
|
||||||
|
sep = ","
|
||||||
|
x = []
|
||||||
|
y = []
|
||||||
|
|
||||||
with open(filename, 'r', newline='') as f:
|
with open(filename, 'r', newline='') as f:
|
||||||
lines = f.readlines()
|
lines = f.readlines()
|
||||||
x = []
|
|
||||||
y = []
|
|
||||||
for line in lines:
|
for line in lines:
|
||||||
if line[0] != "*" and line[0] != "#" and line[0] != "$":
|
if line[0] != "*" and line[0] != "#" and line[0] != "$":
|
||||||
row = line.split(sep)
|
row = line.split(sep)
|
||||||
if len(row) >= 2:
|
|
||||||
if is_float(row[0]) and is_float(row[1]):
|
|
||||||
x.append(float(row[0]))
|
|
||||||
y.append(float(row[1]))
|
|
||||||
|
|
||||||
|
if len(row) < 2:
|
||||||
|
continue
|
||||||
|
|
||||||
|
try:
|
||||||
|
fx, fy = float(row[0]), float(row[1])
|
||||||
|
x.append(fx)
|
||||||
|
y.append(fy)
|
||||||
|
except Exception as e:
|
||||||
|
continue
|
||||||
|
|
||||||
|
return x, y
|
||||||
|
|
||||||
|
def read_csv_file_format(self, x, y):
|
||||||
data_type_lst = ['Q(t)', 'Z(t)', 'Z(x)']
|
data_type_lst = ['Q(t)', 'Z(t)', 'Z(x)']
|
||||||
data_type, ok = QInputDialog.getItem(
|
data_type, ok = QInputDialog.getItem(
|
||||||
self, 'Data type', 'Chose the type of data:', data_type_lst)
|
self, 'Data type',
|
||||||
|
'Chose the type of data:',
|
||||||
|
data_type_lst
|
||||||
|
)
|
||||||
|
|
||||||
if not ok:
|
if not ok:
|
||||||
return
|
return
|
||||||
|
|
@ -1291,25 +1313,45 @@ class ResultsWindow(PamhyrWindow):
|
||||||
tmp_unit = {'Z': ' (m)',
|
tmp_unit = {'Z': ' (m)',
|
||||||
'Q': ' (m³/s)'}
|
'Q': ' (m³/s)'}
|
||||||
|
|
||||||
data = {'type_x': tmp_dict[data_type[2]],
|
data = {
|
||||||
'type_y': tmp_dict[data_type[0]],
|
'type_x': tmp_dict[data_type[2]],
|
||||||
'legend': legend,
|
'type_y': tmp_dict[data_type[0]],
|
||||||
'unit': tmp_unit[data_type[0]],
|
'legend': legend,
|
||||||
'x': x,
|
'unit': tmp_unit[data_type[0]],
|
||||||
'y': y}
|
'x': x, 'y': y
|
||||||
|
}
|
||||||
|
|
||||||
if data_type == 'Z(x)':
|
return data
|
||||||
line = self.canvas_2.axes.plot(x, y, marker="+",
|
|
||||||
label=legend + ' (m)')
|
|
||||||
self.plot_rkc.canvas.draw_idle()
|
|
||||||
self.plot_rkc.update_idle()
|
|
||||||
if data_type == 'Q(t)':
|
|
||||||
line = self.canvas_4.axes.plot(x, y, marker="+",
|
|
||||||
label=legend + ' (m³/s)')
|
|
||||||
self.plot_h._line.append(line)
|
|
||||||
self.plot_h.enable_legend()
|
|
||||||
self.plot_h.canvas.draw_idle()
|
|
||||||
self.plot_h.update_idle
|
|
||||||
|
|
||||||
for p in self._additional_plot:
|
def update_plot_additional_data(self):
|
||||||
self._additional_plot[p].add_imported_plot(data)
|
results = self._results[self._current_results[0]]
|
||||||
|
|
||||||
|
for data in results.get("additional_data"):
|
||||||
|
data = data._data
|
||||||
|
x, y = data['x'], data['y']
|
||||||
|
legend = data['legend']
|
||||||
|
unit = data['unit']
|
||||||
|
|
||||||
|
if (
|
||||||
|
data['type_x'] == 'water_elevation' and
|
||||||
|
data['type_y'] == 'time'
|
||||||
|
):
|
||||||
|
line = self.canvas_2.axes.plot(
|
||||||
|
x, y, marker="+",
|
||||||
|
label=legend + ' ' + unit
|
||||||
|
)
|
||||||
|
self.plot_rkc.canvas.draw_idle()
|
||||||
|
self.plot_rkc.update_idle()
|
||||||
|
|
||||||
|
if data['type_x'] == 'discharge' and data['type_y'] == 'time':
|
||||||
|
line = self.canvas_4.axes.plot(
|
||||||
|
x, y, marker="+",
|
||||||
|
label=legend + ' ' + unit
|
||||||
|
)
|
||||||
|
self.plot_h._line.append(line)
|
||||||
|
self.plot_h.enable_legend()
|
||||||
|
self.plot_h.canvas.draw_idle()
|
||||||
|
self.plot_h.update_idle()
|
||||||
|
|
||||||
|
for p in self._additional_plot:
|
||||||
|
self._additional_plot[p].add_imported_plot(data)
|
||||||
|
|
|
||||||
|
|
@ -180,6 +180,9 @@ class MainTranslate(UnitTranslate):
|
||||||
)
|
)
|
||||||
|
|
||||||
# Message box
|
# Message box
|
||||||
|
self._dict["Error"] = _translate(
|
||||||
|
"MainWindow", "Error"
|
||||||
|
)
|
||||||
self._dict["Warning"] = _translate(
|
self._dict["Warning"] = _translate(
|
||||||
"MainWindow", "Warning"
|
"MainWindow", "Warning"
|
||||||
)
|
)
|
||||||
|
|
@ -234,6 +237,17 @@ class MainTranslate(UnitTranslate):
|
||||||
self._dict["mb_diff_results_param_msg"] = _translate(
|
self._dict["mb_diff_results_param_msg"] = _translate(
|
||||||
"MainWindow", "Results comparison parameters is invalid"
|
"MainWindow", "Results comparison parameters is invalid"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
self._dict["mb_open_results_title"] = _translate(
|
||||||
|
"MainWindow", "Open results"
|
||||||
|
)
|
||||||
|
self._dict["mb_open_results_no_results_msg"] = _translate(
|
||||||
|
"MainWindow", "No results found"
|
||||||
|
)
|
||||||
|
self._dict["mb_open_results_invalid_results_msg"] = _translate(
|
||||||
|
"MainWindow", "Failed to read results"
|
||||||
|
)
|
||||||
|
|
||||||
self._dict["mb_diff_results_compatibility_msg"] = _translate(
|
self._dict["mb_diff_results_compatibility_msg"] = _translate(
|
||||||
"MainWindow",
|
"MainWindow",
|
||||||
"Results comparison with two "
|
"Results comparison with two "
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue