@@ -281,10 +281,8 @@ const JobsBase: React.FC<JobsBaseProps> = ({
281
281
< Typography
282
282
variant = "body2"
283
283
sx = { {
284
- overflow : 'hidden' ,
285
- textOverflow : 'ellipsis' ,
286
- whiteSpace : 'nowrap' ,
287
- maxWidth : '240px' ,
284
+ ...ellipsisWrap ,
285
+ maxWidth : `calc(${ ellipsisWrap . maxWidth } + 60px)` ,
288
286
} }
289
287
title = { output }
290
288
>
@@ -353,13 +351,17 @@ const JobsBase: React.FC<JobsBaseProps> = ({
353
351
variant = "body2"
354
352
sx = { {
355
353
fontWeight : 'bold' ,
356
- marginRight : '4px ' ,
354
+ marginRight : '16px ' ,
357
355
whiteSpace : 'nowrap' , // Stops the key from wrapping
358
356
} }
359
357
>
360
358
{ key } :
361
359
</ Typography >
362
- < Typography variant = "body2" sx = { { flex : '1 1 auto' } } >
360
+ < Typography
361
+ variant = "body2"
362
+ title = { String ( value ) }
363
+ sx = { { flex : '1 1 auto' , ...ellipsisWrap , maxWidth : `calc(${ ellipsisWrap . maxWidth } + 300px)` } }
364
+ >
363
365
{ value }
364
366
</ Typography >
365
367
</ Box >
@@ -416,7 +418,7 @@ const JobsBase: React.FC<JobsBaseProps> = ({
416
418
} ) ;
417
419
} ;
418
420
419
- const rowStyles = {
421
+ const bandedRows = {
420
422
backgroundColor :
421
423
index % 2 === 0
422
424
? theme . palette . mode === 'light'
@@ -427,7 +429,7 @@ const JobsBase: React.FC<JobsBaseProps> = ({
427
429
: theme . palette . background . default , // Odd rows (default background color)
428
430
} ;
429
431
430
- const hoverStyles = ( theme : Theme , index : number ) : React . CSSProperties => {
432
+ const bandedRowsHover = ( theme : Theme , index : number ) : React . CSSProperties => {
431
433
return {
432
434
backgroundColor :
433
435
theme . palette . mode === 'light'
@@ -440,11 +442,50 @@ const JobsBase: React.FC<JobsBaseProps> = ({
440
442
} ;
441
443
} ;
442
444
445
+ const ellipsisWrap = {
446
+ whiteSpace : 'nowrap' ,
447
+ overflow : 'hidden' ,
448
+ textOverflow : 'ellipsis' ,
449
+ maxWidth : '200px' ,
450
+ } ;
451
+
443
452
const formatJobType = ( jobType : string ) : string => {
444
453
const formattedType = jobType . replace ( 'JobType.' , '' ) ;
445
454
return formattedType . charAt ( 0 ) . toUpperCase ( ) + formattedType . slice ( 1 ) . toLowerCase ( ) ;
446
455
} ;
447
456
457
+ const runDetails = [
458
+ { icon : < VpnKey fontSize = "small" /> , label : 'Reduction ID:' , value : job . id } ,
459
+ { icon : < WorkOutline fontSize = "small" /> , label : 'Job type:' , value : job . type ? formatJobType ( job . type ) : 'N/A' } ,
460
+ {
461
+ icon : < ImageAspectRatio fontSize = "small" /> ,
462
+ label : 'Runner image:' ,
463
+ value : job . runner_image || 'N/A' ,
464
+ } ,
465
+ { icon : < Schema fontSize = "small" /> , label : 'Instrument:' , value : job . run ?. instrument_name || 'N/A' } ,
466
+ {
467
+ icon : < Schedule fontSize = "small" /> ,
468
+ label : 'Reduction start:' ,
469
+ value : formatDateTime ( job . start ) || 'N/A' ,
470
+ } ,
471
+ {
472
+ icon : < Schedule fontSize = "small" /> ,
473
+ label : 'Reduction end:' ,
474
+ value : formatDateTime ( job . end ) || 'N/A' ,
475
+ } ,
476
+ {
477
+ icon : < StackedBarChart fontSize = "small" /> ,
478
+ label : 'Good frames:' ,
479
+ value : job . run ?. good_frames ?. toLocaleString ( ) || 'N/A' ,
480
+ } ,
481
+ {
482
+ icon : < StackedBarChart fontSize = "small" /> ,
483
+ label : 'Raw frames:' ,
484
+ value : job . run ?. raw_frames ?. toLocaleString ( ) || 'N/A' ,
485
+ } ,
486
+ { icon : < People fontSize = "small" /> , label : 'Users:' , value : job . run ?. users || 'N/A' } ,
487
+ ] ;
488
+
448
489
return (
449
490
< >
450
491
< Snackbar
@@ -479,28 +520,82 @@ const JobsBase: React.FC<JobsBaseProps> = ({
479
520
</ Alert >
480
521
</ Snackbar >
481
522
482
- < TableRow sx = { { ...rowStyles , '&:hover' : hoverStyles ( theme , index ) } } onClick = { ( ) => setOpen ( ! open ) } >
483
- < TableCell sx = { { width : '4%' } } >
523
+ < TableRow
524
+ sx = { {
525
+ ...bandedRows ,
526
+ height : '50px' ,
527
+ '&:hover' : bandedRowsHover ( theme , index ) ,
528
+ } }
529
+ onClick = { ( ) => setOpen ( ! open ) }
530
+ >
531
+ < TableCell >
484
532
< IconButton aria-label = "expand row" size = "small" >
485
533
{ open ? < KeyboardArrowUp /> : < KeyboardArrowDown /> }
486
534
</ IconButton >
487
535
</ TableCell >
488
- < TableCell sx = { { width : '4%' } } >
536
+ < TableCell
537
+ sx = { {
538
+ ...ellipsisWrap ,
539
+ } }
540
+ >
489
541
< JobStatus state = { job . state } />
490
542
</ TableCell >
491
- < TableCell sx = { { width : '12%' } } > { job . run ?. experiment_number || 'N/A' } </ TableCell >
492
- < TableCell sx = { { width : '10%' } } > { extractFileName ( job . run ?. filename || 'N/A' ) } </ TableCell >
493
- < TableCell sx = { { width : '15%' } } > { formatDateTime ( job . run ?. run_start || 'N/A' ) } </ TableCell >
494
- < TableCell sx = { { width : '15%' } } > { formatDateTime ( job . run ?. run_end || 'N/A' ) } </ TableCell >
495
- < TableCell sx = { { width : '15%' } } > { job . start ? formatDateTime ( job . start ) : 'N/A' } </ TableCell >
496
- < TableCell sx = { { width : '15%' } } > { job . end ? formatDateTime ( job . end ) : 'N/A' } </ TableCell >
497
- < TableCell sx = { { width : '32%' } } > { job . run ?. title || 'N/A' } </ TableCell >
543
+ < TableCell
544
+ sx = { {
545
+ ...ellipsisWrap ,
546
+ } }
547
+ >
548
+ { job . run ?. experiment_number || 'N/A' }
549
+ </ TableCell >
550
+ < TableCell
551
+ sx = { {
552
+ ...ellipsisWrap ,
553
+ } }
554
+ >
555
+ { extractFileName ( job . run ?. filename || 'N/A' ) }
556
+ </ TableCell >
557
+ < TableCell
558
+ sx = { {
559
+ ...ellipsisWrap ,
560
+ } }
561
+ >
562
+ { formatDateTime ( job . run ?. run_start || 'N/A' ) }
563
+ </ TableCell >
564
+ < TableCell
565
+ sx = { {
566
+ ...ellipsisWrap ,
567
+ } }
568
+ >
569
+ { formatDateTime ( job . run ?. run_end || 'N/A' ) }
570
+ </ TableCell >
571
+ < TableCell
572
+ sx = { {
573
+ ...ellipsisWrap ,
574
+ } }
575
+ >
576
+ { formatDateTime ( job . start ) || 'N/A' }
577
+ </ TableCell >
578
+ < TableCell
579
+ sx = { {
580
+ ...ellipsisWrap ,
581
+ } }
582
+ >
583
+ { formatDateTime ( job . end ) || 'N/A' }
584
+ </ TableCell >
585
+ < TableCell
586
+ sx = { {
587
+ ...ellipsisWrap ,
588
+ } }
589
+ >
590
+ { job . run ?. title || 'N/A' }
591
+ </ TableCell >
498
592
{ customRowCells && customRowCells ( job ) }
499
593
</ TableRow >
594
+
500
595
< TableRow >
501
596
< TableCell
502
597
colSpan = { totalColumnCount }
503
- style = { { paddingBottom : 0 , paddingTop : 0 , backgroundColor : rowStyles . backgroundColor } }
598
+ style = { { paddingBottom : 0 , paddingTop : 0 , backgroundColor : bandedRows . backgroundColor } }
504
599
>
505
600
< Collapse in = { open } timeout = "auto" unmountOnExit >
506
601
< Box margin = { 2 } >
@@ -534,80 +629,25 @@ const JobsBase: React.FC<JobsBaseProps> = ({
534
629
< Typography variant = "h6" gutterBottom sx = { { fontWeight : 'bold' } } >
535
630
Run details
536
631
</ Typography >
537
- < Box sx = { { display : 'flex' , alignItems : 'center' , marginBottom : '4px' } } >
538
- < VpnKey fontSize = "small" style = { { marginRight : '8px' } } />
539
- < Typography variant = "body2" sx = { { fontWeight : 'bold' , marginRight : '4px' } } >
540
- Reduction ID:
541
- </ Typography >
542
- < Typography variant = "body2" > { job . id } </ Typography >
543
- </ Box >
544
- < Box sx = { { display : 'flex' , alignItems : 'center' , marginBottom : '4px' } } >
545
- < WorkOutline fontSize = "small" style = { { marginRight : '8px' } } />
546
- < Typography variant = "body2" sx = { { fontWeight : 'bold' , marginRight : '4px' } } >
547
- Job type:
548
- </ Typography >
549
- < Typography variant = "body2" > { job . type ? formatJobType ( job . type ) : 'N/A' } </ Typography >
550
- </ Box >
551
- < Box sx = { { display : 'flex' , alignItems : 'center' , marginBottom : '4px' } } >
552
- < ImageAspectRatio fontSize = "small" style = { { marginRight : '8px' } } />
553
- < Typography variant = "body2" sx = { { fontWeight : 'bold' , marginRight : '4px' } } >
554
- Runner image:
555
- </ Typography >
556
- < Typography
557
- variant = "body2"
632
+ { runDetails . map ( ( { icon, label, value } , index ) => (
633
+ < Box
634
+ key = { index }
558
635
sx = { {
559
- whiteSpace : 'nowrap ' ,
560
- overflow : 'hidden ' ,
561
- textOverflow : 'ellipsis' ,
562
- maxWidth : '200px ' ,
636
+ display : 'flex ' ,
637
+ alignItems : 'center ' ,
638
+ gap : 1 ,
639
+ marginBottom : '4px ' ,
563
640
} }
564
- title = { job . runner_image }
565
641
>
566
- { job . runner_image ? job . runner_image : 'N/A' }
567
- </ Typography >
568
- </ Box >
569
- < Box sx = { { display : 'flex' , alignItems : 'center' , marginBottom : '4px' } } >
570
- < Schema fontSize = "small" style = { { marginRight : '8px' } } />
571
- < Typography variant = "body2" sx = { { fontWeight : 'bold' , marginRight : '4px' } } >
572
- Instrument:
573
- </ Typography >
574
- < Typography variant = "body2" > { job . run ?. instrument_name || 'N/A' } </ Typography >
575
- </ Box >
576
- < Box sx = { { display : 'flex' , alignItems : 'center' , marginBottom : '4px' } } >
577
- < Schedule fontSize = "small" style = { { marginRight : '8px' } } />
578
- < Typography variant = "body2" sx = { { fontWeight : 'bold' , marginRight : '4px' } } >
579
- Reduction start:
580
- </ Typography >
581
- < Typography variant = "body2" > { job . start ? formatDateTime ( job . start ) : 'N/A' } </ Typography >
582
- </ Box >
583
- < Box sx = { { display : 'flex' , alignItems : 'center' , marginBottom : '4px' } } >
584
- < Schedule fontSize = "small" style = { { marginRight : '8px' } } />
585
- < Typography variant = "body2" sx = { { fontWeight : 'bold' , marginRight : '4px' } } >
586
- Reduction end:
587
- </ Typography >
588
- < Typography variant = "body2" > { job . end ? formatDateTime ( job . end ) : 'N/A' } </ Typography >
589
- </ Box >
590
- < Box sx = { { display : 'flex' , alignItems : 'center' , marginBottom : '4px' } } >
591
- < StackedBarChart fontSize = "small" style = { { marginRight : '8px' } } />
592
- < Typography variant = "body2" sx = { { fontWeight : 'bold' , marginRight : '4px' } } >
593
- Good frames:
594
- </ Typography >
595
- < Typography variant = "body2" > { job . run ?. good_frames ?. toLocaleString ( ) || 'N/A' } </ Typography >
596
- </ Box >
597
- < Box sx = { { display : 'flex' , alignItems : 'center' , marginBottom : '4px' } } >
598
- < StackedBarChart fontSize = "small" style = { { marginRight : '8px' } } />
599
- < Typography variant = "body2" sx = { { fontWeight : 'bold' , marginRight : '4px' } } >
600
- Raw frames:
601
- </ Typography >
602
- < Typography variant = "body2" > { job . run ?. raw_frames ?. toLocaleString ( ) || 'N/A' } </ Typography >
603
- </ Box >
604
- < Box sx = { { display : 'flex' , alignItems : 'center' , marginBottom : '4px' } } >
605
- < People fontSize = "small" style = { { marginRight : '8px' } } />
606
- < Typography variant = "body2" sx = { { fontWeight : 'bold' , marginRight : '4px' } } >
607
- Users:
608
- </ Typography >
609
- < Typography variant = "body2" > { job . run ?. users || 'N/A' } </ Typography >
610
- </ Box >
642
+ { React . cloneElement ( icon , { sx : { mr : 1 , flexShrink : 0 } } ) }
643
+ < Typography variant = "body2" sx = { { fontWeight : 'bold' , mr : 1 , display : 'inline' } } >
644
+ { label }
645
+ </ Typography >
646
+ < Typography variant = "body2" sx = { { ...ellipsisWrap , display : 'inline' } } title = { String ( value ) } >
647
+ { value }
648
+ </ Typography >
649
+ </ Box >
650
+ ) ) }
611
651
</ Grid >
612
652
< Grid size = { 5 } >
613
653
< Typography variant = "h6" gutterBottom sx = { { fontWeight : 'bold' } } >
@@ -715,10 +755,10 @@ const JobsBase: React.FC<JobsBaseProps> = ({
715
755
onRowsPerPageChange = { handleChangeRowsPerPage }
716
756
/>
717
757
< TableContainer component = { Paper } style = { { maxHeight, overflowY : 'scroll' } } >
718
- < Table stickyHeader >
758
+ < Table stickyHeader sx = { { tableLayout : 'fixed' , width : '100%' } } >
719
759
< TableHead >
720
760
< TableRow >
721
- < TableCell sx = { { ...headerStyles ( theme ) , width : '4 %' } } colSpan = { 2 } >
761
+ < TableCell sx = { { ...headerStyles ( theme ) , width : '10 %' } } colSpan = { 2 } >
722
762
{ selectedInstrument }
723
763
</ TableCell >
724
764
< TableCell
@@ -727,22 +767,22 @@ const JobsBase: React.FC<JobsBaseProps> = ({
727
767
>
728
768
Experiment number { orderBy === 'experiment_number' ? ( orderDirection === 'asc' ? '↑' : '↓' ) : '' }
729
769
</ TableCell >
730
- < TableCell sx = { { width : '10 %' , ...headerStyles ( theme ) } } onClick = { ( ) => handleSort ( 'filename' ) } >
770
+ < TableCell sx = { { width : '8 %' , ...headerStyles ( theme ) } } onClick = { ( ) => handleSort ( 'filename' ) } >
731
771
Filename { orderBy === 'filename' ? ( orderDirection === 'asc' ? '↑' : '↓' ) : '' }
732
772
</ TableCell >
733
- < TableCell sx = { { width : '15 %' , ...headerStyles ( theme ) } } onClick = { ( ) => handleSort ( 'run_start' ) } >
773
+ < TableCell sx = { { width : '12 %' , ...headerStyles ( theme ) } } onClick = { ( ) => handleSort ( 'run_start' ) } >
734
774
Run start { orderBy === 'run_start' ? ( orderDirection === 'asc' ? '↑' : '↓' ) : '' }
735
775
</ TableCell >
736
- < TableCell sx = { { width : '15 %' , ...headerStyles ( theme ) } } onClick = { ( ) => handleSort ( 'run_end' ) } >
776
+ < TableCell sx = { { width : '12 %' , ...headerStyles ( theme ) } } onClick = { ( ) => handleSort ( 'run_end' ) } >
737
777
Run end { orderBy === 'run_end' ? ( orderDirection === 'asc' ? '↑' : '↓' ) : '' }
738
778
</ TableCell >
739
- < TableCell sx = { { width : '15 %' , ...headerStyles ( theme ) } } onClick = { ( ) => handleSort ( 'start' ) } >
779
+ < TableCell sx = { { width : '12 %' , ...headerStyles ( theme ) } } onClick = { ( ) => handleSort ( 'start' ) } >
740
780
Job start { orderBy === 'start' ? ( orderDirection === 'asc' ? '↑' : '↓' ) : '' }
741
781
</ TableCell >
742
- < TableCell sx = { { width : '15 %' , ...headerStyles ( theme ) } } onClick = { ( ) => handleSort ( 'end' ) } >
782
+ < TableCell sx = { { width : '12 %' , ...headerStyles ( theme ) } } onClick = { ( ) => handleSort ( 'end' ) } >
743
783
Job end { orderBy === 'end' ? ( orderDirection === 'asc' ? '↑' : '↓' ) : '' }
744
784
</ TableCell >
745
- < TableCell sx = { { width : '32 %' , ...headerStyles ( theme ) } } > Title</ TableCell >
785
+ < TableCell sx = { { width : '24 %' , ...headerStyles ( theme ) } } > Title</ TableCell >
746
786
{ customHeaders && customHeaders }
747
787
</ TableRow >
748
788
</ TableHead >
0 commit comments