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/shortcuts.js
MrTimscampi 7d9208e951 WIP
2020-11-05 23:09:09 +00:00

402 lines
14 KiB
JavaScript

/* eslint-disable indent */
/**
* Module shortcuts.
* @module components/shortcuts
*/
import { playbackManager } from './playback/playbackmanager';
import inputManager from '../scripts/inputManager';
import { ConnectionManager } from 'jellyfin-apiclient';
import { appRouter } from './appRouter';
import globalize from '../scripts/globalize';
import dom from '../scripts/dom';
import recordingHelper from './recordingcreator/recordinghelper';
function playAllFromHere(card, serverId, queue) {
const parent = card.parentNode;
const className = card.classList.length ? (`.${card.classList[0]}`) : '';
const cards = parent.querySelectorAll(`${className}[data-id]`);
const ids = [];
let foundCard = false;
let startIndex;
for (let i = 0, length = cards.length; i < length; i++) {
if (cards[i] === card) {
foundCard = true;
startIndex = i;
}
if (foundCard || !queue) {
ids.push(cards[i].getAttribute('data-id'));
}
}
const itemsContainer = dom.parentWithClass(card, 'itemsContainer');
if (itemsContainer && itemsContainer.fetchData) {
const queryOptions = queue ? { StartIndex: startIndex } : {};
return itemsContainer.fetchData(queryOptions).then(result => {
if (queue) {
return playbackManager.queue({
items: result.Items
});
} else {
return playbackManager.play({
items: result.Items,
startIndex: startIndex
});
}
});
}
if (!ids.length) {
return;
}
if (queue) {
return playbackManager.queue({
ids: ids,
serverId: serverId
});
} else {
return playbackManager.play({
ids: ids,
serverId: serverId,
startIndex: startIndex
});
}
}
function showProgramDialog(item) {
import('./recordingcreator/recordingcreator' +
'').then(({default:recordingCreator}) => {
recordingCreator.show(item.Id, item.ServerId);
});
}
function getItem(button) {
button = dom.parentWithAttribute(button, 'data-id');
const serverId = button.getAttribute('data-serverid');
const id = button.getAttribute('data-id');
const type = button.getAttribute('data-type');
const apiClient = ConnectionManager.getApiClient(serverId);
if (type === 'Timer') {
return apiClient.getLiveTvTimer(id);
}
if (type === 'SeriesTimer') {
return apiClient.getLiveTvSeriesTimer(id);
}
return apiClient.getItem(apiClient.getCurrentUserId(), id);
}
function notifyRefreshNeeded(childElement, itemsContainer) {
itemsContainer = itemsContainer || dom.parentWithAttribute(childElement, 'is', 'emby-itemscontainer');
if (itemsContainer) {
itemsContainer.notifyRefreshNeeded(true);
}
}
function showContextMenu(card, options) {
getItem(card).then(item => {
const playlistId = card.getAttribute('data-playlistid');
const collectionId = card.getAttribute('data-collectionid');
if (playlistId) {
const elem = dom.parentWithAttribute(card, 'data-playlistitemid');
item.PlaylistItemId = elem ? elem.getAttribute('data-playlistitemid') : null;
}
import('./itemContextMenu').then((itemContextMenu) => {
ConnectionManager.getApiClient(item.ServerId).getCurrentUser().then(user => {
itemContextMenu.show(Object.assign({
item: item,
play: true,
queue: true,
playAllFromHere: !item.IsFolder,
queueAllFromHere: !item.IsFolder,
playlistId: playlistId,
collectionId: collectionId,
user: user
}, options || {})).then(result => {
if (result.command === 'playallfromhere' || result.command === 'queueallfromhere') {
executeAction(card, options.positionTo, result.command);
} else if (result.updated || result.deleted) {
notifyRefreshNeeded(card, options.itemsContainer);
}
});
});
});
});
}
function getItemInfoFromCard(card) {
return {
Type: card.getAttribute('data-type'),
Id: card.getAttribute('data-id'),
TimerId: card.getAttribute('data-timerid'),
CollectionType: card.getAttribute('data-collectiontype'),
ChannelId: card.getAttribute('data-channelid'),
SeriesId: card.getAttribute('data-seriesid'),
ServerId: card.getAttribute('data-serverid'),
MediaType: card.getAttribute('data-mediatype'),
IsFolder: card.getAttribute('data-isfolder') === 'true',
UserData: {
PlaybackPositionTicks: parseInt(card.getAttribute('data-positionticks') || '0')
}
};
}
function showPlayMenu(card, target) {
const item = getItemInfoFromCard(card);
import('./playmenu').then((playMenu) => {
playMenu.show({
item: item,
positionTo: target
});
});
}
function sendToast(text) {
import('./toast/toast').then((toast) => {
toast(text);
});
}
function executeAction(card, target, action) {
target = target || card;
let id = card.getAttribute('data-id');
if (!id) {
card = dom.parentWithAttribute(card, 'data-id');
id = card.getAttribute('data-id');
}
const item = getItemInfoFromCard(card);
const serverId = item.ServerId;
const type = item.Type;
const playableItemId = type === 'Program' ? item.ChannelId : item.Id;
if (item.MediaType === 'Photo' && action === 'link') {
action = 'play';
}
if (action === 'link') {
appRouter.showItem(item, {
context: card.getAttribute('data-context'),
parentId: card.getAttribute('data-parentid')
});
} else if (action === 'programdialog') {
showProgramDialog(item);
} else if (action === 'instantmix') {
playbackManager.instantMix({
Id: playableItemId,
ServerId: serverId
});
} else if (action === 'play' || action === 'resume') {
const startPositionTicks = parseInt(card.getAttribute('data-positionticks') || '0');
playbackManager.play({
ids: [playableItemId],
startPositionTicks: startPositionTicks,
serverId: serverId
});
} else if (action === 'queue') {
if (playbackManager.isPlaying()) {
playbackManager.queue({
ids: [playableItemId],
serverId: serverId
});
sendToast(globalize.translate('MediaQueued'));
} else {
playbackManager.queue({
ids: [playableItemId],
serverId: serverId
});
}
} else if (action === 'playallfromhere') {
playAllFromHere(card, serverId);
} else if (action === 'queueallfromhere') {
playAllFromHere(card, serverId, true);
} else if (action === 'setplaylistindex') {
playbackManager.setCurrentPlaylistItem(card.getAttribute('data-playlistitemid'));
} else if (action === 'record') {
onRecordCommand(serverId, id, type, card.getAttribute('data-timerid'), card.getAttribute('data-seriestimerid'));
} else if (action === 'menu') {
const options = target.getAttribute('data-playoptions') === 'false' ?
{
shuffle: false,
instantMix: false,
play: false,
playAllFromHere: false,
queue: false,
queueAllFromHere: false
} :
{};
options.positionTo = target;
showContextMenu(card, options);
} else if (action === 'playmenu') {
showPlayMenu(card, target);
} else if (action === 'edit') {
getItem(target).then(item => {
editItem(item, serverId);
});
} else if (action === 'playtrailer') {
getItem(target).then(playTrailer);
} else if (action === 'addtoplaylist') {
getItem(target).then(addToPlaylist);
} else if (action === 'custom') {
const customAction = target.getAttribute('data-customaction');
card.dispatchEvent(new CustomEvent(`action-${customAction}`, {
detail: {
playlistItemId: card.getAttribute('data-playlistitemid')
},
cancelable: false,
bubbles: true
}));
}
}
function addToPlaylist(item) {
import('./playlisteditor/playlisteditor').then((playlistEditor) => {
new playlistEditor().show({
items: [item.Id],
serverId: item.ServerId
});
});
}
function playTrailer(item) {
const apiClient = ConnectionManager.getApiClient(item.ServerId);
apiClient.getLocalTrailers(apiClient.getCurrentUserId(), item.Id).then(trailers => {
playbackManager.play({ items: trailers });
});
}
function editItem(item, serverId) {
const apiClient = ConnectionManager.getApiClient(serverId);
return new Promise((resolve, reject) => {
const serverId = apiClient.serverInfo().Id;
if (item.Type === 'Timer') {
if (item.ProgramId) {
import('./recordingcreator/recordingcreator').then((recordingCreator) => {
recordingCreator.show(item.ProgramId, serverId).then(resolve, reject);
});
} else {
import('./recordingcreator/recordingeditor').then((recordingEditor) => {
recordingEditor.show(item.Id, serverId).then(resolve, reject);
});
}
} else {
import('./metadataEditor/metadataEditor').then((metadataEditor) => {
metadataEditor.show(item.Id, serverId).then(resolve, reject);
});
}
});
}
function onRecordCommand(serverId, id, type, timerId, seriesTimerId) {
if (type === 'Program' || timerId || seriesTimerId) {
const programId = type === 'Program' ? id : null;
recordingHelper.toggleRecording(serverId, programId, timerId, seriesTimerId);
}
}
export function onClick(e) {
const card = dom.parentWithClass(e.target, 'itemAction');
if (card) {
let actionElement = card;
let action = actionElement.getAttribute('data-action');
if (!action) {
actionElement = dom.parentWithAttribute(actionElement, 'data-action');
if (actionElement) {
action = actionElement.getAttribute('data-action');
}
}
if (action) {
executeAction(card, actionElement, action);
e.preventDefault();
e.stopPropagation();
return false;
}
}
}
function onCommand(e) {
const cmd = e.detail.command;
if (cmd === 'play' || cmd === 'resume' || cmd === 'record' || cmd === 'menu' || cmd === 'info') {
const target = e.target;
const card = dom.parentWithClass(target, 'itemAction') || dom.parentWithAttribute(target, 'data-id');
if (card) {
e.preventDefault();
e.stopPropagation();
executeAction(card, card, cmd);
}
}
}
export function on(context, options) {
options = options || {};
if (options.click !== false) {
context.addEventListener('click', onClick);
}
if (options.command !== false) {
inputManager.on(context, onCommand);
}
}
export function off(context, options) {
options = options || {};
context.removeEventListener('click', onClick);
if (options.command !== false) {
inputManager.off(context, onCommand);
}
}
export function getShortcutAttributesHtml(item, serverId) {
let html = `data-id="${item.Id}" data-serverid="${serverId || item.ServerId}" data-type="${item.Type}" data-mediatype="${item.MediaType}" data-channelid="${item.ChannelId}" data-isfolder="${item.IsFolder}"`;
const collectionType = item.CollectionType;
if (collectionType) {
html += ` data-collectiontype="${collectionType}"`;
}
return html;
}
/* eslint-enable indent */
export default {
on: on,
off: off,
onClick: onClick,
getShortcutAttributesHtml: getShortcutAttributesHtml
};