Factorisation de la création des plots

This commit is contained in:
Philippe Roy 2023-01-31 11:15:21 +01:00
parent b1be7d960d
commit 4d809d45da
20 changed files with 276 additions and 269 deletions

View File

@ -18,7 +18,7 @@ scene = bge.logic.getCurrentScene()
# Configuration des variables publiques
# 'nom_variable' :
# - Objet 3D : [nom de l'objet 3D, propriété du stockage de la valeur (activate ou activated_real), échelle (1 si ommis)]
# - Objet 3D : [nom de l'objet 3D, propriété associée à la valeur (activate ou activated_real), type de la valeur ('d' (digital, binary), 'a', (analog) ou 'n' (numeric)), échelle (1 si ommis)]
# - Configuration de la broche : [nom de la propriété stockant l'object broche (pyfirmata), type de broche par défaut('d','a' ou 'p'), 'mode de la broche par défaut ('i' ou 'o')]
# - Configuration du graphique : ['marque', 'type de ligne', 'couleur', linewidth]] (matplotlib)
#

View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_file_wx.py

1
monte_charge/twin_plot.py Symbolic link
View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_plot.py

View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_plot_wx.py

View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_file_wx.py

1
poppy_ergo_jr/twin_plot.py Symbolic link
View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_plot.py

View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_plot_wx.py

View File

@ -18,8 +18,8 @@ scene = bge.logic.getCurrentScene()
# Configuration des variables publiques
# 'nom_variable' :
# - Objet 3D : [nom de l'objet 3D, propriété du stockage de la valeur (activate ou activated_real)]
# - Configuration de la broche : [nom de la propriété stockant l'object broche (pyfirmata), type de broche par défaut('d','a' ou 'p'), 'mode de la broche par défaut ('i' ou 'o')]
# - Objet 3D : [nom de l'objet 3D, propriété associée à la valeur (activate ou activated_real), type de la valeur ('d' (digital, binary), 'a', (analog) ou 'n' (numeric)), échelle (1 si ommis)]
# - Configuration de la broche : [nom de la propriété stockant l'object broche (pyfirmata), type de broche par défaut ('d','a' ou 'p'), 'mode de la broche par défaut ('i' ou 'o')]
# - Configuration du graphique : ['marque', 'type de ligne', 'couleur', linewidth]] (Codification de Matplotlib)
#
# 'nom_variable_r' est la valeur réelle de la variable (valeur numérique) 'nom_variable' issue du jumelage numérique.
@ -27,27 +27,27 @@ scene = bge.logic.getCurrentScene()
# Ce distinguo ne concerne que les entrées, les sorties réelles sont forcées par les sorties numériques et vice-versa.
public_vars = {
't' : [['System','time'], [], []],
'bp_ext' : [['Bp cote rue','activated'], ['pin', 'd','i'], ['.','-', 'green', 1]],
'bp_ext_r' : [['Bp cote rue','activated_real'], [], ['.','--', 'green', 1]],
'bp_int' : [['Bp cote cour','activated'], ['pin', 'd','i'], ['.','-', 'darkgreen', 1]],
'bp_int_r' : [['Bp cote cour','activated_real'], [], ['.','--', 'darkgreen', 1]],
'fdc_o' : [['Microrupteur fdc ouvert','activated'], ['pin', 'd','i'], ['.','-', 'orange', 1]],
'fdc_o_r' : [['Microrupteur fdc ouvert','activated_real'], [], ['.','--', 'orange', 1]],
'fdc_f' : [['Microrupteur fdc ferme','activated'], ['pin', 'd','i'], ['.','-', 'darkorange', 1]],
'fdc_f_r' : [['Microrupteur fdc ferme','activated_real'], [], ['.','--', 'darkorange', 1]],
'mot_o' : [['Moteur','open'], ['pin_open', 'd','o'], ['.','-', 'violet', 1]],
'mot_f' : [['Moteur','close'], ['pin_close', 'd','o'], ['.','-', 'darkviolet', 1]],
'mot_angle' : [['Moteur','alpha'], [], ['.','-', 'blue', 1]],
'mot_vitesse' : [['Moteur','speed'], [], ['.','-', 'darkblue', 1]],
'mot_pas' : [['Moteur','step'], [], []],
'portail_x' : [['Portail','x'], [], ['.','-', 'turquoise', 1]],
'portail_vitesse' : [['Portail','speed'], [], ['.','-', 'darkturquoise', 1]],
'portail_pas' : [['Portail','step'], [], []],
'gyr' : [['Led','activated'], ['pin', 'd','.'], ['.','-', 'gold', 1]],
'ir_emet' : [['Emetteur IR', 'activated'], ['pin', 'd','o'],['.','-', 'red', 1]],
'ir_recep' : [['Recepteur IR','activated'], ['pin', 'd','i'],['.','-', 'darkred', 1]],
'ir_recep_r' : [['Recepteur IR','activated_real'], [],['.','--', 'darkred', 1]]}
't' : [['System','time','a'],[],[]],
'bp_ext' : [['Bp cote rue','activated','d'],['pin','d','i'],['.','-','green',1]],
'bp_ext_r' : [['Bp cote rue','activated_real','d'],[],['.','--','green',1]],
'bp_int' : [['Bp cote cour','activated','d'],['pin','d','i'],['.','-','darkgreen',1]],
'bp_int_r' : [['Bp cote cour','activated_real','d'],[],['.','--','darkgreen',1]],
'fdc_o' : [['Microrupteur fdc ouvert','activated','d'],['pin','d','i'],['.','-','orange',1]],
'fdc_o_r' : [['Microrupteur fdc ouvert','activated_real','d'],[],['.','--','orange',1]],
'fdc_f' : [['Microrupteur fdc ferme','activated','d'],['pin','d','i'],['.','-','darkorange',1]],
'fdc_f_r' : [['Microrupteur fdc ferme','activated_real','d'],[],['.','--','darkorange',1]],
'mot_o' : [['Moteur','open','d'],['pin_open','d','o'],['.','-','violet',1]],
'mot_f' : [['Moteur','close','d'],['pin_close','d','o'],['.','-','darkviolet',1]],
'mot_angle' : [['Moteur','alpha','a'],[],['.','-','blue',1]],
'mot_vitesse' : [['Moteur','speed','a'],[],['.','-','darkblue',1]],
'mot_pas' : [['Moteur','step','a'],[],[]],
'portail_x' : [['Portail','x','a'],[],['.','-','turquoise',1]],
'portail_vitesse' : [['Portail','speed','a'],[],['.','-','darkturquoise',1]],
'portail_pas' : [['Portail','step','a'],[],[]],
'gyr' : [['Led','activated','d'],['pin','d','.'],['.','-','gold',1]],
'ir_emet' : [['Emetteur IR','activated','d'],['pin','d','o'],['.','-','red',1]],
'ir_recep' : [['Recepteur IR','activated','d'],['pin','d','i'],['.','-','darkred',1]],
'ir_recep_r' : [['Recepteur IR','activated_real','d'],[],['.','--','darkred',1]]}
# Couleurs
color_passive = (0.800, 0.005, 0.315,1) # bouton non activable : magenta

View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_file_wx.py

View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_plot.py

View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_plot_wx.py

View File

@ -34,8 +34,8 @@ daq_data=[]
def get(data):
if data in daq_config:
if len (daq_config[data][0])>2: # Echelle à prendre en compte
return(scene.objects[daq_config[data][0][0]][daq_config[data][0][1]]*daq_config[data][0][2])
if len (daq_config[data][0])>3: # Echelle à prendre en compte
return(scene.objects[daq_config[data][0][0]][daq_config[data][0][1]]*daq_config[data][0][3])
else:
return(scene.objects[daq_config[data][0][0]][daq_config[data][0][1]])
else:
@ -126,6 +126,8 @@ def plot_config_generate(data_groups):
xml_color.text=daq_config[var][2][2]
xml_size = ET.SubElement(xml_var, 'linewidth')
xml_size.text=str(daq_config[var][2][3])
xml_type = ET.SubElement(xml_var, 'type')
xml_type.text=str(daq_config[var][0][2])
# Détection de groupe de graphique
data_group_i=0
@ -160,9 +162,9 @@ def plot(data_groups):
##
def plot_generate_thread(csv_file):
if sys.platform=="linux": # wxPython ne s'installe pas bien sur GNU/linux -> Qt6
if sys.platform=="linux": # wxPython ne s'installe pas bien sur GNU/linux -> Qt5
command = sys.executable + " " + os.path.join(sys.executable, os.getcwd(), "twin_plot_qt.py") + " "+ csv_file
else: # Qt6 ne s'installe pas bien sur Windows -> wxPython
else: # Qt5 ne s'installe pas bien sur Windows -> wxPython
command = sys.executable + " " + os.path.join(sys.executable, os.getcwd(), "twin_plot_wx.py") + " "+ csv_file
os.system(command)

198
twin_plot.py Normal file
View File

@ -0,0 +1,198 @@
import csv # Creating/parsing CSV file
import xml.etree.ElementTree as ET # Creating/parsing XML file
###############################################################################
# twin_plot.py
# @title: Visualisation des données (Matplotlib)
# @project: Blender-EduTech
# @lang: fr
# @authors: Philippe Roy <philippe.roy@ac-grenoble.fr>
# @copyright: Copyright (C) 2023 Philippe Roy
# @license: GNU GPL
###############################################################################
###############################################################################
# Configuration des plots
###############################################################################
def plot_config_get_enable():
twin_config = ET.parse('twin_config.xml').getroot()
if twin_config[1][0].text == "True":
return True
else:
return False
##
# Génère le dictionnaire plot_config à partir du fichier XML plot_config.xml
##
def plot_config_get_dict():
plot_config_tree = ET.parse('plot_config.xml').getroot()
plot_config_tmp={}
for var in plot_config_tree[0][0]:
var_dict={}
for i in range (len(var)):
if var[i] is not None:
var_dict.update({var[i].tag : var[i].text})
plot_config_tmp.update({var.text: var_dict})
return plot_config_tmp
##
# Returne une valeur du dictionnaire plot_config
##
def plot_config_get(plot_config, var, key):
if key in plot_config[var]:
return plot_config[var][key]
else:
return None
##
# Nombre de groupe de courbe(s)
##
def plot_nb(plot_config):
plot_config_list=list(plot_config)
nbgroup = 0
# Regroupement ('group' > 0)
for var in plot_config_list:
if ('group' in plot_config[var]):
if nbgroup < int(plot_config[var]['group']):
nbgroup = int(plot_config[var]['group'])
# Plot solitaire ('group' = 0)
# 'group' = -1 -> variable non affichée
for var in plot_config_list:
if ('group' in plot_config[var]):
if int(plot_config[var]['group']) == 0:
nbgroup +=1
return nbgroup
###############################################################################
# Fichier CSV
###############################################################################
##
# Fichier CSV -> Tableau X,Y
##
def csv_read(file):
# Lecture fichier CSV
fields = []
rows = []
with open(file, newline='') as csv_buff:
csv_reader = csv.reader(csv_buff, delimiter=';')
fields = next(csv_reader)
for row in csv_reader:
rows.append(row)
# Mise en tableau à deux colonnes (xdata,ydata)
xdata=[]
ydata=[]
i=0
for field in fields:
xdata_row=[]
ydata_row=[]
for row in rows:
xdata_row.append(float(row[0].replace(',', '.'))) # Revenir au format US des décimaux
ydata_row.append(float(row[i].replace(',', '.'))) # Revenir au format US des décimaux
xdata.append(xdata_row)
ydata.append(ydata_row)
i+=1
return fields, xdata, ydata
###############################################################################
# Création des graphiques
###############################################################################
def plot_static(canvas, fields, xdata, ydata, plot_config, title):
# Configuration des plots activée
plot_config_enable=plot_config_get_enable()
# Plots
# Groupe de plots : si group = 0 -> nouveau groupe, plot solitaire
# si group = -1 -> pas de plot
# si group > 0 -> numéro du groupe
plt_i=0 # Compteur de plot
plt_grp=[] # Groupe de plot [[numéro du plot, groupe du fichier CSV]]
for i in range(len(fields)):
var = fields[i]
plt_current=-1 # Numéro du plot à créer
if ('group' in plot_config[var]): # Pas de Plot
if int(plot_config[var]['group']) !=-1: # Pas de Plot
# Plot solitaire
if int(plot_config[var]['group']) ==0:
plt_current = plt_i
plt_grp.append([plt_i, 0])
plt_i +=1
# Plot groupé
else:
plt_new = True # Flag d'un nouveau groupe
for j in range(len(plt_grp)):
if plt_grp[j][1] == int(plot_config[var]['group']): # Groupe déjà existant
plt_current = plt_grp[j][0]
plt_new = False
break
# Nouveau groupe
if plt_new:
plt_current = plt_i
plt_grp.append([plt_i, int(plot_config[var]['group'])])
plt_i +=1
# Création du plot unique
if plot_nb(plot_config) ==1:
if plot_config_enable: # Configuration des plots activée
canvas.plt.plot(xdata[i], ydata[i], label=var, color=plot_config_get(plot_config, var, 'color'), linewidth=plot_config_get(plot_config, var, 'linewidth'),
linestyle=plot_config_get(plot_config, var, 'linestyle'), marker=plot_config_get(plot_config, var, 'marker'))
else:
canvas.plt.plot(xdata[i], ydata[i], '.-', label=var) # Configuration matplotlib par défaut
# Légende ou titre d'axe y
if plt_grp[plt_current][1]==0:
canvas.plt.set_ylabel(var)
else:
canvas.plt.legend()
# Création des subplots
if plot_nb(plot_config) >1:
if plot_config_enable: # Configuration des plots activée
canvas.plt[plt_current].plot(xdata[i], ydata[i], label=var, color=plot_config_get(plot_config, var, 'color'), linewidth=plot_config_get(plot_config, var, 'linewidth'),
linestyle=plot_config_get(plot_config, var, 'linestyle'), marker=plot_config_get(plot_config, var, 'marker'))
else:
canvas.plt[plt_current].plot(xdata[i], ydata[i], '.-', label=var) # Configuration matplotlib par défaut
# Légende ou titre d'axe y
if plt_grp[plt_current][1]==0:
canvas.plt[plt_current].set_ylabel(var)
else:
canvas.plt[plt_current].legend()
# Décoration
if plot_nb(plot_config) ==1: # 1 plot
canvas.plt.set_xlabel("Temps (s)")
canvas.plt.set_title(title)
canvas.plt.axhline(linewidth=1, color='k')
canvas.plt.grid(True, linestyle='--')
# canvas.plt.legend()
else: # Plusieurs plots
canvas.plt[plt_i-1].set_xlabel("Temps (s)")
canvas.plt[0].set_title(title)
for i in range (plt_i):
canvas.plt[i].axhline(linewidth=1, color='k')
canvas.plt[i].grid(True, linestyle='--')
# canvas.plt[i].legend()
# Redraw
canvas.draw()

View File

@ -1,15 +1,11 @@
import sys
import random
import importlib
import matplotlib
import matplotlib.pyplot as plts
import csv
import xml.etree.ElementTree as ET # Creating/parsing XML file
from twin_plot import plot_config_get_dict, plot_config_get, plot_config_get_enable, plot_nb, csv_read, plot_static # Gestion communes des graphiques (Qt, wx)
matplotlib.use('Qt5Agg')
from PyQt5 import QtCore, QtGui, QtWidgets
from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg, NavigationToolbar2QT as NavigationToolbar
from PyQt5 import QtCore, QtGui, QtWidgets # GUI Qt5
import matplotlib # Grapheur Matplotlib
import matplotlib.pyplot as plts
matplotlib.use('Qt5Agg')
from matplotlib.backends.backend_qt5agg import FigureCanvasQTAgg, NavigationToolbar2QT as NavigationToolbar
###############################################################################
# twin_plot_qt.py
@ -21,70 +17,18 @@ import matplotlib.pyplot as plts
# @license: GNU GPL
###############################################################################
# Lecture des configurations
twin_config = ET.parse('twin_config.xml').getroot()
plot_config_tree = ET.parse('plot_config.xml').getroot()
plot_config={}
###############################################################################
# Configuration des plots
###############################################################################
##
# Génère le dictionnaire plot_config à partir du fichier XML plot_config.xml
##
def plot_config_dict():
for var in plot_config_tree[0][0]:
var_dict={}
for i in range (len(var)):
if var[i] is not None:
var_dict.update({var[i].tag : var[i].text})
plot_config.update({var.text: var_dict})
##
# Returne une valeur du dictionnaire plot_config
##
def plot_config_get(var, key):
if key in plot_config[var]:
return plot_config[var][key]
else:
return None
##
# Nombre de groupe de courbe(s)
##
def plot_nb():
plot_config_list=list(plot_config)
nbgroup = 0
# Regroupement ('group' > 0)
for var in plot_config_list:
if ('group' in plot_config[var]):
if nbgroup < int(plot_config[var]['group']):
nbgroup = int(plot_config[var]['group'])
# Plot solitaire ('group' = 0)
# 'group' = -1 -> variable non affichée
for var in plot_config_list:
if ('group' in plot_config[var]):
if int(plot_config[var]['group']) == 0:
nbgroup +=1
return nbgroup
###############################################################################
# Zone de dessin
###############################################################################
class MplCanvas(FigureCanvasQTAgg):
def __init__(self, parent=None, width=5, height=4, dpi=100):
if plot_nb() ==1: # plot_nb() : nombre de graphiques
fig, self.plt = plts.subplots() # plot_nb() : nombre de graphiques
if plot_nb(plot_config) ==1: # plot_nb() : nombre de graphiques
fig, self.plt = plts.subplots()
else:
fig, self.plt = plts.subplots(plot_nb(), 1, sharex=True) # plot_nb() : nombre de graphiques
fig, self.plt = plts.subplots(plot_nb(plot_config), 1, sharex=True) # plot_nb() : nombre de graphiques
super(MplCanvas, self).__init__(fig)
###############################################################################
@ -212,9 +156,6 @@ class MainWindow(QtWidgets.QMainWindow):
# Création du graphique
def __init__(self, *args, **kwargs):
# Configuration des plots
plot_config_dict()
# Zone graphique (barre d'outil et graphique)
# FIXME : perd de la place quand on agrandi
super(MainWindow, self).__init__(*args, **kwargs)
@ -235,110 +176,9 @@ class MainWindow(QtWidgets.QMainWindow):
self.setCentralWidget(widget)
# print (self.getContentsMargins())
# Lecture fichier CSV
fields = []
rows = []
with open(sys.argv[1], newline='') as csv_buff:
csv_reader = csv.reader(csv_buff, delimiter=';')
fields = next(csv_reader)
for row in csv_reader:
rows.append(row)
# Mise en tableau à deux colonnes (xdata,ydata)
xdata=[]
ydata=[]
i=0
for field in fields:
xdata_row=[]
ydata_row=[]
for row in rows:
xdata_row.append(float(row[0].replace(',', '.'))) # Revenir au format US des décimaux
ydata_row.append(float(row[i].replace(',', '.'))) # Revenir au format US des décimaux
xdata.append(xdata_row)
ydata.append(ydata_row)
i+=1
# Plots
# Groupe de plots : si group = 0 -> nouveau groupe, plot solitaire
# si group = -1 -> pas de plot
# si group > 0 -> numéro du groupe
plt_i=0 # Compteur de plot
plt_grp=[] # Groupe de plot [[numéro du plot, groupe du fichier CSV]]
for i in range(len(fields)):
var = fields[i]
plt_current=-1 # Numéro du plot à créer
if ('group' in plot_config[var]): # Pas de Plot
if int(plot_config[var]['group']) !=-1: # Pas de Plot
# Plot solitaire
if int(plot_config[var]['group']) ==0:
plt_current = plt_i
plt_grp.append([plt_i, 0])
plt_i +=1
# Plot groupé
else:
plt_new = True # Flag d'un nouveau groupe
for j in range(len(plt_grp)):
if plt_grp[j][1] == int(plot_config[var]['group']): # Groupe déjà existant
plt_current = plt_grp[j][0]
plt_new = False
break
# Nouveau groupe
if plt_new:
plt_current = plt_i
plt_grp.append([plt_i, int(plot_config[var]['group'])])
plt_i +=1
# Création du plot unique
if plot_nb() ==1:
if twin_config[1][0].text == "True": # Configuration des plots activée
self.canvas.plt.plot(xdata[i], ydata[i], label=var, color=plot_config_get(var, 'color'), linewidth=plot_config_get(var, 'linewidth'),
linestyle=plot_config_get(var, 'linestyle'), marker=plot_config_get(var, 'marker'))
else:
self.canvas.plt.plot(xdata[i], ydata[i], '.-', label=var) # Configuration matplotlib par défaut
# Légende ou titre d'axe y
if plt_grp[plt_current][1]==0:
self.canvas.plt.set_ylabel(var)
else:
self.canvas.plt.legend()
# Création des subplots
if plot_nb() >1:
if twin_config[1][0].text == "True": # Configuration des plots activée
self.canvas.plt[plt_current].plot(xdata[i], ydata[i], label=var, color=plot_config_get(var, 'color'), linewidth=plot_config_get(var, 'linewidth'),
linestyle=plot_config_get(var, 'linestyle'), marker=plot_config_get(var, 'marker'))
else:
self.canvas.plt[plt_current].plot(xdata[i], ydata[i], '.-', label=var) # Configuration matplotlib par défaut
# Légende ou titre d'axe y
if plt_grp[plt_current][1]==0:
self.canvas.plt[plt_current].set_ylabel(var)
else:
self.canvas.plt[plt_current].legend()
# Décoration
if plot_nb() ==1: # 1 plot
self.canvas.plt.set_xlabel("Temps (s)")
# self.canvas.plt[0].set_ylabel("Valeurs")
self.canvas.plt.set_title(sys.argv[1])
self.canvas.plt.axhline(linewidth=1, color='k')
self.canvas.plt.grid(True, linestyle='--')
# self.canvas.plt.legend()
else: # Plusieurs plots
self.canvas.plt[plt_i-1].set_xlabel("Temps (s)")
# self.canvas.plt[0].set_ylabel("Valeurs")
self.canvas.plt[0].set_title(sys.argv[1])
for i in range (plt_i):
self.canvas.plt[i].axhline(linewidth=1, color='k')
self.canvas.plt[i].grid(True, linestyle='--')
# self.canvas.plt[i].legend()
# Redraw
self.canvas.draw()
# Création des graphive à partir du fichier CSV
fields, xdata, ydata = csv_read(sys.argv[1])
plot_static(self.canvas, fields, xdata, ydata, plot_config, sys.argv[1])
self.show()
###############################################################################
@ -346,6 +186,11 @@ class MainWindow(QtWidgets.QMainWindow):
###############################################################################
if __name__ == "__main__":
# Configuration des plots
plot_config=plot_config_get_dict()
# Fenêtre
app = QtWidgets.QApplication(sys.argv)
# w = DynamicPlot()
w = MainWindow() # StaticPlot()

View File

@ -1,10 +1,8 @@
import sys
import importlib
import csv
import xml.etree.ElementTree as ET # Creating/parsing XML file
from twin_plot import plot_config_get_dict, plot_config_get, plot_config_get_enable, plot_nb, csv_read, plot_static # Gestion communes des graphiques (Qt, wx)
import wx
import matplotlib
import wx # GUI wxPython
import matplotlib # Grapheur Matplotlib
from matplotlib.figure import Figure
from matplotlib.backends.backend_wxagg import (FigureCanvasWxAgg as FigureCanvas, NavigationToolbar2WxAgg as NavigationToolbar)
@ -18,61 +16,8 @@ from matplotlib.backends.backend_wxagg import (FigureCanvasWxAgg as FigureCanvas
# @license: GNU GPL
###############################################################################
# Lecture des configurations
twin_config = ET.parse('twin_config.xml').getroot()
plot_config_tree = ET.parse('plot_config.xml').getroot()
plot_config={}
###############################################################################
# Configuration des graphiques
###############################################################################
##
# Génère le dictionnaire plot_config à partir du fichier XML plot_config.xml
##
def plot_config_dict():
for var in plot_config_tree[0][0]:
var_dict={}
for i in range (len(var)):
if var[i] is not None:
var_dict.update({var[i].tag : var[i].text})
plot_config.update({var.text: var_dict})
##
# Returne une valeur du dictionnaire plot_config
##
def plot_config_get(var, key):
if key in plot_config[var]:
return plot_config[var][key]
else:
return None
##
# Nombre de groupe de courbe(s)
##
def plot_nb():
plot_config_list=list(plot_config)
nbgroup = 0
# Regroupement ('group' > 0)
for var in plot_config_list:
if ('group' in plot_config[var]):
if nbgroup < int(plot_config[var]['group']):
nbgroup = int(plot_config[var]['group'])
# Plot solitaire ('group' = 0)
# 'group' = -1 -> variable non affichée
for var in plot_config_list:
if ('group' in plot_config[var]):
if int(plot_config[var]['group']) == 0:
nbgroup +=1
return nbgroup
###############################################################################
# Création des graphiques
###############################################################################
@ -181,32 +126,32 @@ def plot_draw(plt):
plt[i].grid(True, linestyle='--')
# self.canvas.plt[i].legend()
###############################################################################
# Zone de dessin
###############################################################################
class CanvasFrame(wx.Frame):
def __init__(self):
super().__init__(None, -1, 'Visualisation des données')
# Configuration des graphiques
plot_config_dict()
# Création des zones graphique (Plots)
self.figure = Figure()
if plot_nb() ==1: # plot_nb() : nombre de graphiques
plt = self.figure.subplots() # plot_nb() : nombre de graphiques
else:
plt = self.figure.subplots(plot_nb(), 1, sharex=True) # plot_nb() : nombre de graphiques
# Dessin
plot_draw(plt)
plt = self.figure.subplots(plot_nb(plot_config), 1, sharex=True) # plot_nb() : nombre de graphiques
self.canvas = FigureCanvas(self, -1, self.figure)
# Création des graphive à partir du fichier CSV
fields, xdata, ydata = csv_read(sys.argv[1])
plot_static(self.canvas, fields, xdata, ydata, plot_config, sys.argv[1])
self.show()
# # Dessin
# plot_draw(plt)
# Implantation de la fenêtre (canvas)
self.canvas = FigureCanvas(self, -1, self.figure)
self.sizer = wx.BoxSizer(wx.VERTICAL)
self.sizer.Add(self.canvas, 1, wx.TOP | wx.LEFT | wx.EXPAND)
self.add_toolbar()
@ -231,5 +176,10 @@ class App(wx.App):
return True
if __name__ == "__main__":
# Configuration des plots
plot_config=plot_config_get_dict()
# Fenêtre
app = App()
app.MainLoop()
app.MainLoop() # StaticPlot()

View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_file_wx.py

1
volet_roulant/twin_plot.py Symbolic link
View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_plot.py

View File

@ -0,0 +1 @@
/home/phroy/Bureau/seriousgames/blender-edutech/git/digital_twin/twin_plot_wx.py

View File

@ -18,7 +18,7 @@ scene = bge.logic.getCurrentScene()
# Configuration des variables publiques
# 'nom_variable' :
# - Objet 3D : [nom de l'objet 3D, propriété du stockage de la valeur (activate ou activated_real)]
# - Objet 3D : [nom de l'objet 3D, propriété associée à la valeur (activate ou activated_real), type de la valeur ('d' (digital, binary), 'a', (analog) ou 'n' (numeric)), échelle (1 si ommis)]
# - Configuration de la broche : [nom de la propriété stockant l'object broche (pyfirmata), type de broche par défaut('d','a' ou 'p'), 'mode de la broche par défaut ('i' ou 'o')]
# - Configuration du graphique : ['marque', 'type de ligne', 'couleur', linewidth]] (matplotlib)
#