Files
shaka-player/test/ui/ui_customization_unit.js
T
Jacob Trimble 702dc360e0 Fix destroying UI in some tests.
These tests were creating two UI instances in the same container.  This
caused the second one to replace the first without destroying the first.
This caused test contamination since there could be extra CastProxy
instances.  This wouldn't always happen since the no-longer-referenced
objects would be garbage-collected eventually; but depending on timing,
the CastSender tests might fail.

Change-Id: I7f4a008f56224ee33bee15c5e0370a225a5fc033
2020-02-14 23:11:15 +00:00

207 lines
6.9 KiB
JavaScript

/** @license
* Copyright 2016 Google LLC
* SPDX-License-Identifier: Apache-2.0
*/
describe('UI Customization', () => {
const UiUtils = shaka.test.UiUtils;
/** @type {!Element} */
let cssLink;
/** @type {!HTMLElement} */
let container;
/** @type {!HTMLMediaElement} */
let video;
beforeAll(async () => {
// Add css file
cssLink = document.createElement('link');
await UiUtils.setupCSS(cssLink);
});
afterEach(async () => {
await UiUtils.cleanupUI();
});
afterAll(() => {
document.head.removeChild(cssLink);
});
beforeEach(() => {
container =
/** @type {!HTMLElement} */ (document.createElement('div'));
document.body.appendChild(container);
video = shaka.test.UiUtils.createVideoElement();
container.appendChild(video);
});
it('only the specified controls are created', () => {
const config = {controlPanelElements: ['time_and_duration', 'mute']};
UiUtils.createUIThroughAPI(container, video, config);
// Only current time and mute button should've been created
UiUtils.confirmElementFound(container, 'shaka-current-time');
UiUtils.confirmElementFound(container, 'shaka-mute-button');
UiUtils.confirmElementMissing(container, 'shaka-volume-bar');
UiUtils.confirmElementMissing(container, 'shaka-fullscreen-button');
UiUtils.confirmElementMissing(container, 'shaka-overflow-menu-button');
});
it('only the specified overflow menu buttons are created', () => {
const config = {overflowMenuButtons: ['cast']};
UiUtils.createUIThroughAPI(container, video, config);
UiUtils.confirmElementFound(container, 'shaka-cast-button');
UiUtils.confirmElementMissing(container, 'shaka-caption-button');
});
it('seek bar only created when configured', async () => {
const ui =
UiUtils.createUIThroughAPI(container, video, {addSeekBar: false});
UiUtils.confirmElementMissing(container, 'shaka-seek-bar');
await ui.destroy();
UiUtils.createUIThroughAPI(container, video, {addSeekBar: true});
UiUtils.confirmElementFound(container, 'shaka-seek-bar');
});
it('big play button only created when configured', async () => {
const ui =
UiUtils.createUIThroughAPI(container, video, {addBigPlayButton: false});
UiUtils.confirmElementMissing(container, 'shaka-play-button-container');
UiUtils.confirmElementMissing(container, 'shaka-play-button');
await ui.destroy();
UiUtils.createUIThroughAPI(container, video, {addBigPlayButton: true});
UiUtils.confirmElementFound(container, 'shaka-play-button-container');
UiUtils.confirmElementFound(container, 'shaka-play-button');
});
it('settings menus are positioned lower when seek bar is absent', () => {
const config = {addSeekBar: false};
UiUtils.createUIThroughAPI(container, video, config);
function confirmLowPosition(className) {
const elements =
container.getElementsByClassName(className);
expect(elements.length).toBe(1);
expect(
elements[0].classList.contains('shaka-low-position')).toBe(true);
}
UiUtils.confirmElementMissing(container, 'shaka-seek-bar');
confirmLowPosition('shaka-overflow-menu');
confirmLowPosition('shaka-resolutions');
confirmLowPosition('shaka-audio-languages');
confirmLowPosition('shaka-text-languages');
confirmLowPosition('shaka-playback-rates');
});
it('controls are created in specified order', () => {
const config = {
controlPanelElements: [
'mute',
'time_and_duration',
'fullscreen',
],
};
UiUtils.createUIThroughAPI(container, video, config);
const controlsButtonPanels =
container.getElementsByClassName('shaka-controls-button-panel');
expect(controlsButtonPanels.length).toBe(1);
const controlsButtonPanel =
/** @type {!HTMLElement} */ (controlsButtonPanels[0]);
const buttons = controlsButtonPanel.childNodes;
expect(buttons.length).toBe(3);
expect( /** @type {!HTMLElement} */ (buttons[0]).className)
.toContain('shaka-mute-button');
expect( /** @type {!HTMLElement} */ (buttons[1]).className)
.toContain('shaka-current-time');
expect( /** @type {!HTMLElement} */ (buttons[2]).className)
.toContain('shaka-fullscreen');
});
it('layout can be re-configured after the creation', async () => {
const config = {controlPanelElements: ['time_and_duration', 'mute']};
const ui = UiUtils.createUIThroughAPI(container, video, config);
// Only current time and mute button should've been created
UiUtils.confirmElementFound(container, 'shaka-current-time');
UiUtils.confirmElementFound(container, 'shaka-mute-button');
UiUtils.confirmElementFound(container, 'shaka-seek-bar');
UiUtils.confirmElementMissing(container, 'shaka-volume-bar');
UiUtils.confirmElementMissing(container, 'shaka-fullscreen-button');
UiUtils.confirmElementMissing(container, 'shaka-overflow-menu-button');
// Reconfigure the layout
const newConfig = {
controlPanelElements: [
'volume',
'fullscreen',
],
addSeekBar: false,
};
const eventManager = new shaka.util.EventManager();
const waiter = new shaka.test.Waiter(eventManager);
const controls = ui.getControls();
goog.asserts.assert(controls != null, 'Should have a controls object!');
const p = waiter.waitForEvent(controls, 'uiupdated');
ui.configure(newConfig);
// Wait for the change to take effect
await p;
// New elements should be there
UiUtils.confirmElementFound(container, 'shaka-volume-bar');
UiUtils.confirmElementFound(container, 'shaka-fullscreen-button');
// Old elements should not be there
UiUtils.confirmElementMissing(container, 'shaka-current-time');
UiUtils.confirmElementMissing(container, 'shaka-mute-button');
UiUtils.confirmElementMissing(container, 'shaka-seek-bar');
});
// Regression for #1948
it('cast proxy and controls are unchanged by reconfiguration', async () => {
const config = {controlPanelElements: ['time_and_duration', 'mute']};
/** @type {!shaka.ui.Overlay} */
const ui = UiUtils.createUIThroughAPI(container, video, config);
const eventManager = new shaka.util.EventManager();
const waiter = new shaka.test.Waiter(eventManager);
// Save controls and cast proxy objects
const controls = ui.getControls();
const castProxy = controls.getCastProxy();
goog.asserts.assert(controls != null, 'Should have a controls object!');
const p = waiter.waitForEvent(controls, 'uiupdated');
const newConfig = {controlPanelElements: ['volume']};
ui.configure(newConfig);
// Wait for the change to take effect
// The fact that this resolves is implicit proof that the controls
// object stayed the same, but we check it again below to be explicit.
await p;
const newControls = ui.getControls();
const newCastProxy = newControls.getCastProxy();
expect(newControls).toBe(controls);
expect(newCastProxy).toBe(castProxy);
});
});