2023-03-08 12:03:57 -05:00
|
|
|
import classNames from 'classnames';
|
|
|
|
|
import { usePromise } from 'hooks/usePromise';
|
2023-03-08 16:36:14 -05:00
|
|
|
import React, { useEffect, useRef, useState } from 'react'
|
2023-03-08 12:03:57 -05:00
|
|
|
import { useTranslation } from 'react-i18next';
|
|
|
|
|
import { canExport, getProfile, setProfile } from 'services/config';
|
2023-03-08 17:38:39 -05:00
|
|
|
import { addLog, run, useLog } from 'services/s3si';
|
2023-03-08 12:03:57 -05:00
|
|
|
import { Checkbox } from './Checkbox';
|
|
|
|
|
import { Loading } from './Loading';
|
|
|
|
|
|
|
|
|
|
type RunPanelProps = {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
export const RunPanel: React.FC<RunPanelProps> = () => {
|
|
|
|
|
const { t } = useTranslation();
|
|
|
|
|
const { result } = usePromise(() => getProfile(0));
|
|
|
|
|
const [exportBattle, setExportBattle] = useState(true);
|
|
|
|
|
const [exportCoop, setExportCoop] = useState(true);
|
|
|
|
|
const [loading, setLoading] = useState(false);
|
|
|
|
|
|
|
|
|
|
if (!result) {
|
|
|
|
|
return <Loading />
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const onClick = async () => {
|
|
|
|
|
setLoading(true);
|
|
|
|
|
try {
|
2023-03-08 17:38:39 -05:00
|
|
|
addLog({
|
|
|
|
|
level: 'log',
|
|
|
|
|
msg: ['Export started at', new Date().toLocaleString()],
|
|
|
|
|
})
|
2023-03-08 12:03:57 -05:00
|
|
|
const { state } = result;
|
|
|
|
|
const newState = await run(state, {
|
2023-03-09 06:33:32 -05:00
|
|
|
exporter: "stat.ink",
|
2023-03-08 12:03:57 -05:00
|
|
|
monitor: false,
|
|
|
|
|
withSummary: false,
|
|
|
|
|
skipMode: exportBattle === false ? 'vs' : exportCoop === false ? 'coop' : undefined,
|
|
|
|
|
});
|
|
|
|
|
await setProfile(0, {
|
|
|
|
|
...result,
|
|
|
|
|
state: newState,
|
|
|
|
|
})
|
2023-03-08 17:38:39 -05:00
|
|
|
} catch (e) {
|
|
|
|
|
console.error(e)
|
|
|
|
|
addLog({
|
|
|
|
|
level: 'error',
|
|
|
|
|
msg: [e],
|
|
|
|
|
})
|
2023-03-08 12:03:57 -05:00
|
|
|
} finally {
|
2023-03-08 17:38:39 -05:00
|
|
|
addLog({
|
|
|
|
|
level: 'log',
|
|
|
|
|
msg: ['Export ended at', new Date().toLocaleString()],
|
|
|
|
|
})
|
2023-03-08 12:03:57 -05:00
|
|
|
setLoading(false);
|
|
|
|
|
}
|
|
|
|
|
}
|
2023-03-08 16:36:14 -05:00
|
|
|
const disabled = !canExport(result);
|
2023-03-08 12:03:57 -05:00
|
|
|
|
|
|
|
|
return <>
|
2023-03-08 17:38:39 -05:00
|
|
|
<div className="tooltip" data-tip={disabled ? t('请先在设置中完成Nintendo Account登录和stat.ink的API密钥') : undefined}>
|
2023-03-08 16:36:14 -05:00
|
|
|
<Checkbox disabled={disabled || loading} value={exportBattle} onChange={setExportBattle}>{t('导出对战数据')}</Checkbox>
|
|
|
|
|
<Checkbox disabled={disabled || loading} value={exportCoop} onChange={setExportCoop}>{t('导出打工数据')}</Checkbox>
|
|
|
|
|
<button
|
|
|
|
|
onClick={onClick}
|
2023-07-04 07:40:22 -04:00
|
|
|
className={classNames('btn btn-primary w-full', {
|
2023-03-08 16:36:14 -05:00
|
|
|
'btn-disabled': disabled || (!exportBattle && !exportCoop),
|
|
|
|
|
})}
|
2023-07-04 07:40:22 -04:00
|
|
|
disabled={loading}
|
|
|
|
|
>{loading ? <span className='loading' /> : t('导出')}</button>
|
2023-03-08 16:36:14 -05:00
|
|
|
</div>
|
2023-03-08 12:03:57 -05:00
|
|
|
</>
|
|
|
|
|
}
|
2023-03-08 16:36:14 -05:00
|
|
|
|
|
|
|
|
export type LogPanelProps = {
|
|
|
|
|
className?: string
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
export const LogPanel: React.FC<LogPanelProps> = ({ className }) => {
|
|
|
|
|
const { renderedLogs } = useLog();
|
|
|
|
|
const div = useRef<HTMLDivElement>(null);
|
|
|
|
|
const { t } = useTranslation();
|
|
|
|
|
|
|
|
|
|
useEffect(() => {
|
|
|
|
|
if (div.current) {
|
|
|
|
|
div.current.scrollTop = div.current.scrollHeight;
|
|
|
|
|
}
|
|
|
|
|
}, [renderedLogs])
|
|
|
|
|
|
2023-03-09 06:33:32 -05:00
|
|
|
return <div ref={div} className={`bg-neutral text-neutral-content overflow-auto rounded p-4 ${className}`}>
|
2023-03-08 16:36:14 -05:00
|
|
|
{renderedLogs.length === 0 && <pre><code>{t('欢迎! 请点击"导出"按钮开始使用.')}</code></pre>}
|
|
|
|
|
{renderedLogs.map((line, i) => <pre key={i}><code>{line}</code></pre>)}
|
|
|
|
|
</div>
|
|
|
|
|
}
|