kcc-gem-theme-original 2.0.0 → 2.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (73) hide show
  1. checksums.yaml +4 -4
  2. data/_includes/body.html +0 -1
  3. data/_includes/emergency-alerts.html +6 -28
  4. data/_includes/hash/theme_hash.yml +1 -1
  5. data/_includes/nav-global.html +1 -1
  6. data/_layouts/default.html +4 -2
  7. data/assets/js/alerts/addAccordionOrTabHistoryStates.js +3 -1
  8. data/assets/js/alerts/alerts.js +47 -39
  9. data/assets/js/alerts/contentHashLink.js +42 -34
  10. data/assets/js/alerts/createAlertsHtml.js +147 -24
  11. data/assets/js/alerts/parseMarkdownToHTML.js +7 -7
  12. data/assets/js/dist/102.e3ffeb2fc43382608e65.bundle.js +1 -0
  13. data/assets/js/dist/123.e3ffeb2fc43382608e65.bundle.js +1 -0
  14. data/assets/js/dist/143.e3ffeb2fc43382608e65.bundle.js +1 -0
  15. data/assets/js/dist/183.e3ffeb2fc43382608e65.bundle.js +1 -0
  16. data/assets/js/dist/3.e3ffeb2fc43382608e65.bundle.js +1 -0
  17. data/assets/js/dist/303.e3ffeb2fc43382608e65.bundle.js +1 -0
  18. data/assets/js/dist/339.e3ffeb2fc43382608e65.bundle.js +1 -0
  19. data/assets/js/dist/354.e3ffeb2fc43382608e65.bundle.js +1 -0
  20. data/assets/js/dist/{384.6cd5a5c7a6d9a4cada31.bundle.js → 384.e3ffeb2fc43382608e65.bundle.js} +1 -1
  21. data/assets/js/dist/453.e3ffeb2fc43382608e65.bundle.js +2 -0
  22. data/assets/js/dist/484.e3ffeb2fc43382608e65.bundle.js +2 -0
  23. data/assets/js/dist/484.e3ffeb2fc43382608e65.bundle.js.LICENSE.txt +11 -0
  24. data/assets/js/dist/602.e3ffeb2fc43382608e65.bundle.js +1 -0
  25. data/assets/js/dist/635.e3ffeb2fc43382608e65.bundle.js +2 -0
  26. data/assets/js/dist/695.e3ffeb2fc43382608e65.bundle.js +2 -0
  27. data/assets/js/dist/723.e3ffeb2fc43382608e65.bundle.js +1 -0
  28. data/assets/js/dist/780.e3ffeb2fc43382608e65.bundle.js +1 -0
  29. data/assets/js/dist/885.e3ffeb2fc43382608e65.bundle.js +1 -0
  30. data/assets/js/dist/885.e3ffeb2fc43382608e65.css +1 -0
  31. data/assets/js/dist/965.e3ffeb2fc43382608e65.bundle.js +1 -0
  32. data/assets/js/dist/976.e3ffeb2fc43382608e65.bundle.js +1 -0
  33. data/assets/js/dist/977.e3ffeb2fc43382608e65.bundle.js +1 -0
  34. data/assets/js/dist/theme.e3ffeb2fc43382608e65.bundle.js +2 -0
  35. data/assets/js/dist/theme.e3ffeb2fc43382608e65.css +1 -0
  36. data/assets/js/nav/searchToggleNav.js +5 -7
  37. data/assets/js/nav/toggleNavSearchDropdownOnWindowResize.js +19 -9
  38. data/assets/js/src/all.js +31 -8
  39. data/assets/js/src/searchPageJumpLinkFix.js +27 -0
  40. data/assets/js/src/searchResultsWCAGFix.js +43 -0
  41. data/assets/scss/0-tools/_bootstrap-overrides.scss +20 -5
  42. data/assets/scss/0-tools/_gsc-overrides.scss +4 -0
  43. data/assets/scss/0-tools/_gsc-search-page-overrides.scss +290 -0
  44. data/assets/scss/0-tools/_vars.scss +16 -2
  45. data/assets/scss/1-base/_html.scss +5 -0
  46. data/assets/scss/1-base/_links.scss +0 -31
  47. data/assets/scss/1-base/_typography.scss +12 -5
  48. data/assets/scss/3-layout/_positioning.scss +5 -44
  49. data/assets/scss/searchPageOverrides.scss +2 -0
  50. metadata +36 -25
  51. data/assets/js/alerts/checkForPrefersReducedMotion.js +0 -17
  52. data/assets/js/dist/102.6cd5a5c7a6d9a4cada31.bundle.js +0 -1
  53. data/assets/js/dist/143.6cd5a5c7a6d9a4cada31.bundle.js +0 -1
  54. data/assets/js/dist/183.6cd5a5c7a6d9a4cada31.bundle.js +0 -1
  55. data/assets/js/dist/3.6cd5a5c7a6d9a4cada31.bundle.js +0 -1
  56. data/assets/js/dist/303.6cd5a5c7a6d9a4cada31.bundle.js +0 -1
  57. data/assets/js/dist/354.6cd5a5c7a6d9a4cada31.bundle.js +0 -1
  58. data/assets/js/dist/453.6cd5a5c7a6d9a4cada31.bundle.js +0 -2
  59. data/assets/js/dist/604.6cd5a5c7a6d9a4cada31.bundle.js +0 -1
  60. data/assets/js/dist/635.6cd5a5c7a6d9a4cada31.bundle.js +0 -2
  61. data/assets/js/dist/695.6cd5a5c7a6d9a4cada31.bundle.js +0 -2
  62. data/assets/js/dist/723.6cd5a5c7a6d9a4cada31.bundle.js +0 -1
  63. data/assets/js/dist/965.6cd5a5c7a6d9a4cada31.bundle.js +0 -1
  64. data/assets/js/dist/977.6cd5a5c7a6d9a4cada31.bundle.js +0 -1
  65. data/assets/js/dist/theme.6cd5a5c7a6d9a4cada31.bundle.js +0 -2
  66. data/assets/js/dist/theme.6cd5a5c7a6d9a4cada31.css +0 -1
  67. /data/assets/js/dist/{384.6cd5a5c7a6d9a4cada31.css → 384.e3ffeb2fc43382608e65.css} +0 -0
  68. /data/assets/js/dist/{453.6cd5a5c7a6d9a4cada31.bundle.js.LICENSE.txt → 453.e3ffeb2fc43382608e65.bundle.js.LICENSE.txt} +0 -0
  69. /data/assets/js/dist/{635.6cd5a5c7a6d9a4cada31.bundle.js.LICENSE.txt → 635.e3ffeb2fc43382608e65.bundle.js.LICENSE.txt} +0 -0
  70. /data/assets/js/dist/{695.6cd5a5c7a6d9a4cada31.bundle.js.LICENSE.txt → 695.e3ffeb2fc43382608e65.bundle.js.LICENSE.txt} +0 -0
  71. /data/assets/js/dist/{bootstrap.6cd5a5c7a6d9a4cada31.bundle.js → bootstrap.e3ffeb2fc43382608e65.bundle.js} +0 -0
  72. /data/assets/js/dist/{bootstrap.6cd5a5c7a6d9a4cada31.css → bootstrap.e3ffeb2fc43382608e65.css} +0 -0
  73. /data/assets/js/dist/{theme.6cd5a5c7a6d9a4cada31.bundle.js.LICENSE.txt → theme.e3ffeb2fc43382608e65.bundle.js.LICENSE.txt} +0 -0
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 7d585bf8bb05486f13e73b0c8000824cf5c3b6261f625cc154e81ed11318ba67
4
- data.tar.gz: bbbd3181330658c59c84301b8b730202ecb5b1cd7b1934570d2bfec3ccefb385
3
+ metadata.gz: fada477c0b1120213f9856e65b57fd499bfe3720f99dd6ba2b86c74e7e45ee9f
4
+ data.tar.gz: 361e43daa1391a01f68ef297f7218e91290a1cfb38986f51cad8146c45668396
5
5
  SHA512:
6
- metadata.gz: 05e41285b450c49036e185b45533f17b326f39fed5a7bab0406c5de8747f378006104ac0a05a205a1b8e1aa24fc825212e2b5a0babe8e438b354cc7ba6c235f0
7
- data.tar.gz: 1dc93726a4ee8cc80e2cb1513a02e4d693ec79fd73ac0ba52aa4f7f08e6b4ea28ea65f6c0b572545a01b2809b8e10b2d3873533a42fb89a6c3bd14ecbb59979a
6
+ metadata.gz: 1b46540c354e54687acd5aeda6eec8b1de933b50a8860b7295cdcee3d6d100bcff88a1d901258d799b9e096bcbd89a1967d5329b0857804d944af9ccdfca6f88
7
+ data.tar.gz: 96542056dc296851d3d4b0a533ff96f30c22d0f57ab099fdf00f6b64153bff9c10082bee83aea9225d499e760df8d909e735a09b9cbafaca499a736fdf454c11
data/_includes/body.html CHANGED
@@ -3,4 +3,3 @@
3
3
  </head>
4
4
  <body{% if page.homepage == true %} id="homePage"{% endif %} data-bs-no-jquery>
5
5
  {% unless site.exclude_nav_skip_link == true or page.exclude_nav_skip_link == true %}<a class="visually-hidden-focusable links__skip-nav" href="#content">Jump to main content</a>{% endunless %}
6
- <h1 class="visually-hidden">{%- if page.outline_title -%}{{ page.outline_title }}{% else %}{{ page.title }}{%- endif -%}</h1>
@@ -1,29 +1,7 @@
1
- <div id="emergencyAlerts" class="position__offset-alert{% if site.core_site == true %} position__offset-alert-core{% endif %}{% if site.core_root == true %} position__offset-alert-core--root{% endif %}">
2
- <!-- Alerts get built here via JS if they are set to be active -->
3
- {%- comment -%}
4
- <div class="container position__offset-alert">
5
- <div class="row">
6
- <div class="col">
7
- <div class="alert alert-warning">
8
- <p class="typography__alert mb-0"><strong>Alert</strong>:&nbsp;All KCC facilities will be closed March 18-30. Credit classes resume online March 23. <a href="https://coronavirus.kcc.edu/" target="_blank" rel="noopener noreferrer">coronavirus.kcc.edu</a> has&nbsp;details.</p>
9
- </div>
10
- </div>
11
- </div>
12
- </div>
13
- {% endcomment %}
1
+ <div class="container">
2
+ <div class="row">
3
+ <div class="col">
4
+ <div id="emergencyAlerts" role="status" aria-hidden="true"></div>
14
5
  </div>
15
- {%- comment -%}
16
-
17
- <!-- TODO:
18
-
19
- AFTER CORE IS LAUNCHED
20
-
21
- REMOVE:
22
- ```
23
- {% if site.core_site == true %} position__offset-alert-core{% endif %}{% if site.core_root == true %} position__offset-alert-core--root{% endif %}
24
- ```
25
- (ALSO REMOVE FROM CONFIG)
26
-
27
- ENDTODO -->
28
-
29
- {%- endcomment -%}
6
+ </div>
7
+ </div>
@@ -1 +1 @@
1
- 6cd5a5c7a6d9a4cada31
1
+ e3ffeb2fc43382608e65
@@ -21,6 +21,7 @@
21
21
  role="button"
22
22
  class="nav-global__search-toggle d-lg-none ms-auto btn btn-link"
23
23
  aria-label="Toggle Search"
24
+ aria-controls="searchCollapse"
24
25
  >
25
26
  <span
26
27
  id="searchImg"
@@ -31,7 +32,6 @@
31
32
  </button>
32
33
  <div
33
34
  id="searchCollapse"
34
- aria-hidden="true"
35
35
  class="nav-global__gcse-wrapper nav-global__search-collapse ms-auto"
36
36
  >
37
37
  <gcse:searchbox-only resultsUrl="{{ page.baseurl }}search/"></gcse:searchbox-only>
@@ -18,8 +18,10 @@ layout: compress
18
18
  {% if site.translate == true %}{% include translate.html %}{% endif %}
19
19
  {% include nav-global.html %}
20
20
  {% if page.no_local_nav != true %}{% include nav-local.html %}{% endif %}
21
- {% if page.no_alert != true %}{% include emergency-alerts.html %}{% endif %}
22
- {{ content }}
21
+ <main id="content" class="positioning__offset-nav">
22
+ {% if page.no_alert != true %}{% include emergency-alerts.html %}{% endif %}
23
+ {{ content }}
24
+ </main>
23
25
  {% include footer.html %}
24
26
  {% include scripts/vendor.html %}
25
27
  {% include scripts/kcc-theme.html %}
@@ -20,7 +20,9 @@ function accordionHandler(e) {
20
20
 
21
21
  const accordionIsOpening = Boolean(JSON.parse(e.target.getAttribute('aria-expanded')));
22
22
 
23
- accordionIsOpening ? addHistoryState(e.target, e.target.dataset.bsTarget) : null;
23
+ if (accordionIsOpening) {
24
+ addHistoryState(e.target, e.target.dataset.bsTarget);
25
+ }
24
26
  }
25
27
 
26
28
  function tabHandler(e) {
@@ -3,55 +3,63 @@
3
3
  // © 2020 Kankakee Community College
4
4
  // =================================================== */
5
5
  import createAlertsHtml from './createAlertsHtml';
6
- import checkForPrefersReducedMotion from './checkForPrefersReducedMotion';
7
6
 
8
- const sheetKey = '1plXBiZY5pVbhNT-mszxEuqCl4zy8wMnz9gXXbbT_yLs'; // Corresponds to the ID of the Google Sheet
9
- const sheetTab = 'Alerts'; // Corresponds to the tab of workbook: either 'Alerts' or 'Alerts Testing' unless you make a new one.
10
- // const devSheetTab = 'ALERTS_TESTING';
11
- const emergencyAlertsDiv = 'emergencyAlerts'
7
+ const apiKey = 'AIzaSyCEBsbXfFcdbkASlg-PodD1rT_Fe3Nw62A';
12
8
  const sheetParams = {
13
- spreadsheetId: sheetKey,
14
- range: sheetTab
15
- // range: devSheetTab
16
- }; // Configures the Object used for `sheets.spreadsheets.values.get()` parameters
17
- const apiParams = { // This is configuration for API call with spreadsheets that are setup as readonly
18
- 'apiKey': 'AIzaSyCEBsbXfFcdbkASlg-PodD1rT_Fe3Nw62A',
19
- 'discoveryDocs': ['https://www.googleapis.com/discovery/v1/apis/sheets/v4/rest']
9
+ spreadsheetId: '1pqYRAhZvOHB52KqttV_d5P8qWvh9j8pPR15MCoGjMK0',
10
+ range: 'Alerts'
20
11
  };
21
- const pageHasAccordionOrTabs = (document.querySelector('#accordion') || document.querySelector('.navTabs')) ? true : false;
22
12
 
23
- async function loadModule(module) {
24
- const { default: module_func } = await import(`./${module}`);
13
+ const pageHasAccordionOrTabs = (document.querySelector('#accordion') || document.querySelector('.navTabs'));
25
14
 
26
- return module_func();
15
+ function importHashLinkModule(Collapse) {
16
+ import('./contentHashLink')
17
+ .then(({ default: contentHashLink }) => contentHashLink(Collapse));
27
18
  }
28
19
 
29
- export default function alerts(Collapse) {
30
- checkForPrefersReducedMotion();
20
+ async function fetchSheetData(spreadsheetId, range, apiKey) {
21
+ // Use encodeURIComponent to handle spaces and '!' in the range string
22
+ const encodedRange = encodeURIComponent(range);
23
+ const url = `https://sheets.googleapis.com/v4/spreadsheets/${spreadsheetId}/values/${encodedRange}?key=${apiKey}`;
31
24
 
32
- if (!document.getElementById(emergencyAlertsDiv)) {
33
- if (pageHasAccordionOrTabs) {
34
- return import('./contentHashLink').then(({default: contentHashLink}) => contentHashLink(Collapse));
25
+ try {
26
+ const response = await fetch(url);
27
+
28
+ if (!response.ok) {
29
+ const error = await response.json();
30
+ throw new Error(`Google Sheets API Error: ${error.error.message}`);
35
31
  }
32
+
33
+ const data = await response.json();
34
+
35
+ // Google returns an empty object if the range is empty;
36
+ // we default to an empty array for consistency.
37
+ return data.values || [];
38
+ } catch (err) {
39
+ console.error("Failed to fetch sheet data:", err);
40
+ throw err;
36
41
  }
42
+ }
37
43
 
38
- new Promise((resolve, reject) => { // First build the alert, whether by cache or API call
39
- gapi.load('client', () => {
40
- gapi.client.init(apiParams).then(() => {
41
- return gapi.client.sheets.spreadsheets.values.get(sheetParams);
42
- }).then(response => {
43
- createAlertsHtml(response) // Promise is resolved after HTML alert is built
44
- resolve();
45
- }, err => {
46
- console.error("Error trying to fetch the alert from gapi:", err);
44
+ export default function alerts(Collapse) {
45
+ if (!document.getElementById('emergencyAlerts') && pageHasAccordionOrTabs) {
46
+ // Handle page with no emergency alerts
47
+ importHashLinkModule(Collapse);
48
+ } else {
49
+ // Handle pages with alerts
50
+ // const response = await fetchSheetData(sheetParams.spreadsheetId, sheetParams.range, apiKey);
51
+ fetchSheetData(sheetParams.spreadsheetId, sheetParams.range, apiKey)
52
+ .then(response => {
53
+ createAlertsHtml(response);
54
+ if (pageHasAccordionOrTabs) {
55
+ importHashLinkModule(Collapse);
56
+ }
47
57
  })
48
- });
49
-
50
- }).then(() => {
51
- window.setTimeout(() => {
52
- if (pageHasAccordionOrTabs) {
53
- import('./contentHashLink').then(({default: contentHashLink}) => contentHashLink(Collapse));
54
- }
55
- }, 100)
56
- }) // Run accordion/tab JS, which includes a `scrollTo()`, after alert has painted
58
+ .catch(error => {
59
+ console.error("Error received:", error.message);
60
+ if (pageHasAccordionOrTabs) {
61
+ importHashLinkModule(Collapse);
62
+ }
63
+ })
64
+ }
57
65
  }
@@ -12,22 +12,16 @@
12
12
  //
13
13
  import Tab from 'bootstrap/js/dist/tab'; // Import Tab from Bootstrap 5
14
14
 
15
- const idRegex = /.*[\?&]id=([^&]+).*$/; // Lets just cache these reused regex's here
15
+ const idRegex = /.*[\?&]id=([^&]+).*$/;
16
16
  const endingSlashRegex = /\/$/g;
17
- const PREFERS_REDUCED_MOTION_LOCALSTORAGE_KEY = 'userPrefersReducedMotion'; // This localStorage key is set by module: './checkForPrefersReducedMotion.js'
18
- const scrollIntoViewOptionsObject = {
19
- behavior: 'smooth',
20
- block: 'center'
21
- }
22
- const reducedMotionscrollIntoViewOptionsObject = {
23
- block: 'center'
24
- }
17
+ const motionQuery = window.matchMedia('(prefers-reduced-motion: reduce)');
25
18
 
26
19
  function focusElement(el) {
27
- const prefersReducedMotion = window.localStorage.getItem(PREFERS_REDUCED_MOTION_LOCALSTORAGE_KEY);
28
-
29
- prefersReducedMotion == 'true' ? el.scrollIntoView(reducedMotionscrollIntoViewOptionsObject) : el.scrollIntoView(scrollIntoViewOptionsObject);
30
- return el.focus();
20
+ el.focus();
21
+ el.scrollIntoView({
22
+ behavior: motionQuery.matches ? 'instant' : 'smooth',
23
+ block: 'start'
24
+ });
31
25
  }
32
26
 
33
27
  function processIdQuery(query, hash) {
@@ -60,28 +54,43 @@ function openAllAccordions(Collapse) {
60
54
  })
61
55
  }
62
56
 
57
+ function handleTabs(hash) {
58
+ const tab = document.querySelector(`.nav-tabs [data-bs-target="${hash}"]`);
59
+ const bsTab = new Tab(tab);
60
+
61
+ tab.addEventListener('shown.bs.tab', _e => {
62
+ if (window.location.search) {
63
+ checkForQuery(window.location.search, hash);
64
+ } else {
65
+ findContentTarget(`${hash}-label`); // You need to .scrollIntoView() & .focus() on the tab-label which is an anchor or button. It won't work to do .scrollIntoView() and .focus() on the div
66
+ }
67
+ });
68
+
69
+ bsTab.show();
70
+ }
71
+
72
+ function handleAccordions(hash, Collapse) {
73
+ const card = document.querySelector(hash);
74
+ const bsCard = new Collapse(card, {toggle: false});
75
+
76
+ card.addEventListener('shown.bs.collapse', _e => {
77
+ if (window.location.search) {
78
+ checkForQuery(window.location.search, hash);
79
+ } else {
80
+ findContentTarget(`button[data-bs-target="${hash}"]`);
81
+ }
82
+ });
83
+
84
+ bsCard.show();
85
+ }
86
+
63
87
  function checkForMatchingTabOrAccordion(hash, Collapse) {
64
88
  if ( document.querySelector(`.nav-tabs [data-bs-target="${hash}"]`) ) { // Looks for a matching BS5 tab element
65
- const tab = document.querySelector(`.nav-tabs [data-bs-target="${hash}"]`);
66
- const bsTab = new Tab(tab);
67
-
68
- tab.addEventListener('shown.bs.tab', _e => {
69
- window.location.search ?
70
- checkForQuery(window.location.search, hash)
71
- : findContentTarget(`${hash}-label`); // You need to .scrollIntoView() & .focus() on the tab-label which is an <a href="...">. It won't work to do .scrollIntoView() and .focus() on the div
72
- });
73
- bsTab.show();
89
+ handleTabs(hash);
74
90
  } else if ( document.querySelector(`${hash}.collapse`) ) { // Looks for a matching BS5 collapse element
75
- const card = document.querySelector(hash);
76
- const bsCard = new Collapse(card, {toggle: false});
77
-
78
- card.addEventListener('shown.bs.collapse', _e => {
79
- window.location.search ?
80
- checkForQuery(window.location.search, hash)
81
- : findContentTarget(`button[data-bs-target="${hash}"]`);
82
- });
83
- bsCard.show();
91
+ handleAccordions(hash, Collapse);
84
92
  } else if (hash === '#please-open-all-accordions') {
93
+ // The #please-open-all-accordions hash is a helper for accessibility testing
85
94
  openAllAccordions(Collapse);
86
95
  }
87
96
  }
@@ -101,9 +110,8 @@ function contentHashLink(Collapse) {
101
110
  checkForHash(Collapse);
102
111
  }, false);
103
112
 
104
- import('./addAccordionOrTabHistoryStates').then(({ default: addAccordionOrTabHistoryStates }) => {
105
- addAccordionOrTabHistoryStates();
106
- });
113
+ import('./addAccordionOrTabHistoryStates')
114
+ .then(({ default: addAccordionOrTabHistoryStates }) => addAccordionOrTabHistoryStates());
107
115
  }
108
116
 
109
117
  export default contentHashLink;
@@ -1,53 +1,176 @@
1
1
  /*
2
2
  // Custom JS | written by https://github.com/wdzajicek
3
- // © 2020 Kankakee Community College
4
3
  // =================================================== */
5
4
  // JS module to build alert message using data from Google Sheets API v4
6
5
  //
7
6
  // This exported module requires you pass it's default-function the `response` object from the API call, as the only argument
8
7
  //
9
8
  import parseMarkdownToHTML from './parseMarkdownToHTML.js'; // Parses a simplified markdown into html & creates the paragraph el's with appropriate class
10
- //
11
- const alertDiv = document.getElementById('emergencyAlerts'); // This targets an element built into the DOM that we inject everything into.
12
9
 
13
- function injectAlert(target, alert) {
14
- target.innerHTML = alert;
15
- return target.classList.add('position__offset-alert--visible');
16
- }
10
+ const parent = document.getElementById('emergencyAlerts'); // This targets an element built into the DOM that we inject everything into.
17
11
 
12
+ // returns the BS5 color class depending on the choice in the Google Sheet
18
13
  function checkAlertType(type) {
19
14
  return type == 'SCHOOL EMERGENCY/CLOSURE - red' ? 'danger'
15
+ : type == 'SCHOOL WARNING - yellow' ? 'warning'
20
16
  : type == 'SCHOOL INFO - blue' ? 'primary'
21
17
  : type == 'SCHOOL INFO - cyan' ? 'info'
22
18
  : 'warning';
23
19
  }
24
20
 
25
- function createAlertsHtml(response) { // Incoming response from our Google Sheet via the Sheets API
26
- let [visibility, allPages, content, expire, start, end, type] = response.result.values[2]; // The 3rd row has our table's data
21
+ // Since the alert systems is rarely used we can get away with a simplified hashing function.
22
+ // There's a tiny possibility of hash clashing but it's not likely and alerts are used a few times a year.
23
+ // If hashes end up clashing a more formal hashing function (from external library) may be needed but will come with bloat.
24
+ function generateAlertKey(alertText) {
25
+ let hash = 0;
26
+
27
+ for (let i = 0; i < alertText.length; i++) {
28
+ const char = alertText.charCodeAt(i);
29
+ // Simple bitwise shifting math to scramble the integer uniquely
30
+ hash = (hash << 5) - hash + char;
31
+ hash |= 0; // Convert to 32bit integer
32
+ }
33
+
34
+ // Math.abs ensures we get a clean positive string ID like "college_alert_293847"
35
+ return `college_alert_${Math.abs(hash)}`;
36
+ }
37
+
38
+ // return true if the alert was dismissed already:
39
+ function isAlertDismissed(alertId) {
40
+ // 1. Grab the history object (default to empty object if it doesn't exist)
41
+ const storage = JSON.parse(localStorage.getItem('alert_history') || '{}');
42
+
43
+ // 2. Check if the specific alertId exists as a key in that object
44
+ // This returns true if found, false if not.
45
+ return alertId in storage;
46
+ }
47
+
48
+ // Returns alert HTML or false if the alert is not current or was dismissed already:
49
+ function createAlert(alertData) {
50
+ const [visibility, allPages, content, expire, start, end, type, today] = alertData;
27
51
  if (visibility === 'FALSE') // Predefined dropdown options in the Sheet are `'TRUE'` & `'FALSE'`
28
- return;
52
+ return false;
53
+
54
+ // Generate a unique key/ID for the alert
55
+ const key = generateAlertKey(content);
29
56
 
30
- const d = new Date;
57
+ if (isAlertDismissed(key))
58
+ return false;
59
+
60
+ const isEmergencyAlert = type == 'SCHOOL EMERGENCY/CLOSURE - red';
61
+ // By letting Google Sheets define today's date (and the Sheet is locked to Chicago time),
62
+ // we need to worry about JS date nonsense and edge cases
63
+ const d = new Date(today);
31
64
  const s = new Date(start);
32
65
  const e = new Date(end);
33
- const alertType = checkAlertType(type);
34
- const alertIsActive = expire === 'FALSE' || expire === 'TRUE' && s.getTime() <= d.getTime() && e.getTime() > d.getTime();
66
+
67
+ [d, s, e].forEach(d => d.setHours(0, 0, 0, 0));
68
+
69
+ const alertType = checkAlertType(type); // Get the suffix for the BS5 class depending on the alert type
70
+ const isCurrent = s.getTime() <= d.getTime() && e.getTime() >= d.getTime();
71
+ const alertIsActive = expire === 'FALSE' || expire === 'TRUE' && isCurrent;
35
72
  const indexPageOnly = allPages === 'TRUE' || allPages === 'FALSE' && window.location.pathname == '/';
36
73
  let alert = `
37
- <div class="container">
38
- <div class="row">
39
- <div class="col">
40
- <div role="alert" class="alert alert-${alertType} d-lg-flex align-items-center">
41
- <div class="typography__last-p--mb0">
42
- ${parseMarkdownToHTML(content)}
43
- </div>
44
- </div>
45
- </div>
74
+ <div data-alert-id="${key}" class="jsDismissibleAlert alert alert-${alertType} alert-dismissible fade show">
75
+ <div class="typography__last-p--mb0">
76
+ ${parseMarkdownToHTML(content)}
46
77
  </div>
78
+ <button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
47
79
  </div>`;
80
+
81
+ if (alertIsActive && indexPageOnly) {
82
+ return alert;
83
+ } else {
84
+ return false;
85
+ }
86
+ }
87
+
88
+ function saveDismissal(alertId) {
89
+ const now = Date.now();
90
+ // 1. Get the existing object or a fresh one
91
+ const storage = JSON.parse(localStorage.getItem('alert_history') || '{}');
92
+
93
+ // 2. Add the new alert with a timestamp
94
+ storage[alertId] = now;
95
+
96
+ // 3. CLEANUP: Remove any alerts older than 30 days
97
+ const thirtyDays = 30 * 24 * 60 * 60 * 1000;
98
+ for (const id in storage) {
99
+ if (now - storage[id] > thirtyDays) {
100
+ delete storage[id];
101
+ }
102
+ }
103
+
104
+ // 4. Save back to localStorage
105
+ localStorage.setItem('alert_history', JSON.stringify(storage));
106
+ }
107
+
108
+ function initAlertDismissal(activeAlertList) {
109
+ // This BS5 module provides the alert dismissing functionality.
110
+ // No need to call any functions, just importing it registers the proper listeners.
111
+ import('bootstrap/js/dist/alert.js');
112
+
113
+ // Listen for dismissal of alerts so that we can save in history
114
+ [...activeAlertList].forEach((alert, i) => {
115
+ alert.addEventListener('closed.bs.alert', e => { // 'closed.bs.alert' is a BS5 event
116
+
117
+ saveDismissal(e.target.dataset.alertId);
118
+ });
119
+ })
120
+ }
121
+
122
+ function createAlertsHtml(response) { // Incoming response from our Google Sheet via the Sheets API
123
+ // row 1 and 2 are instructions and a header row (index 0 and 1)
124
+ // row 3, 4, and 5 can contain an alert (index 2, 3, and 4)
125
+ const alertsHTML = [response[2], response[3], response[4]]
126
+ .map(createAlert)
127
+ .filter(Boolean)
128
+ .join('');
129
+
130
+ if (!alertsHTML) return;
131
+
132
+ parent.insertAdjacentHTML('beforeend', alertsHTML);
133
+ parent.removeAttribute('aria-hidden');
134
+
135
+ // Must happen after alert injection so that we can use it to check for presence of alerts
136
+ const activeAlertList = document.querySelectorAll('.jsDismissibleAlert');
137
+
138
+ // No need to go any further if there are not alerts in the page
139
+ if (activeAlertList.length === 0)
140
+ return;
141
+
142
+ // This BS5 module provides the alert dismissing functionality.
143
+ // No need to call any functions, just importing it registers the proper listeners.
144
+ import('bootstrap/js/dist/alert.js');
48
145
 
49
- [d,s,e].map(d => d.setHours(0, 0, 0, 0));
50
- return alertIsActive && indexPageOnly ? injectAlert(alertDiv, alert) : null;
146
+ // Listen for dismissal of alerts so that we can save in history
147
+ [...activeAlertList].forEach((alert, i) => {
148
+ alert.addEventListener('close.bs.alert', e => { // 'close.bs.alert' is a BS5 event
149
+ const currentAlert = e.target;
150
+
151
+ // Save in history the alerts we've already dismissed.
152
+ saveDismissal(currentAlert.dataset.alertId);
153
+
154
+ // We need to handle focus since the alert HTML gets destroyed by BS5's JS
155
+ // Look for the next alert directly below this one
156
+ const nextSibling = currentAlert.nextElementSibling;
157
+ // If a next alert exists, make it the target. Otherwise, default to #content (the main element).
158
+ const nextTarget = (nextSibling && nextSibling.classList.contains('jsDismissibleAlert'))
159
+ ? nextSibling
160
+ : document.getElementById('content');
161
+
162
+ // Move focus cleanly after the fade animation
163
+ if (nextTarget) {
164
+ if (!nextTarget.hasAttribute('tabindex')) { // Ensure the element can be focused
165
+ nextTarget.setAttribute('tabindex', '-1');
166
+ }
167
+
168
+ setTimeout(() => {
169
+ nextTarget.focus();
170
+ }, 150);
171
+ }
172
+ });
173
+ })
51
174
  }
52
175
 
53
176
  export default createAlertsHtml;
@@ -1,4 +1,4 @@
1
- const inlineMarkdownElementsObject = {
1
+ const INLINE_MARKDOWN_ELEMENTS_OBJECT = {
2
2
  'strong': /\*\*([^\*]*)\*\*/g,
3
3
  'em': /_([^_]*)_/g
4
4
  }
@@ -36,9 +36,9 @@ function replacer(match, p1) {
36
36
  if ( p1 === '' ) { // Filters out the '__' (double underscore) matches.
37
37
  return match;
38
38
  } else {
39
- for (var el in inlineMarkdownElementsObject) {
40
- if (inlineMarkdownElementsObject.hasOwnProperty(el)) {
41
- match = match.replace(inlineMarkdownElementsObject[el], '<' + el + '>$1</' + el + '>' );
39
+ for (var el in INLINE_MARKDOWN_ELEMENTS_OBJECT) {
40
+ if (INLINE_MARKDOWN_ELEMENTS_OBJECT.hasOwnProperty(el)) {
41
+ match = match.replace(INLINE_MARKDOWN_ELEMENTS_OBJECT[el], '<' + el + '>$1</' + el + '>' );
42
42
  }
43
43
  }
44
44
  return match;
@@ -46,9 +46,9 @@ function replacer(match, p1) {
46
46
  }
47
47
 
48
48
  function createInlineElements(string) {
49
- for (var el in inlineMarkdownElementsObject) {
50
- if (inlineMarkdownElementsObject.hasOwnProperty(el)) {
51
- string = string.replace(inlineMarkdownElementsObject[el], replacer);
49
+ for (var el in INLINE_MARKDOWN_ELEMENTS_OBJECT) {
50
+ if (INLINE_MARKDOWN_ELEMENTS_OBJECT.hasOwnProperty(el)) {
51
+ string = string.replace(INLINE_MARKDOWN_ELEMENTS_OBJECT[el], replacer);
52
52
  }
53
53
  }
54
54
  return string;
@@ -0,0 +1 @@
1
+ "use strict";(self.webpackChunkkcc_gem_theme=self.webpackChunkkcc_gem_theme||[]).push([[102],{2102:function(e,n){const t=document.getElementById("currentYear");n.default=function(){const e=(new Date).getFullYear();t.innerHTML!==`${e}`&&(t.innerHTML=e)}}}]);
@@ -0,0 +1 @@
1
+ "use strict";(self.webpackChunkkcc_gem_theme=self.webpackChunkkcc_gem_theme||[]).push([[123],{5123:function(e,t){const c=document.querySelector('a[href="#content"'),n=window.matchMedia("(prefers-reduced-motion: reduce)");t.default=function(){c.addEventListener("click",e=>{e.preventDefault();const t=e.target.getAttribute("href"),c=document.querySelector(t);c&&(c.hasAttribute("tabindex")||c.setAttribute("tabindex","-1"),c.focus(),c.scrollIntoView({behavior:n.matches?"instant":"smooth"}))})}}}]);
@@ -0,0 +1 @@
1
+ "use strict";(self.webpackChunkkcc_gem_theme=self.webpackChunkkcc_gem_theme||[]).push([[143],{6143:function(t,e){e.default=function(){[...document.querySelectorAll("img[data-src]")].forEach(t=>{t.setAttribute("src",t.getAttribute("data-src")),t.onload=function(){t.removeAttribute("data-src")}})}}}]);
@@ -0,0 +1 @@
1
+ "use strict";(self.webpackChunkkcc_gem_theme=self.webpackChunkkcc_gem_theme||[]).push([[183],{2183:function(e,t){const c=/\\?---?/g,n=/---/;function o(e){return-1===e.search(n)?"—":e}t.default=function(e){let t;const n=document.createNodeIterator(e,NodeFilter.SHOW_TEXT,e=>-1!==e.nodeValue.search(c)?NodeFilter.FILTER_ACCEPT:NodeFilter.FILTER_REJECT);for(;t=n.nextNode();)t.data=t.data.replace(c,o)}}}]);
@@ -0,0 +1 @@
1
+ "use strict";(self.webpackChunkkcc_gem_theme=self.webpackChunkkcc_gem_theme||[]).push([[3],{6003:function(e,c){const n=document.querySelectorAll(".hero-slider__slider--slide-heading"),s=/\*\*([^\*]+)\*\*/g;c.default=function(){[...n].forEach(e=>{e.innerHTML=e.innerHTML.replace(s,'<span class="typography__power-text">$1</span>')})}}}]);
@@ -0,0 +1 @@
1
+ "use strict";(self.webpackChunkkcc_gem_theme=self.webpackChunkkcc_gem_theme||[]).push([[303],{4303:function(t,e){const l=".hero-slider__slider",n="Pause";function s(t,e,s){const o=s===n;$(l).slick(e),function(t,e,l){t.setAttribute("aria-label",l)}(t,0,s),t.classList.toggle("hero-slider__button--play"),t.innerHTML=s,o&&$(l).slick("slickNext")}e.default=function(){$(l).on("init",function(t,e){!function(){const t=function(t){const e=document.createElement("button");return e.setAttribute("role","button"),e.setAttribute("type","button"),e.setAttribute("aria-label","Pause"),e.setAttribute("style","display: block;"),e.innerHTML="Pause",e.classList.add("hero-slider__button--toggle"),t.appendChild(e),e}(document.querySelector(l));t.addEventListener("click",e=>{"Pause"===t.innerHTML?s(t,"slickPause","Play"):s(t,"slickPlay",n)})}()}),$(l).slick({dots:!0,slidesToShow:1,slidesToScroll:1,autoplay:!0,autoplaySpeed:4e3,prevArrow:'<button type="button" data-role="none" class="prev slick-prev" aria-label="Previous" role="button" style="display: block;">Previous</button>',nextArrow:'<button type="button" data-role="none" class="next slick-next" aria-label="Next" role="button" style="display: block;">Next</button>'})}}}]);
@@ -0,0 +1 @@
1
+ "use strict";(self.webpackChunkkcc_gem_theme=self.webpackChunkkcc_gem_theme||[]).push([[339],{9306:function(t,n,r){var e=r(4901),o=r(6823),i=TypeError;t.exports=function(t){if(e(t))return t;throw new i(o(t)+" is not a function")}},8551:function(t,n,r){var e=r(34),o=String,i=TypeError;t.exports=function(t){if(e(t))return t;throw new i(o(t)+" is not an object")}},2195:function(t,n,r){var e=r(9504),o=e({}.toString),i=e("".slice);t.exports=function(t){return i(o(t),8,-1)}},6955:function(t,n,r){var e=r(2140),o=r(4901),i=r(2195),u=r(8227)("toStringTag"),c=Object,f="Arguments"===i(function(){return arguments}());t.exports=e?i:function(t){var n,r,e;return void 0===t?"Undefined":null===t?"Null":"string"==typeof(r=function(t,n){try{return t[n]}catch(t){}}(n=c(t),u))?r:f?i(n):"Object"===(e=i(n))&&o(n.callee)?"Arguments":e}},6699:function(t,n,r){var e=r(3724),o=r(4913),i=r(6980);t.exports=e?function(t,n,r){return o.f(t,n,i(1,r))}:function(t,n,r){return t[n]=r,t}},6980:function(t){t.exports=function(t,n){return{enumerable:!(1&t),configurable:!(2&t),writable:!(4&t),value:n}}},2106:function(t,n,r){var e=r(283),o=r(4913);t.exports=function(t,n,r){return r.get&&e(r.get,n,{getter:!0}),r.set&&e(r.set,n,{setter:!0}),o.f(t,n,r)}},6840:function(t,n,r){var e=r(4901),o=r(4913),i=r(283),u=r(9433);t.exports=function(t,n,r,c){c||(c={});var f=c.enumerable,a=void 0!==c.name?c.name:n;if(e(r)&&i(r,a,c),c.global)f?t[n]=r:u(n,r);else{try{c.unsafe?t[n]&&(f=!0):delete t[n]}catch(t){}f?t[n]=r:o.f(t,n,{value:r,enumerable:!1,configurable:!c.nonConfigurable,writable:!c.nonWritable})}return t}},9433:function(t,n,r){var e=r(4576),o=Object.defineProperty;t.exports=function(t,n){try{o(e,t,{value:n,configurable:!0,writable:!0})}catch(r){e[t]=n}return n}},3724:function(t,n,r){var e=r(9039);t.exports=!e(function(){return 7!==Object.defineProperty({},1,{get:function(){return 7}})[1]})},4055:function(t,n,r){var e=r(4576),o=r(34),i=e.document,u=o(i)&&o(i.createElement);t.exports=function(t){return u?i.createElement(t):{}}},2839:function(t,n,r){var e=r(4576).navigator,o=e&&e.userAgent;t.exports=o?String(o):""},9519:function(t,n,r){var e,o,i=r(4576),u=r(2839),c=i.process,f=i.Deno,a=c&&c.versions||f&&f.version,s=a&&a.v8;s&&(o=(e=s.split("."))[0]>0&&e[0]<4?1:+(e[0]+e[1])),!o&&u&&(!(e=u.match(/Edge\/(\d+)/))||e[1]>=74)&&(e=u.match(/Chrome\/(\d+)/))&&(o=+e[1]),t.exports=o},9039:function(t){t.exports=function(t){try{return!!t()}catch(t){return!0}}},616:function(t,n,r){var e=r(9039);t.exports=!e(function(){var t=function(){}.bind();return"function"!=typeof t||t.hasOwnProperty("prototype")})},9565:function(t,n,r){var e=r(616),o=Function.prototype.call;t.exports=e?o.bind(o):function(){return o.apply(o,arguments)}},350:function(t,n,r){var e=r(3724),o=r(9297),i=Function.prototype,u=e&&Object.getOwnPropertyDescriptor,c=o(i,"name"),f=c&&"something"===function(){}.name,a=c&&(!e||e&&u(i,"name").configurable);t.exports={EXISTS:c,PROPER:f,CONFIGURABLE:a}},9504:function(t,n,r){var e=r(616),o=Function.prototype,i=o.call,u=e&&o.bind.bind(i,i);t.exports=e?u:function(t){return function(){return i.apply(t,arguments)}}},7751:function(t,n,r){var e=r(4576),o=r(4901);t.exports=function(t,n){return arguments.length<2?(r=e[t],o(r)?r:void 0):e[t]&&e[t][n];var r}},5966:function(t,n,r){var e=r(9306),o=r(4117);t.exports=function(t,n){var r=t[n];return o(r)?void 0:e(r)}},4576:function(t,n,r){var e=function(t){return t&&t.Math===Math&&t};t.exports=e("object"==typeof globalThis&&globalThis)||e("object"==typeof window&&window)||e("object"==typeof self&&self)||e("object"==typeof r.g&&r.g)||e("object"==typeof this&&this)||function(){return this}()||Function("return this")()},9297:function(t,n,r){var e=r(9504),o=r(8981),i=e({}.hasOwnProperty);t.exports=Object.hasOwn||function(t,n){return i(o(t),n)}},421:function(t){t.exports={}},5917:function(t,n,r){var e=r(3724),o=r(9039),i=r(4055);t.exports=!e&&!o(function(){return 7!==Object.defineProperty(i("div"),"a",{get:function(){return 7}}).a})},3706:function(t,n,r){var e=r(9504),o=r(4901),i=r(7629),u=e(Function.toString);o(i.inspectSource)||(i.inspectSource=function(t){return u(t)}),t.exports=i.inspectSource},1181:function(t,n,r){var e,o,i,u=r(8622),c=r(4576),f=r(34),a=r(6699),s=r(9297),p=r(7629),l=r(6119),v=r(421),b="Object already initialized",y=c.TypeError,g=c.WeakMap;if(u||p.state){var h=p.state||(p.state=new g);h.get=h.get,h.has=h.has,h.set=h.set,e=function(t,n){if(h.has(t))throw new y(b);return n.facade=t,h.set(t,n),n},o=function(t){return h.get(t)||{}},i=function(t){return h.has(t)}}else{var m=l("state");v[m]=!0,e=function(t,n){if(s(t,m))throw new y(b);return n.facade=t,a(t,m,n),n},o=function(t){return s(t,m)?t[m]:{}},i=function(t){return s(t,m)}}t.exports={set:e,get:o,has:i,enforce:function(t){return i(t)?o(t):e(t,{})},getterFor:function(t){return function(n){var r;if(!f(n)||(r=o(n)).type!==t)throw new y("Incompatible receiver, "+t+" required");return r}}}},4901:function(t){var n="object"==typeof document&&document.all;t.exports=void 0===n&&void 0!==n?function(t){return"function"==typeof t||t===n}:function(t){return"function"==typeof t}},4117:function(t){t.exports=function(t){return null==t}},34:function(t,n,r){var e=r(4901);t.exports=function(t){return"object"==typeof t?null!==t:e(t)}},6395:function(t){t.exports=!1},757:function(t,n,r){var e=r(7751),o=r(4901),i=r(1625),u=r(7040),c=Object;t.exports=u?function(t){return"symbol"==typeof t}:function(t){var n=e("Symbol");return o(n)&&i(n.prototype,c(t))}},283:function(t,n,r){var e=r(9504),o=r(9039),i=r(4901),u=r(9297),c=r(3724),f=r(350).CONFIGURABLE,a=r(3706),s=r(1181),p=s.enforce,l=s.get,v=String,b=Object.defineProperty,y=e("".slice),g=e("".replace),h=e([].join),m=c&&!o(function(){return 8!==b(function(){},"length",{value:8}).length}),x=String(String).split("String"),d=t.exports=function(t,n,r){"Symbol("===y(v(n),0,7)&&(n="["+g(v(n),/^Symbol\(([^)]*)\).*$/,"$1")+"]"),r&&r.getter&&(n="get "+n),r&&r.setter&&(n="set "+n),(!u(t,"name")||f&&t.name!==n)&&(c?b(t,"name",{value:n,configurable:!0}):t.name=n),m&&r&&u(r,"arity")&&t.length!==r.arity&&b(t,"length",{value:r.arity});try{r&&u(r,"constructor")&&r.constructor?c&&b(t,"prototype",{writable:!1}):t.prototype&&(t.prototype=void 0)}catch(t){}var e=p(t);return u(e,"source")||(e.source=h(x,"string"==typeof n?n:"")),t};Function.prototype.toString=d(function(){return i(this)&&l(this).source||a(this)},"toString")},4913:function(t,n,r){var e=r(3724),o=r(5917),i=r(8686),u=r(8551),c=r(6969),f=TypeError,a=Object.defineProperty,s=Object.getOwnPropertyDescriptor,p="enumerable",l="configurable",v="writable";n.f=e?i?function(t,n,r){if(u(t),n=c(n),u(r),"function"==typeof t&&"prototype"===n&&"value"in r&&v in r&&!r[v]){var e=s(t,n);e&&e[v]&&(t[n]=r.value,r={configurable:l in r?r[l]:e[l],enumerable:p in r?r[p]:e[p],writable:!1})}return a(t,n,r)}:a:function(t,n,r){if(u(t),n=c(n),u(r),o)try{return a(t,n,r)}catch(t){}if("get"in r||"set"in r)throw new f("Accessors not supported");return"value"in r&&(t[n]=r.value),t}},1625:function(t,n,r){var e=r(9504);t.exports=e({}.isPrototypeOf)},4270:function(t,n,r){var e=r(9565),o=r(4901),i=r(34),u=TypeError;t.exports=function(t,n){var r,c;if("string"===n&&o(r=t.toString)&&!i(c=e(r,t)))return c;if(o(r=t.valueOf)&&!i(c=e(r,t)))return c;if("string"!==n&&o(r=t.toString)&&!i(c=e(r,t)))return c;throw new u("Can't convert object to primitive value")}},7750:function(t,n,r){var e=r(4117),o=TypeError;t.exports=function(t){if(e(t))throw new o("Can't call method on "+t);return t}},6119:function(t,n,r){var e=r(5745),o=r(3392),i=e("keys");t.exports=function(t){return i[t]||(i[t]=o(t))}},7629:function(t,n,r){var e=r(6395),o=r(4576),i=r(9433),u="__core-js_shared__",c=t.exports=o[u]||i(u,{});(c.versions||(c.versions=[])).push({version:"3.49.0",mode:e?"pure":"global",copyright:"© 2013–2025 Denis Pushkarev (zloirock.ru), 2025–2026 CoreJS Company (core-js.io). All rights reserved.",license:"https://github.com/zloirock/core-js/blob/v3.49.0/LICENSE",source:"https://github.com/zloirock/core-js"})},5745:function(t,n,r){var e=r(7629);t.exports=function(t,n){return e[t]||(e[t]=n||{})}},4495:function(t,n,r){var e=r(9519),o=r(9039),i=r(4576).String;t.exports=!!Object.getOwnPropertySymbols&&!o(function(){var t=Symbol("symbol detection");return!i(t)||!(Object(t)instanceof Symbol)||!Symbol.sham&&e&&e<41})},8981:function(t,n,r){var e=r(7750),o=Object;t.exports=function(t){return o(e(t))}},2777:function(t,n,r){var e=r(9565),o=r(34),i=r(757),u=r(5966),c=r(4270),f=r(8227),a=TypeError,s=f("toPrimitive");t.exports=function(t,n){if(!o(t)||i(t))return t;var r,f=u(t,s);if(f){if(void 0===n&&(n="default"),r=e(f,t,n),!o(r)||i(r))return r;throw new a("Can't convert object to primitive value")}return void 0===n&&(n="number"),c(t,n)}},6969:function(t,n,r){var e=r(2777),o=r(757);t.exports=function(t){var n=e(t,"string");return o(n)?n:n+""}},2140:function(t,n,r){var e={};e[r(8227)("toStringTag")]="z",t.exports="[object z]"===String(e)},6823:function(t){var n=String;t.exports=function(t){try{return n(t)}catch(t){return"Object"}}},3392:function(t,n,r){var e=r(9504),o=0,i=Math.random(),u=e(1.1.toString);t.exports=function(t){return"Symbol("+(void 0===t?"":t)+")_"+u(++o+i,36)}},7040:function(t,n,r){var e=r(4495);t.exports=e&&!Symbol.sham&&"symbol"==typeof Symbol.iterator},8686:function(t,n,r){var e=r(3724),o=r(9039);t.exports=e&&o(function(){return 42!==Object.defineProperty(function(){},"prototype",{value:42,writable:!1}).prototype})},8622:function(t,n,r){var e=r(4576),o=r(4901),i=e.WeakMap;t.exports=o(i)&&/native code/.test(String(i))},8227:function(t,n,r){var e=r(4576),o=r(5745),i=r(9297),u=r(3392),c=r(4495),f=r(7040),a=e.Symbol,s=o("wks"),p=f?a.for||a:a&&a.withoutSetter||u;t.exports=function(t){return i(s,t)||(s[t]=c&&i(a,t)?a[t]:p("Symbol."+t)),s[t]}}}]);
@@ -0,0 +1 @@
1
+ "use strict";(self.webpackChunkkcc_gem_theme=self.webpackChunkkcc_gem_theme||[]).push([[354],{5354:function(e,t,n){n(4603),n(7566),n(8721);const r=document.getElementById("SearchTermForm");function a(e){const t=e.target,n=`?q=${encodeURIComponent(t.querySelector("#searchTermInput").value)}`;return e.preventDefault(),window.location=new URL("https://www.kcc.edu/search"+n)}t.default=function(){r.addEventListener("submit",a)}},655:function(e,t,n){var r=n(6955),a=String;e.exports=function(e){if("Symbol"===r(e))throw new TypeError("Cannot convert a Symbol value to a string");return a(e)}},2812:function(e){var t=TypeError;e.exports=function(e,n){if(e<n)throw new t("Not enough arguments");return e}},4603:function(e,t,n){var r=n(6840),a=n(9504),o=n(655),u=n(2812),i=URLSearchParams,c=i.prototype,s=a(c.append),h=a(c.delete),f=a(c.forEach),l=a([].push),v=new i("a=1&a=2&b=3");v.delete("a",1),v.delete("b",void 0),v+""!="a=2"&&r(c,"delete",function(e){var t=arguments.length,n=t<2?void 0:arguments[1];if(t&&void 0===n)return h(this,e);var r=[];f(this,function(e,t){l(r,{key:t,value:e})}),u(t,1);for(var a,i=o(e),c=o(n),v=0,m=r.length;v<m;)h(this,(a=r[v]).key),v++;for(v=0;v<m;)(a=r[v++]).key===i&&a.value===c||s(this,a.key,a.value)},{enumerable:!0,unsafe:!0})},7566:function(e,t,n){var r=n(6840),a=n(9504),o=n(655),u=n(2812),i=URLSearchParams,c=i.prototype,s=a(c.getAll),h=a(c.has),f=new i("a=1");!f.has("a",2)&&f.has("a",void 0)||r(c,"has",function(e){var t=arguments.length,n=t<2?void 0:arguments[1];if(t&&void 0===n)return h(this,e);var r=s(this,e);u(t,1);for(var a=o(n),i=0;i<r.length;)if(r[i++]===a)return!0;return!1},{enumerable:!0,unsafe:!0})},8721:function(e,t,n){var r=n(3724),a=n(9504),o=n(2106),u=URLSearchParams.prototype,i=a(u.forEach);r&&!("size"in u)&&o(u,"size",{get:function(){var e=0;return i(this,function(){e++}),e},configurable:!0,enumerable:!0})}}]);
@@ -1 +1 @@
1
- "use strict";(self.webpackChunkkcc_gem_theme=self.webpackChunkkcc_gem_theme||[]).push([[384],{384:function(e,c,k){k.r(c)}}]);
1
+ "use strict";(self.webpackChunkkcc_gem_theme=self.webpackChunkkcc_gem_theme||[]).push([[384],{8003:function(e,c,k){k.r(c)}}]);