Skip to content

Commit f4dd988

Browse files
committed
✅ src: Fixes broken tests due to IE11 on Windows 7
Adds a couple of IE11 only fixes via CSS hacks or conventional CSS. Updates broken tests after adding IE11 fixes. To learn more, please see #128 which details all the bugs that experienced while building this project.
1 parent f845061 commit f4dd988

6 files changed

+76
-34
lines changed

index.html

+1-1
Original file line numberDiff line numberDiff line change
@@ -138,7 +138,7 @@
138138
}
139139

140140
section {
141-
max-width: 300px;
141+
max-width: 600px;
142142
width: 100%;
143143
margin: 16px auto;
144144
}

src/app-datepicker-dialog.ts

+5-1
Original file line numberDiff line numberDiff line change
@@ -237,7 +237,11 @@ export class AppDatepickerDialog extends LitElement {
237237
margin: 0 0 0 8px;
238238
}
239239
240-
/** NOTE: IE11-only fix */
240+
/**
241+
* NOTE: IE11-only fix via CSS hack.
242+
*
243+
* Visit https://bit.ly/2DEUNZu|CSS for more relevant browsers' hacks.
244+
*/
241245
@media screen and (-ms-high-contrast: none) {
242246
mwc-button[dialog-dismiss] {
243247
min-width: 10ch;

src/app-datepicker.ts

+19-9
Original file line numberDiff line numberDiff line change
@@ -429,7 +429,7 @@ export class AppDatepicker extends LitElement {
429429
@property({ type: String, reflect: true })
430430
public weekNumberType: string = WEEK_NUMBER_TYPE.FIRST_4_DAY_WEEK;
431431

432-
@property({ type: Boolean })
432+
@property({ type: Boolean, reflect: true })
433433
public landscape: boolean = false;
434434

435435
@property({ type: String })
@@ -489,7 +489,8 @@ export class AppDatepicker extends LitElement {
489489
resetButton,
490490
css`
491491
:host {
492-
width: var(--app-datepicker-width);
492+
min-width: 300px;
493+
width: 300px;
493494
/** NOTE: Magic number as 16:9 aspect ratio does not look good */
494495
/* height: calc((var(--app-datepicker-width) / .66) - var(--app-datepicker-footer-height, 56px)); */
495496
background-color: #fff;
@@ -501,10 +502,10 @@ export class AppDatepicker extends LitElement {
501502
}
502503
:host([landscape]) {
503504
display: flex;
504-
flex-direction: row;
505505
506506
/** <iphone-5-landscape-width> - <standard-side-margin-width> */
507-
--app-datepicker-width: calc(568px - 16px * 2);
507+
min-width: calc(568px - 16px * 2);
508+
width: calc(568px - 16px * 2);
508509
}
509510
510511
.datepicker-header + .datepicker-body {
@@ -539,6 +540,13 @@ export class AppDatepicker extends LitElement {
539540
color: currentColor;
540541
}
541542
543+
/**
544+
* NOTE: IE11-only fix. This prevents formatted focused date from overflowing the container.
545+
*/
546+
.datepicker-toolbar {
547+
width: 100%;
548+
}
549+
542550
.btn__selector-year {
543551
font-size: 16px;
544552
font-weight: 700;
@@ -561,7 +569,6 @@ export class AppDatepicker extends LitElement {
561569
562570
.calendar-view__month-selector {
563571
display: flex;
564-
flex-direction: row;
565572
align-items: center;
566573
567574
position: absolute;
@@ -601,7 +608,6 @@ export class AppDatepicker extends LitElement {
601608
602609
.calendar-view__full-calendar {
603610
display: flex;
604-
flex-direction: row;
605611
justify-content: center;
606612
607613
position: relative;
@@ -641,7 +647,6 @@ export class AppDatepicker extends LitElement {
641647
642648
.calendar-label {
643649
display: flex;
644-
flex-direction: row;
645650
align-items: center;
646651
justify-content: center;
647652
@@ -895,15 +900,20 @@ export class AppDatepicker extends LitElement {
895900
dispatchCustomEvent(this, 'datepicker-first-updated', { firstFocusableElement });
896901
}
897902

898-
protected updated() {
903+
protected updated(changed) {
899904
const startView = this._startView;
900905

901906
if (startView === START_VIEW.YEAR_LIST) {
902907
const selectedYearScrollTop =
903908
(this._selectedDate.getUTCFullYear() - this._todayDate.getUTCFullYear() - 2) * 48;
904909

905910
targetScrollTo(this._yearViewFullList, { top: selectedYearScrollTop, left: 0 });
906-
} else if (startView === START_VIEW.CALENDAR && !this._hasCalendarSetup) {
911+
return;
912+
}
913+
914+
const shouldTriggerCalendarLayout = changed.has('landscape') || !this._hasCalendarSetup;
915+
916+
if (startView === START_VIEW.CALENDAR && shouldTriggerCalendarLayout) {
907917
const dragEl = this._calendarViewFullCalendar;
908918
const totalDraggableDistance = this._datepickerBodyCalendarView.getBoundingClientRect().width;
909919
let started = false;

src/common-styles.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@ export const datepickerVariables = css`
5151
:host {
5252
display: block;
5353
54-
--app-datepicker-width: 300px;
54+
/* --app-datepicker-width: 300px; */
5555
/* --app-datepicker-primary-color: #4285f4; */
5656
--app-datepicker-primary-color: #1a73e8;
5757
--app-datepicker-border-radius: 8px;

src/test/app-datepicker.spec.ts

+46-22
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import {
88
toFormattedDateString,
99
} from '../datepicker-helpers.js';
1010
import {
11+
getComputedStylePropertyValue,
1112
getShadowInnerHTML,
1213
shadowQuery,
1314
shadowQueryAll,
@@ -28,6 +29,12 @@ const {
2829
* of SauceLabs's configurations.
2930
*/
3031
const defaultLocale = 'en-US';
32+
/**
33+
* NOTE: This is not a random/ magic date selected for the testing. It's been selected for a reason
34+
* which has explained in detail at https://github.com/motss/app-datepicker/issues/128.
35+
*/
36+
const date13 = '2020-01-13';
37+
const date15 = '2020-01-15';
3138

3239
describe('app-datepicker', () => {
3340
describe('initial render (calendar view)', () => {
@@ -200,8 +207,8 @@ describe('app-datepicker', () => {
200207
});
201208

202209
it(`renders with correct 'min'`, async () => {
203-
const minVal = '2020-01-03';
204-
const valueVal = '2020-01-05';
210+
const minVal = date13;
211+
const valueVal = date15;
205212

206213
el.min = minVal;
207214
el.value = valueVal;
@@ -210,15 +217,15 @@ describe('app-datepicker', () => {
210217
const firstSelectableDate =
211218
shadowQuery(
212219
el,
213-
'.calendar-container:nth-child(2) .full-calendar__day[aria-label="Jan 3, 2020"]');
220+
'.calendar-container:nth-of-type(2) .full-calendar__day[aria-label="Jan 13, 2020"]');
214221
const allDisabledDates =
215222
shadowQueryAll(
216223
el,
217-
'.calendar-container:nth-child(2) .full-calendar__day.day--disabled');
224+
'.calendar-container:nth-of-type(2) .full-calendar__day.day--disabled');
218225
const focusedDate =
219226
shadowQuery(
220227
el,
221-
'.calendar-container:nth-child(2) .full-calendar__day.day--focused');
228+
'.calendar-container:nth-of-type(2) .full-calendar__day.day--focused');
222229
const lastDayBeforeMinDate = allDisabledDates[allDisabledDates.length - 1];
223230

224231
isNotNull(firstSelectableDate, 'First selectable date not found');
@@ -230,11 +237,11 @@ describe('app-datepicker', () => {
230237
'First selectable is disabled day');
231238
strictEqual(
232239
lastDayBeforeMinDate.getAttribute('aria-label'),
233-
'Jan 2, 2020',
240+
'Jan 12, 2020',
234241
`Last day before 'min' not matched`);
235242
strictEqual(
236243
focusedDate.getAttribute('aria-label'),
237-
'Jan 5, 2020',
244+
'Jan 15, 2020',
238245
'Focused date not matched');
239246

240247
strictEqual(el.min, minVal, `'min' property not matched`);
@@ -245,8 +252,8 @@ describe('app-datepicker', () => {
245252
});
246253

247254
it(`renders with correct 'max'`, async () => {
248-
const maxVal = '2020-01-05';
249-
const valueVal = '2020-01-03';
255+
const maxVal = date15;
256+
const valueVal = date13;
250257

251258
el.max = maxVal;
252259
el.value = valueVal;
@@ -255,15 +262,15 @@ describe('app-datepicker', () => {
255262
const lastSelectableDate =
256263
shadowQuery(
257264
el,
258-
'.calendar-container:nth-child(2) .full-calendar__day[aria-label="Jan 5, 2020"]');
265+
'.calendar-container:nth-of-type(2) .full-calendar__day[aria-label="Jan 15, 2020"]');
259266
const firstDayAfterMaxDate =
260267
shadowQuery(
261268
el,
262-
'.calendar-container:nth-child(2) .full-calendar__day.day--disabled');
269+
'.calendar-container:nth-of-type(2) .full-calendar__day.day--disabled');
263270
const focusedDate =
264271
shadowQuery(
265272
el,
266-
'.calendar-container:nth-child(2) .full-calendar__day.day--focused');
273+
'.calendar-container:nth-of-type(2) .full-calendar__day.day--focused');
267274

268275
isNotNull(lastSelectableDate, 'Last selectable date not found');
269276
isNotNull(firstDayAfterMaxDate, `Last day before 'min' not found`);
@@ -274,11 +281,11 @@ describe('app-datepicker', () => {
274281
'Last selectable is disabled day');
275282
strictEqual(
276283
firstDayAfterMaxDate.getAttribute('aria-label'),
277-
'Jan 6, 2020',
284+
'Jan 16, 2020',
278285
`First day after 'max' not matched`);
279286
strictEqual(
280287
focusedDate.getAttribute('aria-label'),
281-
'Jan 3, 2020',
288+
'Jan 13, 2020',
282289
'Focused date not matched');
283290

284291
strictEqual(el.max, maxVal, `'max' property not matched`);
@@ -296,10 +303,10 @@ describe('app-datepicker', () => {
296303
toFormattedDateString(todayDate),
297304
`'value' does not match with today's date`);
298305

299-
const val = '2020-01-03';
306+
const val = date15;
300307

301308
/** NOTE: To ensure 'min' is lesser than 'val' */
302-
el.min = '2020-01-01';
309+
el.min = date13;
303310
el.value = val;
304311
await el.updateComplete;
305312

@@ -328,8 +335,8 @@ describe('app-datepicker', () => {
328335
strictEqual(el.firstDayOfWeek, 0, `'firstDayOfWeek' not matched`);
329336

330337
/** NOTE: Ensure dates are not disabled during testings */
331-
el.min = '2020-01-03';
332-
el.value = '2020-01-05';
338+
el.min = date13;
339+
el.value = date15;
333340
await el.updateComplete;
334341

335342
const expectedFirstDayInMonthIdx = [
@@ -350,7 +357,7 @@ describe('app-datepicker', () => {
350357
await el.updateComplete;
351358

352359
const fullCalendarDays =
353-
shadowQueryAll(el, '.calendar-container:nth-child(2) .full-calendar__day');
360+
shadowQueryAll(el, '.calendar-container:nth-of-type(2) .full-calendar__day');
354361
const firstDayInMonthIdx =
355362
fullCalendarDays.findIndex(n => !n.classList.contains('day--empty'));
356363

@@ -382,8 +389,8 @@ describe('app-datepicker', () => {
382389
});
383390

384391
it(`renders with correct 'weekNumberType'`, async () => {
385-
el.min = '2020-01-03';
386-
el.value = '2020-01-05';
392+
el.min = date13;
393+
el.value = date15;
387394
el.showWeekNumber = true;
388395
await el.updateComplete;
389396

@@ -406,7 +413,7 @@ describe('app-datepicker', () => {
406413
await el.updateComplete;
407414

408415
const firstWeekdayLabel =
409-
getShadowInnerHTML(shadowQuery(el, '.calendar-container:nth-child(2) .weekday-label'));
416+
getShadowInnerHTML(shadowQuery(el, '.calendar-container:nth-of-type(2) .weekday-label'));
410417

411418
strictEqual(
412419
el.weekNumberType,
@@ -419,6 +426,23 @@ describe('app-datepicker', () => {
419426
}
420427
});
421428

429+
it(`renders with correct 'landscape'`, async () => {
430+
strictEqual(el.landscape, false, `'landscape' not matched`);
431+
strictEqual(
432+
getComputedStylePropertyValue(el, 'display'),
433+
'block',
434+
`Element has no 'display: block'`);
435+
436+
el.landscape = true;
437+
await el.updateComplete;
438+
439+
isTrue(el.hasAttribute('landscape'), `Element has no 'landscape' attribute`);
440+
strictEqual(
441+
getComputedStylePropertyValue(el, 'display'),
442+
'flex',
443+
`Element has no 'display: flex`);
444+
});
445+
422446
});
423447

424448
// describe('updates via attributes', () => {});

src/test/test-helpers.ts

+4
Original file line numberDiff line numberDiff line change
@@ -48,3 +48,7 @@ export const getShadowInnerHTML = (target: Element | HTMLElement) => {
4848
export const getOuterHTML =
4949
(target: Element | HTMLElement) =>
5050
target && target.outerHTML && stripExpressionDelimiters(target.outerHTML!);
51+
52+
export const getComputedStylePropertyValue =
53+
(target: Element | HTMLElement, property: string) =>
54+
window.getComputedStyle && window.getComputedStyle(target)[property];

0 commit comments

Comments
 (0)