Add data_visualization/js/visualization.js
This commit is contained in:
parent
27cdb79e16
commit
ad22625c86
1 changed files with 144 additions and 0 deletions
144
data_visualization/js/visualization.js
Normal file
144
data_visualization/js/visualization.js
Normal file
|
|
@ -0,0 +1,144 @@
|
||||||
|
/* Visualization Logic for Kiesel Atmung Experiment */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @file visualization.js
|
||||||
|
* @description Visualization of temperature and audio intensity data using Chart.js.
|
||||||
|
* Provides two main render functions: renderTemperatureChart() and renderAudioChart().
|
||||||
|
*/
|
||||||
|
|
||||||
|
let temperatureChart = null;
|
||||||
|
let audioChart = null;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper to format time labels for Chart.js.
|
||||||
|
* @param {string|number|Date} timestamp
|
||||||
|
* @returns {string}
|
||||||
|
*/
|
||||||
|
const formatTime = (timestamp) => {
|
||||||
|
const date = new Date(timestamp);
|
||||||
|
return date.toLocaleTimeString([], { hour: '2-digit', minute: '2-digit' });
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @function renderTemperatureChart
|
||||||
|
* @description Creates or updates the temperature time series chart.
|
||||||
|
* @param {Array<{time: string|number|Date, value: number}>} data
|
||||||
|
* @returns {void}
|
||||||
|
*/
|
||||||
|
export function renderTemperatureChart(data = []) {
|
||||||
|
const ctx = document.getElementById('temperature-chart');
|
||||||
|
if (!ctx) return;
|
||||||
|
|
||||||
|
const labels = data.map(d => formatTime(d.time));
|
||||||
|
const values = data.map(d => d.value);
|
||||||
|
|
||||||
|
const config = {
|
||||||
|
type: 'line',
|
||||||
|
data: {
|
||||||
|
labels,
|
||||||
|
datasets: [{
|
||||||
|
label: 'Temperatur (°C)',
|
||||||
|
data: values,
|
||||||
|
borderColor: 'rgba(255, 99, 132, 1)',
|
||||||
|
backgroundColor: 'rgba(255, 99, 132, 0.2)',
|
||||||
|
tension: 0.25,
|
||||||
|
pointRadius: 2,
|
||||||
|
fill: true
|
||||||
|
}]
|
||||||
|
},
|
||||||
|
options: {
|
||||||
|
responsive: true,
|
||||||
|
maintainAspectRatio: false,
|
||||||
|
scales: {
|
||||||
|
x: {
|
||||||
|
title: { display: true, text: 'Zeit' },
|
||||||
|
ticks: { autoSkip: true, maxTicksLimit: 8 }
|
||||||
|
},
|
||||||
|
y: {
|
||||||
|
title: { display: true, text: '°C' }
|
||||||
|
}
|
||||||
|
},
|
||||||
|
plugins: {
|
||||||
|
tooltip: {
|
||||||
|
mode: 'index',
|
||||||
|
intersect: false,
|
||||||
|
callbacks: {
|
||||||
|
label: ctx => `${ctx.parsed.y.toFixed(2)} °C`
|
||||||
|
}
|
||||||
|
},
|
||||||
|
legend: { display: true }
|
||||||
|
},
|
||||||
|
interaction: {
|
||||||
|
mode: 'nearest',
|
||||||
|
axis: 'x',
|
||||||
|
intersect: false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
if (temperatureChart) {
|
||||||
|
temperatureChart.data = config.data;
|
||||||
|
temperatureChart.update();
|
||||||
|
} else {
|
||||||
|
temperatureChart = new Chart(ctx, config);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @function renderAudioChart
|
||||||
|
* @description Displays audio intensity over time as a bar chart.
|
||||||
|
* @param {Array<{time: string|number|Date, amplitude: number}>} data
|
||||||
|
* @returns {void}
|
||||||
|
*/
|
||||||
|
export function renderAudioChart(data = []) {
|
||||||
|
const ctx = document.getElementById('audio-chart');
|
||||||
|
if (!ctx) return;
|
||||||
|
|
||||||
|
const labels = data.map(d => formatTime(d.time));
|
||||||
|
const values = data.map(d => d.amplitude);
|
||||||
|
|
||||||
|
const config = {
|
||||||
|
type: 'bar',
|
||||||
|
data: {
|
||||||
|
labels,
|
||||||
|
datasets: [{
|
||||||
|
label: 'Audiointensität',
|
||||||
|
data: values,
|
||||||
|
backgroundColor: 'rgba(54, 162, 235, 0.5)',
|
||||||
|
borderColor: 'rgba(54, 162, 235, 1)',
|
||||||
|
borderWidth: 1
|
||||||
|
}]
|
||||||
|
},
|
||||||
|
options: {
|
||||||
|
responsive: true,
|
||||||
|
maintainAspectRatio: false,
|
||||||
|
scales: {
|
||||||
|
x: {
|
||||||
|
title: { display: true, text: 'Zeit' },
|
||||||
|
ticks: { autoSkip: true, maxTicksLimit: 8 }
|
||||||
|
},
|
||||||
|
y: {
|
||||||
|
title: { display: true, text: 'Amplitude' },
|
||||||
|
beginAtZero: true
|
||||||
|
}
|
||||||
|
},
|
||||||
|
plugins: {
|
||||||
|
tooltip: {
|
||||||
|
callbacks: {
|
||||||
|
label: ctx => `${ctx.parsed.y.toFixed(2)}`
|
||||||
|
}
|
||||||
|
},
|
||||||
|
legend: { display: true }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
if (audioChart) {
|
||||||
|
audioChart.data = config.data;
|
||||||
|
audioChart.update();
|
||||||
|
} else {
|
||||||
|
audioChart = new Chart(ctx, config);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// End of visualization logic
|
||||||
Loading…
Reference in a new issue