| import React from 'react' |
| import Plot from 'react-plotly.js' |
| import { Box, Text, Stack, Title, Group, Badge } from '@mantine/core' |
| import { useXRD } from '../context/XRDContext' |
|
|
| const XRDGraph = () => { |
| const { rawData, processedData, MODEL_MIN_2THETA, MODEL_MAX_2THETA } = useXRD() |
| |
| if (!rawData) { |
| return ( |
| <Box style={{ display: 'flex', alignItems: 'center', justifyContent: 'center', height: 350 }}> |
| <Text size="xl" c="dimmed"> |
| No data loaded |
| </Text> |
| </Box> |
| ) |
| } |
| |
| |
| const rawTrace = { |
| x: rawData.x, |
| y: rawData.y, |
| type: 'scattergl', |
| mode: 'lines', |
| name: 'Raw Data', |
| line: { |
| color: 'rgba(128, 128, 128, 1)', |
| width: 1.5, |
| }, |
| hovertemplate: '2θ: %{x:.2f}°<br>Intensity: %{y:.2f}<extra></extra>', |
| } |
| |
| |
| const processedTrace = processedData ? { |
| x: processedData.x, |
| y: processedData.y, |
| type: 'scattergl', |
| mode: 'lines', |
| name: 'Normalized', |
| line: { |
| color: 'rgba(30, 136, 229, 1)', |
| width: 2, |
| }, |
| hovertemplate: '2θ: %{x:.2f}°<br>Intensity: %{y:.4f}<extra></extra>', |
| } : null |
| |
| |
| const rawLayout = { |
| xaxis: { |
| title: { |
| text: '2θ (degrees)', |
| font: { |
| size: 14, |
| color: '#333', |
| }, |
| standoff: 10, |
| }, |
| gridcolor: 'rgba(128, 128, 128, 0.2)', |
| showline: true, |
| linewidth: 1, |
| linecolor: 'rgba(128, 128, 128, 0.3)', |
| mirror: true, |
| range: [Math.min(...rawData.x) - 0.5, Math.max(...rawData.x) + 0.5], |
| }, |
| yaxis: { |
| title: { |
| text: 'Intensity (a.u.)', |
| font: { |
| size: 14, |
| color: '#333', |
| }, |
| standoff: 10, |
| }, |
| gridcolor: 'rgba(128, 128, 128, 0.2)', |
| showline: true, |
| linewidth: 1, |
| linecolor: 'rgba(128, 128, 128, 0.3)', |
| mirror: true, |
| }, |
| hovermode: 'closest', |
| showlegend: false, |
| margin: { |
| l: 60, |
| r: 40, |
| t: 20, |
| b: 60, |
| }, |
| paper_bgcolor: 'transparent', |
| plot_bgcolor: 'transparent', |
| height: 280, |
| } |
| |
| |
| const processedLayout = { |
| xaxis: { |
| title: { |
| text: '2θ (degrees)', |
| font: { |
| size: 14, |
| color: '#333', |
| }, |
| standoff: 10, |
| }, |
| gridcolor: 'rgba(128, 128, 128, 0.2)', |
| range: [MODEL_MIN_2THETA - 0.5, MODEL_MAX_2THETA + 0.5], |
| showline: true, |
| linewidth: 1, |
| linecolor: 'rgba(128, 128, 128, 0.3)', |
| mirror: true, |
| }, |
| yaxis: { |
| title: { |
| text: 'Normalized Intensity', |
| font: { |
| size: 14, |
| color: '#333', |
| }, |
| standoff: 10, |
| }, |
| gridcolor: 'rgba(128, 128, 128, 0.2)', |
| range: [-5, 105], |
| showline: true, |
| linewidth: 1, |
| linecolor: 'rgba(128, 128, 128, 0.3)', |
| mirror: true, |
| }, |
| hovermode: 'closest', |
| showlegend: false, |
| margin: { |
| l: 60, |
| r: 40, |
| t: 20, |
| b: 60, |
| }, |
| paper_bgcolor: 'transparent', |
| plot_bgcolor: 'transparent', |
| height: 280, |
| shapes: [ |
| { |
| type: 'rect', |
| xref: 'x', |
| yref: 'paper', |
| x0: MODEL_MIN_2THETA, |
| y0: 0, |
| x1: MODEL_MAX_2THETA, |
| y1: 1, |
| fillcolor: 'rgba(147, 51, 234, 0.05)', |
| line: { |
| width: 0, |
| }, |
| }, |
| ], |
| } |
| |
| |
| const config = { |
| responsive: true, |
| displayModeBar: true, |
| displaylogo: false, |
| modeBarButtonsToRemove: ['lasso2d', 'select2d'], |
| } |
| |
| return ( |
| <Stack gap="md"> |
| {/* Raw Data Graph */} |
| <Box> |
| <Group justify="space-between" mb="xs"> |
| <Title order={5}>Original Data</Title> |
| <Badge color="gray" variant="light"> |
| {rawData.x.length} points |
| </Badge> |
| </Group> |
| <Plot |
| data={[rawTrace]} |
| layout={rawLayout} |
| config={config} |
| style={{ width: '100%' }} |
| useResizeHandler={true} |
| /> |
| </Box> |
| |
| {/* Processed Data Graph */} |
| {processedData && ( |
| <Box> |
| <Group justify="space-between" mb="xs"> |
| <Title order={5}>Normalized for Model Input</Title> |
| <Badge color="violet" variant="light"> |
| {processedData.x.length} points • {MODEL_MIN_2THETA}-{MODEL_MAX_2THETA}° |
| </Badge> |
| </Group> |
| <Plot |
| data={[processedTrace]} |
| layout={processedLayout} |
| config={config} |
| style={{ width: '100%' }} |
| useResizeHandler={true} |
| /> |
| </Box> |
| )} |
| </Stack> |
| ) |
| } |
|
|
| export default XRDGraph |
|
|