lbry-desktop/ui/component/downloadProgress/view.jsx

203 lines
6 KiB
React
Raw Normal View History

2021-10-01 22:00:57 +02:00
// @flow
2021-10-05 18:20:34 +02:00
import React, { useState, useEffect } from 'react';
2021-10-01 22:00:57 +02:00
import { shell } from 'electron';
2021-10-05 18:20:34 +02:00
import Button from 'component/button';
2021-10-01 22:00:57 +02:00
import * as ICONS from 'constants/icons';
2021-10-05 18:20:34 +02:00
import { buildURI } from 'lbry-redux';
import { formatBytes } from 'util/format-bytes';
import usePersistedState from 'effects/use-persisted-state';
2021-10-01 22:00:57 +02:00
type Props = {
2021-10-05 18:20:34 +02:00
downloadList: any[],
stopDownload: (outpoint: string) => void,
updateDownloadingStatus: (outpoint: string) => void,
2021-10-01 22:00:57 +02:00
};
2021-10-05 18:20:34 +02:00
function DownloadProgress({ downloadList, stopDownload, updateDownloadingStatus }: Props) {
const [isShow, setIsShow] = usePersistedState('download-progress', true);
2021-10-01 22:00:57 +02:00
const [cancelHash] = useState({});
2021-10-05 18:20:34 +02:00
const [checkDownloadingHash] = useState({});
2021-10-01 22:00:57 +02:00
const handleCancel = (hash, value) => {
cancelHash[hash] = value;
};
if (downloadList.length === 0) return null;
2021-10-05 18:20:34 +02:00
downloadList.map((item) => {
if (item && !checkDownloadingHash[item.outpoint]) {
updateDownloadingStatus(item.outpoint);
checkDownloadingHash[item.outpoint] = true;
}
});
2021-10-01 22:00:57 +02:00
if (!isShow) {
return (
2021-10-05 18:20:34 +02:00
<Button
iconSize={40}
icon={ICONS.DOWNLOAD}
className="download-progress__toggle-button"
onClick={() => setIsShow(true)}
/>
2021-10-01 22:00:57 +02:00
);
}
return (
2021-10-05 18:20:34 +02:00
<div className="download-progress__header">
<Button className="download-progress__top-close-button" onClick={() => setIsShow(false)}>
2021-10-01 22:00:57 +02:00
<div />
2021-10-05 18:20:34 +02:00
</Button>
2021-10-01 22:00:57 +02:00
{downloadList.map((item, index) => {
let releaseTime = '';
if (item.metadata && item.metadata.release_time) {
releaseTime = new Date(parseInt(item.metadata.release_time) * 1000).toISOString().split('T')[0];
}
return (
2021-10-05 18:20:34 +02:00
<div key={item.outpoint}>
{index !== 0 && <hr className="download-progress__divider" />}
<DownloadProgressItem
2021-10-01 22:00:57 +02:00
fileName={item.suggested_file_name}
title={item.metadata.title}
releaseTime={releaseTime}
writtenBytes={item.written_bytes}
totalBytes={item.total_bytes}
addedOn={item.added_on}
directory={item.download_directory}
2021-10-05 18:20:34 +02:00
stopDownload={stopDownload}
2021-10-01 22:00:57 +02:00
outpoint={item.outpoint}
2021-10-05 18:20:34 +02:00
isCancel={cancelHash[item.outpoint]}
claimID={item.claim_id}
claimName={item.claim_name}
2021-10-01 22:00:57 +02:00
handleCancel={handleCancel}
/>
2021-10-01 22:49:19 +02:00
</div>
2021-10-01 22:00:57 +02:00
);
})}
</div>
);
}
2021-10-05 18:20:34 +02:00
type DownloadProgressItemProps = {
2021-10-01 22:00:57 +02:00
fileName: string,
writtenBytes: number,
totalBytes: number,
addedOn: number,
title: string,
releaseTime: string,
directory: string,
outpoint: string,
isCancel: boolean,
2021-10-05 18:20:34 +02:00
claimID: string,
claimName: string,
stopDownload: (outpoint: string) => void,
2021-10-01 22:00:57 +02:00
handleCancel: (hash: string, value: boolean) => void,
};
2021-10-05 18:20:34 +02:00
function DownloadProgressItem({
2021-10-01 22:00:57 +02:00
fileName,
writtenBytes,
totalBytes,
addedOn,
title,
releaseTime,
directory,
outpoint,
isCancel,
2021-10-05 18:20:34 +02:00
claimID,
claimName,
2021-10-01 22:00:57 +02:00
stopDownload,
handleCancel,
2021-10-05 18:20:34 +02:00
}: DownloadProgressItemProps) {
2021-10-01 22:00:57 +02:00
const processStopDownload = () => {
2021-10-05 18:20:34 +02:00
handleCancel(outpoint, false);
stopDownload(outpoint);
2021-10-01 22:00:57 +02:00
};
2021-10-05 18:20:34 +02:00
const [percent, setPercent] = useState(0);
const [progressText, setProgressText] = useState('');
useEffect(() => {
const updatePercent = ((writtenBytes / totalBytes) * 100).toFixed(0);
setPercent(updatePercent);
let updateText = '';
const downloadSpeed = Math.ceil(writtenBytes / (Date.now() / 1000 - addedOn));
const remainingSecond = Math.ceil((totalBytes - writtenBytes) / downloadSpeed);
const remainingMinutes = Math.floor(remainingSecond / 60);
if (remainingMinutes > 0) {
updateText += __('%remainingMinutes% minutes %remainSecond% seconds remaining', {
remainingMinutes: remainingMinutes,
remainSecond: remainingSecond - 60 * remainingMinutes,
});
} else {
updateText += __('%remainSecond% seconds remaining', { remainSecond: remainingSecond - 60 * remainingMinutes });
}
updateText += ' -- ';
updateText += __('%written% of %total%', {
written: formatBytes(writtenBytes),
total: formatBytes(totalBytes),
});
updateText += ' ';
updateText += __('(%speed%/sec)', {
speed: formatBytes(downloadSpeed),
});
setProgressText(updateText);
}, [writtenBytes, totalBytes, addedOn]);
2021-10-01 22:00:57 +02:00
const openDownloadFolder = () => {
shell.openPath(directory);
};
return (
2021-10-05 18:20:34 +02:00
<div className=" download-progress__state-container">
<div className="download-progress__state-bar">
<Button
label={title}
className="download-progress__state-filename"
navigate={buildURI({ claimName, claimID })}
/>
2021-10-01 22:00:57 +02:00
<div
2021-10-05 18:20:34 +02:00
className="download-progress__close-button"
2021-10-01 22:00:57 +02:00
onClick={() => {
2021-10-05 18:20:34 +02:00
handleCancel(outpoint, true);
2021-10-01 22:00:57 +02:00
}}
>
&times;
</div>
</div>
2021-10-05 18:20:34 +02:00
<div className="download-progress__state-bar">
<a className="download-progress__state-filename-link" onClick={openDownloadFolder}>
2021-10-01 22:00:57 +02:00
{fileName}
</a>
2021-10-05 18:20:34 +02:00
<p className="download-progress__release-time">{releaseTime}</p>
2021-10-01 22:00:57 +02:00
</div>
2021-10-05 18:20:34 +02:00
<div className="download-progress__state-bar">
<div className="download-progress__bar-container">
<div className="download-progress__bar-content" style={{ width: `${percent}%` }} />
2021-10-01 22:00:57 +02:00
</div>
</div>
2021-10-05 18:20:34 +02:00
<p className="download-progress__count-time">{progressText}</p>
2021-10-01 22:00:57 +02:00
{isCancel && (
2021-10-05 18:20:34 +02:00
<div className="download-progress__cancel">
<p>{__('Do you cancel download this file?')}</p>
<div className="download-progress__cancel-confirm">
<Button label={__('Yes')} className="download-progress__cancel-ok" onClick={processStopDownload} />
<Button
label={__('No')}
className="download-progress__cancel-ok"
onClick={() => handleCancel(outpoint, false)}
/>
2021-10-01 22:00:57 +02:00
</div>
</div>
)}
</div>
);
}
export default DownloadProgress;