File size: 7,263 Bytes
57537fb
 
 
 
 
 
 
 
 
 
 
753bf84
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
57537fb
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
9291a0b
 
 
 
 
 
 
 
 
 
 
57537fb
9291a0b
 
57537fb
 
 
 
 
 
 
9291a0b
 
 
 
 
 
 
 
 
 
57537fb
 
 
 
 
753bf84
 
 
 
 
 
 
 
 
 
 
 
 
 
07004f3
 
 
753bf84
07004f3
753bf84
 
 
 
 
 
 
 
 
57537fb
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
dfb98ef
 
57537fb
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
# ui.R
ui <- page_navbar(
    id = "main_nav",
    header = tagList(
        shinyjs::useShinyjs(),
        tags$head(
            tags$meta(charset = "utf-8"),
            tags$meta(`http-equiv` = "X-UA-Compatible", content = "IE=edge"),
            tags$meta(name = "viewport", content = "width=device-width, initial-scale=1"),
            # Include external CSS and JS from www/ folder
            tags$link(rel = "stylesheet", type = "text/css", href = "styles.css"),
            tags$script(src = "app.js"),
            # Layer Control Interactions
            tags$script(HTML("
                $(document).ready(function() {
                  // Layer Control Interactions
                  var $layerControl = $('.map-layer-control');

                  $layerControl.on('mouseenter', function() {
                    $(this).addClass('expanded');
                  });

                  $layerControl.on('mouseleave', function() {
                    $(this).removeClass('expanded');
                  });

                  // Auto-close when a radio button (basemap) is selected
                  $layerControl.on('change', 'input[type=\\'radio\\']', function() {
                    $layerControl.removeClass('expanded');
                  });
                });
            "))
        ),
        # Frozen overlay div
        div(
            class = "frozen-overlay",
            div(
                class = "frozen-overlay-content",
                tags$button(class = "frozen-overlay-close", "×", title = "Cancel loading"),
                p(class = "frozen-overlay-station", ""),
                div(class = "spinner-border text-primary", role = "status"),
                p(class = "frozen-overlay-message", "Loading data...")
            )
        )
    ),
    title = "JMA Explorer",
    theme = bs_theme(version = 5, bootswatch = "cosmo"),
    sidebar = sidebar(
        title = "Filters",
        # Data Resolution
        radioButtons("data_resolution", "Time Resolution", choices = c("10 Minutes", "Hourly", "Daily", "Monthly"), selected = "Daily", inline = TRUE),
        # Station Search
        selectizeInput("station_selector", "Find Station", choices = NULL, multiple = FALSE, options = list(placeholder = "Type to search...")),
        div(
            style = "display: flex; align-items: center; gap: 8px;",
            tags$label("Select Date Range"),
            tooltip(
                bsicons::bs_icon("info-circle", size = "1em"),
                "Filter stations that have data overlapping with this date range."
            )
        ),
        dateRangeInput("date_range",
            label = NULL,
            start = Sys.Date() - 366,
            end = Sys.Date(),
            min = "1872-01-01",
            max = Sys.Date(),
            format = "yyyy-mm-dd",
            separator = " to "
        ),
        hr(),
        strong(textOutput("visible_count", inline = TRUE)),
        hr(),
        p("Data source: JMA (Japan Meteorological Agency)"),
        p(style = "font-size: 0.8em; color: #666;", "Includes: 10-min, Hourly, Daily, and Monthly data"),
        hr(),
        div(
            style = "display: flex; align-items: flex-start; gap: 8px;",
            tags$small("Tip: Click map points to view detailed weather plots.")
        )
    ),
    nav_panel(
        title = "Map View",
        div(
            class = "outer",
            maplibreOutput("map", height = "100%", width = "100%"),

            # Layer Control Panel (Collapsible)
            absolutePanel(
                top = 130, left = 10,
                class = "map-layer-control",
                style = "z-index: 1000;",
                div(class = "control-icon", icon("layer-group")),
                div(
                    class = "control-content",
                    radioButtons(
                        inputId = "basemap",
                        label = "Basemap",
                        choices = c(
                            "OpenFreeMap Positron" = "ofm_positron",
                            "OpenFreeMap Bright" = "ofm_bright",
                            "Satellite (Sentinel-2)" = "sentinel"
                        ),
                        selected = "ofm_positron"
                    ),
                    hr(style = "margin: 8px 0;"),
                    checkboxInput(
                        inputId = "show_labels",
                        label = "Show Labels",
                        value = TRUE
                    )
                )
            ),

            # Home Button Overlay (matching DWD style)
            absolutePanel(
                id = "zoom_home_panel",
                top = 80, left = 10,
                actionButton("zoom_home", bsicons::bs_icon("house-fill"), class = "btn-home", title = "Zoom to all stations")
            )
        )
    ),
    nav_panel(
        title = "Station Info",
        div(
            class = "strict-table",
            style = "padding: 20px;",
            div(
                style = "margin-bottom: 10px; color: #666; display: flex; align-items: center; gap: 6px;",
                bsicons::bs_icon("info-circle"),
                "Double-click a row to load station data and view the dashboard."
            ),
            h4("Filtered Stations Metadata"),
            p("List of stations matching the current resolution and date filters."),
            DT::dataTableOutput("station_info_table")
        )
    ),
    nav_panel(
        title = "Dashboard",
        value = "Dashboard",
        # Empty State
        conditionalPanel(
            condition = "!output.station_ready",
            div(
                style = "height: 600px; display: flex; align-items: center; justify-content: center;",
                p("Select a station from the map or the dropdown to view the dashboard.", style = "color: #999; font-size: 1.2em;")
            )
        ),
        # Dashboard Content
        conditionalPanel(
            condition = "output.station_ready",
            div(
                class = "h-100 p-3",
                uiOutput("station_info_header"),
                navset_card_pill(
                    id = "dashboard_subtabs",
                    nav_panel(
                        title = "Plots",
                        div(
                            style = "padding: 0px;",
                            uiOutput("jma_plots_container")
                        )
                    ),
                    nav_panel(
                        title = "Data",
                        div(
                            style = "margin-top: 10px;",
                            DT::dataTableOutput("daily_data")
                        )
                    )
                )
            )
        )
    ),
    nav_spacer(),
    nav_item(
        tooltip(
            tags$a(
                id = "fullscreen_toggle",
                href = "#",
                onclick = "toggleFullScreen(); return false;",
                style = "display: flex; align-items: center; color: rgba(0,0,0,0.55); padding: 0.5rem 1rem; text-decoration: none;",
                bsicons::bs_icon("arrows-fullscreen", size = "1.2rem")
            ),
            "Toggle Fullscreen",
            placement = "bottom"
        )
    )
)