1import { BaseTemplate } from './BaseTemplate.js'; 2 3class AnalyticsTemplate extends BaseTemplate { 4 constructor() { 5 super(); 6 } 7 8 connectedCallback() { 9 super.connectedCallback(); 10 11 // Responsive styling on load handler 12 this.updateLeftPosition(); 13 this.updateResponsiveStyles(); 14 this.render(); 15 16 // Responsive styling on resize handler 17 this._handleResizeBound = () => { 18 this.updateLeftPosition(); 19 this.updateResponsiveStyles(); 20 }; 21 22 window.addEventListener('resize', this._handleResizeBound); 23 } 24 25 disconnectedCallback() { 26 window.removeEventListener('resize', this._handleResizeBound); 27 super.disconnectedCallback(); 28 } 29 30 render() { 31 const slotWrapper = this.getContentWrapper(); 32 if(!slotWrapper) return; 33 34 slotWrapper.innerHTML = ` 35 <style> 36 .template-header { 37 display: flex; 38 flex-direction: column; 39 padding: 1rem 2rem .5rem; 40 } 41 42 .header-top { 43 display: flex; 44 justify-content: space-between; 45 align-items: center; 46 flex-wrap: wrap; 47 margin-bottom: .5rem; 48 } 49 50 .header-actions { 51 display: flex; 52 justify-content: flex-end; 53 gap: 0.5rem; 54 flex-wrap: wrap; 55 } 56 57 ::slotted(h1[slot="header-title"]) { 58 color: #038580; 59 font-size: 32px; 60 font-weight: 500; 61 line-height: 40px; 62 margin: 0; 63 } 64 65 ::slotted(a[slot="watch-tutorial"]) { 66 display: inline-flex; 67 align-items: center; 68 font-size: 14px; 69 color: #026E80 !important; 70 text-decoration: none; 71 font-weight: 500; 72 gap: 4px; 73 white-space: nowrap; 74 line-height: 18px; 75 } 76 77 .template-content { 78 padding: .5rem 2rem 1rem; 79 } 80 81 @media (max-width: 768px) { 82 .header-top { 83 flex-direction: row; 84 justify-content: space-between; 85 gap: 0.5rem; 86 margin-bottom: 1rem; 87 } 88 89 .header-actions { 90 flex-direction: column; 91 width: 100%; 92 } 93 94 .header-actions ::slotted(*) { 95 width: 100%; 96 } 97 } 98 </style> 99 100 <slot name="banner"></slot> 101 <header class="template-header"> 102 <div class="header-top"> 103 <slot name="header-title"></slot> 104 <slot name="watch-tutorial"></slot> 105 </div> 106 <div class="header-actions"> 107 <slot name="export-data"></slot> 108 </div> 109 </header> 110 <div class="template-content"> 111 <slot></slot> 112 </div> 113 `; 114 } 115 116 updateResponsiveStyles() { 117 const isMobile = window.innerWidth <= 768; 118 119 const slots = ['export-data']; 120 slots.forEach(slotName => { 121 const button = this.querySelector(`button-element[slot="${slotName}"]`); 122 if(button) { 123 if(isMobile) { 124 button.setAttribute('full-width', ''); 125 } else { 126 button.removeAttribute('full-width'); 127 } 128 } 129 }); 130 } 131 132} 133 134customElements.define('analytics-template', AnalyticsTemplate);
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.