1/********************************************************* 2COYOTE SCRIPTS 3 4Below you'll find a spot to stick all of your sweet sweet java, and some functions that were in Bones 5that I think will come in handy. 6**********************************************************/ 7 8jQuery(document).ready(function($) { 9 10 "use strict"; 11 12 13 /******************************************************** 14 TRAINING SCROLLER 15 ********************************************************/ 16 $('.training-square').click(function(){ 17 18 let target = $(this).data('start'); 19 $(this).toggleClass('border'); 20 21 let trainingObj = $(this).closest('.current-section').find('div.training-cats').children(); 22 23 trainingObj.each((i, value) => { 24 25 const trainingIssueArray = []; 26 trainingIssueArray.push(value.id); 27 28 if(target == value.id) { 29 $(value).toggleClass('hide'); 30 } 31 32 }); 33 34 }); 35 36 /* Events - Hide Issues filters that are not used */ 37 38 $('.previous-events .training-square').each(function(){ 39 var curIssue = $(this).data('issue'); 40 var foundIssue = 0; 41 $('.results-grid .featured-item.issue-' + curIssue).each(function(){ 42 console.log("found:" + curIssue); 43 foundIssue = 1; 44 }); 45 if(foundIssue == 1) { 46 $(this).addClass('visible'); 47 } 48 }); 49 50 51 52/******************************************************** 53Pillbox Selector 54********************************************************/ 55 56$('.pillbox:not(.archive) div').click(function(){ 57 $(this).parent().find('div').removeClass('active'); 58 $(this).addClass('active'); 59 var targetType = $(this).data('target'); 60 61 if(targetType == 'all') { 62 $(this).parent().nextAll('.featured-list').find('.featured-item').removeClass('hide'); 63 } else { 64 $(this).parent().nextAll('.featured-list').find('.featured-item').addClass('hide'); 65 $(this).parent().nextAll('.featured-list').find('.type-' + targetType).removeClass('hide') 66 } 67}); 68 69 70$('.pillbox.archive div').click(function(){ 71 $(this).siblings().removeClass('active'); 72 $(this).addClass('active'); 73 var targetType = $(this).data('target'); 74 75 if(targetType == 'all') { 76 $(this).parent().nextAll('.results-grid').find('.featured-list .featured-item').removeClass('hide'); 77 } else { 78 $(this).parent().nextAll('.results-grid').find('.featured-list .featured-item').addClass('hide'); 79 $(this).parent().nextAll('.results-grid').find('.featured-list .type-' + targetType).removeClass('hide') 80 } 81}); 82 83/******************************************************** 84Events Filter 85********************************************************/ 86 87 88$('.training-link-box .training-square').click(function(){ 89 var issueCount = 0; 90 $('.results-grid .featured-item').addClass('hide'); 91 $('.training-link-box .training-square.border').each(function(i){ 92 93 issueCount++; 94 var curIssue = $(this).data('issue'); 95 $('.results-grid .featured-item.issue-' + curIssue ).removeClass('hide'); 96 }) 97 98 //show all if no issues are selected 99 if(issueCount == 0) $('.results-grid .featured-item').removeClass('hide'); 100}); 101 102 103 104 105 /******************************************************** 106 EDITIONS SCROLLER 107 ********************************************************/ 108 109 let selectedIssueArray = []; 110 111 $('.edition-square').click(function(){ 112 113 let edition = $(this); 114 let target = $(this).data('slug'); 115 116 edition.toggleClass('border'); 117 118 if(selectedIssueArray.includes(target)) { 119 selectedIssueArray.splice(selectedIssueArray.indexOf(target), 1); 120 } else { 121 selectedIssueArray.push(target); 122 } 123 124 let articleObj = $(this).closest('.editions-filter').find('div.editions-single-articles-wrap').children(); 125 console.log(selectedIssueArray); 126 127 articleObj.each((i, value) => { 128 let articleIssueArray = []; 129 articleIssueArray.push(value.className); 130 131 let classNames = articleIssueArray[0].split(' '); 132 const intersection = selectedIssueArray.filter(e => classNames.includes(e)); 133 134 if(selectedIssueArray.length <= 0 && intersection.length <= 0) { 135 $(value).removeClass('hide'); 136 } 137 138 if(intersection.length <= 0 && selectedIssueArray.length != 0) { 139 $(value).addClass('hide'); 140 } else { 141 $(value).removeClass('hide'); 142 } 143 }); 144 145 }); 146 147 /*********************************************** 148 HEADER ACTION AREA SEARCH BAR TOGGLE 149 ***********************************************/ 150 if($(window).width() > 480) { 151 152 $('.promagnifier').click(function(){ 153 // $(this).closest('.chn-search').siblings().toggleClass('transition'); 154 // $(this).closest('.chn-search').toggleClass('transition'); 155 $('.chn-interactive').toggleClass('opensearch'); 156 }); 157 } 158 159 /************************************************************ 160 HNR FILTERING 161 ************************************************************/ 162 $('.month').click(function(){ 163 var myMonth = $(this).attr('id'); 164 $('.' + myMonth).toggleClass('month-filter-out'); 165 $(this).toggleClass('fade'); 166 }); 167 168 $('.year').click(function(){ 169 var myYear = $(this).attr('id'); 170 $('.' + myYear).toggleClass('year-filter-out'); 171 $(this).toggleClass('fade'); 172 }); 173 174 /************************************************************ 175 FEATURED PIECES SPACING 176 ************************************************************/ 177 if($('.featured-right').find('.featured-4')) { 178 $('.featured-3').addClass('margintopbottom'); 179 } else { 180 $('.featured-3').addClass('margintop'); 181 } 182 183 184 /************************************************************ 185 STAFF ACCORDIAN 186 ************************************************************/ 187 $('.staff-title').click(function() { 188 var $this = $(this); 189 var $wrap = $this.closest('.staff-wrap'); 190 var $currentBellows = $this.next('.bellows'); 191 var isOpening = !$currentBellows[0].style.maxHeight; 192 193 // Close all siblings 194 $wrap.find('.staff-title').removeClass('seagreen'); 195 $wrap.find('.staff-chev').removeClass('rotate'); 196 $wrap.find('.bellows').each(function() { 197 this.style.maxHeight = null; 198 }); 199 200 // If the clicked one was closed, open it now 201 if (isOpening) { 202 $this.addClass('seagreen'); 203 $this.children('.staff-chev').addClass('rotate'); 204 $currentBellows[0].style.maxHeight = $currentBellows[0].scrollHeight + "px"; 205 } 206 }); 207 208 209 210 /**************************************************** 211 ORG SLIDE 212 ****************************************************/ 213 $('.about-org-wrap').slick({ 214 dots: true, 215 slidesPerRow: 7, 216 rows: 9, 217 arrows: true, 218 prevArrow: "<div class='arrow-container left-arrow-container'><</div>", 219 nextArrow: "<div class='arrow-container right-arrow-container'>></div></div>", 220 autoplay: true, 221 autoplaySpeed: 5000, 222 pauseOnHover: false, 223 responsive: [ 224 { 225 breakpoint: 992, 226 settings: { 227 rows: 4, 228 slidesPerRow: 4 229 } 230 }, 231 { 232 breakpoint: 481, 233 settings: { 234 rows: 4, 235 slidesPerRow: 2, 236 dots: false, 237 mobileFirst: true 238 } 239 } 240 ] 241 }); 242 243 /********************************************************* 244 ROTATING FEATURE 245 **********************************************************/ 246 let featuredTimeouts = setFeaturedTimeouts(); 247 248 // setInterval(function () { 249 250 $('.left-piece').each(function(){ 251 const me = $(this); 252 me.on('mouseover', function(){ 253 // Clear ALL timers on mouseover 254 for (let i=0; i<featuredTimeouts.length; i++) { 255 clearTimeout(featuredTimeouts[i]); 256 } 257 featuredTimeouts = []; 258 }); 259 260 me.on('mouseout', function() { 261 featuredTimeouts = setFeaturedTimeouts(); 262 }); 263 }); 264 265 // }, 100); 266 267 function setFeaturedTimeouts() 268 { 269 let time = 0; 270 let timeouts = []; 271 272 $('.left-piece').each(function(){ 273 const me = $(this); 274 timeouts.push(setTimeout(function() { 275 me.siblings().removeClass('current'); 276 me.addClass('current'); 277 }, time)); 278 time += 3000 279 }) 280 281 return timeouts; 282 } 283 284 285 286 287 /************************************************************ 288 READ MORE TEXT 289 ************************************************************/ 290 291 $('.excerpt-read-more').text("read more >"); 292 293 /************************************************************ 294 ISSUE ACCORDIAN 295 ************************************************************/ 296 297 $('.issue-arrow').click(function(e){ 298 if ($(this).css("transform") == 'none'){ 299 $(this).css("transform","rotate(180deg)"); 300 } else { 301 $(this).css("transform", "none"); 302 } 303 304 $(this).siblings().slideToggle(); 305 }); 306 307 308 /*********************************************** 309 YARPP RELATED POSTS 310 ***********************************************/ 311 $('.yarpp-related').addClass('gutters important-gutters'); 312 313 314 $('.chn-search').children().click(function() { 315 $('.chn-interactive').toggleClass('searcheffect'); 316 $('.interactive-logo').toggleClass('hide'); 317 }); 318 319 /*********************************************** 320 MOBILE MENU 321 ***********************************************/ 322 $('.mobile-icon').click(function(){ 323 $('nav').toggleClass('show-mobile-menu'); 324 }); 325 326 /*********************************************** 327 MEMBERSHIP PAGE 328 ***********************************************/ 329 330 // $('.square-tile-single').not('.library-item').click(function(ev){ 331 $('.square-tile-section.about-section .square-tile-single').click(function(ev){ 332 ev.preventDefault(); 333 var link = $(this).parent('.library-link'); 334 var tile = $(this).find('.about-us-tile'); 335 if (tile.hasClass('visible')) { 336 return; 337 338 } else { 339 // SlideUp all content boxes 340 var targetsClass = '.' + tile.data('target'), 341 intended = $(targetsClass);
342 $('.arrow_box').slideUp(); 343 $('.library-link').removeClass('open'); 344 link.addClass('open'); 345 $('.about-us-tile').removeClass('visible'); 346 tile.addClass('visible'); 347 intended.slideDown(); 348 } 349 }); 350 351 352 /*********************************************** 353 PUBLICATIONS PAGE 354 ***********************************************/ 355 356 if (window.location.pathname.includes('/publications/page/')) { 357 console.log('is paged'); 358 const section = document.getElementById('recent-publications'); 359 360 if (section) { 361 section.scrollIntoView({ behavior: 'smooth' }); 362 } 363 } 364 365 366 /************************************************************ 367 STATIC HEADER POPUPS 368 ************************************************************/ 369 370 $('.pop-link').click(function(e){ 371 e.preventDefault(); 372 var target = $(this).attr('data-target'); 373 $('.' + target + '-outer').addClass('pop-open'); 374 }); 375 376 $('.static-popup-overlay').click(function(){ 377 $(this).parents().removeClass('pop-open'); 378 }); 379 380 /************************************************************* 381 DYNAMIC POPUPS 382 *************************************************************/ 383 function setCookie(name, value, days) { 384 let expires = ""; 385 if (days) { 386 const date = new Date(); 387 date.setTime(date.getTime() + (days * 24 * 60 * 60 * 1000)); // Convert days to milliseconds 388 expires = "; expires=" + date.toUTCString(); 389 } 390 document.cookie = name + "=" + (value || "") + expires + "; path=/"; 391 } 392 function checkCookie(name) { 393 const cookieArr = document.cookie.split(";"); // Split all cookies into an array 394 for (let i = 0; i < cookieArr.length; i++) { 395 const cookiePair = cookieArr[i].trim().split("="); // Trim whitespace and split into name and value 396 if (cookiePair[0] === name) { 397 return true; // Cookie found 398 } 399 } 400 return false; // Cookie not found 401 } 402 403 $('.dynamic-popup-overlay').click(function(){ 404 $(this).closest('.dynamic-popup-outer').addClass('pop-gone'); 405 if( $('body').hasClass('page-template-page_voices') ) { 406 setCookie("hide-subscribe-to-voices", "true", 365); 407 } 408 }); 409 if ( $('body').hasClass('page-template-page_voices') && checkCookie("hide-subscribe-to-voices") ) { 410 // do nothing 411 } else { 412 $('.dynamic-popup-outer').removeClass('hide'); 413 } 414 415 416 417 418 /************************************************************* 419 NON-LINK LINKS 420 *************************************************************/ 421 $('.non-link').click(function(e) { 422 e.preventDefault(); 423 }); 424 425 /************************************************************* 426 EVENTS SHOW BUTTON 427 *************************************************************/ 428 let itemsToShow = 10; // Number of items to show per click 429 let currentItemIndex = 0; // Index to track how many items have been shown 430 431 $('#showPastEventsButton').click(function() { 432 $('.not-recent-wrap').show(); 433 // Get all the children with the .not-recent class inside .not-recent-wrap 434 const $items = $('.not-recent-wrap').children('.not-recent'); 435 436 // Calculate the new number of items to show 437 const nextItemIndex = currentItemIndex + itemsToShow; 438 439 // Loop through the items to remove the .not-recent class from the first 10 (or remaining) items 440 $items.slice(currentItemIndex, nextItemIndex).removeClass('not-recent'); 441 442 // Update the index to track the current position 443 currentItemIndex = nextItemIndex; 444 445 // Check if all items are displayed, if so, hide the button 446 if (currentItemIndex >= $items.length) { 447 $(this).hide(); 448 } 449 }); 450 451 /************************************************************* 452 SINGLE RESOURCE TABLE OF CONTENTS 453 *************************************************************/ 454 const single_resource_toc = function() { 455 const accordionTriggers = document.querySelectorAll('.content-area-item.has-sublinks .toc--trigger'); 456 457 accordionTriggers.forEach(trigger => { 458 trigger.addEventListener('click', function (event) { 459 event.preventDefault(); 460 const isExpanded = this.getAttribute('aria-expanded') === 'true'; 461 const parentItem = this.closest('.content-area-item'); 462 if (!parentItem) return; 463 464 const collapsed = parentItem.nextElementSibling; 465 if (!collapsed || !collapsed.classList.contains('collapsed')) return; 466 467 if (isExpanded) { 468 // Close it 469 this.setAttribute('aria-expanded', 'false'); 470 $(collapsed).slideUp(400); 471 collapsed.setAttribute('aria-hidden', 'true'); 472 } else { 473 // Open it 474 this.setAttribute('aria-expanded', 'true'); 475 $(collapsed).slideDown(400); 476 collapsed.setAttribute('aria-hidden', 'false'); 477 } 478 }); 479 }); 480 } 481 single_resource_toc(); 482 483}); //end of document.ready function 484 485 486/* 487 * Use this handy function and variable to get the CSS viewport dimensions. 488 * ( source: http://andylangton.co.uk/blog/development/get-viewport-size-width-and-height-javascript ) 489*/ 490function updateViewportDimensions() { 491 var w=window,d=document,e=d.documentElement,g=d.getElementsByTagName('body')[0],x=w.innerWidth||e.clientWidth||g.clientWidth,y=w.innerHeight||e.clientHeight||g.clientHeight; 492 return { width:x,height:y }; 493} 494 495var viewport = updateViewportDimensions(); 496 497 498/* 499 * Throttle Resize-triggered Events 500 * Wrap your actions in this function to throttle the frequency of firing them off, for better performance, esp. on mobile.
501 * ( source: http://stackoverflow.com/questions/2854407/javascript-jquery-window-resize-how-to-fire-after-the-resize-is-completed ) 502*/ 503var waitForFinalEvent = (function () { 504 var timers = {}; 505 return function (callback, ms, uniqueId) { 506 if (!uniqueId) { uniqueId = "Don't call this twice without a uniqueId"; } 507 if (timers[uniqueId]) { clearTimeout (timers[uniqueId]); } 508 timers[uniqueId] = setTimeout(callback, ms); 509 }; 510})(); 511 512// how long to wait before deciding the resize has stopped, in ms. Around 50-100 should work ok. 513var timeToWaitForLast = 100; 514 515/* Anchor Links animation */ 516$(document).on('click', '.single-resource_library a[href^="#"]', function (event) { 517 event.preventDefault(); 518 519 $('html, body').animate({ 520 scrollTop: $($.attr(this, 'href')).offset().top - 50 521 }, 500); 522});
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.