';
+ html += `
${escapeHtml(title)}
`;
+ const allowBottomPadding = true;
+
+ if (enableScrollX()) {
+ html += '
';
+ html += '
';
+ html += '
';
+ return html;
+ }, [enableScrollX, getPortraitShape]);
+
+ const loadSuggestions = useCallback((page, userId) => {
+ const screenWidth: any = dom.getWindowSize();
+ let itemLimit = 5;
+ if (screenWidth.innerWidth >= 1600) {
+ itemLimit = 8;
+ } else if (screenWidth.innerWidth >= 1200) {
+ itemLimit = 6;
+ }
+ const url = window.window.ApiClient.getUrl('Movies/Recommendations', {
+ userId: userId,
+ categoryLimit: 6,
+ ItemLimit: itemLimit,
+ Fields: 'PrimaryImageAspectRatio,MediaSourceCount,BasicSyncInfo',
+ ImageTypeLimit: 1,
+ EnableImageTypes: 'Primary,Backdrop,Banner,Thumb'
+ });
+ window.ApiClient.getJSON(url).then(recommendations => {
+ if (!recommendations.length) {
+ page.querySelector('.noItemsMessage').classList.remove('hide');
+ page.querySelector('.recommendations').innerHTML = '';
+ return;
+ }
+
+ const html = recommendations.map(getRecommendationHtml).join('');
+ page.querySelector('.noItemsMessage').classList.add('hide');
+ const recs = page.querySelector('.recommendations');
+ recs.innerHTML = html;
+ imageLoader.lazyChildren(recs);
+
+ // FIXME: Wait for all sections to load
+ autoFocus(page);
+ });
+ }, [autoFocus, getRecommendationHtml]);
+
+ const loadSuggestionsTab = useCallback((view) => {
+ const parentId = props.topParentId;
+ const userId = window.ApiClient.getCurrentUserId();
+ loadResume(view, userId, parentId);
+ loadLatest(view, userId, parentId);
+ loadSuggestions(view, userId);
+ }, [loadLatest, loadResume, loadSuggestions, props.topParentId]);
+
+ const initSuggestedTab = useCallback((tabContent) => {
+ function setScrollClasses(elem: { classList: { add: (arg0: string) => void; remove: (arg0: string) => void; }; }, scrollX: boolean) {
+ if (scrollX) {
+ elem.classList.add('hiddenScrollX');
+
+ if (layoutManager.tv) {
+ elem.classList.add('smoothScrollX');
+ elem.classList.add('padded-top-focusscale');
+ elem.classList.add('padded-bottom-focusscale');
+ }
+
+ elem.classList.add('scrollX');
+ elem.classList.remove('vertical-wrap');
+ } else {
+ elem.classList.remove('hiddenScrollX');
+ elem.classList.remove('smoothScrollX');
+ elem.classList.remove('scrollX');
+ elem.classList.add('vertical-wrap');
+ }
+ }
+ const containers = tabContent.querySelectorAll('.itemsContainer');
+
+ for (const container of containers) {
+ setScrollClasses(container, enableScrollX());
+ }
+ }, [enableScrollX]);
+
+ useEffect(() => {
+ const page = element.current;
+
+ if (!page) {
+ console.error('Unexpected null reference');
+ return;
+ }
+
+ initSuggestedTab(page);
+ }, [initSuggestedTab]);
+
+ useEffect(() => {
+ const page = element.current;
+
+ if (!page) {
+ console.error('Unexpected null reference');
+ return;
+ }
+ loadSuggestionsTab(page);
+ }, [loadSuggestionsTab]);
+ return (
+
+
+
+
+ {globalize.translate('HeaderContinueWatching')}
+
+
+
+
+
+
+
+
+
+
+ {globalize.translate('HeaderLatestMovies')}
+
+
+
+
+
+
+
+
+
+
+
+
+ {globalize.translate('MessageNoMovieSuggestionsAvailable')}
+
+
+
+ );
+};
+
+export default SuggestionsView;
diff --git a/src/view/movies/TrailersView.tsx b/src/view/movies/TrailersView.tsx
new file mode 100644
index 0000000000..3eb6909b72
--- /dev/null
+++ b/src/view/movies/TrailersView.tsx
@@ -0,0 +1,132 @@
+import '../../elements/emby-itemscontainer/emby-itemscontainer';
+
+import { BaseItemDtoQueryResult } from '@thornbill/jellyfin-sdk/dist/generated-client';
+import React, { FunctionComponent, useCallback, useEffect, useMemo, useRef, useState } from 'react';
+
+import loading from '../../components/loading/loading';
+import globalize from '../../scripts/globalize';
+import * as userSettings from '../../scripts/settings/userSettings';
+import AlphaPickerContainer from '../components/AlphaPickerContainer';
+import Filter from '../components/Filter';
+import ItemsContainer from '../components/ItemsContainer';
+import Pagination from '../components/Pagination';
+import Sort from '../components/Sort';
+import { IQuery } from '../components/type';
+
+const SortMenuOptions = () => {
+ return [{
+ name: globalize.translate('Name'),
+ id: 'SortName'
+ }, {
+ name: globalize.translate('OptionImdbRating'),
+ id: 'CommunityRating,SortName'
+ }, {
+ name: globalize.translate('OptionDateAdded'),
+ id: 'DateCreated,SortName'
+ }, {
+ name: globalize.translate('OptionDatePlayed'),
+ id: 'DatePlayed,SortName'
+ }, {
+ name: globalize.translate('OptionParentalRating'),
+ id: 'OfficialRating,SortName'
+ }, {
+ name: globalize.translate('OptionPlayCount'),
+ id: 'PlayCount,SortName'
+ }, {
+ name: globalize.translate('OptionReleaseDate'),
+ id: 'PremiereDate,SortName'
+ }];
+};
+
+type IProps = {
+ topParentId: string | null;
+}
+
+const TrailersView: FunctionComponent
= ({ topParentId }: IProps) => {
+ const savedQueryKey = topParentId + '-trailers';
+ const savedViewKey = savedQueryKey + '-view';
+
+ const [ itemsResult, setItemsResult ] = useState();
+ const element = useRef(null);
+
+ const query = useMemo(() => ({
+ SortBy: 'SortName',
+ SortOrder: 'Ascending',
+ IncludeItemTypes: 'Trailer',
+ Recursive: true,
+ Fields: 'PrimaryImageAspectRatio,SortName,BasicSyncInfo',
+ ImageTypeLimit: 1,
+ EnableImageTypes: 'Primary,Backdrop,Banner,Thumb',
+ Limit: userSettings.libraryPageSize(undefined),
+ StartIndex: 0,
+ ParentId: topParentId }), [topParentId]);
+
+ userSettings.loadQuerySettings(savedQueryKey, query);
+
+ const getCurrentViewStyle = useCallback(() => {
+ return userSettings.get(savedViewKey, false) || 'Poster';
+ }, [savedViewKey]);
+
+ const reloadItems = useCallback(() => {
+ const page = element.current;
+
+ if (!page) {
+ console.error('Unexpected null reference');
+ return;
+ }
+ loading.show();
+ window.ApiClient.getItems(window.ApiClient.getCurrentUserId(), query).then((result) => {
+ setItemsResult(result);
+ window.scrollTo(0, 0);
+
+ loading.hide();
+ });
+ }, [query]);
+
+ const onViewStyleChange = useCallback(() => {
+ const page = element.current;
+
+ if (!page) {
+ console.error('Unexpected null reference');
+ return;
+ }
+ const viewStyle = getCurrentViewStyle();
+ const itemsContainer = page.querySelector('.itemsContainer') as HTMLDivElement;
+ if (viewStyle == 'List') {
+ itemsContainer.classList.add('vertical-list');
+ itemsContainer.classList.remove('vertical-wrap');
+ } else {
+ itemsContainer.classList.remove('vertical-list');
+ itemsContainer.classList.add('vertical-wrap');
+ }
+
+ itemsContainer.innerHTML = '';
+ }, [getCurrentViewStyle]);
+
+ useEffect(() => {
+ onViewStyleChange();
+ reloadItems();
+ }, [onViewStyleChange, query, reloadItems]);
+
+ return (
+
+ );
+};
+
+export default TrailersView;