Skip to content
Snippets Groups Projects
Commit 0171b7fc authored by antcsny's avatar antcsny
Browse files

adding figure creation to plot raw data

parent b077f442
No related merge requests found
......@@ -4,6 +4,7 @@ from typing import List, Any, Dict, Tuple
import re
from .processing import *
from .utils import from_class_to_text
# %%
def PlotFilter (filter: np.ndarray, sampling_rate: int = 1000):
......@@ -184,4 +185,228 @@ def Spectrogram_plot (
if save:
savefig("Spectrogram\\" + name)
return f, extent
\ No newline at end of file
return f, extent
def plot_unique_position(data:pd.DataFrame, axis:plt.Axes, byvariable:str, Motor:int) -> plt.Axes:
"""plots on secondary axis a unique motor position run when multiple runs are present in the dataframe in argument
the runs are differenciated with the 'byvariable' value
Args:
data (pd.DataFrame): data containing the Position _A{Motor} column
axis (plt.Axes): axis to duplicate
byvariable (str): common column in the dataframe, differenciating the runs
Motor (int): Motor's position to plot
Returns:
plt.Axes: new axis with ploted position
"""
ax2 = axis.twinx()
position_df = data.loc[data[byvariable] == data.iloc[0][byvariable]] # look for the data with condition 'byvariable' == (first value found of byvariable)
lin = sns.lineplot(data=position_df, x='Sample_time',y=f'Position_A{Motor}', color='grey', alpha = 0.1, ax=ax2,label=f'Axis {Motor} position',legend=False)
ax2.set_ylabel(f'Motor {Motor} angle (°)')
return lin
def check_arguments(plot_type:str, variable:str, byvariable:str):
""" Checks that the variables to plot are suited for ploting
"""
if plot_type not in ['Lineplot', 'Boxplot']:
print('Bad plot type argument')
return False
if variable not in ['Current', 'Temperature', 'Position_Error']:
print('Bad variable argument')
return False
if byvariable not in ['Class', 'Speed']:
print('Bad by variable argument')
return False
return True
def plot_all_axis(DB, variable:str, byvariable:str, byvalues:List, MovingMotor:int, Speed:int = 50, Class:int = 0, plot_type:str = 'Lineplot', doposition:bool = False, saving:bool = False):
"""Plots variable's data from the Dataframe on each robot axis (6 subplots), differenciating the data by 'byvariable' column's name.
Create a 'Lineplot' or a 'Boxplot', depending on the argument plot
Which motor's data to plot is defined by the arg Motor, same with Speed.
Choose to plot the motor's position on a secondary axis, figure saving and showing with the boolean arguments
Args:
data (pd.DataFrame): Pandas dataframe containing the data
variable (str): Variable to plot
byvariable (str): Variable that discriminates the data
Motor (int): Motor number
Speed (int): Motor speed
plot_type (str, optional): 'Lineplot' or 'Boxplot' : format of the data plot. Defaults to 'Lineplot'
doposition (bool, optional): motor's position plot. Defaults to False.
saving (bool, optional): figure saving. Defaults to False.
"""
if not check_arguments(plot_type, variable, byvariable):
return
columns = [byvariable,'Sample_time',f'Position_A{MovingMotor}',*[f'{variable}_A{j}'for j in range(1,7,1)]]
dataframe = pd.DataFrame() # Data gathering
rms = []
for v in byvalues:
if byvariable == 'Speed':
df = DB.robot(2).by_class(Class).by_speed(v).by_moving_motor(MovingMotor).select_column(*columns).run()
df['Speed'] = df.Speed.astype('category')
df['Sample_time'] -= df['Sample_time'].min() # limits data to 2-3 iterations
dataframe = pd.concat([dataframe, df[0:500]])
if byvariable == 'Class':
df = DB.robot(2).by_class(v).by_speed(Speed).by_moving_motor(MovingMotor).run()
df['Class'] = df.Class.astype('category')
df['Sample_time'] -= df['Sample_time'].min()
dataframe = pd.concat([dataframe, df[300:900]]) # limits data to 2-3 iterations
rms.append(np.sqrt(np.mean(df[f'{variable}_A{MovingMotor}']**2)))
print(f'Motor {MovingMotor} runs rms :',rms)
fig = plt.figure(figsize=(3*6,2*4)) # Data plot
for i in range(1,7,1):
axis = plt.subplot(2,3,i)
if(plot_type=='Boxplot'):
sns.boxplot(data=dataframe, y=f'{variable}_A{i}', hue=byvariable, ax=axis)
if(plot_type=='Lineplot'):
lin1 = sns.lineplot(data= dataframe, x='Sample_time', y=f'{variable}_A{i}', hue=byvariable, ax=axis, alpha=0.6)
if doposition :
lin2 = plot_unique_position(dataframe, axis, byvariable, MovingMotor)
axis.legend(fontsize=8, loc='upper right', handles=lin1.get_lines()+lin2.get_lines())
else:
axis.legend(fontsize=8, loc='upper right')
axis.set_title(f'Motor {i}')
if byvariable == 'Speed':
fig.suptitle(f"{plot_type} of {variable} by {byvariable} for Axis {MovingMotor} moving loaded with {from_class_to_text(Class)}")
if byvariable == 'Class':
fig.suptitle(f"{plot_type} of {variable} by {byvariable} for Axis {MovingMotor} moving at {Speed}% Speed")
fig.tight_layout()
if saving:
figures = Path(f"figures/{variable} by motor by {byvariable}")
if not figures.exists():
figures.mkdir(parents=True)
fig.savefig(f"figures/{variable} by motor by {byvariable}/{plot_type}_of_{variable}_by{byvariable}_Axis{MovingMotor}.png")
return fig
def plot_moving_axes(DB, variable:str, byvariable:str, byvalues:List, Speed:int = 50, Class:int = 0, plot_type:str = 'Lineplot', doposition:bool = False, saving:bool = False):
"""Plots the current of the motor responsible of axis movement for the axes moving (ex : A1 moving - current Motor 1, A2 moving - current Motor 2,...)
differenciating the data by 'byvariable' column's name.
Create a 'Lineplot' or a 'Boxplot', depending on the argument plot
Which motor's data to plot is defined by the arg Motor, same with Speed.
Choose to plot the motor's position on a secondary axis, figure saving and showing with the boolean arguments
Args:
data (pd.DataFrame): Pandas dataframe containing the data
variable (str): Variable to plot
byvariable (str): Variable that discriminates the data
Motor (int): Motor number
Speed (int): Motor speed
plot_type (str, optional): 'Lineplot' or 'Boxplot' : format of the data plot. Defaults to 'Lineplot'
doposition (bool, optional): motor's position plot. Defaults to False.
saving (bool, optional): figure saving. Defaults to False.
"""
if not check_arguments(plot_type, variable, byvariable):
return
fig = plt.figure(figsize=(3*6,2*4))
for Motor in range (1,7,1):
dataframe = pd.DataFrame() # Data gathering
columns = [byvariable,'Sample_time',f'{variable}_A{Motor}',f'Position_A{Motor}']
rms = []
for v in byvalues:
if byvariable == 'Speed':
df = DB.robot(2).by_class(Class).by_speed(v).by_moving_motor(Motor).select_column(*columns).run()
df['Speed'] = df.Speed.astype('category')
df['Sample_time'] -= df['Sample_time'].min()
dataframe = pd.concat([dataframe, df[0:500]]) # limits data to 2-3 iterations
if byvariable == 'Class':
df = DB.robot(2).by_class(v).by_speed(Speed).by_moving_motor(Motor).select_column(*columns).run()
df['Class'] = df.Class.astype('category')
df['Sample_time'] -= df['Sample_time'].min()
dataframe = pd.concat([dataframe, df[300:900]])
rms.append(np.sqrt(np.mean(df[f'{variable}_A{Motor}']**2))) # limits data to 2-3 iterations
print(f'Motor {Motor} runs rms :',rms)
axis = plt.subplot(2,3,Motor)
if(plot_type=='Boxplot'):
sns.boxplot(data=dataframe, y=f'{variable}_A{Motor}', hue=byvariable, ax=axis)
if(plot_type=='Lineplot'):
lin1 = sns.lineplot(data= dataframe, x='Sample_time', y=f'{variable}_A{Motor}', hue=byvariable, ax=axis, alpha=0.6)
lin1.set_ylabel(f'{variable}_A{Motor}, Axis {Motor} moving')
if doposition :
lin2 = plot_unique_position(dataframe, axis, byvariable, Motor)
axis.legend(fontsize=8, loc='upper right', handles=lin1.get_lines()+lin2.get_lines())
else:
axis.legend(fontsize=8, loc='upper right')
axis.set_title(f'Motor {Motor}')
if byvariable == 'Speed':
fig.suptitle(f"{plot_type} of {variable} by {byvariable} loaded with {from_class_to_text(Class)}")
if byvariable == 'Class':
fig.suptitle(f"{plot_type} of {variable} by {byvariable} moving at {Speed}% Speed")
fig.tight_layout()
if saving:
figures = Path(f"figures/{variable} by moving motors by {byvariable}")
if not figures.exists():
figures.mkdir(parents=True)
fig.savefig(f"{figures}/{plot_type}_of_{variable}_by{byvariable}{str(byvalues)}_allAxes.png")
return fig
def plot_grouped_load(DB, variable:str, Classes:List[List], Motor:int, Speed:int, doposition:bool = False, saving:bool = False) -> plt.Figure:
"""Plots variable's data from the DataBase, grouping the curves by load classes.
Each list in Classes will create a subplot, with the curves of the classes
Which motor's data to plot is defined by the arg Motor, same with Speed.
Choose to plot the motor's position on a secondary axis and figure saving with the boolean arguments
Args:
DB (_type_): Database containing the data
variable (str): Column of the database to plot
Classes (List[List]): List of list of loads classes.
Motor (int): Motor number
Speed (int): Motor speed
doposition (bool, optional): motor's position plot. Defaults to False.
saving (bool, optional): figure saving. Defaults to False.
Returns:
plt.Figure: created figure
"""
columns = ['Class','Sample_time',f'Position_A{Motor}',*[f'{variable}_A{j}'for j in range(1,7,1)]]
fig = plt.figure(figsize=(len(Classes)*5,4))
for i, cla in enumerate(Classes):
axis = plt.subplot(1,len(Classes),i+1)
dataframe = pd.DataFrame()
rms = []
for c in cla:
# Data gathering from the database
df = DB.robot(2).by_class(c).by_speed(Speed).by_moving_motor(Motor).select_column(*columns).run()
df['Sample_time'] -= df['Sample_time'].min()
df['Class'] = df.Class.astype('category')
dataframe = pd.concat([dataframe, df[300:900]]) # limits data to 2-3 iterations
rms.append(np.sqrt(np.mean(df[f'{variable}_A{Motor}']**2)))
print(f'Motor {Motor} runs rms :',rms)
lin1 = sns.lineplot(data=dataframe,x='Sample_time', y=f'{variable}_A{Motor}', hue='Class', ax=axis, alpha=0.6) # data plot
if doposition:
lin2 = plot_unique_position(dataframe, axis, 'Class', Motor)
axis.legend(fontsize=8, loc='upper right', handles=lin1.get_lines()+lin2.get_lines())
else:
axis.legend(fontsize=8, loc='upper right')
axis.legend(fontsize=8, loc='upper right', handles=lin1.get_lines()+lin2.get_lines())
fig.suptitle(f'{variable} of Motor {Motor} running at {Speed}% speed grouped by load')
fig.tight_layout()
if saving:
figures = Path(f"figures/{variable} by motor by grouped Load")
if not figures.exists():
figures.mkdir(parents=True)
fig.savefig(f"figures/{variable} by motor by grouped Load/{variable}_A{Motor}_by_grouped_load.png")
return fig
......@@ -381,3 +381,10 @@ def Spectrogram (
return Sx, SFT
def Density_spectrum (time: pd.Series | np.ndarray, signal: pd.Series | np.ndarray):
signal = signal - signal.mean()
b,a = scs.butter(7,0.99, btype='low', analog=False)
signal = scs.filtfilt(b,a,signal)
x,y = autocorrelation(time, signal)
signal_windowed = moving_window(y, 1)
return FFT(signal_windowed ,(time[1]-time[0])*1000, 32*len(signal_windowed) )
#%% Imports and variables
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import seaborn as sns
import scipy.signal as scs
from pathlib import Path
from tools.database import Database
from tools.utils import from_class_to_text
from tools.plots import plot_all_axis, plot_grouped_load, plot_moving_axes
DB = Database(f"D:\VSB\Programs\DB\Robot2-LoadTest.sqlite")
# %% plot motor 1 current with position in background
""" plt.figure(figsize=(9,6))
df = DB.robot(2).by_class(0).by_speed(70).by_moving_motor(1).run()
df['Sample_time'] -= df['Sample_time'].min()
plt.plot(df['Sample_time'],df['Current_A1'])
plt.ylabel('Current (A)')
plt.xlabel('Time (s)')
ax2 = plt.twinx()
ax2.plot(df['Sample_time'],df['Position_A1'],color='orange',alpha=0.3)
plt.ylabel('Motor position (°)')
plt.title('Motor 1 current (A) in time (s) moving at 70% speed ')
plt.show()
"""
# %% Curent plot by speed
""" fig1 = plot_all_axis(DB,'Lineplot','Current','Speed',[40,50,60,70,80],Motor=1)
plt.show() """
# %% Weight analysis
fig1 = plot_all_axis(DB,'Current','Class',[0,2],MovingMotor=1, saving=True)
fig2 = plot_grouped_load(DB, 'Current', [[0,2],[4,6],[8,10],[12,14]], 1, 60, doposition=True, saving=True)
fig3 = plot_moving_axes(DB,'Current','Class',[0,2], doposition=True,saving=True)
plt.show()
# %%
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment