commit b856cb894f734d92b275e8caba5c56b45d54656c Author: floppydiskette Date: Wed Dec 11 21:20:28 2024 +0000 add sauce diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..39ef9b0 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +data/ +.vscode/ diff --git a/css/colours.css b/css/colours.css new file mode 100644 index 0000000..2bfeddc --- /dev/null +++ b/css/colours.css @@ -0,0 +1,40 @@ +/* ------------------------------------------------------------------- + * Colours for the CumulusMX Alternative Interface + * Produced using w3Schools colour generator + * + * Key Colour: #4e5b31 + * + * Theme modified to change font 'color's to either lightest or darkest + * theme colour. Also modified names for text, borders & hover colours. + * I have added a few extras. Not all are used. + * Neil Thomas + ------------------------------------------------------------------*/ + +/* Check that your theme is named as shown below */ + +.w3-theme-white {color:#2e5473; background-color:#FFFFFF;} +.w3-theme-l5 {color:#2e5473; background-color:#f7fafc;} +.w3-theme-l4 {color:#2e5473; background-color:#e4edf4;} +.w3-theme-l3 {color:#2e5473 ; background-color:#c9dbe9;} +.w3-theme-l2 {color:#2e5473 ; background-color:#aec9df;} +.w3-theme-l1 {color:#2e5473 ; background-color:#93b7d4;} +.w3-theme-d1 {color:#f7fafc ; background-color:#6195c0;} +.w3-theme-d2 {color:#f7fafc ; background-color:#4a86b7;} +.w3-theme-d3 {color:#f7fafc ; background-color:#4075a1;} +.w3-theme-d4 {color:#f7fafc ; background-color:#37658a;} +.w3-theme-d5 {color:#f7fafc ; background-color:#2e5473;} + +.w3-theme-light {color:#2e5473 ; background-color:#f7fafc;} +.w3-theme-dark {color:#f7fafc ; background-color:#2e5473;} +.w3-theme-action {color:#f7fafc ; background-color:#2e5473;} + +.w3-theme {color:#f7fafc ; background-color:#78a5c9;} +.w3-theme-txt {color:#78a5c9;} +.w3-theme-bdr {border-color:#78a5c9;} +.w3-theme-d5-bdr {border-color:#2e5473;} +.w3-theme-l1-bdr {border-color:#f7fafc;} + +.w3-theme-hvr:hover {color:#f7fafc; background-color:#78a5c9;} +.w3-theme-d5-hvr:hover {color:#f7fafc; background-color:#2e5473;} +.w3-theme-txt-hvr:hover {color:#78a5c9;} +.w3-theme-bdr-hvr:hover {border-color:#78a5c9;} diff --git a/css/gauges.css b/css/gauges.css new file mode 100644 index 0000000..ed4068b --- /dev/null +++ b/css/gauges.css @@ -0,0 +1,101 @@ +/* CSS for SteelSeries Gauges + * Mark Crossley | modified by Neil Thomas + * v2.5.0 - 03 Dec 2014 | Feb 2021 + */ + +.gauge { + position: relative; +} + +.odo { + position: absolute; + top: 67%; + left: 50%; + transform: translateX(-50%); + -webkit-transform: translateX(-50%); +} +.gaugeSmall { + max-width:181px; + max-height: 181px; + width:100%; + height:100%; +} +.at-gaugeSmall { + width: 221px; + margin-left:8px; + margin-right:8px; +} + +.gaugeMedium { + max-width: 221px; + max-height:221px; +} +.at-gaugeMedium { + width: 261px; + margin-left:8px; + margin-right:8px; +} + +.gaugeLarge { + max-width:261px; + max-height:261px; + width:100%; + height:100%; +} + +.at-gaugeLarge { + width:301px; + margin-left:8px; + margin-right:8px; +} + +@media screen and (max-width:550px) { + .at-gaugeSmall { width:100%; } + .at-gaugeMedium{ width:100%;} +} + +@media screenand (max-width:640px) { + .at-gaugeLarge { width:100%;} + } + +@font-face { + font-family: 'LCDMono2Ultra'; + src: url('data:font/woff;charset=utf-8;base64,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') format('woff'), + url('../fonts/lcdmono2ultra-webfont.eot'), + url('../fonts/lcdmono2ultra-webfont.ttf') format('truetype'), + url('../fonts/lcdmono2ultra-webfont.svg#LCDMono2Ultra') format('svg'); + font-weight: normal; + font-style: normal; +} + +.ddimgtooltip{ + z-index: 2000; + box-shadow: 3px 3px 5px #818181; /*shadow for CSS3 capable browsers.*/ + border-radius: 8px; + display: none; + position: absolute; + border: 2px solid #2e5473!important; /* Changed to match d5 of theme */ + background: #f7fafc!important; /* Changed to match l1 of theme */ + color: #2e5473!important; /* Changed to match d5 of theme */ + padding: 0 7px 3px 7px; + /*font-family: sans-serif; */ + font-size: 86%!important; + max-width: 300px; +} + +.tipinfo{ + text-align: left; + padding: 3px 0 3px 2px; +} + +.tipinfo h5, .tipinfo h6 { + + line-height:1.2em; + margin:0; + padding:0; +} + +.tipimg{ + width: 438px; /* suggest 380 for wxgraphs */ + height: 175px; /* suggest 260 for wxgraphs */ +} diff --git a/css/mx-templates.css b/css/mx-templates.css new file mode 100644 index 0000000..906ff38 --- /dev/null +++ b/css/mx-templates.css @@ -0,0 +1,249 @@ +/* ----------------------------------- + * Styles for CumulusMX Templates + Last modified: 2021/03/19 09:23:15 + * ----------------------------------*/ + +html, +body, +p, +h1, +h2, +h3, +h4, +h5, +h6, +li, +td, +th { + font-family: "Rosario", sans-serif; +} + +p { + font-size: 15px; +} + +#Header { + border-style: solid; + border-width: 0 0 10px 0; +} + +.site-width { + max-width: 1140px; + margin: auto; +} + +.graph-width { + max-width: 1250px; + margin: auto; +} + +#Footer { + border-width: 5px 0 0 0; + border-style: solid; +} + +.logo { + max-width: 250px; + margin: 5px 0 5px 16px; +} + +.subText { + font-size: 80% !important; + font-weight: 400; +} + +body { + background-image: url("../images/picture.jpg"); + background-position: bottom left; + background-repeat: no-repeat; + background-attachment: fixed; +} + +.statusPanel h5 { + margin-bottom: -5px; +} +/* ------------------------------------- + * Flex boxes + * -------------------------------------*/ +.at-flex-start { + display: flex; +} +.at-flex-end { + display: flex; + justify-content: flex-end; + flex-wrap: wrap; +} + +.at-flex-justify { + display: flex; + justify-content: space-around; + flex-wrap: wrap; +} + +.at-flex-between { + display: flex; + justify-content: space-between; + flex-wrap: wrap; +} + +.at-flex-bottom, +.at-flex-items-bottom { + align-items: flex-end; +} + +.at-flex-items-center { + align-items: center; +} + +/* -------------------------------------------------- + * Menu enhancements + * --------------------------------------------------*/ +#Main_Menu { + margin-bottom: 4px; + border-width: 2px 0 0 0; + border-style: solid; + min-height: 32px; +} + +.at-slim { + padding: 4px 14px !important; +} + +.at-divider { + margin: 0 5px; + color: #f80; +} + +.at-spacer { + min-height: 2em; +} + +.at-menu-lable { + display: block; + width: 100%; + font-size: 13px; + font-style: italic; + padding-bottom: 2px !important; + padding-top: 4px !important; + border-bottom: 1px dotted #c2cfa5 !important; +} + +.at-menu-bar { + display: block; + height: 2px; + padding: 0 2px !important; +} + +.at-indent { + padding-left: 40px !important; +} + +/* ------------------------------- + * Model enhancements + * ------------------------------*/ + +.w3-modal-content { + margin-top: 10%; + border-radius: 8px; +} + +.w3-modal header { + border-radius: 8px 8px 0 0; +} +.w3-modal footer { + border-radius: 0 0 8px 8px; +} +.w3-modal .w3-btn { + border-radius: 0 8px; +} + +/* ---------------------------------------- + * Media enhancements + * ---------------------------------------*/ +@media screen and (max-width: 780px) { + #Footer { + position: unset; + } + #Content { + /*margin-top: 170px!important;*/ + margin-bottom: 5px !important; + } + + .statusPanel { + text-align: center !important; + margin: auto !important; + } +} + +@media screen and (max-height: 768px) { + #Footer { + position: unset; + item: center; + } + #Content { + margin-bottom: 5px !important; + } +} + +/* -------------------------------------- + * LED enhancements + * -------------------------------------*/ +.at-led-round { + display: inline-block; + height: 1.2em; + width: 1.2em; + margin: 0 0.5em -3px 0.5em; + border-radius: 50%; + background-color: #888; + box-shadow: inset 3px 3px 2px rgba(220, 220, 220, 0.6), + inset -2px -2px 2px rgba(32, 32, 32, 0.6); +} + +.at-led-block { + display: inline-block; + height: 1.2em; + width: 1.2em; + margin: 0 0.5em -3px 0.5em; + background-color: #888; + box-shadow: inset 3px 3px 2px rgba(220, 220, 220, 0.6), + inset -2px -2px 2px rgba(32, 32, 32, 0.6); +} + +.at-led-brick { + display: inline-block; + height: 0.8em; + width: 1.6em; + margin: 0 0.5em -3px 0.5em; + background-color: #888; + box-shadow: inset 3px 3px 2px rgba(220, 220, 220, 0.6), + inset -2px -2px 2px rgba(32, 32, 32, 0.6); +} +.at-led-oval { + display: inline-block; + height: 1em; + width: 2em; + margin: 0 0.5em -3px 0.5em; + border-radius: 50%; + background-color: #888; + box-shadow: inset 3px 3px 2px rgba(220, 220, 220, 0.6), + inset -2px -2px 2px rgba(32, 32, 32, 0.6); +} + +.at-led-green { + background-color: #0b0; +} + +.at-led-flash-red { + animation: flashR 1s infinite; +} + +@keyframes flashR { + 0%, + 60% { + background-color: #f00; + } + 61%, + 100% { + background-color: #800; + } +} diff --git a/css/w3Pro.css b/css/w3Pro.css new file mode 100644 index 0000000..b8b5b0f --- /dev/null +++ b/css/w3Pro.css @@ -0,0 +1,247 @@ +/* W3PRO.CSS 4.15 December 2020 by Jan Egil and Borge Refsnes */ +html { + box-sizing: border-box; +} +*, +*:before, +*:after { + box-sizing: inherit; +} +/* Extract from normalize.css by Nicolas Gallagher and Jonathan Neal git.io/normalize */ +html { + -ms-text-size-adjust: 100%; + -webkit-text-size-adjust: 100%; +} +body { + margin: 0; +} +article, +aside, +details, +figcaption, +figure, +footer, +header, +main, +menu, +nav, +section { + display: block; +} +summary { + display: list-item; +} +audio, +canvas, +progress, +video { + display: inline-block; +} +progress { + vertical-align: baseline; +} +audio:not([controls]) { + display: none; + height: 0; +} +[hidden], +template { + display: none; +} +a { + background-color: transparent; +} +a:active, +a:hover { + outline-width: 0; +} +abbr[title] { + border-bottom: none; + text-decoration: underline; + text-decoration: underline dotted; +} +b, +strong { + font-weight: bolder; +} +dfn { + font-style: italic; +} +mark { + background: #ff0; + color: #000; +} +small { + font-size: 80%; +} +sub, +sup { + font-size: 75%; + line-height: 0; + position: relative; + vertical-align: baseline; +} +sub { + bottom: -0.25em; +} +sup { + top: -0.5em; +} +figure { + margin: 1em 40px; +} +img { + border-style: none; +} +code, +kbd, +pre, +samp { + font-family: monospace, monospace; + font-size: 1em; +} +hr { + box-sizing: content-box; + height: 0; + overflow: visible; +} +button, +input, +select, +textarea, +optgroup { + font: inherit; + margin: 0; +} +optgroup { + font-weight: bold; +} +button, +input { + overflow: visible; +} +button, +select { + text-transform: none; +} +button, +[type="button"], +[type="reset"], +[type="submit"] { + -webkit-appearance: button; +} +button::-moz-focus-inner, +[type="button"]::-moz-focus-inner, +[type="reset"]::-moz-focus-inner, +[type="submit"]::-moz-focus-inner { + border-style: none; + padding: 0; +} +button:-moz-focusring, +[type="button"]:-moz-focusring, +[type="reset"]:-moz-focusring, +[type="submit"]:-moz-focusring { + outline: 1px dotted ButtonText; +} +fieldset { + border: 1px solid #c0c0c0; + margin: 0 2px; + padding: 0.35em 0.625em 0.75em; +} +legend { + color: inherit; + display: table; + max-width: 100%; + padding: 0; + white-space: normal; +} +textarea { + overflow: auto; +} +[type="checkbox"], +[type="radio"] { + padding: 0; +} +[type="number"]::-webkit-inner-spin-button, +[type="number"]::-webkit-outer-spin-button { + height: auto; +} +[type="search"] { + -webkit-appearance: textfield; + outline-offset: -2px; +} +[type="search"]::-webkit-search-decoration { + -webkit-appearance: none; +} +::-webkit-file-upload-button { + -webkit-appearance: button; + font: inherit; +} +/* End extract */ +html, +body { + font-family: Verdana, sans-serif; + font-size: 15px; + line-height: 1.5; +} +html { + overflow-x: hidden; +} +h1 { + font-size: 36px; +} +h2 { + font-size: 30px; +} +h3 { + font-size: 24px; +} +h4 { + font-size: 20px; +} +h5 { + font-size: 18px; +} +h6 { + font-size: 16px; +} +.w3-serif { + font-family: serif; +} +.w3-sans-serif { + font-family: sans-serif; +} +.w3-cursive { + font-family: cursive; +} +.w3-monospace { + font-family: monospace; +} +h1, +h2, +h3, +h4, +h5, +h6 { + font-family: "Segoe UI", Arial, sans-serif; + font-weight: 400; + margin: 10px 0; +} +.w3-wide { + letter-spacing: 4px; +} +hr { + border: 0; + border-top: 1px solid #eee; + margin: 20px 0; +} +.w3-image { + max-width: 100%; + height: auto; +} +img { + vertical-align: middle; +} +a { + color: inherit; +} diff --git a/css/wah.css b/css/wah.css new file mode 100644 index 0000000..8de105d --- /dev/null +++ b/css/wah.css @@ -0,0 +1,184 @@ +:root { + --background: #f2efbd; + --background-dim: #d2d0a4; + --foreground: #2a271c; + --border-color: #f27405; + --border: var(--border-color) 2px solid; + --shadow-color: hsla(11, 96%, 43%, 0.4); + --shadow: drop-shadow(8px 8px var(--shadow-color)); + --shadow-small: drop-shadow(3px 3px var(--shadow-color)); + --links: hsl(183, 93%, 27%); + --links-hover: hsl(183, 93%, 15%); + --table-header: hsla(11, 96%, 43%, 0.2); +} + +html { + height: 100%; + color-scheme: light; +} + +body { + color: var(--foreground); + min-height: 100%; + background-color: hsla(0, 0%, 0%, 0); + padding: 10px; + font-family: serif; +} + +/*noinspection CssUnknownTarget*/ +body::before { + content: ""; + position: fixed; + top: 0; + left: 0; + background-image: url("/images/background.jpg"); + width: 100%; + height: 100%; + z-index: -1; + opacity: 0.8; + background-size: cover; + background-attachment: fixed; + overflow: hidden; +} + +h1, +h2, +h3, +h4, +h5, +h6 { + margin: 0; +} + +p, +ul, +ol, +dl, +menu, +dir { + margin: 0; +} + +hr { + border: none; + border-top: var(--border); +} + +a { + color: var(--links); + text-decoration: underline dotted; +} + +a:hover { + color: var(--links-hover); + text-decoration: underline solid; +} + +div.page-container { + /* width: 1000px; */ + width: 800px; + margin: 5px auto; +} + +div.page-container > div { + background-color: var(--background); + filter: var(--shadow); + padding: 10px; + border: var(--border); + margin-bottom: 20px; + /* temporary */ + /* height: 600px; */ +} + +div.page-container > div:last-child { + margin-bottom: 0; +} + +div#header h1 { + margin: 0; + font-style: italic; +} + +div#header h1, +div#header p { + display: inline; +} + +div#content { + position: relative; +} + +div#content::after { + display: block; + content: ""; + clear: both; +} + +div#footer { + display: grid; + grid-template-columns: auto 1fr; + grid-template-rows: 1fr; + grid-column-gap: 0px; + grid-row-gap: 0px; + align-items: center; +} + +div#footer div:last-child { + text-align: right; +} + +div#footer div:last-child img { + image-rendering: pixelated; + margin: 0; + padding: 0; + width: 88px; + height: 31px; +} + +/* -------------------------------------------------------------------------- */ + +table.almanac td:nth-child(odd) { + font-weight: bold; +} + +table.almanac td { + padding: 0 10px; +} + +table.almanac td:nth-child(even) { + padding: 0 15px; +} + +table.almanac { + min-width: 100%; +} + +table.conditions-now { + border-collapse: collapse; + border: var(--border); + filter: var(--shadow-small); + background-color: var(--background); +} + +table.conditions-now th { + text-align: left; + background-color: var(--background-dim); + border-top: var(--border); +} + +table.conditions-now tr td, +table.conditions-now tr th { + padding: 5px 10px 5px 5px; +} +table.conditions-now tr td:nth-child(2) { + padding-right: 40px; +} + +table.conditions-now tr td:nth-child(odd) { + font-weight: bold; +} + +table.conditions-now tr:last-child td:nth-child(3) { + font-weight: normal; + font-style: italic; +} diff --git a/gauges.htm b/gauges.htm new file mode 100644 index 0000000..e7ec4d4 --- /dev/null +++ b/gauges.htm @@ -0,0 +1,328 @@ + + + + + + + + + + Cumulus MX + + + + + + + + + + + + + + + + + + + + + + + +
+
+
+
+
+

Gauges

+
+
+
+
Status: +
+
+
+ +
+ +
+
+ Temperature
+
+
+
Other + Temps
+
+
+
+
+
+
+
+ Humidity
+
+
+
+
+
+
+
+
+
+ +
+
+
+ +
+
+ +
Temperature
+
+
+ +
+
+
+
+ +
Other Temps
+
+
+ +
+
+
+
+ +
Humidity
+
+
+ +
+
+
+
+ +
Wind
+
+ +
+
+
+ +
Wind Direction
+
+ +
+
+
+ +
Wind Rose
+
+ +
+
+
+ +
Pressure
+
+ +
+
+
+ +
Rainfall
+
+ +
+
+
+ +
Rainfall Rate
+
+ +
+
+
+ +
UV Radiation
+
+ +
+
+
+ +
Solar
+
+ +
+
+
+ +
Cloudbase
+
+ +
+
+
+ +
+
+
+
+ + + +
+
+
+ × +

Gauge Units

+
+
+
+
Temperature:
+
+
+ +
Rainfall
+
+
+ +
Pressure
+
+
+
 
+
+
+ +
Wind Speed
+
+
+
 
+
+
+ +
Cloud Base
+
+
+
+
+
+

Powered by Cumulus MX

+
+
+
+ + + + + + + + + + + + diff --git a/historic.htm b/historic.htm new file mode 100644 index 0000000..5199e69 --- /dev/null +++ b/historic.htm @@ -0,0 +1,112 @@ + + + + + + + + + Cumulus MX + + + + + + + + + + + + + + + + + + + + +
+
+
+

Charts based on summary data

+

Welcome to

+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ + + + + + + + +
+

Mouse over the chart to see the values at any given time. + You can add or remove data sets from the chart by clicking the entry on the chart legend.

+
+
+
+
+ + + + + + + + + + \ No newline at end of file diff --git a/images/CumulusMX-Logo.png b/images/CumulusMX-Logo.png new file mode 100644 index 0000000..ecf0246 Binary files /dev/null and b/images/CumulusMX-Logo.png differ diff --git a/images/background.jpg b/images/background.jpg new file mode 100644 index 0000000..4e94b27 Binary files /dev/null and b/images/background.jpg differ diff --git a/images/favicon.png b/images/favicon.png new file mode 100644 index 0000000..26f009f Binary files /dev/null and b/images/favicon.png differ diff --git a/images/moon.png b/images/moon.png new file mode 100644 index 0000000..66d8a33 Binary files /dev/null and b/images/moon.png differ diff --git a/images/picture.jpg b/images/picture.jpg new file mode 100644 index 0000000..2336b37 Binary files /dev/null and b/images/picture.jpg differ diff --git a/index.php b/index.php new file mode 100644 index 0000000..f62fb4f --- /dev/null +++ b/index.php @@ -0,0 +1,199 @@ + + + + + + + + + Cumulus MX + + + + + + + + + + + + + +
+ +
+

Almanac

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Dawn:Sun Rise:Moon Rise:MoonVisible % +
Dusk:Sun Set:Moon Set:
Daylight:Day Length:Moon Phase:
+

+

Conditions at local time

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Temperature and Humidity
Temperature  + Dew Point  +
Windchill  + Humidity %
Heat Index Feels + Like  +
Temp change last hour 
Rainfall
Rainfall Today  + Rainfall Rate /hr +
Rainfall This Month  + Rainfall This Year  +
Rainfall Last Hour  + Last rainfall
Rainfall Since Midnight Rainfall Last 24 Hours  +
Wind
Wind Speed (gust)  + Wind Speed (avg)  +
Wind Bearing° + Beaufort
Wind Variation (last 10 minutes)From ° to °
Pressure (sea + level)
Barometer  +  /hr
+
+ +
+ + + diff --git a/js/alltimerecdata.js b/js/alltimerecdata.js new file mode 100644 index 0000000..1640c61 --- /dev/null +++ b/js/alltimerecdata.js @@ -0,0 +1,40 @@ +// Last modified: 2021/03/19 09:15:55 + + +$.getJSON("data/websitedata.json", function (json) { + console.log("success"); + var cmx_data = json; + + $(document).prop('title', cmx_data['cmx-location'] + ' weather'); + $('meta[name=description]').attr('content', cmx_data['cmx-location'] + ' weather data'); + $('meta[name=keywords]').attr('content', $('meta[name=keywords]').attr('content') + ', ' + cmx_data['cmx-location'] + ' weather data'); + + $.getJSON("data/alltimerecdata.json", function (json) { + console.log("success"); + Object.keys(json).forEach(key => { + cmx_data[key] = json[key]; + }); + + // Update all spans with id beginning "cmx-" + $('span[id^=cmx-]').each(function () { + this.innerHTML = cmx_data[this.id]; + }); + // Update all spans with class beginning "cmx-" + $('span[class^=cmx-]').each(function () { + this.innerHTML = cmx_data[this.className]; + }); + }) + .fail(function (jqxhr, textStatus, error) { + var err = textStatus + ", " + error; + console.log("Request Failed: " + err); + }); + + +}) + .fail(function (jqxhr, textStatus, error) { + var err = textStatus + ", " + error; + console.log("Request Failed: " + err); + }); + +$(document).ready(function () { +}); diff --git a/js/cumuluscharts.js b/js/cumuluscharts.js new file mode 100644 index 0000000..35f0972 --- /dev/null +++ b/js/cumuluscharts.js @@ -0,0 +1,2468 @@ +// Last modified: 2023/12/29 15:03:52 + +var chart, config; + +var myRangeBtns = { + buttons: [{ + count: 12, + type: 'hour', + text: '12h' + }, { + count: 24, + type: 'hour', + text: '24h' + }, { + count: 2, + type: 'day', + text: '2d' + }, { + type: 'all', + text: 'All' + }], + inputEnabled: false, + selected: 1 +}; + +$(document).ready(function () { + $('#mySelect').change(function () { + changeGraph($('#mySelect').val()); + }); + + + $.ajax({ + url: "data/availabledata.json", + dataType: "json", + success: function (result) { + if (result.Temperature === undefined || result.Temperature.Count == 0) { + $('#mySelect option[value="temp"]').remove(); + } + if (result.DailyTemps === undefined || result.DailyTemps.Count == 0) { + $('#mySelect option[value="dailytemp"]').remove(); + } + if (result.Humidity === undefined || result.Humidity.Count == 0) { + $('#mySelect option[value="humidity"]').remove(); + } + if (result.Solar === undefined || result.Solar.Count == 0) { + $('#mySelect option[value="solar"]').remove(); + } + if (result.Sunshine === undefined || result.Sunshine.Count == 0) { + $('#mySelect option[value="sunhours"]').remove(); + } + if (result.AirQuality === undefined || result.AirQuality.Count == 0) { + $('#mySelect option[value="airquality"]').remove(); + } + if (result.ExtraTemp == undefined || result.ExtraTemp.Count == 0) { + $('#mySelect option[value="extratemp"]').remove(); + } + if (result.ExtraHum == undefined || result.ExtraHum.Count == 0) { + $('#mySelect option[value="extrahum"]').remove(); + } + if (result.ExtraDewPoint == undefined || result.ExtraDewPoint.Count == 0) { + $('#mySelect option[value="extradew"]').remove(); + } + if (result.SoilTemp == undefined || result.SoilTemp.Count == 0) { + $('#mySelect option[value="soiltemp"]').remove(); + } + if (result.SoilMoist == undefined || result.SoilMoist.Count == 0) { + $('#mySelect option[value="soilmoist"]').remove(); + } + if (result.LeafWetness == undefined || result.LeafWetness.Count == 0) { + $('#mySelect option[value="leafwet"]').remove(); + } + if (result.UserTemp == undefined || result.UserTemp.Count == 0) { + $('#mySelect option[value="usertemp"]').remove(); + } + if (result.CO2 == undefined || result.CO2.Count == 0) { + $('#mySelect option[value="co2"]').remove(); + } + } + }); + + $.ajax({ + url: "data/graphconfig.json", + dataType: "json", + success: function (result) { + config = result; + var value = parent.location.hash.replace('#', ''); + if (value == '') + value = 'temp'; + + changeGraph(value); + // set the correct option + $('#mySelect option[value="' + value + '"]').attr('selected', true); + } + }); +}); + + +function changeGraph(graph) { + switch (graph) { + case 'temp': + doTemp(); + break; + case 'dailytemp': + doDailyTemp(); + break; + case 'press': + doPress(); + break; + case 'wind': + doWind(); + break; + case 'windDir': + doWindDir(); + break; + case 'rain': + doRain(); + break; + case 'dailyrain': + doDailyRain(); + break; + case 'humidity': + doHum(); + break; + case 'solar': + doSolar(); + break; + case 'sunhours': + doSunHours(); + break; + case 'airquality': + doAirQuality(); + break; + case 'extratemp': + doExtraTemp(); + break; + case 'extrahum': + doExtraHum(); + break; + case 'extradew': + doExtraDew(); + break; + case 'soiltemp': + doSoilTemp(); + break; + case 'soilmoist': + doSoilMoist(); + break; + case 'leafwet': + doLeafWet(); + break; + case 'usertemp': + doUserTemp(); + break; + case 'co2': + doCO2(); + break; + default: + doTemp(); + break; + } + parent.location.hash = graph; +} + +var doTemp = function () { + var freezing = config.temp.units === 'C' ? 0 : 32; + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { + text: 'Temperature' + }, + credits: { + enabled: true + }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { + text: 'Temperature (°' + config.temp.units + ')' + }, + opposite: false, + labels: { + align: 'right', + x: -5, + formatter: function () { + return '' + this.value + ''; + } + }, + plotLines: [{ + // freezing line + value: freezing, + color: 'rgb(0, 0, 180)', + width: 1, + zIndex: 2 + }] + }, { + // right + gridLineWidth: 0, + linkedTo: 0, + opposite: true, + labels: { + align: 'left', + x: 5, + formatter: function () { + return '' + this.value + ''; + } + } + }], + legend: { + enabled: true + }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { + lineWidth: 2 + } + }, + tooltip: { + shared: true, + crosshairs: true, + valueDecimals: config.temp.decimals, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/tempdata.json', + cache: false, + dataType: 'json', + success: function (resp) { + var titles = { + 'temp': 'Temperature', + 'dew': 'Dew Point', + 'apptemp': 'Apparent', + 'feelslike': 'Feels Like', + 'wchill': 'Wind Chill', + 'heatindex': 'Heat Index', + 'humidex': 'Humidex', + 'intemp': 'Inside' + }; + var idxs = ['temp', 'dew', 'apptemp', 'feelslike', 'wchill', 'heatindex', 'humidex', 'intemp']; + var yaxis = 0; + + idxs.forEach(function (idx) { + var valueSuffix = ' °' + config.temp.units; + yaxis = 0; + + if (idx in resp) { + if (idx === 'humidex') { + valueSuffix = null; + if (config.temp.units == 'F') { + chart.yAxis[1].remove(); + chart.addAxis({ + id: 'humidex', + title: { text: 'Humidex' }, + opposite: true, + labels: { + align: 'left' + }, + alignTicks: true, + gridLineWidth: 0, // Not working? + gridZIndex: -10, // Hides the grid lines for this axis + showEmpty: false + }, false, false); + + yaxis = 'humidex'; + } + } + + chart.addSeries({ + name: titles[idx], + id: 'series-' + idx, + data: resp[idx], + color: config.series[idx].colour, + yAxis: yaxis, + tooltip: { valueSuffix: valueSuffix } + }, false); + + if (idx === 'temp') { + chart.get('series-' + idx).options.zIndex = 99; + } + } + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doPress = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { + text: 'Pressure' + }, + credits: { + enabled: true + }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { + text: 'Pressure (' + config.press.units + ')' + }, + opposite: false, + labels: { + align: 'right', + x: -5 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + title: { + text: null + }, + labels: { + align: 'left', + x: 5 + } + }], + legend: { + enabled: true + }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { + lineWidth: 2 + } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' ' + config.press.units, + valueDecimals: config.press.decimals, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [{ + name: 'Pressure', + color: config.series.press.colour + }], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/pressdata.json', + dataType: 'json', + cache: false, + success: function (resp) { + chart.hideLoading(); + chart.series[0].setData(resp.press); + } + }); +}; + +var compassP = function (deg) { + var a = ['N', 'NE', 'E', 'SE', 'S', 'SW', 'W', 'NW']; + return a[Math.floor((deg + 22.5) / 45) % 8]; +}; + +var doWindDir = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'scatter', + alignTicks: false + }, + title: { + text: 'Wind Direction' + }, + credits: { + enabled: true + }, + navigator: { + series: { + // pseudo scatter + type: 'line', + dataGrouping: { + groupPixelWidth: 1, + anchor: 1 + }, + lineWidth: 0, + marker: { + // enable the marker to simulate a scatter + enabled: true, + radius: 1 + } + } + }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { + text: 'Bearing' + }, + opposite: false, + min: 0, + max: 360, + tickInterval: 45, + labels: { + align: 'right', + x: -5, + formatter: function () { + return compassP(this.value); + } + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + title: { + text: null + }, + min: 0, + max: 360, + tickInterval: 45, + labels: { + align: 'left', + x: 5, + formatter: function () { + return compassP(this.value); + } + } + }], + legend: { + enabled: true + }, + plotOptions: { + scatter: { + cursor: 'pointer', + enableMouseTracking: true, + boostThreshold: 200, + marker: { + states: { + hover: { + enabled: false + }, + select: { + enabled: false + } + } + }, + shadow: false, + label: { + enabled: false + } + } + }, + tooltip: { + enabled: true, + split: true, + useHTML: true + }, + series: [{ + name: 'Bearing', + type: 'scatter', + color: config.series.bearing.colour, + marker: { + symbol: 'circle', + radius: 2 + }, + enableMouseTracking: false, + showInNavigator: false + }, { + name: 'Avg Bearing', + type: 'scatter', + color: config.series.avgbearing.colour, + marker: { + symbol: 'circle', + radius: 2 + }, + showInNavigator: true, + tooltip: { + headerFormat: '', + xDateFormat: '%A, %b %e %H:%M ', + pointFormatter() { + return '\u25CF ' + + this.series.name + ': ' + (this.y == 0 ? 'calm' : this.y + '°') + '
'; + } + } + }], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/wdirdata.json', + dataType: 'json', + cache: false, + success: function (resp) { + chart.hideLoading(); + chart.series[0].setData(resp.bearing); + chart.series[1].setData(resp.avgbearing); + } + }); +}; + +var doWind = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { + text: 'Wind Speed' + }, + credits: { + enabled: true + }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { + text: 'Wind Speed (' + config.wind.units + ')' + }, + opposite: false, + min: 0, + labels: { + align: 'right', + x: -5 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + min: 0, + title: { + text: null + }, + labels: { + align: 'left', + x: 5 + } + }], + legend: { + enabled: true + }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { + lineWidth: 2 + } + }, + tooltip: { + shared: true, + crosshairs: true, + valueSuffix: ' ' + config.wind.units, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [{ + name: 'Wind Speed', + color: config.series.wspeed.colour, + tooltip: { + valueDecimals: config.wind.avgdecimals + } + }, { + name: 'Wind Gust', + color: config.series.wgust.colour, + tooltip: { + valueDecimals: config.wind.gustdecimals + } + }], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/winddata.json', + dataType: 'json', + cache: false, + success: function (resp) { + chart.hideLoading(); + chart.series[0].setData(resp.wspeed); + chart.series[1].setData(resp.wgust); + } + }); +}; + +var doRain = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: true + }, + title: { + text: 'Rainfall' + }, + credits: { + enabled: true + }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { + text: 'Rainfall rate (' + config.rain.units + '/hr)' + }, + min: 0, + opposite: false, + labels: { + align: 'right', + x: -5 + }, + showEmpty: false + }, { + // right + opposite: true, + title: { + text: 'Rainfall (' + config.rain.units + ')' + }, + min: 0, + labels: { + align: 'left', + x: 5 + } + }], + legend: { + enabled: true + }, + plotOptions: { + series: { + boostThreshold: 0, + dataGrouping: { + enabled: false + }, + showInNavigator: true, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { + lineWidth: 2 + } + }, + tooltip: { + shared: true, + crosshairs: true, + valueDecimals: config.rain.decimals, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [{ + name: 'Daily rain', + type: 'area', + color: config.series.rfall.colour, + yAxis: 1, + tooltip: { valueSuffix: ' ' + config.rain.units }, + fillOpacity: 0.3 + }, { + name: 'Rain rate', + type: 'line', + color: config.series.rrate.colour, + yAxis: 0, + tooltip: { valueSuffix: ' ' + config.rain.units + '/hr' } + }], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/raindata.json', + dataType: 'json', + cache: false, + success: function (resp) { + chart.hideLoading(); + chart.series[0].setData(resp.rfall); + chart.series[1].setData(resp.rrate); + } + }); +}; + +var doHum = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { + text: 'Relative Humidity' + }, + credits: { + enabled: true + }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { + text: 'Humidity (%)' + }, + opposite: false, + min: 0, + max: 100, + labels: { + align: 'right', + x: -5 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + min: 0, + max: 100, + title: { + text: null + }, + labels: { + align: 'left', + x: 5 + } + }], + legend: { + enabled: true + }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { + lineWidth: 2 + } + }, + tooltip: { + shared: true, + crosshairs: true, + valueSuffix: ' %', + valueDecimals: config.hum.decimals, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/humdata.json', + dataType: 'json', + cache: false, + success: function (resp) { + var titles = { + 'hum': 'Outdoor Humidity', + 'inhum': 'Indoor Humidity' + } + var idxs = ['hum', 'inhum']; + var cnt = 0; + idxs.forEach(function (idx) { + if (idx in resp) { + chart.addSeries({ + name: titles[idx], + color: config.series[idx].colour, + data: resp[idx] + }, false); + + cnt++; + } + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doSolar = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: true + }, + title: { + text: 'Solar' + }, + credits: { + enabled: true + }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [], + legend: { + enabled: true + }, + plotOptions: { + series: { + boostThreshold: 0, + dataGrouping: { + enabled: false + }, + showInNavigator: true, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { + lineWidth: 2 + } + }, + tooltip: { + shared: true, + crosshairs: true, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/solardata.json', + dataType: 'json', + cache: false, + success: function (resp) { + var titles = { + SolarRad: 'Solar Radiation', + CurrentSolarMax: 'Theoretical Max', + UV: 'UV Index' + }; + var types = { + SolarRad: 'area', + CurrentSolarMax: 'area', + UV: 'line' + }; + var colours = { + SolarRad: 'rgb(255,165,0)', + CurrentSolarMax: 'rgb(128,128,128)', + UV: 'rgb(0,0,255)' + }; + var tooltips = { + SolarRad: { + valueSuffix: ' W/m\u00B2', + valueDecimals: 0 + }, + CurrentSolarMax: { + valueSuffix: ' W/m\u00B2', + valueDecimals: 0 + }, + UV: { + valueSuffix: null, + valueDecimals: config.uv.decimals + } + }; + + var idxs = ['SolarRad', 'CurrentSolarMax', 'UV']; + var cnt = 0; + var solarAxisCreated = false; + + idxs.forEach(function (idx) { + if (idx in resp) { + if (idx === 'UV') { + chart.addAxis({ + id: 'uv', + title: { text: 'UV Index' }, + opposite: true, + min: 0, + labels: { + align: 'left' + }, + showEmpty: false + }); + } else if (!solarAxisCreated) { + chart.addAxis({ + id: 'solar', + title: { text: 'Solar Radiation (W/m\u00B2)' }, + min: 0, + opposite: false, + labels: { + align: 'right', + x: -5 + }, + showEmpty: false + }); + solarAxisCreated = true; + } + + + chart.addSeries({ + name: titles[idx], + type: types[idx], + yAxis: idx === 'UV' ? 'uv' : 'solar', + tooltip: tooltips[idx], + data: resp[idx], + color: config.series[idx.toLowerCase()].colour, + fillOpacity: idx === 'CurrentSolarMax' ? 0.2 : 0.5, + zIndex: 100 - cnt + }, false); + + cnt++; + } + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doSunHours = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'column', + alignTicks: false + }, + title: { + text: 'Sunshine Hours' + }, + credits: { + enabled: true + }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { + text: 'Sunshine Hours' + }, + min: 0, + opposite: false, + labels: { + align: 'right', + x: -12 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + title: { + text: null + }, + labels: { + align: 'left', + x: 12 + } + }], + legend: { + enabled: true + }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + pointPadding: 0, + groupPadding: 0.1, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + } + }, + tooltip: { + shared: true, + crosshairs: true, + xDateFormat: "%A, %b %e" + }, + series: [{ + name: 'Sunshine Hours', + type: 'column', + color: config.series.sunshine.colour, + yAxis: 0, + valueDecimals: 1, + tooltip: { + valueSuffix: ' Hrs' + } + }] + }; + + chart = new Highcharts.Chart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/sunhours.json', + dataType: 'json', + cache: false, + success: function (resp) { + chart.hideLoading(); + chart.series[0].setData(resp.sunhours); + } + }); +}; + +var doDailyRain = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'column', + alignTicks: false + }, + title: { + text: 'Daily Rainfall' + }, + credits: { + enabled: true + }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { + text: 'Daily Rainfall' + }, + min: 0, + opposite: false, + labels: { + align: 'right', + x: -12 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + title: { + text: null + }, + labels: { + align: 'left', + x: 12 + } + }], + legend: { + enabled: true + }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + pointPadding: 0, + groupPadding: 0.1, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + } + }, + tooltip: { + shared: true, + crosshairs: true, + xDateFormat: "%A, %b %e" + }, + series: [{ + name: 'Daily Rainfall', + type: 'column', + color: config.series.rfall.colour, + yAxis: 0, + valueDecimals: config.rain.decimals, + tooltip: { + valueSuffix: ' ' + config.rain.units + } + }] + }; + + chart = new Highcharts.Chart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/dailyrain.json', + dataType: 'json', + cache: false, + success: function (resp) { + chart.hideLoading(); + chart.series[0].setData(resp.dailyrain); + } + }); +}; + +var doDailyTemp = function () { + var freezing = config.temp.units === 'C' ? 0 : 32; + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { + text: 'Daily Temperature' + }, + credits: { + enabled: true + }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { + text: 'Daily Temperature (°' + config.temp.units + ')' + }, + opposite: false, + labels: { + align: 'right', + x: -5, + formatter: function () { + return '' + this.value + ''; + } + }, + plotLines: [{ + // freezing line + value: freezing, + color: 'rgb(0, 0, 180)', + width: 1, + zIndex: 2 + }] + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + title: { + text: null + }, + labels: { + align: 'left', + x: 5, + formatter: function () { + return '' + this.value + ''; + } + } + }], + legend: { + enabled: true + }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { + lineWidth: 2 + } + }, + tooltip: { + shared: true, + crosshairs: true, + valueSuffix: ' °' + config.temp.units, + valueDecimals: config.temp.decimals, + xDateFormat: "%A, %b %e" + }, + rangeSelector: { + enabled: false + }, + series: [] + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/dailytemp.json', + dataType: 'json', + cache: false, + success: function (resp) { + var titles = { + 'avgtemp': 'Avg Temp', + 'mintemp': 'Min Temp', + 'maxtemp': 'Max Temp' + }; + var idxs = ['avgtemp', 'mintemp', 'maxtemp']; + + idxs.forEach(function (idx) { + if (idx in resp) { + chart.addSeries({ + name: titles[idx], + data: resp[idx], + color: config.series[idx].colour + }, false); + } + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doAirQuality = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Air Quality' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'µg/m³' }, + opposite: false, + min: 0, + labels: { + align: 'right', + x: -5 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + min: 0, + title: { text: null }, + labels: { + align: 'left', + x: 5 + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' µg/m³', + valueDecimals: 1, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/airquality.json', + dataType: 'json', + cache: false, + success: function (resp) { + var titles = { + 'pm2p5': 'PM 2.5', + 'pm10': 'PM 10' + } + var idxs = ['pm2p5', 'pm10']; + idxs.forEach(function (idx) { + if (idx in resp) { + chart.addSeries({ + name: titles[idx], + color: config.series[idx].colour, + data: resp[idx] + }, false); + } + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doExtraTemp = function () { + var freezing = config.temp.units === 'C' ? 0 : 32; + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Extra Temperature' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Temperature (°' + config.temp.units + ')' }, + opposite: false, + labels: { + align: 'right', + x: -5, + formatter: function () { + return '' + this.value + ''; + } + }, + plotLines: [{ + // freezing line + value: freezing, + color: 'rgb(0, 0, 180)', + width: 1, + zIndex: 2 + }] + }, { + // right + gridLineWidth: 0, + opposite: true, + linkedTo: 0, + labels: { + align: 'left', + x: 5, + formatter: function () { + return '' + this.value + ''; + } + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' °' + config.temp.units, + valueDecimals: config.temp.decimals, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/extratempdata.json', + dataType: 'json', + success: function (resp) { + Object.entries(resp).forEach(([key, value]) => { + var id = config.series.extratemp.name.findIndex(val => val == key); + chart.addSeries({ + name: key, + color: config.series.extratemp.colour[id], + data: value + }); + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doExtraHum = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Extra Humidity' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Humidity (%)' }, + opposite: false, + min: 0, + max: 100, + labels: { + align: 'right', + x: -5 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + min: 0, + max: 100, + title: { text: null }, + labels: { + align: 'left', + x: 5 + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' %', + valueDecimals: config.hum.decimals, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/extrahumdata.json', + dataType: 'json', + success: function (resp) { + Object.entries(resp).forEach(([key, value]) => { + var id = config.series.extrahum.name.findIndex(val => val == key); + chart.addSeries({ + name: key, + color: config.series.extrahum.colour[id], + data: value + }); + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doExtraDew = function () { + var freezing = config.temp.units === 'C' ? 0 : 32; + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Extra Dew Point' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Dew Point (°' + config.temp.units + ')' }, + opposite: false, + labels: { + align: 'right', + x: -5, + formatter: function () { + return '' + this.value + ''; + } + }, + plotLines: [{ + // freezing line + value: freezing, + color: 'rgb(0, 0, 180)', + width: 1, + zIndex: 2 + }] + }, { + // right + gridLineWidth: 0, + opposite: true, + linkedTo: 0, + labels: { + align: 'left', + x: 5, + formatter: function () { + return '' + this.value + ''; + } + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' °' + config.temp.units, + valueDecimals: config.temp.decimals, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/extradewdata.json', + dataType: 'json', + success: function (resp) { + Object.entries(resp).forEach(([key, value]) => { + var id = config.series.extradew.name.findIndex(val => val == key); + chart.addSeries({ + name: key, + color: config.series.extradew.colour[id], + data: value + }); + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doSoilTemp = function () { + var freezing = config.temp.units === 'C' ? 0 : 32; + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Soil Temperature' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Temperature (°' + config.temp.units + ')' }, + opposite: false, + labels: { + align: 'right', + x: -5, + formatter: function () { + return '' + this.value + ''; + } + }, + plotLines: [{ + // freezing line + value: freezing, + color: 'rgb(0, 0, 180)', + width: 1, + zIndex: 2 + }] + }, { + // right + gridLineWidth: 0, + opposite: true, + linkedTo: 0, + labels: { + align: 'left', + x: 5, + formatter: function () { + return '' + this.value + ''; + } + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' °' + config.temp.units, + valueDecimals: config.temp.decimals, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/soiltempdata.json', + dataType: 'json', + success: function (resp) { + Object.entries(resp).forEach(([key, value]) => { + var id = config.series.soiltemp.name.findIndex(val => val == key); + chart.addSeries({ + name: key, + color: config.series.soiltemp.colour[id], + data: value + }); + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doSoilMoist = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Soil Moisture' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Moisture (' + config.soilmoisture.units + ')' }, + opposite: false, + labels: { + align: 'right', + x: -5 + } + }, { + // right + gridLineWidth: 0, + opposite: true, + linkedTo: 0, + labels: { + align: 'left', + x: 5 + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' ' + config.soilmoisture.units, + valueDecimals: 0, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/soilmoistdata.json', + dataType: 'json', + success: function (resp) { + Object.entries(resp).forEach(([key, value]) => { + var id = config.series.soilmoist.name.findIndex(val => val == key); + chart.addSeries({ + name: key, + color: config.series.soilmoist.colour[id], + data: value + }); + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doLeafWet = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Leaf Wetness' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Leaf Wetness' + (config.leafwet.units == '' ? '' : '(' + config.leafwet.units + ')') }, + opposite: false, + min: 0, + labels: { + align: 'right', + x: -5 + } + }, { + // right + gridLineWidth: 0, + opposite: true, + min: 0, + linkedTo: 0, + labels: { + align: 'left', + x: 5 + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' ' + config.leafwet.units, + valueDecimals: config.leafwet.decimals, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/leafwetdata.json', + dataType: 'json', + success: function (resp) { + Object.entries(resp).forEach(([key, value]) => { + var id = config.series.leafwet.name.findIndex(val => val == key); + chart.addSeries({ + name: key, + color: config.series.leafwet.colour[id], + data: value + }); + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doUserTemp = function () { + var freezing = config.temp.units === 'C' ? 0 : 32; + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'User Temperature' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Temperature (°' + config.temp.units + ')' }, + opposite: false, + labels: { + align: 'right', + x: -5, + formatter: function () { + return '' + this.value + ''; + } + }, + plotLines: [{ + // freezing line + value: freezing, + color: 'rgb(0, 0, 180)', + width: 1, + zIndex: 2 + }] + }, { + // right + gridLineWidth: 0, + opposite: true, + linkedTo: 0, + labels: { + align: 'left', + x: 5, + formatter: function () { + return '' + this.value + ''; + } + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' °' + config.temp.units, + valueDecimals: config.temp.decimals, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/usertempdata.json', + dataType: 'json', + success: function (resp) { + Object.entries(resp).forEach(([key, value]) => { + var id = config.series.usertemp.name.findIndex(val => val == key); + chart.addSeries({ + name: key, + color: config.series.usertemp.colour[id], + data: value + }); + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doCO2 = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'CO₂ Sensor' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + id: 'co2', + title: { text: 'CO₂ (ppm)' }, + opposite: false, + min: 0, + minRange: 10, + alignTicks: true, + showEmpty: false, + labels: { + align: 'right', + x: -5 + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: true, + xDateFormat: "%A, %b %e, %H:%M" + }, + series: [], + rangeSelector: myRangeBtns + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/co2sensordata.json', + dataType: 'json', + success: function (resp) { + Object.entries(resp).forEach(([key, value]) => { + var yaxis = 0; + var tooltip; + // id - remove all spaces and lowercase + var id = key.toLowerCase().split(' ').join(''); + + if (key == 'CO2' || key == 'CO2 Average') { + yaxis = 'co2'; + tooltip = { valueSuffix: ' ppm' }; + } else if (key.startsWith('PM')) { + yaxis = 'pm'; + tooltip = { valueSuffix: ' µg/m³' }; + + + if (!chart.get('pm')) { + chart.addAxis({ + // left + id: 'pm', + title: { text: 'PM (µg/m³)' }, + opposite: false, + min: 0, + minRange: 10, + alignTicks: true, + showEmpty: false, + labels: { + align: 'right', + x: -5 + } + }); + } + } else if (key == 'Temperature') { + yaxis = 'temp'; + tooltip = { valueSuffix: ' °' + config.temp.units }; + chart.addAxis({ + // right + id: 'temp', + title: { text: 'Temperature (°' + config.temp.units + ')' }, + //gridLineWidth: 0, + opposite: true, + alignTicks: true, + showEmpty: false, + labels: { + align: 'left', + x: 5 + } + }); + } else if (key == 'Humidity') { + yaxis = 'hum'; + tooltip = { valueSuffix: ' %' }; + chart.addAxis({ + // right + id: 'hum', + title: { text: 'Humidity (%)' }, + min: 0, + //gridLineWidth: 0, + opposite: true, + alignTicks: true, + showEmpty: false, + labels: { + align: 'left', + x: 5 + } + }); + } + + chart.addSeries({ + name: config.series.co2[id].name, + color: config.series.co2[id].colour, + data: value, + yAxis: yaxis, + tooltip: tooltip + }); + + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; diff --git a/js/historiccharts.js b/js/historiccharts.js new file mode 100644 index 0000000..b653126 --- /dev/null +++ b/js/historiccharts.js @@ -0,0 +1,1134 @@ +// Last modified: 2023/12/29 15:04:44 + +var chart, config, available; + +$(document).ready(function () { + $.ajax({ + url: "data/availabledata.json", + dataType: "json", + success: function (result) { + available = result; + if (result.Temperature === undefined || result.Temperature.Count == 0) { + $('#btnTemp').remove(); + } + if (result.Humidity === undefined || result.Humidity.Count == 0) { + $('#btnHum').remove(); + } + if (result.Solar === undefined || result.Solar.Count == 0) { + $('#btnSolar').remove(); + } + if (result.DegreeDays === undefined || result.DegreeDays.Count == 0) { + $('#btnDegDay').remove(); + } + if (result.TempSum === undefined || result.TempSum.Count == 0) { + $('#btnTempSum').remove(); + } + } + }); + + $.ajax({ + url: "data/graphconfig.json", + dataType: "json", + success: function (result) { + config = result; + changeGraph(parent.location.hash.replace('#', '')); + } + }); +}); + + +function changeGraph(graph) { + switch (graph) { + case 'temp': + doTemp(); + break; + case 'press': + doPress(); + break; + case 'wind': + doWind(); + break; + case 'rain': + doRain(); + break; + case 'humidity': + doHum(); + break; + case 'solar': + doSolar(); + break; + case 'degday': + doDegDays(); + break; + case 'tempsum': + doTempSum(); + break; + default: + doTemp(); + break; + } + parent.location.hash = graph; +} + +var doTemp = function () { + var freezing = config.temp.units === 'C' ? 0 : 32; + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Temperature' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b %y', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Temperature (°' + config.temp.units + ')' }, + opposite: false, + labels: { + align: 'right', + x: -5, + formatter: function () { + return '' + this.value + ''; + } + }, + plotLines: [{ + // freezing line + value: freezing, + color: 'rgb(0, 0, 180)', + width: 1, + zIndex: 2 + }] + }, { + // right + gridLineWidth: 0, + opposite: true, + linkedTo: 0, + labels: { + align: 'left', + x: 5, + formatter: function () { + return '' + this.value + ''; + } + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' °' + config.temp.units, + valueDecimals: config.temp.decimals, + xDateFormat: '%e %b %y' + }, + series: [], + rangeSelector: { + inputEnabled: false, + selected: 1 + } + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/alldailytempdata.json', + dataType: 'json', + success: function (resp) { + var titles = { + 'minTemp': 'Min Temp', + 'maxTemp': 'Max Temp', + 'avgTemp': 'Avg Temp', + 'heatIndex': 'Heat Index', + 'minApp': 'Min Apparent', + 'maxApp': 'Max Apparent', + 'minDew': 'Min Dewpoint', + 'maxDew': 'Max Dewpoint', + 'minFeels': 'Min Feels', + 'maxFeels': 'Max Feels', + 'humidex': 'Humidex', + 'windChill': 'Wind Chill' + }; + var visibility = { + 'minTemp': true, + 'maxTemp': true, + 'avgTemp': false, + 'heatIndex': false, + 'minApp': false, + 'maxApp': false, + 'minDew': false, + 'maxDew': false, + 'minFeels': false, + 'maxFeels': false, + 'humidex': false, + 'windChill': false + }; + var idxs = ['minTemp', 'maxTemp', 'avgTemp', 'heatIndex', 'minApp', 'maxApp', 'minDew', 'maxDew', 'minFeels', 'maxFeels', 'windChill', 'humidex']; + + idxs.forEach(function (idx) { + var valueSuffix = ' °' + config.temp.units; + yaxis = 0; + + if (idx in resp) { + var clrIdx = idx.toLowerCase(); + if ('heatIndex' === idx || 'humidex' === idx) { + clrIdx = 'max' + clrIdx; + } else if ('windChill' === idx) { + clrIdx = 'min' + clrIdx; + } + + if (idx === 'humidex') { + valueSuffix = null; + // Link Humidex and temp scales if using Celsius + // For Fahrenheit use separate scales + if (config.temp.units === 'F') { + chart.yAxis[1].remove(); + chart.addAxis({ + id: 'humidex', + title: { text: 'Humidex' }, + opposite: true, + labels: { + align: 'left' + }, + alignTicks: true, + gridLineWidth: 0, // Not working? + gridZIndex: -10, // Hides the grid lines for this axis + showEmpty: false + }); + yaxis = 'humidex'; + } + } + + chart.addSeries({ + name: titles[idx], + data: resp[idx], + color: config.series[clrIdx].colour, + visible: visibility[idx], + showInNavigator: visibility[idx], + yAxis: yaxis, + tooltip: { valueSuffix: valueSuffix } + }, false); + } + }); + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doPress = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Pressure' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b %y', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Pressure (' + config.press.units + ')' }, + opposite: false, + labels: { + align: 'right', + x: -5 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + title: { text: null }, + labels: { + align: 'left', + x: 5 + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' ' + config.press.units, + valueDecimals: config.press.decimals, + xDateFormat: '%e %b %y' + }, + series: [{ + name: 'High Pressure', + color: config.series.maxpress.colour, + showInNavigator: true + }, { + name: 'Low Pressure', + color: config.series.minpress.colour, + showInNavigator: true + }], + rangeSelector: { + inputEnabled: false, + selected: 1 + } + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/alldailypressdata.json', + dataType: 'json', + success: function (resp) { + chart.hideLoading(); + chart.series[0].setData(resp.maxBaro); + chart.series[1].setData(resp.minBaro); + } + }); +}; + +var compassP = function (deg) { + var a = ['N', 'NE', 'E', 'SE', 'S', 'SW', 'W', 'NW']; + return a[Math.floor((deg + 22.5) / 45) % 8]; +}; + +var doWind = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Wind Speed' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b %y', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Wind Speed (' + config.wind.units + ')' }, + opposite: false, + min: 0, + labels: { + align: 'right', + x: -5 + } + }, { + // right + //linkedTo: 0, + gridLineWidth: 0, + opposite: true, + min: 0, + title: { text: 'Wind Run (' + config.wind.rununits + ')' }, + labels: { + align: 'left', + x: 5 + }, + showEmpty: false + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' ' + config.wind.units, + xDateFormat: '%e %b %y' + }, + series: [{ + name: 'Wind Speed', + color: config.series.wspeed.colour, + showInNavigator: true, + tooltip: { + valueDecimals: config.wind.avgdecimals + } + }, { + name: 'Wind Gust', + color: config.series.wgust.colour, + showInNavigator: true, + tooltip: { + valueDecimals: config.wind.gustdecimals + } + }, { + name: 'Wind Run', + type: 'column', + color: config.series.windrun.colour, + yAxis: 1, + visible: false, + tooltip: { + valueSuffix: ' ' + config.wind.rununits, + valueDecimals: 0 + }, + zIndex: -1 + }], + rangeSelector: { + inputEnabled: false, + selected: 1 + } + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/alldailywinddata.json', + dataType: 'json', + success: function (resp) { + chart.hideLoading(); + chart.series[0].setData(resp.maxWind); + chart.series[1].setData(resp.maxGust); + chart.series[2].setData(resp.windRun); + } + }); +}; + +var doRain = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'column', + alignTicks: true + }, + title: { text: 'Rainfall' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b %y', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Rainfall (' + config.rain.units + ')' }, + opposite: false, + min: 0, + labels: { + align: 'right', + x: -5 + } + }, { + // right + title: { text: 'Rainfall rate (' + config.rain.units + '/hr)' }, + opposite: true, + min: 0, + labels: { + align: 'left', + x: 5 + }, + showEmpty: false + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + pointPadding: 0, + groupPadding: 0.1, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueDecimals: config.rain.decimals, + xDateFormat: '%e %b %y' + }, + series: [{ + name: 'Daily rain', + type: 'column', + color: config.series.rfall.colour, + yAxis: 0, + tooltip: { valueSuffix: ' ' + config.rain.units } + }, { + name: 'Rain rate', + type: 'column', + color: config.series.rrate.colour, + yAxis: 1, + tooltip: { valueSuffix: ' ' + config.rain.units + '/hr' }, + visible: false + }], + rangeSelector: { + inputEnabled: false, + selected: 1 + } + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/alldailyraindata.json', + dataType: 'json', + success: function (resp) { + chart.hideLoading(); + chart.series[0].setData(resp.rain); + chart.series[1].setData(resp.maxRainRate); + } + }); +}; + +var doHum = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false + }, + title: { text: 'Relative Humidity' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b %y', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [{ + // left + title: { text: 'Humidity (%)' }, + opposite: false, + min: 0, + max: 100, + labels: { + align: 'right', + x: -5 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + min: 0, + max: 100, + title: { text: null }, + labels: { + align: 'left', + x: 5 + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + valueSuffix: ' %', + valueDecimals: config.hum.decimals, + xDateFormat: '%e %b %y' + }, + series: [], + rangeSelector: { + inputEnabled: false, + selected: 1 + } + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/alldailyhumdata.json', + dataType: 'json', + success: function (resp) { + var titles = { + 'minHum': 'Minimum Humidity', + 'maxHum': 'Maximum Humidity' + } + var idxs = ['minHum', 'maxHum']; + var cnt = 0; + idxs.forEach(function (idx) { + if (idx in resp) { + chart.addSeries({ + name: titles[idx], + color: config.series[idx.toLowerCase()].colour, + data: resp[idx], + showInNavigator: true + }, false); + + cnt++; + } + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doSolar = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: true + }, + title: { text: 'Solar' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b %y', + week: '%e %b %y', + month: '%b %y', + year: '%Y' + } + }, + yAxis: [], + legend: { enabled: true }, + plotOptions: { + boostThreshold: 0, + series: { + dataGrouping: { + enabled: false + }, + pointPadding: 0, + groupPadding: 0.1, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + xDateFormat: '%e %b %y' + }, + series: [], + rangeSelector: { + inputEnabled: false, + selected: 1 + } + }; + + chart = new Highcharts.StockChart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/alldailysolardata.json', + dataType: 'json', + success: function (resp) { + var titles = { + solarRad: 'Solar Radiation', + uvi: 'UV Index', + sunHours: 'Sunshine Hours' + }; + var types = { + solarRad: 'area', + uvi: 'line', + sunHours: 'column' + }; + var tooltips = { + solarRad: { + valueSuffix: ' W/m\u00B2', + valueDecimals: 0 + }, + uvi: { + valueSuffix: ' ', + valueDecimals: config.uv.decimals + }, + sunHours: { + valueSuffix: ' hours', + valueDecimals: 0 + } + }; + var indexes = { + solarRad: 1, + uvi: 2, + sunHours: 0 + } + var fillColor = { + solarRad: { + linearGradient: { + x1: 0, + y1: 0, + x2: 0, + y2: 1 + }, + stops: [ + [0, config.series.solarrad.colour], + [1, Highcharts.color(config.series.solarrad.colour).setOpacity(0).get('rgba')] + ] + }, + uvi: null, + sunHours: null + }; + var idxs = ['solarRad', 'uvi', 'sunHours']; + + idxs.forEach(function (idx) { + if (idx in resp) { + var clrIdx; + if (idx === 'uvi') + clrIdx = 'uv'; + else if (idx === 'solarRad') + clrIdx = 'solarrad'; + else if (idx === 'sunHours') + clrIdx = 'sunshine'; + + if (idx === 'uvi') { + chart.addAxis({ + id: idx, + title: { text: 'UV Index' }, + opposite: true, + min: 0, + labels: { + align: 'left' + }, + showEmpty: false + }); + } else if (idx === 'sunHours') { + chart.addAxis({ + id: idx, + title: { text: 'Sunshine Hours' }, + opposite: true, + min: 0, + labels: { + align: 'left' + }, + showEmpty: false + }); + } else if (idx === 'solarRad') { + chart.addAxis({ + id: idx, + title: { text: 'Solar Radiation (W/m\u00B2)' }, + min: 0, + opposite: false, + labels: { + align: 'right', + x: -5 + }, + showEmpty: false + }); + } + chart.addSeries({ + name: titles[idx], + type: types[idx], + yAxis: idx, + tooltip: tooltips[idx], + data: resp[idx], + color: config.series[clrIdx].colour, + showInNavigator: idx !== 'sunHours', + index: indexes[idx], + fillColor: fillColor[idx], + zIndex: idx === 'uvi' ? 99 : null + }, false); + } + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doDegDays = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false, + zoomType: 'x' + }, + title: { text: 'Degree Days' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b', + month: '%b', + year: '' + } + }, + yAxis: [{ + // left + title: { text: '°' + config.temp.units + ' days' }, + opposite: false, + min: 0, + labels: { + align: 'right', + x: -10 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + min: 0, + title: { text: null }, + labels: { + align: 'left', + x: 10 + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + xDateFormat: '%e %B', + useHTML: true, + headerFormat: '{point.key}', + pointFormat: '' + + '', + footerFormat: '
\u25CF {series.name}: {point.y:.1f}
' + }, + series: [] + }; + + chart = new Highcharts.Chart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/alldailydegdaydata.json', + dataType: 'json', + success: function (resp) { + var subtitle = ''; + if (available.DegreeDays.indexOf('GDD1') != -1) { + subtitle = 'GDD#1 base: ' + resp.options.gddBase1 + '°' + config.temp.units; + if (available.DegreeDays.indexOf('GDD2') != -1) { + subtitle += ' - '; + } + } + if (available.DegreeDays.indexOf('GDD2') != -1) { + subtitle += 'GDD#2 base: ' + resp.options.gddBase2 + '°' + config.temp.units; + } + + chart.setSubtitle({ text: subtitle }); + + available.DegreeDays.forEach(idx => { + if (idx in resp) { + Object.keys(resp[idx]).forEach(yr => { + chart.addSeries({ + name: idx + '-' + yr, + visible: false, + data: resp[idx][yr] + }, false); + }); + // make the last series visible + chart.series[chart.series.length - 1].visible = true; + } + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; + +var doTempSum = function () { + var options = { + chart: { + renderTo: 'chartcontainer', + type: 'line', + alignTicks: false, + zoomType: 'x' + }, + title: { text: 'Temperature Sum' }, + credits: { enabled: true }, + xAxis: { + type: 'datetime', + ordinal: false, + dateTimeLabelFormats: { + day: '%e %b', + week: '%e %b', + month: '%b', + year: '' + } + }, + yAxis: [{ + // left + title: { text: 'Total °' + config.temp.units }, + opposite: false, + labels: { + align: 'right', + x: -10 + } + }, { + // right + linkedTo: 0, + gridLineWidth: 0, + opposite: true, + title: { text: null }, + labels: { + align: 'left', + x: 10 + } + }], + legend: { enabled: true }, + plotOptions: { + series: { + dataGrouping: { + enabled: false + }, + states: { + hover: { + halo: { + size: 5, + opacity: 0.25 + } + + } + }, + cursor: 'pointer', + marker: { + enabled: false, + states: { + hover: { + enabled: true, + radius: 0.1 + } + } + } + }, + line: { lineWidth: 2 } + }, + tooltip: { + shared: true, + split: false, + xDateFormat: '%e %B', + useHTML: true, + headerFormat: '{point.key}', + pointFormat: '' + + '', + footerFormat: '
\u25CF {series.name}: {point.y:0f}
' + }, + series: [] + }; + + chart = new Highcharts.Chart(options); + chart.showLoading(); + + $.ajax({ + url: 'data/alltempsumdata.json', + dataType: 'json', + success: function (resp) { + var subtitle = ''; + if (available.TempSum.indexOf('Sum0') != -1) { + subtitle = 'Sum#0 base: 0°' + config.temp.units; + if (available.TempSum.indexOf('Sum1') != -1 || available.TempSum.indexOf('Sum2') != -1) { + subtitle += ' - '; + } + } + if (available.TempSum.indexOf('Sum1') != -1) { + subtitle += 'Sum#1 base: ' + resp.options.sumBase1 + '°' + config.temp.units; + if (available.TempSum.indexOf('Sum2') != -1) { + subtitle += ' - '; + } + } + if (available.TempSum.indexOf('Sum2') != -1) { + subtitle += 'Sum#2 base: ' + resp.options.sumBase2 + '°' + config.temp.units; + } + + chart.setSubtitle({ text: subtitle }); + + available.TempSum.forEach(idx => { + if (idx in resp) { + Object.keys(resp[idx]).forEach(yr => { + chart.addSeries({ + name: idx + '-' + yr, + visible: false, + data: resp[idx][yr] + }, false); + }); + // make the last series visible + chart.series[chart.series.length - 1].visible = true; + } + }); + + chart.hideLoading(); + chart.redraw(); + } + }); +}; diff --git a/js/menu.js b/js/menu.js new file mode 100644 index 0000000..9f7d7f2 --- /dev/null +++ b/js/menu.js @@ -0,0 +1,36 @@ +/* + Menu configuration file for NEW CuMX template + Last modified: 2022/07/05 11:39:38 + menu.js - typical name, you define the one used in setpagedata.js + + It is STRONGLY RECOMMENDED that if you customise this file, you create a new file with a different name, e.g. mymenu.js + and change setpagedata.js to use that file. This will avoid your customisations being accidentally overwritten during upgrades + + Properties: + .menu - can be 'b' (both menus), 'w' (wide menu ONLY), 'n' (narrow menu ONLY) + .new_window:true - forces the link to open in new browser window + .forum:true - flags a forum link menu item, it will use the url provided in CuMX config, if that is blank the menu item will be hidden + .webcam:true - flags a webcam link menu item, it will use the url provided in CuMX config, if that is blank the menu item will be hidden +*/ + +menuSrc = [ + {title: "Now", menu: "b", url: "index.htm"}, + {title: "Today", menu: "b", url: "today.htm"}, + {title: "Yesterday", menu: "b", url: "yesterday.htm"}, + {title: "Today-Yest", menu: "b", url: "todayyest.htm"}, + {title: "Gauges", menu: "b", url: "gauges.htm"}, + {title: "Records", menu: "b", submenu: true, items: [ + {title: "This Month", menu: "b", url: "thismonth.htm"}, + {title: "This Year", menu: "b", url: "thisyear.htm"}, + {title: "All Time", menu: "b", url: "record.htm"}, + {title: "Monthly", menu: "b", url: "monthlyrecord.htm"} + ]}, + {title: "Charts", menu: "b", submenu: true, items: [ + {title: "Trends", menu: "b", url: "trends.htm"}, + {title: "Select-a-graph", menu: "b", url: "selectachart.htm"}, + {title: "Historic", menu: "b", url: "historic.htm"} + ]}, + {title: "Reports", menu: "b", url: "noaareport.htm"}, + {title: "Forum", menu: "b", url: "#", forum: true, new_window: true}, + {title: "Webcam", menu: "b", url: "#", webcam: true} +]; diff --git a/js/menuSample.js b/js/menuSample.js new file mode 100644 index 0000000..87c644e --- /dev/null +++ b/js/menuSample.js @@ -0,0 +1,44 @@ +/* + An example extended/modified Menu configuration file for NEW CuMX template + Last modified: 2021/03/19 09:17:14 + menuSample.js - typical name, you define the one used in setpagedata.js + + Properties: + .menu - can be 'b' (both menus), 'w' (wide menu ONLY), 'n' (narrow menu ONLY) + .new_window:true - forces the link to open in new browser window + .forum:true - flags a forum link menu item, it will use the url provided in CuMX config, if that is blank the menu item will be hidden + .webcam:true - flags a webcam link menu item, it will use the url provided in CuMX config, if that is blank the menu item will be hidden +*/ + +menuSrc = [ + { title: "Now", menu: "b", url: "index.htm" }, + { title: "Today", menu: "b", url: "today.htm" }, + { title: "Yesterday", menu: "b", url: "yesterday.htm" }, + { title: "Gauges", menu: "b", url: "gauges.htm" }, + { + title: "Records", menu: "b", submenu: true, items: [ + { title: "This Month", menu: "b", url: "thismonth.htm" }, + { title: "This Year", menu: "b", url: "thisyear.htm" }, + { title: "All Time", menu: "b", url: "record.htm" }, + { title: "Monthly", menu: "b", url: "monthlyrecord.htm" } + ] + }, + { + title: "Charts", menu: "b", submenu: true, items: [ + { title: "Trends", menu: "b", url: "trends.htm" }, + { title: "Select-a-graph", menu: "b", url: "selectachart.htm" }, + { title: "Historic", menu: "b", url: "historic.htm" } + ] + }, + { title: "Reports", menu: "b", url: "noaareport.htm" }, + { title: "Forum", menu: "n", url: "#", new_window: true }, + { title: "Webcam", menu: "n", url: "#", new_window: true }, + { + title: "Other Links", menu: "w", submenu: true, items: [ + { title: "Cumulus Forum", menu: "w", url: "#", forum: true, new_window: true }, + { title: "Webcam", menu: "b", url: "#", webcam: true, new_window: true }, + { title: "My Cat", menu: "b", url: "mycatpage.htm" }, + { title: "Some Cat", menu: "b", url: "https://pixnio.com/free-images/2020/07/26/2020-07-26-08-52-19-1200x1200.jpg", new_window: true } + ] + } +]; diff --git a/js/monthlyrecdata.js b/js/monthlyrecdata.js new file mode 100644 index 0000000..6b8528c --- /dev/null +++ b/js/monthlyrecdata.js @@ -0,0 +1,74 @@ +// Last modified: 2022/07/27 15:35:57 + +$(document).ready(function() { + dataLoadedPromise.then(function() { + var yesterday = new Date() + yesterday.setDate(yesterday.getDate() - 1) + changeData(yesterday.getMonth()); + $('#btnMon' + yesterday.getMonth()).attr('aria-pressed', true); + }); +}); + +var monthnames = new Array("January","February","March","April","May","June","July","August","September","October","November","December"); + +function changeData(month) { + document.getElementById('MonthName').innerHTML = monthnames[month]; + document.getElementById('TempH').innerHTML = cmx_data.monthlyrecs.hightemp[month]; + document.getElementById('TempHT').innerHTML = cmx_data.monthlyrecs.hightempT[month]; + document.getElementById('TempL').innerHTML = cmx_data.monthlyrecs.lowtemp[month]; + document.getElementById('TempLT').innerHTML = cmx_data.monthlyrecs.lowtempT[month]; + document.getElementById('DewPointH').innerHTML = cmx_data.monthlyrecs.highDP[month]; + document.getElementById('DewPointHT').innerHTML = cmx_data.monthlyrecs.highDPT[month]; + document.getElementById('DewPointL').innerHTML = cmx_data.monthlyrecs.lowDP[month]; + document.getElementById('DewPointLT').innerHTML = cmx_data.monthlyrecs.lowDPT[month]; + document.getElementById('AppTempH').innerHTML = cmx_data.monthlyrecs.highapptemp[month]; + document.getElementById('AppTempHT').innerHTML = cmx_data.monthlyrecs.highapptempT[month]; + document.getElementById('AppTempL').innerHTML = cmx_data.monthlyrecs.lowapptemp[month]; + document.getElementById('AppTempLT').innerHTML = cmx_data.monthlyrecs.lowapptempT[month]; + document.getElementById('FeelsLikeH').innerHTML = cmx_data.monthlyrecs.highfeelslike[month]; + document.getElementById('FeelsLikeHT').innerHTML = cmx_data.monthlyrecs.highfeelslikeT[month]; + document.getElementById('FeelsLikeL').innerHTML = cmx_data.monthlyrecs.lowfeelslike[month]; + document.getElementById('FeelsLikeLT').innerHTML = cmx_data.monthlyrecs.lowfeelslikeT[month]; + document.getElementById('WChillL').innerHTML = cmx_data.monthlyrecs.lowchill[month]; + document.getElementById('WChillLT').innerHTML = cmx_data.monthlyrecs.lowchillT[month]; + document.getElementById('HeatIndexH').innerHTML = cmx_data.monthlyrecs.highheatindex[month]; + document.getElementById('HeatIndexHT').innerHTML = cmx_data.monthlyrecs.highheatindexT[month]; + document.getElementById('MinTempH').innerHTML = cmx_data.monthlyrecs.highmintemp[month]; + document.getElementById('MinTempHT').innerHTML = cmx_data.monthlyrecs.highmintempT[month]; + document.getElementById('MaxTempL').innerHTML = cmx_data.monthlyrecs.lowmaxtemp[month]; + document.getElementById('MaxTempLT').innerHTML = cmx_data.monthlyrecs.lowmaxtempT[month]; + document.getElementById('HumH').innerHTML = cmx_data.monthlyrecs.highhum[month]; + document.getElementById('HumHT').innerHTML = cmx_data.monthlyrecs.highhumT[month]; + document.getElementById('HumL').innerHTML = cmx_data.monthlyrecs.lowhum[month]; + document.getElementById('HumLT').innerHTML = cmx_data.monthlyrecs.lowhumT[month]; + document.getElementById('HighDailyTempRange').innerHTML = cmx_data.monthlyrecs.hightemprange[month]; + document.getElementById('HighDailyTempRangeT').innerHTML = cmx_data.monthlyrecs.hightemprangeT[month]; + document.getElementById('LowDailyTempRange').innerHTML = cmx_data.monthlyrecs.lowtemprange[month]; + document.getElementById('LowDailyTempRangeT').innerHTML = cmx_data.monthlyrecs.lowtemprangeT[month]; + document.getElementById('RainRateH').innerHTML = cmx_data.monthlyrecs.rainrate[month]; + document.getElementById('RainRateHT').innerHTML = cmx_data.monthlyrecs.rainrateT[month]; + document.getElementById('HourlyRainH').innerHTML = cmx_data.monthlyrecs.hourlyrain[month]; + document.getElementById('HourlyRainHT').innerHTML = cmx_data.monthlyrecs.hourlyrainT[month]; + document.getElementById('Rain24HourH').innerHTML = cmx_data.monthlyrecs.rain24h[month]; + document.getElementById('Rain24HourHT').innerHTML = cmx_data.monthlyrecs.rain24hT[month]; + document.getElementById('DailyRainH').innerHTML = cmx_data.monthlyrecs.dailyrain[month]; + document.getElementById('DailyRainHT').innerHTML = cmx_data.monthlyrecs.dailyrainT[month]; + document.getElementById('MonthlyRainH').innerHTML = cmx_data.monthlyrecs.monthlyrain[month]; + document.getElementById('MonthlyRainHT').innerHTML = cmx_data.monthlyrecs.monthlyrainT[month]; + document.getElementById('LongestDryPeriod').innerHTML = cmx_data.monthlyrecs.dryperiod[month]; + document.getElementById('LongestDryPeriodT').innerHTML = cmx_data.monthlyrecs.dryperiodT[month]; + document.getElementById('LongestWetPeriod').innerHTML = cmx_data.monthlyrecs.wetperiod[month]; + document.getElementById('LongestWetPeriodT').innerHTML = cmx_data.monthlyrecs.wetperiodT[month]; + document.getElementById('GustH').innerHTML = cmx_data.monthlyrecs.highgust[month]; + document.getElementById('GustHT').innerHTML = cmx_data.monthlyrecs.highgustT[month]; + document.getElementById('WindH').innerHTML = cmx_data.monthlyrecs.highwind[month]; + document.getElementById('WindHT').innerHTML = cmx_data.monthlyrecs.highwindT[month]; + document.getElementById('WindRunH').innerHTML = cmx_data.monthlyrecs.highwindrun[month]; + document.getElementById('WindRunHT').innerHTML = cmx_data.monthlyrecs.highwindrunT[month]; + document.getElementById('PressL').innerHTML = cmx_data.monthlyrecs.lowpress[month]; + document.getElementById('PressLT').innerHTML = cmx_data.monthlyrecs.lowpressT[month]; + document.getElementById('PressH').innerHTML = cmx_data.monthlyrecs.highpress[month]; + document.getElementById('PressHT').innerHTML = cmx_data.monthlyrecs.highpressT[month]; + $('#btnArray').children('button').attr("aria-pressed", false); + $('#btnMon' + month).attr('aria-pressed', true); +} diff --git a/js/noaarpts.js b/js/noaarpts.js new file mode 100644 index 0000000..44d3a93 --- /dev/null +++ b/js/noaarpts.js @@ -0,0 +1,142 @@ +/* ---------------------------------------------------------- + * noaarpts.js + * Last modified: 2021/07/10 13:19:42 + * Populates the dropdown menus using the records began date + * + * Requires jQuery + * ----------------------------------------------------------*/ + +let rptPath = 'data/reports/'; // Your path should have a trailing "/", eg. 'Reports/' +let startYear, endYear; +let startMonth, endMonth; +let rptAvail = {}; + +if (rptPath.length && rptPath.slice(-1) !== '/') + rptPath += '/'; + +$(document).ready(function () { + dataLoadedPromise.then(function () { + startYear = cmx_data.recordsbegandateISO.split('-')[0] * 1; + startMonth = cmx_data.recordsbegandateISO.split('-')[1] * 1; + endYear = cmx_data.metdateyesterdayISO.split('-')[0] * 1; + endMonth = cmx_data.metdateyesterdayISO.split('-')[1] * 1; + + // This does the initial disable of out of range months this year + rptAvail[endYear] = []; + for (let m = 1; m < 13; m++) { + // greater than end month + rptAvail[endYear][m] = m <= endMonth; + // if start year is this year, then less start month + if (startYear == endYear) { + rptAvail[endYear][m] = rptAvail[endYear][m] && m >= startMonth + } + $('#opt-' + m).prop('hidden', !rptAvail[endYear][m]); + } + + // get the current year report and display it whilst we sort out the rest in background + getYearRpt(endYear); + + // add the year select dropdown values, most recent first + for (let y = endYear; y >= startYear; y--) { + let option = $(''); + optgrp.attr('label', k); + result1[k].forEach(function (val) { + var option = $('