@brightspace-ui/core 1.213.1 → 1.216.0

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 (76) hide show
  1. package/components/button/button-mixin.js +1 -1
  2. package/components/calendar/calendar.js +5 -5
  3. package/components/card/card-footer-link.js +2 -2
  4. package/components/card/card.js +1 -1
  5. package/components/demo/code-view.js +2 -2
  6. package/components/demo/demo-snippet.js +5 -2
  7. package/components/dialog/dialog-confirm.js +1 -0
  8. package/components/dialog/dialog-mixin.js +7 -2
  9. package/components/dropdown/dropdown-button-subtle.js +1 -1
  10. package/components/dropdown/dropdown-button.js +1 -1
  11. package/components/dropdown/dropdown-content-mixin.js +6 -6
  12. package/components/dropdown/dropdown-context-menu.js +1 -1
  13. package/components/dropdown/dropdown-menu.js +1 -0
  14. package/components/dropdown/dropdown-more.js +1 -1
  15. package/components/dropdown/dropdown-opener-mixin.js +1 -0
  16. package/components/dropdown/dropdown-tabs.js +1 -0
  17. package/components/dropdown/dropdown.js +1 -0
  18. package/components/expand-collapse/expand-collapse-content.js +4 -4
  19. package/components/filter/filter.js +5 -4
  20. package/components/focus-trap/focus-trap.js +6 -5
  21. package/components/form/demo/form-demo.js +1 -1
  22. package/components/form/demo/form-dialog-demo.js +4 -4
  23. package/components/form/demo/form-native-demo.js +1 -1
  24. package/components/form/form-element-mixin.js +12 -3
  25. package/components/form/form-errory-summary.js +2 -2
  26. package/components/form/form-native.js +1 -1
  27. package/components/form/form.js +1 -1
  28. package/components/hierarchical-view/hierarchical-view-mixin.js +7 -6
  29. package/components/html-block/demo/html-block.html +31 -0
  30. package/components/html-block/html-block.js +18 -7
  31. package/components/inputs/demo/input-radio-solo-test.js +1 -1
  32. package/components/inputs/demo/input-radio-spacer-test.js +1 -1
  33. package/components/inputs/demo/input-select-test.js +1 -1
  34. package/components/inputs/input-checkbox.js +1 -1
  35. package/components/inputs/input-date-range.js +4 -3
  36. package/components/inputs/input-date-time-range-to.js +1 -1
  37. package/components/inputs/input-date-time-range.js +4 -3
  38. package/components/inputs/input-date-time.js +6 -5
  39. package/components/inputs/input-date.js +3 -0
  40. package/components/inputs/input-number.js +2 -1
  41. package/components/inputs/input-percent.js +2 -1
  42. package/components/inputs/input-search.js +3 -3
  43. package/components/inputs/input-text.js +8 -8
  44. package/components/inputs/input-textarea.js +5 -5
  45. package/components/inputs/input-time-range.js +4 -4
  46. package/components/inputs/input-time.js +1 -1
  47. package/components/link/link.js +1 -1
  48. package/components/list/README.md +91 -59
  49. package/components/list/demo/list-drag-and-drop.js +25 -16
  50. package/components/list/list-header.js +1 -0
  51. package/components/list/list-item-button.js +1 -0
  52. package/components/list/list-item-checkbox-mixin.js +4 -2
  53. package/components/list/list-item-drag-drop-mixin.js +12 -6
  54. package/components/list/list-item-generic-layout.js +5 -4
  55. package/components/list/list-item-mixin.js +1 -0
  56. package/components/list/list-item.js +1 -0
  57. package/components/list/list.js +9 -4
  58. package/components/menu/demo/custom-view.js +1 -1
  59. package/components/menu/menu-item-link.js +1 -1
  60. package/components/menu/menu-item-mixin.js +1 -1
  61. package/components/menu/menu.js +2 -2
  62. package/components/overflow-group/overflow-group.js +1 -1
  63. package/components/scroll-wrapper/demo/scroll-wrapper-test.js +1 -1
  64. package/components/selection/selection-action.js +1 -1
  65. package/components/selection/selection-input.js +1 -1
  66. package/components/selection/selection-select-all.js +1 -1
  67. package/components/switch/switch-mixin.js +1 -1
  68. package/components/table/table-col-sort-button.js +1 -1
  69. package/components/tabs/tabs.js +20 -15
  70. package/components/tooltip/tooltip.js +1 -1
  71. package/custom-elements.json +97 -69
  72. package/directives/animate/animate.js +35 -18
  73. package/helpers/demo/announce-test.js +1 -0
  74. package/mixins/arrow-keys-mixin.js +3 -1
  75. package/package.json +1 -1
  76. package/templates/primary-secondary/primary-secondary.js +2 -1
@@ -5,6 +5,11 @@ import { HtmlBlockMathRenderer } from '../../helpers/mathjax.js';
5
5
  import { requestInstance } from '../../mixins/provider-mixin.js';
6
6
 
7
7
  export const htmlBlockContentStyles = css`
8
+ .d2l-html-block-compact {
9
+ font-size: 0.8rem;
10
+ font-weight: 400;
11
+ line-height: 1.2rem;
12
+ }
8
13
  h1, h2, h3, h4, h5, h6, b, strong, b *, strong * {
9
14
  font-weight: bold;
10
15
  }
@@ -49,7 +54,11 @@ export const htmlBlockContentStyles = css`
49
54
  ul, ol {
50
55
  list-style-position: outside;
51
56
  margin: 1em 0;
52
- padding-left: 3em;
57
+ padding-inline-start: 3em;
58
+ }
59
+ .d2l-html-block-compact ul,
60
+ .d2l-html-block-compact ol {
61
+ padding-inline-start: 1.5em;
53
62
  }
54
63
  ul, ul[type="disc"] {
55
64
  list-style-type: disc;
@@ -95,11 +104,6 @@ export const htmlBlockContentStyles = css`
95
104
  :host([dir="rtl"]) {
96
105
  text-align: right;
97
106
  }
98
- :host([dir="rtl"]) ul,
99
- :host([dir="rtl"]) ol {
100
- padding-left: 0;
101
- padding-right: 3em;
102
- }
103
107
  `;
104
108
 
105
109
  let renderers;
@@ -120,6 +124,11 @@ class HtmlBlock extends LitElement {
120
124
 
121
125
  static get properties() {
122
126
  return {
127
+ /**
128
+ * Whether compact styles should be applied
129
+ * @type {Boolean}
130
+ */
131
+ compact: { type: Boolean },
123
132
  /**
124
133
  * Whether to disable deferred rendering of the user-authored HTML. Do *not* set this
125
134
  * unless your HTML relies on script executions that may break upon stamping.
@@ -153,6 +162,7 @@ class HtmlBlock extends LitElement {
153
162
 
154
163
  constructor() {
155
164
  super();
165
+ this.compact = false;
156
166
  this.noDeferredRendering = false;
157
167
 
158
168
  const rendererContextAttributes = getRenderers().reduce((attrs, currentRenderer) => {
@@ -185,7 +195,7 @@ class HtmlBlock extends LitElement {
185
195
 
186
196
  if (this._renderContainer) return;
187
197
 
188
- this.shadowRoot.innerHTML += '<div class="d2l-html-block-rendered"></div><slot></slot>';
198
+ this.shadowRoot.innerHTML += `<div class="d2l-html-block-rendered${this.compact ? ' d2l-html-block-compact' : ''}"></div><slot></slot>`;
189
199
 
190
200
  this.shadowRoot.querySelector('slot').addEventListener('slotchange', async e => await this._render(e.target));
191
201
  this._renderContainer = this.shadowRoot.querySelector('.d2l-html-block-rendered');
@@ -207,6 +217,7 @@ class HtmlBlock extends LitElement {
207
217
  }
208
218
 
209
219
  _findSlottedElement(tagName, slot) {
220
+ if (!this.shadowRoot) return;
210
221
  if (!slot) slot = this.shadowRoot.querySelector('slot');
211
222
  return slot.assignedNodes({ flatten: true })
212
223
  .find(node => (node.nodeType === Node.ELEMENT_NODE && node.tagName === tagName.toUpperCase()));
@@ -38,7 +38,7 @@ class TestInputRadioSolo extends LitElement {
38
38
  }
39
39
 
40
40
  focus() {
41
- const elem = this.shadowRoot.querySelector('input');
41
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('input');
42
42
  if (elem) elem.focus();
43
43
  }
44
44
 
@@ -19,7 +19,7 @@ class TestInputRadioSpacer extends LitElement {
19
19
  }
20
20
 
21
21
  focus() {
22
- const elem = this.shadowRoot.querySelector('input');
22
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('input');
23
23
  if (elem) elem.focus();
24
24
  }
25
25
 
@@ -53,7 +53,7 @@ class TestInputSelect extends SkeletonMixin(RtlMixin(LitElement)) {
53
53
  }
54
54
 
55
55
  focus() {
56
- const elem = this.shadowRoot.querySelector('select');
56
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('select');
57
57
  if (elem) elem.focus();
58
58
  }
59
59
 
@@ -205,7 +205,7 @@ class InputCheckbox extends SkeletonMixin(RtlMixin(LitElement)) {
205
205
  }
206
206
 
207
207
  focus() {
208
- const elem = this.shadowRoot.querySelector('input.d2l-input-checkbox');
208
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('input.d2l-input-checkbox');
209
209
  if (elem) elem.focus();
210
210
  }
211
211
 
@@ -163,8 +163,8 @@ class InputDateRange extends SkeletonMixin(FormElementMixin(RtlMixin(LocalizeCor
163
163
  }
164
164
 
165
165
  render() {
166
- const startDateInput = this.shadowRoot.querySelector('.d2l-input-date-range-start');
167
- const endDateInput = this.shadowRoot.querySelector('.d2l-input-date-range-end');
166
+ const startDateInput = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input-date-range-start');
167
+ const endDateInput = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input-date-range-end');
168
168
  const tooltipStart = (this.validationError && !this.startOpened && !this.childErrors.has(startDateInput)) ? html`<d2l-tooltip align="start" announced for="${this._startInputId}" state="error">${this.validationError}</d2l-tooltip>` : null;
169
169
  const tooltipEnd = (this.validationError && !this.endOpened && !this.childErrors.has(endDateInput)) ? html`<d2l-tooltip align="start" announced for="${this._endInputId}" state="error">${this.validationError}</d2l-tooltip>` : null;
170
170
  return html`
@@ -252,11 +252,12 @@ class InputDateRange extends SkeletonMixin(FormElementMixin(RtlMixin(LocalizeCor
252
252
  }
253
253
 
254
254
  focus() {
255
- const input = this.shadowRoot.querySelector('d2l-input-date');
255
+ const input = this.shadowRoot && this.shadowRoot.querySelector('d2l-input-date');
256
256
  if (input) input.focus();
257
257
  }
258
258
 
259
259
  async validate() {
260
+ if (!this.shadowRoot) return;
260
261
  const startDateInput = this.shadowRoot.querySelector('.d2l-input-date-range-start');
261
262
  const endDateInput = this.shadowRoot.querySelector('.d2l-input-date-range-end');
262
263
  const errors = await Promise.all([startDateInput.validate(), endDateInput.validate(), super.validate()]);
@@ -179,7 +179,7 @@ class InputDateTimeRangeTo extends SkeletonMixin(LocalizeCoreElement(LitElement)
179
179
  }
180
180
 
181
181
  _startObserving() {
182
- if (!this._parentNode) return;
182
+ if (!this.shadowRoot || !this._parentNode) return;
183
183
 
184
184
  const leftElem = this.shadowRoot.querySelector('.d2l-input-date-time-range-start-container');
185
185
  this._leftElemResizeObserver = this._leftElemResizeObserver || new ResizeObserver(() => {
@@ -209,8 +209,8 @@ class InputDateTimeRange extends SkeletonMixin(FormElementMixin(RtlMixin(Localiz
209
209
  }
210
210
 
211
211
  render() {
212
- const startDateTimeInput = this.shadowRoot.querySelector('.d2l-input-date-time-range-start');
213
- const endDateTimeInput = this.shadowRoot.querySelector('.d2l-input-date-time-range-end');
212
+ const startDateTimeInput = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input-date-time-range-start');
213
+ const endDateTimeInput = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input-date-time-range-end');
214
214
 
215
215
  const tooltipStart = (this.validationError && !this.startOpened && !this.childErrors.has(startDateTimeInput)) ? html`<d2l-tooltip align="start" announced for="${this._startInputId}" position="bottom" state="error">${this.validationError}</d2l-tooltip>` : null;
216
216
  const tooltipEnd = (this.validationError && !this.endOpened && !this.childErrors.has(endDateTimeInput)) ? html`<d2l-tooltip align="start" announced for="${this._endInputId}" position="bottom" state="error">${this.validationError}</d2l-tooltip>` : null;
@@ -308,11 +308,12 @@ class InputDateTimeRange extends SkeletonMixin(FormElementMixin(RtlMixin(Localiz
308
308
  }
309
309
 
310
310
  focus() {
311
- const input = this.shadowRoot.querySelector('d2l-input-date-time');
311
+ const input = this.shadowRoot && this.shadowRoot.querySelector('d2l-input-date-time');
312
312
  if (input) input.focus();
313
313
  }
314
314
 
315
315
  async validate() {
316
+ if (!this.shadowRoot) return;
316
317
  const startDateTimeInput = this.shadowRoot.querySelector('.d2l-input-date-time-range-start');
317
318
  const endDateTimeInput = this.shadowRoot.querySelector('.d2l-input-date-time-range-end');
318
319
  const errors = await Promise.all([startDateTimeInput.validate(), endDateTimeInput.validate(), super.validate()]);
@@ -296,11 +296,12 @@ class InputDateTime extends LabelledMixin(SkeletonMixin(FormElementMixin(Localiz
296
296
  }
297
297
 
298
298
  focus() {
299
- const elem = this.shadowRoot.querySelector('d2l-input-date');
299
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('d2l-input-date');
300
300
  if (elem) elem.focus();
301
301
  }
302
302
 
303
303
  async validate() {
304
+ if (!this.shadowRoot) return;
304
305
  const dateInput = this.shadowRoot.querySelector('d2l-input-date');
305
306
  const timeInput = this.shadowRoot.querySelector('d2l-input-time');
306
307
  const errors = await Promise.all([dateInput.validate(), timeInput.validate(), super.validate()]);
@@ -319,7 +320,7 @@ class InputDateTime extends LabelledMixin(SkeletonMixin(FormElementMixin(Localiz
319
320
  if (!newDate) {
320
321
  this.value = '';
321
322
  } else {
322
- const inputTime = this.shadowRoot.querySelector('d2l-input-time');
323
+ const inputTime = this.shadowRoot && this.shadowRoot.querySelector('d2l-input-time');
323
324
  let time;
324
325
  if (e.detail && e.detail.setToNow) time = _getFormattedDefaultTime('now');
325
326
  else time = inputTime ? inputTime.value : _getFormattedDefaultTime(this.timeDefaultValue);
@@ -346,12 +347,12 @@ class InputDateTime extends LabelledMixin(SkeletonMixin(FormElementMixin(Localiz
346
347
  }
347
348
 
348
349
  _handleInputTimeBlur() {
349
- const tooltip = this.shadowRoot.querySelector('d2l-tooltip');
350
+ const tooltip = this.shadowRoot && this.shadowRoot.querySelector('d2l-tooltip');
350
351
  if (tooltip) tooltip.hide();
351
352
  }
352
353
 
353
354
  _handleInputTimeFocus() {
354
- const tooltip = this.shadowRoot.querySelector('d2l-tooltip');
355
+ const tooltip = this.shadowRoot && this.shadowRoot.querySelector('d2l-tooltip');
355
356
  if (tooltip) tooltip.show();
356
357
  }
357
358
 
@@ -360,7 +361,7 @@ class InputDateTime extends LabelledMixin(SkeletonMixin(FormElementMixin(Localiz
360
361
  }
361
362
 
362
363
  async _handleTimeChange(e) {
363
- const date = this.shadowRoot.querySelector('d2l-input-date').value;
364
+ const date = this.shadowRoot && this.shadowRoot.querySelector('d2l-input-date').value;
364
365
  const time = e.target.value;
365
366
  this.value = this.localized ? _formatLocalDateTimeInISO(date, time) : getUTCDateTimeFromLocalDateTime(date, time);
366
367
  this._dispatchChangeEvent();
@@ -336,6 +336,7 @@ class InputDate extends LabelledMixin(SkeletonMixin(FormElementMixin(LocalizeCor
336
336
  }
337
337
 
338
338
  async validate() {
339
+ if (!this.shadowRoot) return;
339
340
  const textInput = this.shadowRoot.querySelector('d2l-input-text');
340
341
  const errors = await Promise.all([textInput.validate(), super.validate()]);
341
342
  return [...errors[0], ...errors[1]];
@@ -407,6 +408,7 @@ class InputDate extends LabelledMixin(SkeletonMixin(FormElementMixin(LocalizeCor
407
408
  }
408
409
 
409
410
  _handleDropdownOpen() {
411
+ if (!this.shadowRoot) return;
410
412
  const calendarOffset = this.shadowRoot.querySelector('d2l-calendar').getBoundingClientRect();
411
413
  const fullCalendarVisible = calendarOffset.y + calendarOffset.height < window.innerHeight;
412
414
  if (this._dropdown && !this._dropdown.openedAbove && !fullCalendarVisible) {
@@ -432,6 +434,7 @@ class InputDate extends LabelledMixin(SkeletonMixin(FormElementMixin(LocalizeCor
432
434
  async _handleFirstDropdownOpen() {
433
435
  this._dropdownFirstOpened = true;
434
436
  await this.updateComplete;
437
+ if (!this.shadowRoot) return;
435
438
  this._calendar = this.shadowRoot.querySelector('d2l-calendar');
436
439
  this._dropdown = this.shadowRoot.querySelector('d2l-dropdown-content');
437
440
  await this._calendar.updateComplete;
@@ -366,7 +366,7 @@ class InputNumber extends LabelledMixin(SkeletonMixin(FormElementMixin(LocalizeC
366
366
  }
367
367
 
368
368
  async focus() {
369
- const elem = this.shadowRoot.querySelector('d2l-input-text');
369
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('d2l-input-text');
370
370
  if (elem) {
371
371
  elem.focus();
372
372
  } else {
@@ -376,6 +376,7 @@ class InputNumber extends LabelledMixin(SkeletonMixin(FormElementMixin(LocalizeC
376
376
  }
377
377
 
378
378
  async validate() {
379
+ if (!this.shadowRoot) return;
379
380
  const inputTextElem = this.shadowRoot.querySelector('d2l-input-text');
380
381
  await inputTextElem.updateComplete;
381
382
  const childErrors = await inputTextElem.validate();
@@ -132,11 +132,12 @@ class InputPercent extends LabelledMixin(SkeletonMixin(FormElementMixin(Localize
132
132
  }
133
133
 
134
134
  focus() {
135
- const elem = this.shadowRoot.querySelector('d2l-input-number');
135
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('d2l-input-number');
136
136
  if (elem) elem.focus();
137
137
  }
138
138
 
139
139
  async validate() {
140
+ if (!this.shadowRoot) return;
140
141
  const inputNumberElem = this.shadowRoot.querySelector('d2l-input-number');
141
142
  await inputNumberElem.updateComplete;
142
143
  const childErrors = await inputNumberElem.validate();
@@ -123,7 +123,7 @@ class InputSearch extends LocalizeCoreElement(RtlMixin(LitElement)) {
123
123
  }
124
124
 
125
125
  focus() {
126
- const elem = this.shadowRoot.querySelector('d2l-input-text');
126
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('d2l-input-text');
127
127
  if (elem) elem.focus();
128
128
  }
129
129
 
@@ -132,7 +132,7 @@ class InputSearch extends LocalizeCoreElement(RtlMixin(LitElement)) {
132
132
  this._dispatchEvent();
133
133
  if (!this.noClear && this.value.length > 0) {
134
134
  this.updateComplete.then(() => {
135
- this.shadowRoot.querySelector('d2l-button-icon').focus();
135
+ if (this.shadowRoot) this.shadowRoot.querySelector('d2l-button-icon').focus();
136
136
  });
137
137
  }
138
138
  }
@@ -158,7 +158,7 @@ class InputSearch extends LocalizeCoreElement(RtlMixin(LitElement)) {
158
158
  this._setLastSearchValue('');
159
159
  this._dispatchEvent();
160
160
  }
161
- this.shadowRoot.querySelector('d2l-input-text').focus();
161
+ if (this.shadowRoot) this.shadowRoot.querySelector('d2l-input-text').focus();
162
162
  }
163
163
 
164
164
  _handleInput(e) {
@@ -271,13 +271,13 @@ class InputText extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixin(Li
271
271
 
272
272
  /** @ignore */
273
273
  get selectionEnd() {
274
- const elem = this.shadowRoot.querySelector('.d2l-input');
274
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input');
275
275
  return elem ? elem.selectionEnd : 0;
276
276
  }
277
277
 
278
278
  /** @ignore */
279
279
  get selectionStart() {
280
- const elem = this.shadowRoot.querySelector('.d2l-input');
280
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input');
281
281
  return elem ? elem.selectionStart : 0;
282
282
  }
283
283
 
@@ -301,7 +301,7 @@ class InputText extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixin(Li
301
301
 
302
302
  /** @ignore */
303
303
  get validity() {
304
- const elem = this.shadowRoot.querySelector('.d2l-input');
304
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input');
305
305
  if (!elem.validity.valid) {
306
306
  return elem.validity;
307
307
  }
@@ -318,7 +318,7 @@ class InputText extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixin(Li
318
318
  disconnectedCallback() {
319
319
  super.disconnectedCallback();
320
320
  if (this._intersectionObserver) this._intersectionObserver.disconnect();
321
- const container = this.shadowRoot.querySelector('.d2l-input-text-container');
321
+ const container = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input-text-container');
322
322
  if (!container) return;
323
323
  container.removeEventListener('blur', this._handleBlur, true);
324
324
  container.removeEventListener('focus', this._handleFocus, true);
@@ -331,7 +331,7 @@ class InputText extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixin(Li
331
331
 
332
332
  this._setValue(this.value, true);
333
333
 
334
- const container = this.shadowRoot.querySelector('.d2l-input-text-container');
334
+ const container = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input-text-container');
335
335
  if (!container) return;
336
336
  container.addEventListener('blur', this._handleBlur, true);
337
337
  container.addEventListener('focus', this._handleFocus, true);
@@ -464,7 +464,7 @@ class InputText extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixin(Li
464
464
  }
465
465
 
466
466
  async focus() {
467
- const elem = this.shadowRoot.querySelector('.d2l-input');
467
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input');
468
468
  if (elem) {
469
469
  elem.focus();
470
470
  } else {
@@ -572,7 +572,7 @@ class InputText extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixin(Li
572
572
  this._prevValue = (oldVal === undefined) ? '' : oldVal;
573
573
  this._value = val;
574
574
 
575
- const input = this.shadowRoot.querySelector('.d2l-input');
575
+ const input = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input');
576
576
  if (!input) return;
577
577
 
578
578
  this.setValidity({ tooShort: this.minlength && this.value.length > 0 && this.value.length < this.minlength });
@@ -595,7 +595,7 @@ class InputText extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixin(Li
595
595
  _updateInputLayout() {
596
596
 
597
597
  // defer until we're visible
598
- if (!this._isIntersecting) return;
598
+ if (!this.shadowRoot || !this._isIntersecting) return;
599
599
 
600
600
  const firstContainer = this.shadowRoot.querySelector('.d2l-input-inside-before');
601
601
  const firstSlotHasNodes = firstContainer.querySelector('slot').assignedNodes({ flatten: true }).length > 0
@@ -165,7 +165,7 @@ class InputTextArea extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixi
165
165
  /** @ignore */
166
166
  get textarea() {
167
167
  // temporary until consumers are updated
168
- return this.shadowRoot.querySelector('textarea');
168
+ return this.shadowRoot && this.shadowRoot.querySelector('textarea');
169
169
  }
170
170
 
171
171
  /** @ignore */
@@ -178,8 +178,8 @@ class InputTextArea extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixi
178
178
 
179
179
  /** @ignore */
180
180
  get validity() {
181
- const elem = this.shadowRoot.querySelector('textarea');
182
- if (!elem.validity.valid) {
181
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('textarea');
182
+ if (elem && !elem.validity.valid) {
183
183
  return elem.validity;
184
184
  }
185
185
  return super.validity;
@@ -264,7 +264,7 @@ class InputTextArea extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixi
264
264
  }
265
265
 
266
266
  async focus() {
267
- const elem = this.shadowRoot.querySelector('textarea');
267
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('textarea');
268
268
  if (elem) {
269
269
  elem.focus();
270
270
  } else {
@@ -274,7 +274,7 @@ class InputTextArea extends LabelledMixin(FormElementMixin(SkeletonMixin(RtlMixi
274
274
  }
275
275
 
276
276
  async select() {
277
- const elem = this.shadowRoot.querySelector('textarea');
277
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('textarea');
278
278
  if (elem) {
279
279
  elem.select();
280
280
  } else {
@@ -210,9 +210,8 @@ class InputTimeRange extends SkeletonMixin(FormElementMixin(RtlMixin(LocalizeCor
210
210
  const startLabel = this.startLabel ? this.startLabel : this.localize('components.input-time-range.startTime');
211
211
  const endLabel = this.endLabel ? this.endLabel : this.localize('components.input-time-range.endTime');
212
212
 
213
- const startTimeInput = this.shadowRoot.querySelector('.d2l-input-time-range-start');
214
- const endTimeInput = this.shadowRoot.querySelector('.d2l-input-time-range-end');
215
-
213
+ const startTimeInput = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input-time-range-start');
214
+ const endTimeInput = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input-time-range-end');
216
215
  /**
217
216
  * @type {'five'|'ten'|'fifteen'|'twenty'|'thirty'|'sixty'}
218
217
  */
@@ -304,11 +303,12 @@ class InputTimeRange extends SkeletonMixin(FormElementMixin(RtlMixin(LocalizeCor
304
303
  }
305
304
 
306
305
  focus() {
307
- const input = this.shadowRoot.querySelector('d2l-input-time');
306
+ const input = this.shadowRoot && this.shadowRoot.querySelector('d2l-input-time');
308
307
  if (input) input.focus();
309
308
  }
310
309
 
311
310
  async validate() {
311
+ if (!this.shadowRoot) return;
312
312
  const startTimeInput = this.shadowRoot.querySelector('.d2l-input-time-range-start');
313
313
  const endTimeInput = this.shadowRoot.querySelector('.d2l-input-time-range-end');
314
314
  const errors = await Promise.all([startTimeInput.validate(), endTimeInput.validate(), super.validate()]);
@@ -350,7 +350,7 @@ class InputTime extends LabelledMixin(SkeletonMixin(FormElementMixin(LitElement)
350
350
  }
351
351
 
352
352
  focus() {
353
- const elem = this.shadowRoot.querySelector('.d2l-input');
353
+ const elem = this.shadowRoot && this.shadowRoot.querySelector('.d2l-input');
354
354
  if (elem) elem.focus();
355
355
  }
356
356
 
@@ -118,7 +118,7 @@ class Link extends LitElement {
118
118
  }
119
119
 
120
120
  focus() {
121
- const link = this.shadowRoot.querySelector('.d2l-link');
121
+ const link = this.shadowRoot && this.shadowRoot.querySelector('.d2l-link');
122
122
  if (link) link.focus();
123
123
  }
124
124
  }