1
0
Fork 0
mirror of https://github.com/jellyfin/jellyfin-web synced 2025-03-30 19:56:21 +00:00
jellyfin-web/src/components/homesections/homesections.js

752 lines
28 KiB
JavaScript
Raw Normal View History

2022-01-30 00:27:26 +03:00
import escapeHtml from 'escape-html';
2020-08-14 08:46:34 +02:00
import cardBuilder from '../cardbuilder/cardBuilder';
import layoutManager from '../layoutManager';
import imageLoader from '../images/imageLoader';
import globalize from '../../scripts/globalize';
2023-05-01 10:04:13 -04:00
import { appRouter } from '../router/appRouter';
2020-08-14 08:46:34 +02:00
import imageHelper from '../../scripts/imagehelper';
import '../../elements/emby-button/paper-icon-button-light';
import '../../elements/emby-itemscontainer/emby-itemscontainer';
import '../../elements/emby-scroller/emby-scroller';
import '../../elements/emby-button/emby-button';
2021-01-26 16:25:38 -05:00
import './homesections.scss';
2022-04-10 02:22:13 -04:00
import Dashboard from '../../utils/dashboard';
import ServerConnections from '../ServerConnections';
2023-04-19 01:56:05 -04:00
export function getDefaultSection(index) {
switch (index) {
case 0:
return 'smalllibrarytiles';
case 1:
return 'resume';
case 2:
return 'resumeaudio';
case 3:
return 'resumebook';
case 4:
return 'livetv';
case 5:
return 'nextup';
case 6:
return 'latestmedia';
case 7:
return 'none';
default:
return '';
}
}
function getAllSectionsToShow(userSettings, sectionCount) {
const sections = [];
for (let i = 0, length = sectionCount; i < length; i++) {
let section = userSettings.get('homesection' + i) || getDefaultSection(i);
if (section === 'folders') {
section = getDefaultSection(0);
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
sections.push(section);
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
return sections;
}
export function loadSections(elem, apiClient, user, userSettings) {
return getUserViews(apiClient, user.Id).then(function (userViews) {
let html = '';
if (userViews.length) {
const sectionCount = 7;
for (let i = 0; i < sectionCount; i++) {
html += '<div class="verticalSection section' + i + '"></div>';
}
2023-04-19 01:56:05 -04:00
elem.innerHTML = html;
elem.classList.add('homeSectionsContainer');
2023-04-19 01:56:05 -04:00
const promises = [];
const sections = getAllSectionsToShow(userSettings, sectionCount);
for (let i = 0; i < sections.length; i++) {
promises.push(loadSection(elem, apiClient, user, userSettings, userViews, sections, i));
}
2018-10-23 01:05:09 +03:00
return Promise.all(promises)
// Timeout for polyfilled CustomElements (webOS 1.2)
.then(() => new Promise((resolve) => setTimeout(resolve, 0)))
.then(() => {
return resume(elem, {
refresh: true
});
});
2023-04-19 01:56:05 -04:00
} else {
let noLibDescription;
2023-07-06 13:39:48 -04:00
if (user.Policy?.IsAdministrator) {
2023-04-19 01:56:05 -04:00
noLibDescription = globalize.translate('NoCreatedLibraries', '<br><a id="button-createLibrary" class="button-link">', '</a>');
} else {
2023-04-19 01:56:05 -04:00
noLibDescription = globalize.translate('AskAdminToCreateLibrary');
}
2023-04-19 01:56:05 -04:00
html += '<div class="centerMessage padded-left padded-right">';
html += '<h2>' + globalize.translate('MessageNothingHere') + '</h2>';
html += '<p>' + noLibDescription + '</p>';
html += '</div>';
elem.innerHTML = html;
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
const createNowLink = elem.querySelector('#button-createLibrary');
if (createNowLink) {
createNowLink.addEventListener('click', function () {
Dashboard.navigate('library.html');
});
}
}
2023-04-19 01:56:05 -04:00
});
}
export function destroySections(elem) {
const elems = elem.querySelectorAll('.itemsContainer');
for (const e of elems) {
e.fetchData = null;
e.parentContainer = null;
e.getItemsHtml = null;
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
elem.innerHTML = '';
}
2023-04-19 01:56:05 -04:00
export function pause(elem) {
const elems = elem.querySelectorAll('.itemsContainer');
for (const e of elems) {
e.pause();
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
}
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
export function resume(elem, options) {
const elems = elem.querySelectorAll('.itemsContainer');
const promises = [];
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
for (let i = 0, length = elems.length; i < length; i++) {
promises.push(elems[i].resume(options));
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
return Promise.all(promises);
}
function loadSection(page, apiClient, user, userSettings, userViews, allSections, index) {
const section = allSections[index];
const elem = page.querySelector('.section' + index);
if (section === 'latestmedia') {
loadRecentlyAdded(elem, apiClient, user, userViews);
} else if (section === 'librarytiles' || section === 'smalllibrarytiles' || section === 'smalllibrarytiles-automobile' || section === 'librarytiles-automobile') {
loadLibraryTiles(elem, apiClient, user, userSettings, 'smallBackdrop', userViews);
} else if (section === 'librarybuttons') {
loadlibraryButtons(elem, apiClient, user, userSettings, userViews);
} else if (section === 'resume') {
return loadResume(elem, apiClient, 'HeaderContinueWatching', 'Video', userSettings);
} else if (section === 'resumeaudio') {
return loadResume(elem, apiClient, 'HeaderContinueListening', 'Audio', userSettings);
} else if (section === 'activerecordings') {
loadLatestLiveTvRecordings(elem, true, apiClient);
} else if (section === 'nextup') {
loadNextUp(elem, apiClient, userSettings);
} else if (section === 'onnow' || section === 'livetv') {
return loadOnNow(elem, apiClient, user);
} else if (section === 'resumebook') {
return loadResume(elem, apiClient, 'HeaderContinueReading', 'Book', userSettings);
} else {
elem.innerHTML = '';
return Promise.resolve();
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
return Promise.resolve();
}
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
function getUserViews(apiClient, userId) {
return apiClient.getUserViews({}, userId || apiClient.getCurrentUserId()).then(function (result) {
return result.Items;
});
}
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
function enableScrollX() {
return true;
}
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
function getSquareShape() {
return enableScrollX() ? 'overflowSquare' : 'square';
}
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
function getThumbShape() {
return enableScrollX() ? 'overflowBackdrop' : 'backdrop';
}
2023-04-19 01:56:05 -04:00
function getPortraitShape() {
return enableScrollX() ? 'overflowPortrait' : 'portrait';
}
2023-04-19 01:56:05 -04:00
function getLibraryButtonsHtml(items) {
let html = '';
2023-04-19 01:56:05 -04:00
html += '<div class="verticalSection verticalSection-extrabottompadding">';
html += '<h2 class="sectionTitle sectionTitle-cards padded-left">' + globalize.translate('HeaderMyMedia') + '</h2>';
2023-04-19 01:56:05 -04:00
html += '<div is="emby-itemscontainer" class="itemsContainer padded-left padded-right vertical-wrap focuscontainer-x" data-multiselect="false">';
2023-04-19 01:56:05 -04:00
// library card background images
for (let i = 0, length = items.length; i < length; i++) {
const item = items[i];
const icon = imageHelper.getLibraryIcon(item.CollectionType);
html += '<a is="emby-linkbutton" href="' + appRouter.getRouteUrl(item) + '" class="raised homeLibraryButton"><span class="material-icons homeLibraryIcon ' + icon + '" aria-hidden="true"></span><span class="homeLibraryText">' + escapeHtml(item.Name) + '</span></a>';
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
html += '</div>';
html += '</div>';
2023-04-19 01:56:05 -04:00
return html;
}
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
function loadlibraryButtons(elem, apiClient, user, userSettings, userViews) {
elem.classList.remove('verticalSection');
const html = getLibraryButtonsHtml(userViews);
2023-04-19 01:56:05 -04:00
elem.innerHTML = html;
imageLoader.lazyChildren(elem);
}
2023-04-19 01:56:05 -04:00
function getFetchLatestItemsFn(serverId, parentId, collectionType) {
return function () {
const apiClient = ServerConnections.getApiClient(serverId);
let limit = 16;
2023-04-19 01:56:05 -04:00
if (enableScrollX()) {
if (collectionType === 'music') {
limit = 30;
}
2023-09-12 17:02:06 -04:00
} else if (collectionType === 'tvshows') {
limit = 5;
} else if (collectionType === 'music') {
limit = 9;
2023-04-19 01:56:05 -04:00
} else {
2023-09-12 17:02:06 -04:00
limit = 8;
2023-04-19 01:56:05 -04:00
}
2023-04-19 01:56:05 -04:00
const options = {
Limit: limit,
Fields: 'PrimaryImageAspectRatio,BasicSyncInfo,Path',
ImageTypeLimit: 1,
EnableImageTypes: 'Primary,Backdrop,Thumb',
ParentId: parentId
};
2023-04-19 01:56:05 -04:00
return apiClient.getLatestItems(options);
};
}
function getLatestItemsHtmlFn(itemType, viewType) {
return function (items) {
const cardLayout = false;
let shape;
if (itemType === 'Channel' || viewType === 'movies' || viewType === 'books' || viewType === 'tvshows') {
shape = getPortraitShape();
} else if (viewType === 'music' || viewType === 'homevideos') {
shape = getSquareShape();
} else {
2023-04-19 01:56:05 -04:00
shape = getThumbShape();
}
2023-04-19 01:56:05 -04:00
return cardBuilder.getCardsHtml({
items: items,
shape: shape,
preferThumb: viewType !== 'movies' && viewType !== 'tvshows' && itemType !== 'Channel' && viewType !== 'music' ? 'auto' : null,
showUnplayedIndicator: false,
showChildCountIndicator: true,
context: 'home',
overlayText: false,
centerText: !cardLayout,
overlayPlayButton: viewType !== 'photos',
allowBottomPadding: !enableScrollX() && !cardLayout,
cardLayout: cardLayout,
showTitle: viewType !== 'photos',
showYear: viewType === 'movies' || viewType === 'tvshows' || !viewType,
showParentTitle: viewType === 'music' || viewType === 'tvshows' || !viewType || (cardLayout && (viewType === 'tvshows')),
lines: 2
});
};
}
function renderLatestSection(elem, apiClient, user, parent) {
let html = '';
html += '<div class="sectionTitleContainer sectionTitleContainer-cards padded-left">';
if (!layoutManager.tv) {
html += '<a is="emby-linkbutton" href="' + appRouter.getRouteUrl(parent, {
section: 'latest'
}) + '" class="more button-flat button-flat-mini sectionTitleTextButton">';
html += '<h2 class="sectionTitle sectionTitle-cards">';
html += globalize.translate('LatestFromLibrary', escapeHtml(parent.Name));
html += '</h2>';
html += '<span class="material-icons chevron_right" aria-hidden="true"></span>';
html += '</a>';
} else {
html += '<h2 class="sectionTitle sectionTitle-cards">' + globalize.translate('LatestFromLibrary', escapeHtml(parent.Name)) + '</h2>';
}
html += '</div>';
2023-04-19 01:56:05 -04:00
if (enableScrollX()) {
html += '<div is="emby-scroller" class="padded-top-focusscale padded-bottom-focusscale" data-centerfocus="true">';
html += '<div is="emby-itemscontainer" class="itemsContainer scrollSlider focuscontainer-x">';
} else {
html += '<div is="emby-itemscontainer" class="itemsContainer focuscontainer-x padded-left padded-right vertical-wrap">';
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
if (enableScrollX()) {
html += '</div>';
}
html += '</div>';
2023-04-19 01:56:05 -04:00
elem.innerHTML = html;
2023-04-19 01:56:05 -04:00
const itemsContainer = elem.querySelector('.itemsContainer');
itemsContainer.fetchData = getFetchLatestItemsFn(apiClient.serverId(), parent.Id, parent.CollectionType);
itemsContainer.getItemsHtml = getLatestItemsHtmlFn(parent.Type, parent.CollectionType);
itemsContainer.parentContainer = elem;
}
2023-04-19 01:56:05 -04:00
function loadRecentlyAdded(elem, apiClient, user, userViews) {
elem.classList.remove('verticalSection');
const excludeViewTypes = ['playlists', 'livetv', 'boxsets', 'channels'];
2023-04-19 01:56:05 -04:00
for (let i = 0, length = userViews.length; i < length; i++) {
const item = userViews[i];
if (user.Configuration.LatestItemsExcludes.indexOf(item.Id) !== -1) {
continue;
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
if (excludeViewTypes.indexOf(item.CollectionType || []) !== -1) {
continue;
}
2023-04-19 01:56:05 -04:00
const frag = document.createElement('div');
frag.classList.add('verticalSection');
frag.classList.add('hide');
elem.appendChild(frag);
2023-04-19 01:56:05 -04:00
renderLatestSection(frag, apiClient, user, item);
}
}
2021-04-28 20:37:37 -04:00
2023-04-19 01:56:05 -04:00
export function loadLibraryTiles(elem, apiClient, user, userSettings, shape, userViews) {
let html = '';
if (userViews.length) {
html += '<h2 class="sectionTitle sectionTitle-cards padded-left">' + globalize.translate('HeaderMyMedia') + '</h2>';
if (enableScrollX()) {
html += '<div is="emby-scroller" class="padded-top-focusscale padded-bottom-focusscale" data-centerfocus="true">';
2023-04-19 01:56:05 -04:00
html += '<div is="emby-itemscontainer" class="itemsContainer scrollSlider focuscontainer-x">';
} else {
2023-04-19 01:56:05 -04:00
html += '<div is="emby-itemscontainer" class="itemsContainer padded-left padded-right focuscontainer-x vertical-wrap">';
}
2023-04-19 01:56:05 -04:00
html += cardBuilder.getCardsHtml({
items: userViews,
shape: getThumbShape(),
showTitle: true,
centerText: true,
overlayText: false,
lazy: true,
transition: false,
allowBottomPadding: !enableScrollX()
});
if (enableScrollX()) {
html += '</div>';
}
html += '</div>';
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
elem.innerHTML = html;
imageLoader.lazyChildren(elem);
}
2023-04-19 01:56:05 -04:00
const dataMonitorHints = {
'Audio': 'audioplayback,markplayed',
'Video': 'videoplayback,markplayed'
};
2023-04-19 01:56:05 -04:00
function loadResume(elem, apiClient, headerText, mediaType, userSettings) {
let html = '';
2023-04-19 01:56:05 -04:00
const dataMonitor = dataMonitorHints[mediaType] || 'markplayed';
html += '<h2 class="sectionTitle sectionTitle-cards padded-left">' + globalize.translate(headerText) + '</h2>';
if (enableScrollX()) {
html += '<div is="emby-scroller" class="padded-top-focusscale padded-bottom-focusscale" data-centerfocus="true">';
html += `<div is="emby-itemscontainer" class="itemsContainer scrollSlider focuscontainer-x" data-monitor="${dataMonitor}">`;
} else {
html += `<div is="emby-itemscontainer" class="itemsContainer padded-left padded-right vertical-wrap focuscontainer-x" data-monitor="${dataMonitor}">`;
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
if (enableScrollX()) {
html += '</div>';
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
html += '</div>';
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
elem.classList.add('hide');
elem.innerHTML = html;
const itemsContainer = elem.querySelector('.itemsContainer');
itemsContainer.fetchData = getItemsToResumeFn(mediaType, apiClient.serverId());
itemsContainer.getItemsHtml = getItemsToResumeHtmlFn(userSettings.useEpisodeImagesInNextUpAndResume(), mediaType);
itemsContainer.parentContainer = elem;
}
function getItemsToResumeFn(mediaType, serverId) {
return function () {
const apiClient = ServerConnections.getApiClient(serverId);
const limit = enableScrollX() ? 12 : 5;
const options = {
Limit: limit,
Recursive: true,
Fields: 'PrimaryImageAspectRatio,BasicSyncInfo',
ImageTypeLimit: 1,
EnableImageTypes: 'Primary,Backdrop,Thumb',
EnableTotalRecordCount: false,
MediaTypes: mediaType
};
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
return apiClient.getResumableItems(apiClient.getCurrentUserId(), options);
};
}
function getItemsToResumeHtmlFn(useEpisodeImages, mediaType) {
return function (items) {
const cardLayout = false;
2018-10-23 01:05:09 +03:00
return cardBuilder.getCardsHtml({
items: items,
2023-04-19 01:56:05 -04:00
preferThumb: true,
inheritThumb: !useEpisodeImages,
shape: (mediaType === 'Book') ? getPortraitShape() : getThumbShape(),
overlayText: false,
2023-04-19 01:56:05 -04:00
showTitle: true,
showParentTitle: true,
lazy: true,
showDetailsMenu: true,
overlayPlayButton: true,
context: 'home',
centerText: !cardLayout,
allowBottomPadding: false,
cardLayout: cardLayout,
showYear: true,
lines: 2
});
2023-04-19 01:56:05 -04:00
};
}
2023-04-19 01:56:05 -04:00
function getOnNowFetchFn(serverId) {
return function () {
const apiClient = ServerConnections.getApiClient(serverId);
return apiClient.getLiveTvRecommendedPrograms({
2018-10-23 01:05:09 +03:00
userId: apiClient.getCurrentUserId(),
IsAiring: true,
2023-04-19 01:56:05 -04:00
limit: 24,
2018-10-23 01:05:09 +03:00
ImageTypeLimit: 1,
2020-05-04 12:44:12 +02:00
EnableImageTypes: 'Primary,Thumb,Backdrop',
EnableTotalRecordCount: false,
2020-05-04 12:44:12 +02:00
Fields: 'ChannelInfo,PrimaryImageAspectRatio'
2023-04-19 01:56:05 -04:00
});
};
}
function getOnNowItemsHtml(items) {
return cardBuilder.getCardsHtml({
items: items,
preferThumb: 'auto',
inheritThumb: false,
shape: (enableScrollX() ? 'autooverflow' : 'auto'),
showParentTitleOrTitle: true,
showTitle: true,
centerText: true,
coverImage: true,
overlayText: false,
allowBottomPadding: !enableScrollX(),
showAirTime: true,
showChannelName: false,
showAirDateTime: false,
showAirEndTime: true,
defaultShape: getThumbShape(),
lines: 3,
overlayPlayButton: true
});
}
function loadOnNow(elem, apiClient, user) {
if (!user.Policy.EnableLiveTvAccess) {
return Promise.resolve();
}
2023-04-19 01:56:05 -04:00
return apiClient.getLiveTvRecommendedPrograms({
userId: apiClient.getCurrentUserId(),
IsAiring: true,
limit: 1,
ImageTypeLimit: 1,
EnableImageTypes: 'Primary,Thumb,Backdrop',
EnableTotalRecordCount: false,
Fields: 'ChannelInfo,PrimaryImageAspectRatio'
}).then(function (result) {
let html = '';
if (result.Items.length) {
elem.classList.remove('padded-left');
elem.classList.remove('padded-right');
elem.classList.remove('padded-bottom');
elem.classList.remove('verticalSection');
html += '<div class="verticalSection">';
html += '<div class="sectionTitleContainer sectionTitleContainer-cards padded-left">';
html += '<h2 class="sectionTitle sectionTitle-cards">' + globalize.translate('LiveTV') + '</h2>';
html += '</div>';
2023-04-19 01:56:05 -04:00
if (enableScrollX()) {
html += '<div is="emby-scroller" class="padded-top-focusscale padded-bottom-focusscale" data-centerfocus="true" data-scrollbuttons="false">';
html += '<div class="padded-top padded-bottom scrollSlider focuscontainer-x">';
} else {
html += '<div class="padded-top padded-bottom focuscontainer-x">';
}
2023-04-19 01:56:05 -04:00
html += '<a is="emby-linkbutton" href="' + appRouter.getRouteUrl('livetv', {
serverId: apiClient.serverId(),
section: 'programs'
}) + '" class="raised"><span>' + globalize.translate('Programs') + '</span></a>';
2023-04-19 01:56:05 -04:00
html += '<a is="emby-linkbutton" href="' + appRouter.getRouteUrl('livetv', {
serverId: apiClient.serverId(),
section: 'guide'
}) + '" class="raised"><span>' + globalize.translate('Guide') + '</span></a>';
2022-01-13 10:15:24 -05:00
2023-04-19 01:56:05 -04:00
html += '<a is="emby-linkbutton" href="' + appRouter.getRouteUrl('livetv', {
serverId: apiClient.serverId(),
section: 'channels'
}) + '" class="raised"><span>' + globalize.translate('Channels') + '</span></a>';
2023-04-19 01:56:05 -04:00
html += '<a is="emby-linkbutton" href="' + appRouter.getRouteUrl('recordedtv', {
serverId: apiClient.serverId()
}) + '" class="raised"><span>' + globalize.translate('Recordings') + '</span></a>';
2023-04-19 01:56:05 -04:00
html += '<a is="emby-linkbutton" href="' + appRouter.getRouteUrl('livetv', {
serverId: apiClient.serverId(),
section: 'dvrschedule'
}) + '" class="raised"><span>' + globalize.translate('Schedule') + '</span></a>';
2023-04-19 01:56:05 -04:00
html += '<a is="emby-linkbutton" href="' + appRouter.getRouteUrl('livetv', {
serverId: apiClient.serverId(),
section: 'seriesrecording'
}) + '" class="raised"><span>' + globalize.translate('Series') + '</span></a>';
2023-04-19 01:56:05 -04:00
html += '</div>';
if (enableScrollX()) {
html += '</div>';
2023-04-19 01:56:05 -04:00
}
html += '</div>';
html += '</div>';
2023-04-19 01:56:05 -04:00
html += '<div class="verticalSection">';
html += '<div class="sectionTitleContainer sectionTitleContainer-cards padded-left">';
2023-04-19 01:56:05 -04:00
if (!layoutManager.tv) {
html += '<a is="emby-linkbutton" href="' + appRouter.getRouteUrl('livetv', {
serverId: apiClient.serverId(),
section: 'onnow'
}) + '" class="more button-flat button-flat-mini sectionTitleTextButton">';
html += '<h2 class="sectionTitle sectionTitle-cards">';
html += globalize.translate('HeaderOnNow');
html += '</h2>';
html += '<span class="material-icons chevron_right" aria-hidden="true"></span>';
html += '</a>';
} else {
html += '<h2 class="sectionTitle sectionTitle-cards">' + globalize.translate('HeaderOnNow') + '</h2>';
}
html += '</div>';
2023-04-19 01:56:05 -04:00
if (enableScrollX()) {
html += '<div is="emby-scroller" class="padded-top-focusscale padded-bottom-focusscale" data-centerfocus="true">';
html += '<div is="emby-itemscontainer" class="itemsContainer scrollSlider focuscontainer-x">';
} else {
html += '<div is="emby-itemscontainer" class="itemsContainer padded-left padded-right vertical-wrap focuscontainer-x">';
}
if (enableScrollX()) {
html += '</div>';
2023-04-19 01:56:05 -04:00
}
2023-04-19 01:56:05 -04:00
html += '</div>';
html += '</div>';
2023-04-19 01:56:05 -04:00
elem.innerHTML = html;
const itemsContainer = elem.querySelector('.itemsContainer');
itemsContainer.parentContainer = elem;
itemsContainer.fetchData = getOnNowFetchFn(apiClient.serverId());
itemsContainer.getItemsHtml = getOnNowItemsHtml;
}
});
}
function getNextUpFetchFn(serverId, userSettings) {
return function () {
const apiClient = ServerConnections.getApiClient(serverId);
const oldestDateForNextUp = new Date();
oldestDateForNextUp.setDate(oldestDateForNextUp.getDate() - userSettings.maxDaysForNextUp());
return apiClient.getNextUpEpisodes({
Limit: enableScrollX() ? 24 : 15,
Fields: 'PrimaryImageAspectRatio,DateCreated,BasicSyncInfo,Path,MediaSourceCount',
UserId: apiClient.getCurrentUserId(),
ImageTypeLimit: 1,
EnableImageTypes: 'Primary,Backdrop,Banner,Thumb',
EnableTotalRecordCount: false,
DisableFirstEpisode: false,
NextUpDateCutoff: oldestDateForNextUp.toISOString(),
EnableRewatching: userSettings.enableRewatchingInNextUp()
});
2023-04-19 01:56:05 -04:00
};
}
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
function getNextUpItemsHtmlFn(useEpisodeImages) {
return function (items) {
const cardLayout = false;
return cardBuilder.getCardsHtml({
items: items,
preferThumb: true,
inheritThumb: !useEpisodeImages,
shape: getThumbShape(),
overlayText: false,
showTitle: true,
showParentTitle: true,
lazy: true,
overlayPlayButton: true,
context: 'home',
centerText: !cardLayout,
allowBottomPadding: !enableScrollX(),
cardLayout: cardLayout
});
};
}
function loadNextUp(elem, apiClient, userSettings) {
let html = '';
html += '<div class="sectionTitleContainer sectionTitleContainer-cards padded-left">';
if (!layoutManager.tv) {
html += '<a is="emby-linkbutton" href="' + appRouter.getRouteUrl('nextup', {
serverId: apiClient.serverId()
}) + '" class="button-flat button-flat-mini sectionTitleTextButton">';
html += '<h2 class="sectionTitle sectionTitle-cards">';
html += globalize.translate('NextUp');
html += '</h2>';
html += '<span class="material-icons chevron_right" aria-hidden="true"></span>';
html += '</a>';
} else {
html += '<h2 class="sectionTitle sectionTitle-cards">';
html += globalize.translate('NextUp');
html += '</h2>';
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
html += '</div>';
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
if (enableScrollX()) {
html += '<div is="emby-scroller" class="padded-top-focusscale padded-bottom-focusscale" data-centerfocus="true">';
html += '<div is="emby-itemscontainer" class="itemsContainer scrollSlider focuscontainer-x" data-monitor="videoplayback,markplayed">';
} else {
html += '<div is="emby-itemscontainer" class="itemsContainer padded-left padded-right vertical-wrap focuscontainer-x" data-monitor="videoplayback,markplayed">';
2018-10-23 01:05:09 +03:00
}
2023-04-19 01:56:05 -04:00
if (enableScrollX()) {
html += '</div>';
2023-04-19 01:56:05 -04:00
}
html += '</div>';
2023-04-19 01:56:05 -04:00
elem.classList.add('hide');
elem.innerHTML = html;
2023-04-19 01:56:05 -04:00
const itemsContainer = elem.querySelector('.itemsContainer');
itemsContainer.fetchData = getNextUpFetchFn(apiClient.serverId(), userSettings);
itemsContainer.getItemsHtml = getNextUpItemsHtmlFn(userSettings.useEpisodeImagesInNextUpAndResume());
itemsContainer.parentContainer = elem;
}
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
function getLatestRecordingsFetchFn(serverId, activeRecordingsOnly) {
return function () {
const apiClient = ServerConnections.getApiClient(serverId);
return apiClient.getLiveTvRecordings({
userId: apiClient.getCurrentUserId(),
Limit: enableScrollX() ? 12 : 5,
Fields: 'PrimaryImageAspectRatio,BasicSyncInfo',
EnableTotalRecordCount: false,
IsLibraryItem: activeRecordingsOnly ? null : false,
IsInProgress: activeRecordingsOnly ? true : null
});
};
}
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
function getLatestRecordingItemsHtml(activeRecordingsOnly) {
return function (items) {
return cardBuilder.getCardsHtml({
items: items,
shape: enableScrollX() ? 'autooverflow' : 'auto',
showTitle: true,
showParentTitle: true,
coverImage: true,
lazy: true,
showDetailsMenu: true,
centerText: true,
overlayText: false,
showYear: true,
lines: 2,
overlayPlayButton: !activeRecordingsOnly,
allowBottomPadding: !enableScrollX(),
preferThumb: true,
cardLayout: false,
overlayMoreButton: activeRecordingsOnly,
action: activeRecordingsOnly ? 'none' : null,
centerPlayButton: activeRecordingsOnly
});
};
}
2018-10-23 01:05:09 +03:00
2023-04-19 01:56:05 -04:00
function loadLatestLiveTvRecordings(elem, activeRecordingsOnly, apiClient) {
const title = activeRecordingsOnly ?
globalize.translate('HeaderActiveRecordings') :
globalize.translate('HeaderLatestRecordings');
2023-04-19 01:56:05 -04:00
let html = '';
2023-04-19 01:56:05 -04:00
html += '<div class="sectionTitleContainer sectionTitleContainer-cards">';
html += '<h2 class="sectionTitle sectionTitle-cards padded-left">' + title + '</h2>';
html += '</div>';
2023-04-19 01:56:05 -04:00
if (enableScrollX()) {
html += '<div is="emby-scroller" class="padded-top-focusscale padded-bottom-focusscale" data-centerfocus="true">';
html += '<div is="emby-itemscontainer" class="itemsContainer scrollSlider focuscontainer-x">';
} else {
html += '<div is="emby-itemscontainer" class="itemsContainer padded-left padded-right vertical-wrap focuscontainer-x">';
}
2023-04-19 01:56:05 -04:00
if (enableScrollX()) {
html += '</div>';
2023-04-19 01:56:05 -04:00
}
html += '</div>';
2023-04-19 01:56:05 -04:00
elem.classList.add('hide');
elem.innerHTML = html;
2023-04-19 01:56:05 -04:00
const itemsContainer = elem.querySelector('.itemsContainer');
itemsContainer.fetchData = getLatestRecordingsFetchFn(apiClient.serverId(), activeRecordingsOnly);
itemsContainer.getItemsHtml = getLatestRecordingItemsHtml(activeRecordingsOnly);
itemsContainer.parentContainer = elem;
}
export default {
loadLibraryTiles: loadLibraryTiles,
getDefaultSection: getDefaultSection,
loadSections: loadSections,
destroySections: destroySections,
pause: pause,
resume: resume
};