voice-changer/client/demo/src/102_model_setting.tsx

289 lines
13 KiB
TypeScript
Raw Normal View History

2023-02-19 08:20:37 +03:00
import { OnnxExecutionProvider, Framework, fileSelector, Correspondence } from "@dannadori/voice-changer-client-js"
2023-01-28 10:06:21 +03:00
import React, { useState } from "react"
2023-01-10 18:59:09 +03:00
import { useMemo } from "react"
2023-02-16 18:09:56 +03:00
import { useAppState } from "./001_provider/001_AppStateProvider";
import { AnimationTypes, HeaderButton, HeaderButtonProps } from "./components/101_HeaderButton";
2023-01-07 18:25:21 +03:00
2023-01-07 14:07:39 +03:00
export type ServerSettingState = {
2023-02-16 18:09:56 +03:00
modelSetting: JSX.Element;
2023-01-07 14:07:39 +03:00
}
2023-02-16 18:09:56 +03:00
export const useModelSettingArea = (): ServerSettingState => {
const appState = useAppState()
const [showPyTorch, setShowPyTorch] = useState<boolean>(true)
2023-02-16 18:09:56 +03:00
const accodionButton = useMemo(() => {
const accodionButtonProps: HeaderButtonProps = {
stateControlCheckbox: appState.frontendManagerState.stateControls.openModelSettingCheckbox,
tooltip: "Open/Close",
onIcon: ["fas", "caret-up"],
offIcon: ["fas", "caret-up"],
animation: AnimationTypes.spinner,
tooltipClass: "tooltip-right",
};
return <HeaderButton {...accodionButtonProps}></HeaderButton>;
}, []);
2023-01-07 14:07:39 +03:00
const uploadeModelRow = useMemo(() => {
const onPyTorchFileLoadClicked = async () => {
const file = await fileSelector("")
if (file.name.endsWith(".pth") == false) {
alert("モデルファイルの拡張子はpthである必要があります。")
return
}
2023-02-16 18:09:56 +03:00
appState.serverSetting.setFileUploadSetting({
...appState.serverSetting.fileUploadSetting,
2023-01-29 08:41:44 +03:00
pyTorchModel: {
2023-01-29 09:25:44 +03:00
file: file
2023-01-29 08:41:44 +03:00
}
2023-01-10 18:59:09 +03:00
})
2023-01-07 14:07:39 +03:00
}
2023-01-08 14:28:57 +03:00
const onPyTorchFileClearClicked = () => {
2023-02-16 18:09:56 +03:00
appState.serverSetting.setFileUploadSetting({
...appState.serverSetting.fileUploadSetting,
2023-01-10 18:59:09 +03:00
pyTorchModel: null
})
2023-01-08 14:28:57 +03:00
}
2023-01-07 14:07:39 +03:00
const onConfigFileLoadClicked = async () => {
const file = await fileSelector("")
if (file.name.endsWith(".json") == false) {
alert("モデルファイルの拡張子はjsonである必要があります。")
return
}
2023-02-16 18:09:56 +03:00
appState.serverSetting.setFileUploadSetting({
...appState.serverSetting.fileUploadSetting,
2023-01-29 08:41:44 +03:00
configFile: {
2023-01-29 09:25:44 +03:00
file: file
2023-01-29 08:41:44 +03:00
}
2023-01-10 18:59:09 +03:00
})
2023-01-07 14:07:39 +03:00
}
2023-01-08 14:28:57 +03:00
const onConfigFileClearClicked = () => {
2023-02-16 18:09:56 +03:00
appState.serverSetting.setFileUploadSetting({
...appState.serverSetting.fileUploadSetting,
2023-01-10 18:59:09 +03:00
configFile: null
})
2023-01-08 14:28:57 +03:00
}
2023-01-07 14:07:39 +03:00
const onOnnxFileLoadClicked = async () => {
const file = await fileSelector("")
if (file.name.endsWith(".onnx") == false) {
alert("モデルファイルの拡張子はonnxである必要があります。")
return
}
2023-02-16 18:09:56 +03:00
appState.serverSetting.setFileUploadSetting({
...appState.serverSetting.fileUploadSetting,
2023-01-29 08:41:44 +03:00
onnxModel: {
2023-01-29 09:25:44 +03:00
file: file
2023-01-29 08:41:44 +03:00
}
2023-01-10 18:59:09 +03:00
})
2023-01-07 14:07:39 +03:00
}
2023-01-08 14:28:57 +03:00
const onOnnxFileClearClicked = () => {
2023-02-16 18:09:56 +03:00
appState.serverSetting.setFileUploadSetting({
...appState.serverSetting.fileUploadSetting,
2023-01-10 18:59:09 +03:00
onnxModel: null
})
2023-01-08 14:28:57 +03:00
}
2023-02-12 06:25:57 +03:00
const onCorrespondenceFileLoadClicked = async () => {
const file = await fileSelector("")
2023-02-19 08:20:37 +03:00
const correspondenceText = await file.text()
const cors = correspondenceText.split("\n").map(line => {
const items = line.split("|")
if (items.length != 3) {
console.warn("Invalid Correspondence Line:", line)
return null
} else {
const cor: Correspondence = {
sid: Number(items[0]),
correspondence: Number(items[1]),
dirname: items[2]
}
return cor
}
}).filter(x => { return x != null }) as Correspondence[]
appState.serverSetting.updateServerSettings({ ...appState.serverSetting.serverSetting, correspondences: cors })
2023-02-12 06:25:57 +03:00
}
const onCorrespondenceFileClearClicked = () => {
2023-02-19 08:20:37 +03:00
appState.serverSetting.updateServerSettings({ ...appState.serverSetting.serverSetting, correspondences: [] })
2023-02-12 06:25:57 +03:00
}
2023-01-07 18:25:21 +03:00
const onModelUploadClicked = async () => {
2023-02-16 18:09:56 +03:00
appState.serverSetting.loadModel()
2023-01-07 18:25:21 +03:00
}
2023-02-16 18:09:56 +03:00
const uploadButtonClassName = appState.serverSetting.isUploading ? "body-button-disabled" : "body-button"
const uploadButtonAction = appState.serverSetting.isUploading ? () => { } : onModelUploadClicked
const uploadButtonLabel = appState.serverSetting.isUploading ? "wait..." : "upload"
2023-01-14 11:58:57 +03:00
2023-02-16 18:09:56 +03:00
const configFilenameText = appState.serverSetting.fileUploadSetting.configFile?.filename || appState.serverSetting.fileUploadSetting.configFile?.file?.name || ""
const onnxModelFilenameText = appState.serverSetting.fileUploadSetting.onnxModel?.filename || appState.serverSetting.fileUploadSetting.onnxModel?.file?.name || ""
const pyTorchFilenameText = appState.serverSetting.fileUploadSetting.pyTorchModel?.filename || appState.serverSetting.fileUploadSetting.pyTorchModel?.file?.name || ""
2023-02-19 08:20:37 +03:00
const correspondenceFileText = appState.serverSetting.serverSetting.correspondences ? JSON.stringify(appState.serverSetting.serverSetting.correspondences.map(x => { return x.dirname })) : ""
2023-01-29 09:25:44 +03:00
2023-01-07 14:07:39 +03:00
return (
<>
<div className="body-row split-3-3-4 left-padding-1 guided">
<div className="body-item-title left-padding-1">Model Uploader</div>
<div className="body-item-text">
<div></div>
</div>
<div className="body-item-text">
2023-01-28 10:06:21 +03:00
<div>
<input type="checkbox" checked={showPyTorch} onChange={(e) => {
setShowPyTorch(e.target.checked)
}} /> enable PyTorch
</div>
2023-01-07 14:07:39 +03:00
</div>
</div>
2023-02-12 06:25:57 +03:00
2023-01-07 14:07:39 +03:00
<div className="body-row split-3-3-4 left-padding-1 guided">
2023-01-12 10:38:45 +03:00
<div className="body-item-title left-padding-2">Config(.json)</div>
2023-01-07 14:07:39 +03:00
<div className="body-item-text">
2023-01-29 09:25:44 +03:00
<div>{configFilenameText}</div>
2023-01-07 14:07:39 +03:00
</div>
<div className="body-button-container">
2023-01-12 10:38:45 +03:00
<div className="body-button" onClick={onConfigFileLoadClicked}>select</div>
<div className="body-button left-margin-1" onClick={onConfigFileClearClicked}>clear</div>
2023-01-07 14:07:39 +03:00
</div>
</div>
2023-02-12 06:25:57 +03:00
<div className="body-row split-3-3-4 left-padding-1 guided">
<div className="body-item-title left-padding-2">Correspondence</div>
<div className="body-item-text">
<div>{correspondenceFileText}</div>
</div>
<div className="body-button-container">
<div className="body-button" onClick={onCorrespondenceFileLoadClicked}>select</div>
<div className="body-button left-margin-1" onClick={onCorrespondenceFileClearClicked}>clear</div>
</div>
</div>
2023-01-07 14:07:39 +03:00
<div className="body-row split-3-3-4 left-padding-1 guided">
<div className="body-item-title left-padding-2">Onnx(.onnx)</div>
<div className="body-item-text">
2023-01-29 09:25:44 +03:00
<div>{onnxModelFilenameText}</div>
2023-01-07 14:07:39 +03:00
</div>
<div className="body-button-container">
<div className="body-button" onClick={onOnnxFileLoadClicked}>select</div>
2023-01-08 14:28:57 +03:00
<div className="body-button left-margin-1" onClick={onOnnxFileClearClicked}>clear</div>
2023-01-07 14:07:39 +03:00
</div>
</div>
2023-01-28 10:06:21 +03:00
{showPyTorch ?
(
<div className="body-row split-3-3-4 left-padding-1 guided">
<div className="body-item-title left-padding-2">PyTorch(.pth)</div>
<div className="body-item-text">
2023-01-29 09:25:44 +03:00
<div>{pyTorchFilenameText}</div>
2023-01-28 10:06:21 +03:00
</div>
<div className="body-button-container">
<div className="body-button" onClick={onPyTorchFileLoadClicked}>select</div>
<div className="body-button left-margin-1" onClick={onPyTorchFileClearClicked}>clear</div>
</div>
</div>
)
:
(
<></>
)
}
2023-01-07 18:25:21 +03:00
<div className="body-row split-3-3-4 left-padding-1 guided">
<div className="body-item-title left-padding-2"></div>
<div className="body-item-text">
2023-02-16 18:09:56 +03:00
{appState.serverSetting.isUploading ? `uploading.... ${appState.serverSetting.uploadProgress}%` : ""}
2023-01-07 18:25:21 +03:00
</div>
<div className="body-button-container">
2023-01-14 11:58:57 +03:00
<div className={uploadButtonClassName} onClick={uploadButtonAction}>{uploadButtonLabel}</div>
2023-01-07 18:25:21 +03:00
</div>
</div>
2023-01-07 14:07:39 +03:00
</>
)
2023-01-10 18:59:09 +03:00
}, [
2023-02-16 18:09:56 +03:00
appState.serverSetting.fileUploadSetting,
appState.serverSetting.loadModel,
appState.serverSetting.isUploading,
appState.serverSetting.uploadProgress,
2023-02-19 08:20:37 +03:00
appState.serverSetting.serverSetting.correspondences,
appState.serverSetting.updateServerSettings,
appState.serverSetting.setFileUploadSetting,
2023-01-28 10:06:21 +03:00
showPyTorch])
2023-01-07 14:07:39 +03:00
const frameworkRow = useMemo(() => {
const onFrameworkChanged = async (val: Framework) => {
appState.serverSetting.updateServerSettings({ ...appState.serverSetting.serverSetting, framework: val })
2023-01-07 14:07:39 +03:00
}
return (
<div className="body-row split-3-7 left-padding-1 guided">
<div className="body-item-title left-padding-1">Framework</div>
<div className="body-select-container">
<select className="body-select" value={appState.serverSetting.serverSetting.framework} onChange={(e) => {
2023-01-07 14:07:39 +03:00
onFrameworkChanged(e.target.value as
Framework)
}}>
{
Object.values(Framework).map(x => {
return <option key={x} value={x}>{x}</option>
})
}
</select>
</div>
</div>
)
}, [appState.serverSetting.serverSetting.framework, appState.serverSetting.updateServerSettings])
2023-01-07 14:07:39 +03:00
const onnxExecutionProviderRow = useMemo(() => {
if (appState.serverSetting.serverSetting.framework != "ONNX") {
2023-01-07 14:07:39 +03:00
return
}
const onOnnxExecutionProviderChanged = async (val: OnnxExecutionProvider) => {
appState.serverSetting.updateServerSettings({ ...appState.serverSetting.serverSetting, onnxExecutionProvider: val })
2023-01-07 14:07:39 +03:00
}
return (
<div className="body-row split-3-7 left-padding-1">
<div className="body-item-title left-padding-2">OnnxExecutionProvider</div>
<div className="body-select-container">
<select className="body-select" value={appState.serverSetting.serverSetting.onnxExecutionProvider} onChange={(e) => {
2023-01-07 14:07:39 +03:00
onOnnxExecutionProviderChanged(e.target.value as
OnnxExecutionProvider)
}}>
{
Object.values(OnnxExecutionProvider).map(x => {
return <option key={x} value={x}>{x}</option>
})
}
</select>
</div>
</div>
)
}, [appState.serverSetting.serverSetting.framework, appState.serverSetting.serverSetting.onnxExecutionProvider, appState.serverSetting.updateServerSettings])
2023-01-07 14:07:39 +03:00
2023-02-16 18:09:56 +03:00
const modelSetting = useMemo(() => {
2023-01-07 14:07:39 +03:00
return (
<>
2023-02-16 18:09:56 +03:00
{appState.frontendManagerState.stateControls.openModelSettingCheckbox.trigger}
<div className="partition">
<div className="partition-header">
<span className="caret">
{accodionButton}
</span>
<span className="title" onClick={() => { appState.frontendManagerState.stateControls.openModelSettingCheckbox.updateState(!appState.frontendManagerState.stateControls.openModelSettingCheckbox.checked()) }}>
Model Setting
</span>
2023-02-16 19:01:32 +03:00
<span></span>
2023-02-16 18:09:56 +03:00
</div>
<div className="partition-content">
{uploadeModelRow}
{frameworkRow}
{onnxExecutionProviderRow}
2023-01-07 14:07:39 +03:00
</div>
</div>
</>
)
2023-01-12 11:43:36 +03:00
}, [uploadeModelRow, frameworkRow, onnxExecutionProviderRow])
2023-01-07 14:07:39 +03:00
return {
2023-02-16 18:09:56 +03:00
modelSetting,
2023-01-07 14:07:39 +03:00
}
}