|
1 | 1 | ;(function () { |
2 | 2 | 'use strict' |
3 | 3 |
|
4 | | - var nav = document.querySelector('.nav-container-wrap') |
5 | | - var navPanels = nav.querySelector('.panels') |
6 | | - var pageUrl = document.head.querySelector('meta[name=page-url]').getAttribute('content') |
| 4 | + var pageNavigationGroup = window.pageNavigationGroup |
| 5 | + if (!pageNavigationGroup) return |
7 | 6 |
|
8 | 7 | var siteNavigationData = window.siteNavigationData.reduce(function (accum, entry) { |
9 | 8 | return (accum[entry.name] = entry) && accum |
10 | 9 | }, {}) |
11 | | - window.siteNavigationGroups.forEach(function (group) { |
12 | | - var groupName = document.createElement('div') |
13 | | - groupName.className = 'group-name' |
14 | | - groupName.appendChild(document.createTextNode(group.title)) |
15 | | - navPanels.appendChild(groupName) |
16 | | - group.components.forEach(function (componentName) { |
17 | | - var componentNavData = siteNavigationData[componentName] |
18 | | - var navTrees = document.createElement('div') |
19 | | - navTrees.className = 'nav-trees' |
20 | | - var versionBox = document.createElement('div') |
21 | | - versionBox.className = 'version-box' |
22 | | - var selectVersion = document.createElement('select') |
23 | | - selectVersion.className = 'select-version' |
24 | | - componentNavData.versions.forEach(function(version) { |
25 | | - var versionOption = document.createElement('option') |
26 | | - versionOption.value = version.version |
27 | | - versionOption.appendChild(document.createTextNode(version.displayVersion || version.version)) |
28 | | - selectVersion.appendChild(versionOption) |
29 | | - }) |
30 | | - versionBox.appendChild(selectVersion) |
31 | | - navTrees.appendChild(versionBox) |
32 | | - componentNavData.versions.forEach(function(version) { |
33 | | - var navTree = document.createElement('div') |
34 | | - var navItem = document.createElement('div') |
35 | | - navItem.className = 'nav-item is-link nav-top' |
36 | | - var navTitle = document.createElement('a') |
37 | | - // FIXME: this should be component version url |
38 | | - navTitle.href = relativize(pageUrl, '/' + componentNavData.name + '/current/index.html') |
39 | | - navTitle.appendChild(document.createTextNode(componentNavData.title)) |
40 | | - navItem.appendChild(navTitle) |
41 | | - navTree.appendChild(navItem) |
42 | | - navTrees.appendChild(navTree) |
43 | | - }) |
44 | | - navPanels.appendChild(navTrees) |
45 | | - }) |
46 | | - }) |
47 | 10 |
|
48 | | - return |
49 | | - var menuExpandToggle = document.querySelector('.menu-expand-toggle') |
50 | | - var versionToggle = document.querySelector('.clickable') |
51 | | - var versionDropdownList = document.querySelector('.frame-dropdown') |
52 | | - var navMenu = {} |
53 | | - if (!(navMenu.element = nav && nav.querySelector('.nav-menu'))) return |
54 | | - var navControl |
55 | | - // var currentPageItem = navMenu.element.querySelector('.is-current-page') |
| 11 | + var navContainer = document.querySelector('.nav-container') |
| 12 | + buildNav(navContainer, getPage(), pageNavigationGroup, siteNavigationData) |
| 13 | + activateNav(navContainer) |
56 | 14 |
|
57 | | - // NOTE prevent text from being selected by double click |
58 | | - navMenu.element.addEventListener('mousedown', function (e) { |
59 | | - if (e.detail > 1) e.preventDefault() |
60 | | - }) |
61 | | - |
62 | | - find(/*'.nav-toggle',*/ '.in-toggle', navMenu.element).forEach(function (toggleBtn) { |
63 | | - // console.log(toggleBtn, 17) |
64 | | - var navItem = findAncestorWithClass('nav-item', toggleBtn, navMenu.element) |
65 | | - toggleBtn.addEventListener('click', toggleActive.bind(navItem)) |
66 | | - // var dataDepth = toggleBtn.getAttribute('data-depth') |
67 | | - // if (dataDepth === 1) { |
68 | | - // toggleBtn.classList.add("mystyle") |
69 | | - // } |
70 | | - // toggleBtn.addEventListener('click', addActive.bind(navItem)) |
71 | | - |
72 | | - var navItemSpan = findNextElement(toggleBtn) |
73 | | - if (navItemSpan.classList.contains('nav-text')) { |
74 | | - navItemSpan.style.cursor = 'pointer' |
75 | | - navItemSpan.addEventListener('click', toggleActive.bind(navItem)) |
76 | | - // navItemSpan.addEventListener('click', addActive.bind(navItem)) |
| 15 | + function getPage () { |
| 16 | + var head = document.head |
| 17 | + return { |
| 18 | + component: head.querySelector('meta[name="dcterms.subject"]').getAttribute('content'), |
| 19 | + version: head.querySelector('meta[name="dcterms.identifier"]').getAttribute('content'), |
| 20 | + url: head.querySelector('meta[name=page-url]').getAttribute('content'), |
77 | 21 | } |
78 | | - }) |
79 | | - |
80 | | - if ((navControl = document.querySelector('main .nav-control'))) navControl.addEventListener('click', revealNav) |
81 | | - |
82 | | - // Toggle class |
83 | | - function toggleActive (e) { |
84 | | - this.classList.toggle('open') |
85 | | - this.classList.toggle('is-active') |
86 | 22 | } |
87 | 23 |
|
88 | | - function revealNav (e) { |
89 | | - if (nav.classList.contains('is-active')) return hideNav(e) |
90 | | - document.documentElement.classList.add('is-clipped--nav') |
91 | | - nav.classList.add('is-active') |
92 | | - nav.addEventListener('click', concealEvent) |
93 | | - window.addEventListener('click', hideNav) |
94 | | - concealEvent(e) // NOTE don't let event get picked up by window click listener |
95 | | - } |
96 | | - |
97 | | - function hideNav (e) { |
98 | | - if (e.which === 3 || e.button === 2) return |
99 | | - document.documentElement.classList.remove('is-clipped--nav') |
100 | | - nav.classList.remove('is-active') |
101 | | - nav.removeEventListener('click', concealEvent) |
102 | | - window.removeEventListener('click', hideNav) |
103 | | - concealEvent(e) // NOTE don't let event get picked up by window click listener |
104 | | - } |
105 | | - |
106 | | - function find (selector, from) { |
107 | | - return [].slice.call((from || document).querySelectorAll(selector)) |
108 | | - } |
109 | | - |
110 | | - function findAncestorWithClass (className, from, scope) { |
111 | | - if ((from = from.parentNode) !== scope) { |
112 | | - if (from.classList.contains(className)) { |
113 | | - return from |
114 | | - } else { |
115 | | - return findAncestorWithClass(className, from, scope) |
116 | | - } |
117 | | - } |
118 | | - } |
119 | | - |
120 | | - function findNextElement (from, el) { |
121 | | - if ((el = from.nextElementSibling)) return el |
122 | | - el = from |
123 | | - while ((el = el.nextSibling) && el.nodeType !== 1); |
124 | | - return el |
| 24 | + function buildNav (container, page, group, navData) { |
| 25 | + var groupEl = createElement('div', 'components') |
| 26 | + var groupNameEl = createElement('div', 'components-name') |
| 27 | + groupNameEl.appendChild(document.createTextNode(group.title)) |
| 28 | + groupEl.appendChild(groupNameEl) |
| 29 | + var componentsListEl = createElement('ul', 'components_list') |
| 30 | + group.components.forEach(function (componentName) { |
| 31 | + var componentNavData = navData[componentName] |
| 32 | + var componentsListItemsEl = createElement('li', 'components_list-items') |
| 33 | + var componentVersionsEl = createElement('div', 'component_list-version') |
| 34 | + // FIXME we would prefer if the navigation data identified the latest version itself |
| 35 | + var selectedVersion = componentName === page.component ? page.version : group.latestVersions[componentName] |
| 36 | + var componentTitleEl = createElement('span', 'component_list_title') |
| 37 | + componentTitleEl.appendChild(document.createTextNode(componentNavData.title)) |
| 38 | + componentVersionsEl.appendChild(componentTitleEl) |
| 39 | + var componentVersionsSelectEl = createElement('select', 'version_list') |
| 40 | + componentNavData.versions.forEach(function (componentVersion) { |
| 41 | + var optionEl = createElement('option') |
| 42 | + optionEl.value = componentVersion.version |
| 43 | + if (componentVersion.version === selectedVersion) optionEl.setAttribute('selected', '') |
| 44 | + optionEl.appendChild(document.createTextNode(componentVersion.displayVersion || componentVersion.version)) |
| 45 | + componentVersionsSelectEl.appendChild(optionEl) |
| 46 | + }) |
| 47 | + componentVersionsEl.appendChild(componentVersionsSelectEl) |
| 48 | + componentsListItemsEl.appendChild(componentVersionsEl) |
| 49 | + componentNavData.versions.forEach(function (componentVersion) { |
| 50 | + var componentVersionNavEl = createElement('div', 'version_items') |
| 51 | + // TODO only open if no page is found |
| 52 | + if (page.component !== componentName || page.version !== componentVersion.version) { |
| 53 | + componentVersionNavEl.classList.add('hide') |
| 54 | + } |
| 55 | + componentVersionNavEl.dataset.version = componentVersion.version |
| 56 | + buildNavTree(componentVersion.sets, componentVersionNavEl, page, []) |
| 57 | + componentsListItemsEl.appendChild(componentVersionNavEl) |
| 58 | + }) |
| 59 | + componentsListEl.appendChild(componentsListItemsEl) |
| 60 | + }) |
| 61 | + groupEl.appendChild(componentsListEl) |
| 62 | + container.appendChild(groupEl) |
125 | 63 | } |
126 | 64 |
|
127 | | - menuExpandToggle.addEventListener('click', function (e) { |
128 | | - e.preventDefault() |
129 | | - if (nav.classList.contains('collapse-menu')) { |
130 | | - nav.classList.remove('collapse-menu') |
131 | | - } else { |
132 | | - nav.classList.add('collapse-menu') |
133 | | - } |
134 | | - }) |
135 | | - |
136 | | - if (versionToggle) { |
137 | | - versionToggle.addEventListener('click', function (e) { |
138 | | - e.preventDefault() |
139 | | - if (versionDropdownList.classList.contains('show')) { |
140 | | - versionDropdownList.classList.remove('show') |
| 65 | + function buildNavTree (items, parent, page, currentPath) { |
| 66 | + if (!(items || []).length) return |
| 67 | + var navListEl = createElement('ul', 'menu_row') |
| 68 | + // FIXME we could pass some sort of forceOpen flag so hide is automatically removed |
| 69 | + if (currentPath.length) navListEl.classList.add('hide') |
| 70 | + currentPath = currentPath.concat(navListEl) |
| 71 | + items.forEach(function (item) { |
| 72 | + var navItemEl = createElement('li', 'menu_list') |
| 73 | + var navTextEl |
| 74 | + var isCurrentPage |
| 75 | + if (item.url) { |
| 76 | + navTextEl = createElement('a', 'menu_title menu_link') |
| 77 | + navTextEl.href = relativize(page.url, item.url) |
| 78 | + if (page.url === item.url) { |
| 79 | + isCurrentPage = true |
| 80 | + navItemEl.classList.add('is-current-page') |
| 81 | + currentPath.forEach(function (ancestorEl) { |
| 82 | + ancestorEl.classList.remove('hide') |
| 83 | + }) |
| 84 | + } |
141 | 85 | } else { |
142 | | - versionDropdownList.classList.add('show') |
| 86 | + navTextEl = createElement('span', 'menu_title menu_text') |
143 | 87 | } |
144 | | - concealEvent(e) |
| 88 | + navTextEl.innerHTML = item.content |
| 89 | + navItemEl.appendChild(navTextEl) |
| 90 | + // FIXME we could pass some sort of forceOpen flag so hide is automatically removed |
| 91 | + var childNavListEl = buildNavTree(item.items, navItemEl, page, currentPath) |
| 92 | + if (isCurrentPage && childNavListEl) childNavListEl.classList.remove('hide') |
| 93 | + navListEl.appendChild(navItemEl) |
145 | 94 | }) |
| 95 | + return parent.appendChild(navListEl) |
146 | 96 | } |
147 | 97 |
|
148 | | - window.addEventListener('click', function (e) { |
149 | | - versionDropdownList.classList.remove('show') |
150 | | - }) |
151 | | - |
152 | | - // has children in li |
153 | | - function concealEvent (e) { |
154 | | - e.stopPropagation() |
155 | | - } |
156 | | - // scroll left menu to current active page |
157 | | - setTimeout(function () { |
158 | | - if (document.querySelector('.is-current-page')) { |
159 | | - var currentPageMenu = document.querySelector('.is-current-page') |
160 | | - var topPositon = currentPageMenu.offsetTop - 100 |
161 | | - var leftMenu = document.querySelector('.left-sidebar-menu .nav-menu') |
162 | | - leftMenu.scrollTop = topPositon |
163 | | - } |
164 | | - }, 100) //setTime Out end |
165 | | - |
166 | | - // show depth 0 child element |
167 | | - if (document.querySelector('.is-current-page')) { |
168 | | - var otherNavs = document.querySelectorAll('.nav-list > .nav-item[data-depth="0"]') |
169 | | - otherNavs.forEach(function (nav) { |
170 | | - var navSubMenu = Array.from(nav.querySelector('ul.nav-list').children) |
171 | | - // var navDataDepth = Array.from(nav.querySelector('ul.nav-list')) |
172 | | - navSubMenu.forEach(function (item) { |
173 | | - item.classList.remove('is-inactive') |
174 | | - }) |
175 | | - |
176 | | - // hide main menu for top level navigation - |
177 | | - |
178 | | - // if (nav.className.includes('is-current-page')) { |
179 | | - // navMenuControl.style.display = 'none' |
180 | | - // } |
181 | | - |
182 | | - // hide in second level menu |
183 | | - if (nav.className.includes('is-current-path')) { |
184 | | - otherNavs.forEach(function (navItem) { |
185 | | - if (!navItem.className.includes('is-current-path')) { |
186 | | - navItem.classList.add('is-inactive') |
187 | | - } |
188 | | - }) |
189 | | - } |
190 | | - }) |
191 | | - } // if condition end |
192 | | - |
193 | | - // clearTimeout(scrollCurrentPageMenu, 20000) |
194 | | - |
195 | 98 | function relativize (from, to) { |
196 | 99 | if (!(from && to.charAt() === '/')) return to |
197 | 100 | var hash = '' |
|
236 | 139 | } |
237 | 140 | return arr.slice(start, end) |
238 | 141 | } |
| 142 | + |
| 143 | + function createElement (tagName, className) { |
| 144 | + var el = document.createElement(tagName) |
| 145 | + if (className) el.className = className |
| 146 | + return el |
| 147 | + } |
| 148 | + |
| 149 | + function find (selector, from) { |
| 150 | + return [].slice.call((from || document).querySelectorAll(selector)) |
| 151 | + } |
| 152 | + |
| 153 | + // FIXME integrate into nav builder |
| 154 | + function activateNav (container) { |
| 155 | + find('.component_list_title', container).forEach(function (componentTitleEl) { |
| 156 | + componentTitleEl.style.cursor = 'pointer' |
| 157 | + componentTitleEl.addEventListener('click', function () { |
| 158 | + var versionEl = componentTitleEl.parentNode |
| 159 | + var componentVersionEl = versionEl.parentNode |
| 160 | + var activeVersionEl = componentVersionEl.querySelector('.version_items:not(.hide)') |
| 161 | + if (activeVersionEl) { |
| 162 | + activeVersionEl.classList.add('hide') |
| 163 | + } else { |
| 164 | + var activateVersionEl = componentVersionEl.querySelector( |
| 165 | + '.version_items[data-version="' + componentVersionEl.querySelector('.version_list').value + '"]' |
| 166 | + ) |
| 167 | + if (activateVersionEl) activateVersionEl.classList.remove('hide') |
| 168 | + } |
| 169 | + }) |
| 170 | + }) |
| 171 | + |
| 172 | + find('.menu_title', container).forEach(function (menuTitleEl) { |
| 173 | + if (!menuTitleEl.nextElementSibling) return |
| 174 | + if (!menuTitleEl.href) menuTitleEl.style.cursor = 'pointer' |
| 175 | + menuTitleEl.addEventListener('click', function (e) { |
| 176 | + e.preventDefault() |
| 177 | + menuTitleEl.nextElementSibling.classList.toggle('hide') |
| 178 | + }) |
| 179 | + }) |
| 180 | + |
| 181 | + find('.version_list', container).forEach(function (versionListEl) { |
| 182 | + versionListEl.addEventListener('change', function () { |
| 183 | + var componentVersionEl = versionListEl.parentNode.parentNode |
| 184 | + var activeVersionEl = componentVersionEl.querySelector('.version_items:not(.hide)') |
| 185 | + if (activeVersionEl) activeVersionEl.classList.add('hide') |
| 186 | + var activateVersionEl = componentVersionEl.querySelector( |
| 187 | + '.version_items[data-version="' + versionListEl.value + '"]' |
| 188 | + ) |
| 189 | + if (activateVersionEl) activateVersionEl.classList.remove('hide') |
| 190 | + }) |
| 191 | + }) |
| 192 | + } |
239 | 193 | })() |
0 commit comments