diff --git a/locales/en.yml b/locales/en.yml index 05e5601d..065d01f6 100644 --- a/locales/en.yml +++ b/locales/en.yml @@ -211,6 +211,7 @@ config_page: others: section_label_sounds: "Sounds" + section_label_message_formats: "Message Formats" auto_clear_the_message_box: label: "Auto Clear Message box" send_only_translated_messages: @@ -231,6 +232,26 @@ config_page: label: "Send Received Message To VRChat" desc: "Send the message you received from the speaker's voice to VRChat's chatbox." + message_format_common: + example_view: + title: "Preview" + original_translated: "Original + Translated" + original_translated_multi: "Original + Translated (Multi-Translation)" + translated_only_multi: "Translated Only (Multi-Translation)" + translated_only: "Translated Only" + original_only: "Original Only" + settings: + title: "Settings" + original: "Original" + translated: "Translated" + for_multi_translation: For Multi-Translation + send_message_format: + label: "Message Format (Send)" + desc: "You can change the decoration of the message you want to send." + received_message_format: + label: "Message Format (Speaker2Chatbox)" + desc: "It will be used in Speaker2Chatbox for now." + hotkeys: toggle_vrct_visibility: label: "Toggle VRCT visibility" diff --git a/locales/ja.yml b/locales/ja.yml index d36bec89..978a5b29 100644 --- a/locales/ja.yml +++ b/locales/ja.yml @@ -211,6 +211,7 @@ config_page: others: section_label_sounds: "サウンド" + section_label_message_formats: "メッセージフォーマット" auto_clear_the_message_box: label: "送信後はメッセージ入力欄を空にする" send_only_translated_messages: @@ -230,6 +231,25 @@ config_page: send_received_message_to_vrc: label: "受信したメッセージをVRChatに送信する" desc: "スピーカーから聞き取り、文字起こしされたメッセージをVRChatに送信します。" + message_format_common: + example_view: + title: "プレビュー" + original_translated: "原文 + 翻訳" + original_translated_multi: "原文 + 翻訳(多言語)" + translated_only_multi: "翻訳のみ(多言語)" + translated_only: "翻訳のみ" + original_only: "原文のみ" + settings: + title: "設定" + original: "原文" + translated: "翻訳" + for_multi_translation: 多言語翻訳用 + send_message_format: + label: メッセージフォーマット(送信) + desc: VRChatで相手に実際に見えるフォーマットを変更できます。 + received_message_format: + label: メッセージフォーマット(Speaker2Chatbox) + desc: 今のところ、Speaker2Chatboxで送信した時の表示に使われます。 hotkeys: toggle_vrct_visibility: diff --git a/src-python/controller.py b/src-python/controller.py index 3e652886..c34abaf8 100644 --- a/src-python/controller.py +++ b/src-python/controller.py @@ -1462,7 +1462,7 @@ class Controller: @staticmethod def setSendMessageFormatParts(data, *args, **kwargs) -> dict: - config.SEND_MESSAGE_FORMAT_PARTS = str(data) + config.SEND_MESSAGE_FORMAT_PARTS = dict(data) return {"status":200, "result":config.SEND_MESSAGE_FORMAT_PARTS} @staticmethod @@ -1471,7 +1471,7 @@ class Controller: @staticmethod def setReceivedMessageFormatParts(data, *args, **kwargs) -> dict: - config.RECEIVED_MESSAGE_FORMAT_PARTS = str(data) + config.RECEIVED_MESSAGE_FORMAT_PARTS = dict(data) return {"status":200, "result":config.RECEIVED_MESSAGE_FORMAT_PARTS} @staticmethod diff --git a/src-ui/app/config_page/setting_section/setting_box/_components/_atoms/_entry/_Entry.jsx b/src-ui/app/config_page/setting_section/setting_box/_components/_atoms/_entry/_Entry.jsx index 641e7104..49ed1238 100644 --- a/src-ui/app/config_page/setting_section/setting_box/_components/_atoms/_entry/_Entry.jsx +++ b/src-ui/app/config_page/setting_section/setting_box/_components/_atoms/_entry/_Entry.jsx @@ -21,11 +21,11 @@ const _Entry = forwardRef((props, ref) => { }); return ( -
-
+
+
{ + const { currentIsBreakPoint } = useStore_IsBreakPoint(); + const message_format_container_class = clsx(styles.container, { + [styles.is_break_point]: currentIsBreakPoint.data, + }); + + return ( +
+ +
+ +
+ ); +}; + +const ExampleComponent = ({ format, example_view_filter_variable, exampleViewFilterToggleFunction, format_id }) => { + const { currentUiLanguage } = useAppearance(); + const { t } = useTranslation(); + + + const locale_base_path = "config_page.others.message_format_common.example_view."; + + const label_title = t(locale_base_path + "title"); + + const label_original_translated = t(locale_base_path + "original_translated"); + const label_original_translated_multi = t(locale_base_path + "original_translated_multi"); + const label_translated_only_multi = t(locale_base_path + "translated_only_multi"); + const label_translated_only = t(locale_base_path + "translated_only"); + const label_original_only = t(locale_base_path + "original_only"); + + const createExampleMessage = (id) => { + // 言語順序を決定 + let example_text_order = []; + switch (currentUiLanguage.data) { + case "ja": + example_text_order = ["ja", "en", "ko", "fr"]; + break; + case "ko": + example_text_order = ["ko", "ja", "en", "fr"]; + break; + default: // en + example_text_order = ["en", "ja", "ko", "fr"]; + break; + } + + const original = EXAMPLE_TEXTS[example_text_order[0]]; + const translations = example_text_order.slice(1).map(lang => EXAMPLE_TEXTS[lang]); + + const originalPart = `${format.message.prefix}${original}${format.message.suffix}`; + const translationSingle = `${format.translation.prefix}${translations[0]}${format.translation.suffix}`; + const translationMulti = `${format.translation.prefix}${translations.join(format.translation.separator)}${format.translation.suffix}`; + + switch (id) { + case "original_translated": + return format.translation_first + ? `${translationSingle}${format.separator}${originalPart}` + : `${originalPart}${format.separator}${translationSingle}`; + + case "original_only": + return originalPart; + + case "translated_only": + return translationSingle; + + case "translated_only_multi": + return translationMulti; + + case "original_translated_multi": + return format.translation_first + ? `${translationMulti}${format.separator}${originalPart}` + : `${originalPart}${format.separator}${translationMulti}`; + + default: + throw new Error(`Unexpected id: ${id}`); + } + }; + + const ExampleBox = ({label, example_text_id}) => { + return ( +
+

{label}

+
+

{createExampleMessage(example_text_id)}

+
+
+ ); + + }; + + const svg_class_names = clsx(styles.arrow_left_svg, { + [styles.to_down]: example_view_filter_variable[format_id] === "Simplified", + [styles.to_up]: example_view_filter_variable[format_id] === "All" + }); + + + const FilteredExampleBox = ({format_id, id}) => { + if (format_id === "send" && id === "Simplified") { + return ( + <> + + + + ); + } else if ( format_id === "send" && id === "All") { + return ( + <> + + + + + + + ); + + } else if (format_id === "received") { + return ( + <> + + + + + ); + } + }; + + + return ( +
+

{label_title}

+
+ +
+ { format_id === "send" && +
exampleViewFilterToggleFunction(format_id)}> + +
+ } +
+ ); +}; + + +const InputComponent = ({id, variable, setFunction, format_id }) => { + const { t } = useTranslation(); + + const locale_base_path = "config_page.others.message_format_common.settings."; + const label_title = t(locale_base_path + "title"); + + const LABEL_ORIGINAL = t(locale_base_path + "original"); + const LABEL_TRANSLATED = t(locale_base_path + "translated"); + const LABEL_FOR_MULTI_TRANSLATION = t(locale_base_path + "for_multi_translation"); + + const replaceValue = (value) => { + if (value === "") return ""; + + const replaced = value.replace(/\\n/g, "\n"); + return replaced; + }; + + const handleChange = (parent_key, child_key) => (e) => { + const rawValue = e.target.value; + const parsedValue = replaceValue(rawValue); + + if (child_key !== undefined) { + setFunction({ + ...variable, + [parent_key]: { + ...variable[parent_key], + [child_key]: parsedValue + } + }); + } else { + setFunction({ + ...variable, + [parent_key]: parsedValue + }); + } + }; + + const toUiValue = (v) => { + if (typeof v === "string") { + return v.replace(/\n/g, "\\n"); + } + console.log("Empty"); + + return v ?? ""; + }; + + const resetFunction = () => { + if (format_id === "send") { + setFunction(ui_configs.send_message_format_parts); + } else if (format_id === "received") { + setFunction(ui_configs.received_message_format_parts); + } + }; + + const SwapButton = ({ variable, setFunction }) => { + const swapMessageAndTranslate = () => { + setFunction({ ...variable, translation_first: !variable.translation_first }); + }; + + return ( +
+

{variable.translation_first ? LABEL_TRANSLATED : LABEL_ORIGINAL}

+ Swap Icon +

{variable.translation_first ? LABEL_ORIGINAL : LABEL_TRANSLATED}

+
+ ); + }; + + return ( +
+

{label_title}

+
+
+ +
+ { !variable.translation_first ? +
+
+ <_Entry ui_variable={toUiValue(variable.message.prefix)} width={ENTRY_WIDTH} onChange={handleChange("message", "prefix")} /> +

{LABEL_ORIGINAL}

+ <_Entry ui_variable={toUiValue(variable.message.suffix)} width={ENTRY_WIDTH} onChange={handleChange("message", "suffix")} /> +
+
+ <_Entry ui_variable={toUiValue(variable.separator)} width={ENTRY_WIDTH} onChange={handleChange("separator")} /> +
+
+ <_Entry ui_variable={toUiValue(variable.translation.prefix)} width={ENTRY_WIDTH} onChange={handleChange("translation", "prefix")} /> +

{LABEL_TRANSLATED}

+ <_Entry ui_variable={toUiValue(variable.translation.suffix)} width={ENTRY_WIDTH} onChange={handleChange("translation", "suffix")} /> +
+
+ : +
+
+ <_Entry ui_variable={toUiValue(variable.translation.prefix)} width={ENTRY_WIDTH} onChange={handleChange("translation", "prefix")} /> +

{LABEL_TRANSLATED}

+ <_Entry ui_variable={toUiValue(variable.translation.suffix)} width={ENTRY_WIDTH} onChange={handleChange("translation", "suffix")} /> +
+
+ <_Entry ui_variable={toUiValue(variable.separator)} width={ENTRY_WIDTH} onChange={handleChange("separator")} /> +
+
+ <_Entry ui_variable={toUiValue(variable.message.prefix)} width={ENTRY_WIDTH} onChange={handleChange("message", "prefix")} /> +

{LABEL_ORIGINAL}

+ <_Entry ui_variable={toUiValue(variable.message.suffix)} width={ENTRY_WIDTH} onChange={handleChange("message", "suffix")} /> +
+
+ } + { format_id === "send" && +
+

{LABEL_FOR_MULTI_TRANSLATION}

+
+

{LABEL_TRANSLATED}

+ <_Entry ui_variable={toUiValue(variable.translation.separator)} width={ENTRY_WIDTH} onChange={handleChange("translation", "separator")} /> +

{LABEL_TRANSLATED}

+
+
+ } +
+ +
+
+
+ ); +}; \ No newline at end of file diff --git a/src-ui/app/config_page/setting_section/setting_box/_components/message_format/MessageFormat.module.scss b/src-ui/app/config_page/setting_section/setting_box/_components/message_format/MessageFormat.module.scss new file mode 100644 index 00000000..18244109 --- /dev/null +++ b/src-ui/app/config_page/setting_section/setting_box/_components/message_format/MessageFormat.module.scss @@ -0,0 +1,200 @@ +.container { + display: flex; + justify-content: center; + width: 100%; + gap: 2.6rem; + padding-bottom: 2rem; + margin: 1rem 0; + &.is_break_point { + flex-direction: column; + gap: 2.2rem; + align-items: center; + .border { + height: 0.1rem; + width: 60%; + margin: 0; + flex-shrink: 0; + } + .show_more_container { + margin-top: 2rem; + } + .example_container { + gap: 0; + } + .message_format_settings_container { + gap: 0; + } + } +} + +.border { + height: auto; + width: 0.1rem; + background-color: var(--dark_800_color); + margin: 3.2rem 0; + flex-shrink: 0; +} + +.section_title { + font-size: 1.4rem; + text-align: center; + width: 100%; +} + +.example_container { + display: flex; + flex-direction: column; + gap: 2rem; + min-width: 14rem; + max-width: 34rem; + width: 100%; +} + +.example_view_container { + display: flex; + flex-direction: column; + gap: 1.2rem; +} + +.example_wrapper { + display: flex; + flex-direction: column; + align-items: center; + gap: 0.4rem; +} +.example_label { + font-size: 1.4rem; + text-align: start; + width: 100%; + color: var(--dark_basic_text_color); +} +.example_chatbox { + padding: 0.6rem; + background-color: #3A4554; + border-radius: 1rem; + width: 100%; + text-align: center; +} + +.example_text { + font-size: 1.2rem; +} + +.show_more_container { + width: 100%; + display: flex; + justify-content: center; + align-items: center; + padding: 0.6rem 0; + cursor: pointer; + border-radius: 0.6rem; + &:hover { + background-color: var(--dark_850_color); + } + &:active { + background-color: var(--dark_875_color); + } +} + +.arrow_left_svg { + width: 2rem; + color: var(--dark_450_color); + &.to_down { + transform: rotate(-90deg); + } + &.to_up { + transform: rotate(90deg); + } +} + +.message_format_settings_container { + flex-direction: column; + display: flex; + align-items: center; + flex-shrink: 0; + gap: 2rem; +} + +.message_format_settings_wrapper { + display: flex; + flex-direction: column; + gap: 3.8rem; + width: 34rem; + flex-shrink: 0; +} + +.swap_button_container { + width: 100%; + display: flex; + justify-content: end; +} + +.swap_button_wrapper { + display: flex; + justify-content: center; + align-items: center; + gap: 0.8rem; + padding: 0.6rem 1.2rem; + border-radius: 0.4rem; + background-color: var(--dark_850_color); + cursor: pointer; + &:hover { + background-color: var(--dark_800_color); + } + &:active { + background-color: var(--dark_900_color); + } +} + +.swap_text { + font-size: 1.4rem; +} + +.swap_img { + width: 2rem; +} + + +.input_wrapper { + width: 100%; + display: flex; + flex-direction: column; + justify-content: center; + align-items: center; + gap: 1.8rem; +} + +.input_contents { + width: 100%; + display: flex; + justify-content: center; + align-items: center; + gap: 1rem; + color: var(--dark_basic_text_color); +} + +.preset_text { + font-size: 1.6rem; + text-align: center; + flex-shrink: 0; + color: var(--dark_basic_text_color); +} + +.multi_translation_input_wrapper { + display: flex; + flex-direction: column; + gap: 1rem; + justify-content: center; + color: var(--dark_basic_text_color); +} + +.multi_translation_title { + font-size: 1.2rem; +} + +.reset_button_wrapper { + width: 100%; + display: flex; + justify-content: end; + align-items: center; +} \ No newline at end of file diff --git a/src-ui/app/config_page/setting_section/setting_box/_templates/Templates.jsx b/src-ui/app/config_page/setting_section/setting_box/_templates/Templates.jsx index b25af8b9..b23f8043 100644 --- a/src-ui/app/config_page/setting_section/setting_box/_templates/Templates.jsx +++ b/src-ui/app/config_page/setting_section/setting_box/_templates/Templates.jsx @@ -18,6 +18,7 @@ import { WordFilter, WordFilterListToggleComponent, DownloadModels, + MessageFormat, } from "../_components/"; import { Checkbox } from "@common_components"; @@ -129,4 +130,17 @@ export const WordFilterContainer = (props) => ( export const DownloadModelsContainer = (props) => ( -); \ No newline at end of file +); + +export const MessageFormatContainer = (props) => { + return ( +
+
+ +
+
+ +
+
+ ); +}; \ No newline at end of file diff --git a/src-ui/app/config_page/setting_section/setting_box/others/Others.jsx b/src-ui/app/config_page/setting_section/setting_box/others/Others.jsx index 1baf00a5..65027ef3 100644 --- a/src-ui/app/config_page/setting_section/setting_box/others/Others.jsx +++ b/src-ui/app/config_page/setting_section/setting_box/others/Others.jsx @@ -8,6 +8,7 @@ import { import { CheckboxContainer, + MessageFormatContainer, } from "../_templates/Templates"; import { @@ -39,6 +40,11 @@ export const Others = () => {
+
+ + + +
); }; @@ -151,4 +157,48 @@ const SendReceivedMessageToVrcContainer = () => { toggleFunction={toggleEnableSendReceivedMessageToVrc} /> ); +}; + +const SendMessageFormatPartsContainer = () => { + const { t } = useI18n(); + const { + currentSendMessageFormatParts, + setSendMessageFormatParts, + currentMessageFormat_ExampleViewFilter, + toggleMessageFormat_ExampleViewFilter, + } = useOthers(); + + return ( + + ); +}; + +const ReceivedMessageFormatPartsContainer = () => { + const { t } = useI18n(); + const { + currentReceivedMessageFormatParts, + setReceivedMessageFormatParts, + currentMessageFormat_ExampleViewFilter, + toggleMessageFormat_ExampleViewFilter, + } = useOthers(); + + return ( + + ); }; \ No newline at end of file diff --git a/src-ui/app/config_page/setting_section/setting_box/vr/Vr.jsx b/src-ui/app/config_page/setting_section/setting_box/vr/Vr.jsx index 31c38816..4bd9b6f5 100644 --- a/src-ui/app/config_page/setting_section/setting_box/vr/Vr.jsx +++ b/src-ui/app/config_page/setting_section/setting_box/vr/Vr.jsx @@ -14,12 +14,12 @@ import { SectionLabelComponent, } from "../_components/"; +import { ResetButton } from "@common_components"; + import { useVr, } from "@logics_configs"; -import RedoSvg from "@images/redo.svg?react"; - import SquareSvg from "@images/square.svg?react"; import TriangleSvg from "@images/triangle.svg?react"; import { randomIntMinMax } from "@utils"; @@ -528,13 +528,6 @@ const CommonSettingsContainer = () => { ); }; -const ResetButton = ({onClickFunction}) => { - return ( - - ); -}; const SendSampleTextToggleButton = () => { const { t } = useI18n(); diff --git a/src-ui/app/config_page/setting_section/setting_box/vr/Vr.module.scss b/src-ui/app/config_page/setting_section/setting_box/vr/Vr.module.scss index 9d0963e8..a2a76261 100644 --- a/src-ui/app/config_page/setting_section/setting_box/vr/Vr.module.scss +++ b/src-ui/app/config_page/setting_section/setting_box/vr/Vr.module.scss @@ -301,34 +301,6 @@ @include variable-button-wrapper(bottom, 50%, right, -60%, -45deg); } - - -.slider_reset_button { - background-color: var(--dark_875_color); - padding: 0.6rem; - display: flex; - justify-content: center; - align-items: center; - border-radius: 0.4rem; - flex-shrink: 0; - &:hover { - background-color: var(--dark_825_color); - & .slider_reset_svg { - color: var(--dark_200_color); - } - } - &:active { - background-color: var(--dark_925_color); - } -} - -.slider_reset_svg { - width: 1.4rem; - color: var(--dark_550_color); -} - - - .other_controls { margin-top: 6rem; display: flex; diff --git a/src-ui/common_components/index.js b/src-ui/common_components/index.js index 177161eb..e047306c 100644 --- a/src-ui/common_components/index.js +++ b/src-ui/common_components/index.js @@ -1,2 +1,3 @@ export { Checkbox } from "./checkbox/Checkbox"; -export { HomepageLinkButton } from "./homepage_link_button/HomepageLinkButton"; \ No newline at end of file +export { HomepageLinkButton } from "./homepage_link_button/HomepageLinkButton"; +export { ResetButton } from "./reset_button/ResetButton"; \ No newline at end of file diff --git a/src-ui/common_components/reset_button/ResetButton.jsx b/src-ui/common_components/reset_button/ResetButton.jsx new file mode 100644 index 00000000..65974739 --- /dev/null +++ b/src-ui/common_components/reset_button/ResetButton.jsx @@ -0,0 +1,10 @@ +import styles from "./ResetButton.module.scss"; +import RedoSvg from "@images/redo.svg?react"; + +export const ResetButton = ({ onClickFunction }) => { + return ( + + ); +}; \ No newline at end of file diff --git a/src-ui/common_components/reset_button/ResetButton.module.scss b/src-ui/common_components/reset_button/ResetButton.module.scss new file mode 100644 index 00000000..9be83c07 --- /dev/null +++ b/src-ui/common_components/reset_button/ResetButton.module.scss @@ -0,0 +1,24 @@ +.reset_button { + width: fit-content; + background-color: var(--dark_875_color); + padding: 0.6rem; + display: flex; + justify-content: center; + align-items: center; + border-radius: 0.4rem; + flex-shrink: 0; + &:hover { + background-color: var(--dark_825_color); + & .reset_svg { + color: var(--dark_200_color); + } + } + &:active { + background-color: var(--dark_925_color); + } +} + +.reset_svg { + width: 1.4rem; + color: var(--dark_550_color); +} \ No newline at end of file diff --git a/src-ui/logics/configs/others/useOthers.js b/src-ui/logics/configs/others/useOthers.js index c8a417d6..c2b0179f 100644 --- a/src-ui/logics/configs/others/useOthers.js +++ b/src-ui/logics/configs/others/useOthers.js @@ -6,6 +6,9 @@ import { useStore_EnableSendMessageToVrc, useStore_EnableNotificationVrcSfx, useStore_EnableSendReceivedMessageToVrc, + useStore_MessageFormat_ExampleViewFilter, + useStore_SendMessageFormatParts, + useStore_ReceivedMessageFormatParts, } from "@store"; import { useStdoutToPython } from "@useStdoutToPython"; import { useNotificationStatus } from "@logics_common"; @@ -29,6 +32,12 @@ export const useOthers = () => { // Speaker2Chatbox // Send Received Message To VRC const { currentEnableSendReceivedMessageToVrc, updateEnableSendReceivedMessageToVrc, pendingEnableSendReceivedMessageToVrc } = useStore_EnableSendReceivedMessageToVrc(); + // Message Formats + const { currentMessageFormat_ExampleViewFilter, updateMessageFormat_ExampleViewFilter, pendingMessageFormat_ExampleViewFilter } = useStore_MessageFormat_ExampleViewFilter(); + // Send + const { currentSendMessageFormatParts, updateSendMessageFormatParts, pendingSendMessageFormatParts } = useStore_SendMessageFormatParts(); + // Received + const { currentReceivedMessageFormatParts, updateReceivedMessageFormatParts, pendingReceivedMessageFormatParts } = useStore_ReceivedMessageFormatParts(); const { showNotification_SaveSuccess } = useNotificationStatus(); @@ -178,6 +187,53 @@ export const useOthers = () => { showNotification_SaveSuccess(); }; + // Message Formats + // Send + const getSendMessageFormatParts = () => { + pendingSendMessageFormatParts(); + asyncStdoutToPython("/get/data/send_message_format_parts"); + }; + + const setSendMessageFormatParts = (message_format_parts) => { + pendingSendMessageFormatParts(); + asyncStdoutToPython("/set/data/send_message_format_parts", message_format_parts); + }; + + const setSuccessSendMessageFormatParts = (message_format_parts) => { + updateSendMessageFormatParts(message_format_parts); + showNotification_SaveSuccess(); + }; + + // Received + const getReceivedMessageFormatParts = () => { + pendingReceivedMessageFormatParts(); + asyncStdoutToPython("/get/data/received_message_format_parts"); + }; + + const setReceivedMessageFormatParts = (message_format_parts) => { + pendingReceivedMessageFormatParts(); + asyncStdoutToPython("/set/data/received_message_format_parts", message_format_parts); + }; + + const setSuccessReceivedMessageFormatParts = (message_format_parts) => { + updateReceivedMessageFormatParts(message_format_parts); + showNotification_SaveSuccess(); + }; + + + const toggleMessageFormat_ExampleViewFilter = (id) => { + pendingMessageFormat_ExampleViewFilter(); + if (["send", "received"].includes(id) === false) return console.error(`id should be small case 'send' or 'received'. got id: ${id}`); + + updateMessageFormat_ExampleViewFilter({ + ...currentMessageFormat_ExampleViewFilter.data, + [id]: currentMessageFormat_ExampleViewFilter.data[id] === "Simplified" + ? "All" + : "Simplified" + }); + }; + + return { // Auto Clear Message Input Box currentEnableAutoClearMessageInputBox, @@ -230,5 +286,22 @@ export const useOthers = () => { toggleEnableSendReceivedMessageToVrc, updateEnableSendReceivedMessageToVrc, setSuccessEnableSendReceivedMessageToVrc, + + // Message Formats + currentMessageFormat_ExampleViewFilter, + toggleMessageFormat_ExampleViewFilter, + // Send + currentSendMessageFormatParts, + updateSendMessageFormatParts, + getSendMessageFormatParts, + setSendMessageFormatParts, + setSuccessSendMessageFormatParts, + + // Received + currentReceivedMessageFormatParts, + updateReceivedMessageFormatParts, + getReceivedMessageFormatParts, + setReceivedMessageFormatParts, + setSuccessReceivedMessageFormatParts, }; }; \ No newline at end of file diff --git a/src-ui/logics/useReceiveRoutes.js b/src-ui/logics/useReceiveRoutes.js index 00c48a0b..c9380612 100644 --- a/src-ui/logics/useReceiveRoutes.js +++ b/src-ui/logics/useReceiveRoutes.js @@ -275,6 +275,12 @@ export const ROUTE_META_LIST = [ { endpoint: "/get/data/notification_vrc_sfx", ns: configs, hook_name: "useOthers", method_name: "updateEnableNotificationVrcSfx" }, { endpoint: "/set/enable/notification_vrc_sfx", ns: configs, hook_name: "useOthers", method_name: "setSuccessEnableNotificationVrcSfx" }, { endpoint: "/set/disable/notification_vrc_sfx", ns: configs, hook_name: "useOthers", method_name: "setSuccessEnableNotificationVrcSfx" }, + { endpoint: "/set/disable/notification_vrc_sfx", ns: configs, hook_name: "useOthers", method_name: "setSuccessEnableNotificationVrcSfx" }, + + { endpoint: "/get/data/send_message_format_parts", ns: configs, hook_name: "useOthers", method_name: "updateSendMessageFormatParts" }, + { endpoint: "/set/data/send_message_format_parts", ns: configs, hook_name: "useOthers", method_name: "setSuccessSendMessageFormatParts" }, + { endpoint: "/get/data/received_message_format_parts", ns: configs, hook_name: "useOthers", method_name: "updateReceivedMessageFormatParts" }, + { endpoint: "/set/data/received_message_format_parts", ns: configs, hook_name: "useOthers", method_name: "setSuccessReceivedMessageFormatParts" }, // Hotkeys { endpoint: "/get/data/hotkeys", ns: configs, hook_name: "useHotkeys", method_name: "updateHotkeys" }, diff --git a/src-ui/store.js b/src-ui/store.js index 7d2fac28..9241ad41 100644 --- a/src-ui/store.js +++ b/src-ui/store.js @@ -274,6 +274,37 @@ export const { atomInstance: Atom_EnableVrcMicMuteSync, useHook: useStore_Enable export const { atomInstance: Atom_EnableSendMessageToVrc, useHook: useStore_EnableSendMessageToVrc } = createAtomWithHook(true, "EnableSendMessageToVrc"); export const { atomInstance: Atom_EnableSendReceivedMessageToVrc, useHook: useStore_EnableSendReceivedMessageToVrc } = createAtomWithHook(false, "EnableSendReceivedMessageToVrc"); export const { atomInstance: Atom_EnableNotificationVrcSfx, useHook: useStore_EnableNotificationVrcSfx } = createAtomWithHook(true, "EnableNotificationVrcSfx"); +export const { atomInstance: Atom_MessageFormat_ExampleViewFilter, useHook: useStore_MessageFormat_ExampleViewFilter } = createAtomWithHook({ + send: "Simplified", + received: "Simplified", +}, "MessageFormat_ExampleViewFilter"); +export const { atomInstance: Atom_SendMessageFormatParts, useHook: useStore_SendMessageFormatParts } = createAtomWithHook({ + message: { + prefix: "", + suffix: "" + }, + separator: "\n", + translation: { + prefix: "", + separator: "\n", + suffix: "" + }, + translation_first: false, +}, "SendMessageFormatParts"); +export const { atomInstance: Atom_ReceivedMessageFormatParts, useHook: useStore_ReceivedMessageFormatParts } = createAtomWithHook({ + message: { + prefix: "", + suffix: "" + }, + separator: "\n", + translation: { + prefix: "", + separator: "\n", + suffix: "" + }, + translation_first: false, +}, "ReceivedMessageFormatParts"); + // Hotkeys export const { atomInstance: Atom_Hotkeys, useHook: useStore_Hotkeys } = createAtomWithHook({ diff --git a/src-ui/ui_configs.js b/src-ui/ui_configs.js index 915d6a6b..e3bf85f2 100644 --- a/src-ui/ui_configs.js +++ b/src-ui/ui_configs.js @@ -49,6 +49,33 @@ export const ui_configs = { tracker: "LeftHand", }, + send_message_format_parts: { + message: { + prefix: "", + suffix: "" + }, + separator: "\n", + translation: { + prefix: "", + separator: "\n", + suffix: "" + }, + translation_first: false, + }, + received_message_format_parts: { + message: { + prefix: "", + suffix: "" + }, + separator: "\n", + translation: { + prefix: "", + separator: "\n", + suffix: "" + }, + translation_first: false, + }, + selectable_ui_languages: [ {id: "en", label: "English"}, {id: "ja", label: "日本語"},