apmtools 0.2.22__tar.gz → 0.2.24__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.5
2
2
  Name: apmtools
3
- Version: 0.2.022
3
+ Version: 0.2.024
4
4
  Summary: A collection of tools for processing air pollution monitoring data
5
5
  Project-URL: Homepage, https://github.com/federlorenz/apmtools
6
6
  Author-email: Federico Lorenzetti <lorenzetti.federico@gmail.com>
@@ -4,7 +4,7 @@ build-backend = "hatchling.build"
4
4
 
5
5
  [project]
6
6
  name = "apmtools"
7
- version = "0.2.022"
7
+ version = "0.2.024"
8
8
  authors = [
9
9
  { name="Federico Lorenzetti", email="lorenzetti.federico@gmail.com" },
10
10
  ]
@@ -449,72 +449,7 @@ def create_summary_app(
449
449
  subset_columns = columns
450
450
 
451
451
  app_ui = ui.page_sidebar(
452
- ui.div(
453
- ui.tags.style("""
454
- /* Allow the main pane to consume all width remaining after the sidebar. */
455
- .bslib-sidebar-layout > .main,
456
- .bslib-sidebar-layout > main,
457
- .bslib-sidebar-layout .main {
458
- min-width: 0;
459
- width: 100%;
460
- max-width: none;
461
- }
462
- /* Remove the default Bootstrap container width limit, if present. */
463
- .container, .container-fluid { max-width: none !important; }
464
- .summary-plot-container {
465
- width: 100%;
466
- max-width: none;
467
- aspect-ratio: 2 / 1;
468
- min-width: 0;
469
- min-height: 0;
470
- padding: 0;
471
- margin: 0;
472
- position: relative;
473
- }
474
- .summary-plot-container > .html-widget-output,
475
- .summary-plot-container > .shiny-plot-output,
476
- .summary-plot-container > #plot {
477
- width: 100% !important;
478
- height: 100% !important;
479
- max-width: none !important;
480
- }
481
- """),
482
- ui.tags.script("""
483
- // Plotly sometimes retains the pixel width measured before the
484
- // Shiny sidebar and widget have finished laying out.
485
- (() => {
486
- function resizePlot() {
487
- const container = document.querySelector('.summary-plot-container');
488
- if (!container || !window.Plotly) return;
489
- const graph = container.querySelector('.js-plotly-plot');
490
- if (graph) window.Plotly.Plots.resize(graph);
491
- }
492
- const observer = new ResizeObserver(resizePlot);
493
- const attach = () => {
494
- const container = document.querySelector('.summary-plot-container');
495
- if (!container) return false;
496
- observer.observe(container);
497
- resizePlot();
498
- return true;
499
- };
500
- document.addEventListener('DOMContentLoaded', attach);
501
- window.addEventListener('resize', resizePlot);
502
- if (!attach()) {
503
- const startup = new MutationObserver((_, watcher) => {
504
- if (attach()) watcher.disconnect();
505
- });
506
- startup.observe(document.documentElement, {
507
- childList: true, subtree: true
508
- });
509
- }
510
- })();
511
- """),
512
- ui.div(
513
- output_widget("plot", height="100%", width="100%"),
514
- class_="summary-plot-container",
515
- ),
516
- ),
517
- sidebar=ui.sidebar(
452
+ ui.sidebar(
518
453
  ui.h4("Plot controls"),
519
454
  ui.input_select("plot_type", "Plot type",
520
455
  choices=PLOT_TYPES, selected=plot_type),
@@ -578,6 +513,86 @@ def create_summary_app(
578
513
  "Summary.group_stat()."
579
514
  ),
580
515
  ),
516
+ ui.div(
517
+ ui.tags.style("""
518
+ /* Allow the main pane to consume all width remaining after the sidebar. */
519
+ .bslib-sidebar-layout > .main,
520
+ .bslib-sidebar-layout > main,
521
+ .bslib-sidebar-layout .main {
522
+ min-width: 0;
523
+ width: 100%;
524
+ max-width: none;
525
+ }
526
+ /* Remove the default Bootstrap container width limit, if present. */
527
+ .container, .container-fluid { max-width: none !important; }
528
+ .summary-plot-container {
529
+ width: 100%;
530
+ max-width: none;
531
+ /* Height is set from actual rendered width by ResizeObserver. */
532
+ height: 500px;
533
+ min-width: 0;
534
+ min-height: 0;
535
+ padding: 0;
536
+ margin: 0;
537
+ position: relative;
538
+ }
539
+ .summary-plot-container > .html-widget-output,
540
+ .summary-plot-container > .shiny-plot-output,
541
+ .summary-plot-container > #plot {
542
+ width: 100% !important;
543
+ height: 100% !important;
544
+ max-width: none !important;
545
+ }
546
+ """),
547
+ ui.tags.script("""
548
+ (() => {
549
+ // Calculate the actual height in pixels from the rendered width.
550
+ // CSS aspect-ratio alone does not reliably size shinywidgets.
551
+ const install = () => {
552
+ const container = document.querySelector('.summary-plot-container');
553
+ if (!container || container.dataset.aspectObserverInstalled) return !!container;
554
+ container.dataset.aspectObserverInstalled = '1';
555
+ let previousWidth = 0;
556
+ const resize = () => {
557
+ const width = container.getBoundingClientRect().width;
558
+ if (width <= 0) return;
559
+ const height = Math.round(width / 2);
560
+ if (width === previousWidth && container.style.height === `${height}px`) return;
561
+ previousWidth = width;
562
+ container.style.height = `${height}px`;
563
+ const widget = container.querySelector('#plot');
564
+ if (widget) {
565
+ widget.style.width = '100%';
566
+ widget.style.height = `${height}px`;
567
+ }
568
+ const graph = container.querySelector('.js-plotly-plot');
569
+ if (graph && window.Plotly) {
570
+ // Plotly sometimes retains a previous fixed pixel height.
571
+ window.Plotly.relayout(graph, {width: Math.round(width), height: height});
572
+ }
573
+ };
574
+ const observer = new ResizeObserver(resize);
575
+ observer.observe(container);
576
+ window.addEventListener('resize', resize);
577
+ // React to Shiny rendering a new Plotly graph.
578
+ const mutation = new MutationObserver(() => requestAnimationFrame(resize));
579
+ mutation.observe(container, {childList: true, subtree: false});
580
+ requestAnimationFrame(resize);
581
+ return true;
582
+ };
583
+ if (!install()) {
584
+ const startup = new MutationObserver((_, watcher) => {
585
+ if (install()) watcher.disconnect();
586
+ });
587
+ startup.observe(document.documentElement, {childList: true, subtree: true});
588
+ }
589
+ })();
590
+ """),
591
+ ui.div(
592
+ output_widget("plot", height="100%", width="100%"),
593
+ class_="summary-plot-container",
594
+ ),
595
+ ),
581
596
  )
582
597
 
583
598
  def server(input, output, session):
File without changes
File without changes
File without changes