diff --git a/README.md b/README.md index 5efb671..f39f749 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,7 @@ # Page Assist [![Join dialoqbase #welcome](https://img.shields.io/badge/discord-join%20chat-blue.svg)](https://discord.gg/bu54382uBd) +[![Twitter Follow](https://img.shields.io/twitter/follow/page_assist?style=social)](https://twitter.com/page_assist) Page Assist is an open-source browser extension that provides a sidebar and web UI for your local AI model. It allows you to interact with your model from any webpage. ## Installation diff --git a/package.json b/package.json index f7d9ebd..7f7ac74 100644 --- a/package.json +++ b/package.json @@ -7,8 +7,10 @@ "scripts": { "dev": "cross-env TARGET=chrome wxt", "dev:firefox": "cross-env TARGET=firefox wxt -b firefox", + "dev:edge": "cross-env TARGET=chrome wxt -b edge", "build": "cross-env TARGET=chrome wxt build", "build:firefox": "cross-env TARGET=firefox wxt build -b firefox", + "build:edge": "cross-env TARGET=chrome wxt build -b edge", "zip": "cross-env TARGET=chrome wxt zip", "zip:firefox": "cross-env TARGET=firefox wxt zip -b firefox", "compile": "tsc --noEmit", diff --git a/src/assets/locale/ar/settings.json b/src/assets/locale/ar/settings.json index a93eafd..10079f9 100644 --- a/src/assets/locale/ar/settings.json +++ b/src/assets/locale/ar/settings.json @@ -119,6 +119,9 @@ }, "ssmlEnabled": { "label": "تمكين SSML (لغة ترميز توليف الكلام)" + }, + "removeReasoningTagTTS": { + "label": "إزالة علامة التفكير من تحويل النص إلى كلام" } } }, diff --git a/src/assets/locale/da/settings.json b/src/assets/locale/da/settings.json index 74a2346..a790db0 100644 --- a/src/assets/locale/da/settings.json +++ b/src/assets/locale/da/settings.json @@ -113,6 +113,9 @@ }, "ssmlEnabled": { "label": "Aktiver SSML (Speech Synthesis Markup Language)" + }, + "removeReasoningTagTTS": { + "label": "Fjern Ræsonnement Tag fra TTS" } } }, diff --git a/src/assets/locale/de/settings.json b/src/assets/locale/de/settings.json index d8a106d..81e5ca0 100644 --- a/src/assets/locale/de/settings.json +++ b/src/assets/locale/de/settings.json @@ -116,6 +116,9 @@ }, "ssmlEnabled": { "label": "SSML (Speech Synthesis Markup Language) aktivieren" + }, + "removeReasoningTagTTS": { + "label": "Reasoning-Tag aus Text-zu-Sprache entfernen" } } }, diff --git a/src/assets/locale/en/settings.json b/src/assets/locale/en/settings.json index c7c75b7..4fe21cc 100644 --- a/src/assets/locale/en/settings.json +++ b/src/assets/locale/en/settings.json @@ -122,6 +122,9 @@ }, "responseSplitting": { "label": "Response Splitting" + }, + "removeReasoningTagTTS": { + "label": "Remove Reasoning Tag from TTS" } } }, diff --git a/src/assets/locale/es/settings.json b/src/assets/locale/es/settings.json index 4ff0ac6..a56037d 100644 --- a/src/assets/locale/es/settings.json +++ b/src/assets/locale/es/settings.json @@ -116,8 +116,10 @@ }, "ssmlEnabled": { "label": "Habilitar SSML (Speech Synthesis Markup Language)" - } - } + }, + "removeReasoningTagTTS": { + "label": "Eliminar Etiqueta de Razonamiento del TTS" + } } }, "manageModels": { "title": "Administar de Modelos", diff --git a/src/assets/locale/fa/settings.json b/src/assets/locale/fa/settings.json index a66db85..badea7a 100644 --- a/src/assets/locale/fa/settings.json +++ b/src/assets/locale/fa/settings.json @@ -113,6 +113,9 @@ }, "ssmlEnabled": { "label": "فعال کردن SSML (Speech Synthesis Markup Language)" + }, + "removeReasoningTagTTS": { + "label": "حذف برچسب استدلال از تبدیل متن به گفتار" } } }, diff --git a/src/assets/locale/fr/settings.json b/src/assets/locale/fr/settings.json index 8dcfcba..565b628 100644 --- a/src/assets/locale/fr/settings.json +++ b/src/assets/locale/fr/settings.json @@ -116,6 +116,9 @@ }, "ssmlEnabled": { "label": "Activer SSML (langage de balisage de synthèse vocale)" + }, + "removeReasoningTagTTS": { + "label": "Supprimer la balise de raisonnement de la synthèse vocale" } } }, diff --git a/src/assets/locale/it/settings.json b/src/assets/locale/it/settings.json index 7f1e71d..461fd40 100644 --- a/src/assets/locale/it/settings.json +++ b/src/assets/locale/it/settings.json @@ -116,6 +116,9 @@ }, "ssmlEnabled": { "label": "Abilita SSML (Speech Synthesis Markup Language)" + }, + "removeReasoningTagTTS": { + "label": "Rimuovi Tag di Ragionamento dal TTS" } } }, diff --git a/src/assets/locale/ja-JP/settings.json b/src/assets/locale/ja-JP/settings.json index 8c06300..ff1b8bc 100644 --- a/src/assets/locale/ja-JP/settings.json +++ b/src/assets/locale/ja-JP/settings.json @@ -119,6 +119,9 @@ }, "ssmlEnabled": { "label": "SSML (Speech Synthesis Markup Language) を有効にする" + }, + "removeReasoningTagTTS": { + "label": "テキスト読み上げから推論タグを削除" } } }, diff --git a/src/assets/locale/ko/settings.json b/src/assets/locale/ko/settings.json index f7950ea..a1eb539 100644 --- a/src/assets/locale/ko/settings.json +++ b/src/assets/locale/ko/settings.json @@ -119,6 +119,9 @@ }, "ssmlEnabled": { "label": "SSML (Speech Synthesis Markup Language) 활성화" + }, + "removeReasoningTagTTS": { + "label": "TTS에서 추론 태그 제거" } } }, diff --git a/src/assets/locale/ml/settings.json b/src/assets/locale/ml/settings.json index 13700f3..9b7fc44 100644 --- a/src/assets/locale/ml/settings.json +++ b/src/assets/locale/ml/settings.json @@ -119,6 +119,9 @@ }, "ssmlEnabled": { "label": "SSML (സ്പീച്ച് സിന്തസിസ് മാർക്കപ്പ് ലാംഗ്വേജ്) പ്രവർത്തനക്ഷമമാക്കുക" + }, + "removeReasoningTagTTS": { + "label": "ടിടിഎസിൽ നിന്ന് റീസണിംഗ് ടാഗ് നീക്കം ചെയ്യുക" } } }, diff --git a/src/assets/locale/no/settings.json b/src/assets/locale/no/settings.json index 4b9c66d..c7e0b1c 100644 --- a/src/assets/locale/no/settings.json +++ b/src/assets/locale/no/settings.json @@ -116,6 +116,9 @@ }, "ssmlEnabled": { "label": "Aktiver SSML (Speech Synthesis Markup Language)" + }, + "removeReasoningTagTTS": { + "label": "Fjern Resonneringsmerke fra TTS" } } }, diff --git a/src/assets/locale/pt-BR/settings.json b/src/assets/locale/pt-BR/settings.json index dc186ef..d2d087f 100644 --- a/src/assets/locale/pt-BR/settings.json +++ b/src/assets/locale/pt-BR/settings.json @@ -116,6 +116,9 @@ }, "ssmlEnabled": { "label": "Ativar SSML (Linguagem de Marcação de Síntese de Fala)" + }, + "removeReasoningTagTTS": { + "label": "Remover Tag de Raciocínio do TTS" } } }, diff --git a/src/assets/locale/ru/settings.json b/src/assets/locale/ru/settings.json index 80592e4..e8ad036 100644 --- a/src/assets/locale/ru/settings.json +++ b/src/assets/locale/ru/settings.json @@ -117,6 +117,9 @@ }, "ssmlEnabled": { "label": "Включить SSML (язык разметки синтеза речи)" + }, + "removeReasoningTagTTS": { + "label": "Удалить тег рассуждения из TTS" } } }, diff --git a/src/assets/locale/sv/settings.json b/src/assets/locale/sv/settings.json index 84f38dd..1cbee7f 100644 --- a/src/assets/locale/sv/settings.json +++ b/src/assets/locale/sv/settings.json @@ -116,6 +116,9 @@ }, "ssmlEnabled": { "label": "Aktivera SSML (Speech Synthesis Markup Language)" + }, + "removeReasoningTagTTS": { + "label": "Ta bort resonemangstagg från Text till Tal" } } }, diff --git a/src/assets/locale/uk/settings.json b/src/assets/locale/uk/settings.json index 3d937a8..e803248 100644 --- a/src/assets/locale/uk/settings.json +++ b/src/assets/locale/uk/settings.json @@ -116,6 +116,9 @@ }, "ssmlEnabled": { "label": "Ввімкнути SSML (Мова Розмітки для Синтезу Голосу)" + }, + "removeReasoningTagTTS": { + "label": "Видалити тег міркування з TTS" } } }, diff --git a/src/assets/locale/zh/settings.json b/src/assets/locale/zh/settings.json index ccaf4eb..f201179 100644 --- a/src/assets/locale/zh/settings.json +++ b/src/assets/locale/zh/settings.json @@ -119,6 +119,9 @@ }, "ssmlEnabled": { "label": "启用SSML(语音合成标记语言)" + }, + "removeReasoningTagTTS": { + "label": "从语音合成中移除推理标签" } } }, diff --git a/src/assets/tailwind.css b/src/assets/tailwind.css index ee4b772..1ef50b0 100644 --- a/src/assets/tailwind.css +++ b/src/assets/tailwind.css @@ -13,6 +13,12 @@ @tailwind base; @tailwind components; @tailwind utilities; +@layer utilities { + .mask-bottom-fade { + mask-image: linear-gradient(0deg, transparent 0, #000 160px); + -webkit-mask-image: linear-gradient(0deg, transparent 0, #000 160px); + } +} diff --git a/src/components/Common/CodeBlock.tsx b/src/components/Common/CodeBlock.tsx index af1e363..8e660c6 100644 --- a/src/components/Common/CodeBlock.tsx +++ b/src/components/Common/CodeBlock.tsx @@ -42,10 +42,36 @@ export const CodeBlock: FC = ({ language, value }) => { return ( <> -
-
- {language} +
+
+
+ {language || "text"} +
+
+
+ + + + + + +
+
+ {/*
+ {language}
+
*/} + + {value} +
- - {value} -
{previewVisible && ( { const { t } = useTranslation("common") const { cancel, isSpeaking, speak } = useTTS() return ( -
-
-
-
-
- {props.isBot ? ( - !props.botAvatar ? ( -
- ) : ( - props.botAvatar - ) - ) : !props.userAvatar ? ( -
+
+ {/*
*/} +
+
+
+ {props.isBot ? ( + !props.botAvatar ? ( +
) : ( - props.userAvatar - )} -
-
-
- - {props.isBot - ? props.name === "chrome::gemini-nano::page-assist" - ? "Gemini Nano" - : removeModelSuffix( - props.name?.replaceAll(/accounts\/[^\/]+\/models\//g, "") - ) - : "You"} - - - {props.isBot && - props.isSearchingInternet && - props.currentMessageIndex === props.totalMessages - 1 ? ( - - ) : null} -
- {props?.message_type && ( - - {t(`copilot.${props?.message_type}`)} - - )} -
-
- {!editMode ? ( - props.isBot ? ( - <> - {parseReasoning(props.message).map((e, i) => { - if (e.type === "reasoning") { - return ( - - - {t("reasoning.thinking")} - -
- ) : ( - t("reasoning.thought", { - time: humanizeMilliseconds( - props.reasoningTimeTaken - ) - }) - ), - children: - } - ]} - /> - ) - } - - return - })} - - ) : ( -

- {props.message} -

- ) - ) : ( - setEditMode(false)} - isBot={props.isBot} - /> - )} -
- {/* source if available */} - {props.images && - props.images.filter((img) => img.length > 0).length > 0 && ( -
- {props.images - .filter((image) => image.length > 0) - .map((image, index) => ( - Uploaded Image - ))} -
- )} - - {props.isBot && props?.sources && props?.sources.length > 0 && ( - - {t("citations")} -
- ), - children: ( -
- {props?.sources?.map((source, index) => ( - - ))} -
- ) - } - ]} - /> - )} - {!props.isProcessing && !editMode && ( -
- {props.isTTSEnabled && ( - - - - )} - {props.isBot && ( - <> - {!props.hideCopy && ( - - - - )} - - {props.generationInfo && ( - - } - title={t("generationInfo")}> - - - )} - - {!props.hideEditAndRegenerate && - props.currentMessageIndex === props.totalMessages - 1 && ( - - - - )} - - )} - {!props.hideEditAndRegenerate && ( - - - - )} -
+ props.botAvatar + ) + ) : !props.userAvatar ? ( +
+ ) : ( + props.userAvatar )}
+
+ + {props.isBot + ? props.name === "chrome::gemini-nano::page-assist" + ? "Gemini Nano" + : removeModelSuffix( + props.name?.replaceAll(/accounts\/[^\/]+\/models\//g, "") + ) + : "You"} + + + {props.isBot && + props.isSearchingInternet && + props.currentMessageIndex === props.totalMessages - 1 ? ( + + ) : null} +
+ {props?.message_type && ( + + {t(`copilot.${props?.message_type}`)} + + )} +
+
+ {!editMode ? ( + props.isBot ? ( + <> + {parseReasoning(props.message).map((e, i) => { + if (e.type === "reasoning") { + return ( + + + {t("reasoning.thinking")} + +
+ ) : ( + t("reasoning.thought", { + time: humanizeMilliseconds( + props.reasoningTimeTaken + ) + }) + ), + children: + } + ]} + /> + ) + } + + return + })} + + ) : ( +

+ {props.message} +

+ ) + ) : ( + setEditMode(false)} + isBot={props.isBot} + /> + )} +
+ {/* source if available */} + {props.images && + props.images.filter((img) => img.length > 0).length > 0 && ( +
+ {props.images + .filter((image) => image.length > 0) + .map((image, index) => ( + Uploaded Image + ))} +
+ )} + + {props.isBot && props?.sources && props?.sources.length > 0 && ( + + {t("citations")} +
+ ), + children: ( +
+ {props?.sources?.map((source, index) => ( + + ))} +
+ ) + } + ]} + /> + )} + {!props.isProcessing && !editMode ? ( +
+ {props.isTTSEnabled && ( + + + + )} + {props.isBot && ( + <> + {!props.hideCopy && ( + + + + )} + + {props.generationInfo && ( + + } + title={t("generationInfo")}> + + + )} + + {!props.hideEditAndRegenerate && + props.currentMessageIndex === props.totalMessages - 1 && ( + + + + )} + + )} + {!props.hideEditAndRegenerate && ( + + + + )} +
+ ) : ( + // add invisible div to prevent layout shift +
+
+
+ )} +
+ {/*
*/}
) } diff --git a/src/components/Layouts/Header.tsx b/src/components/Layouts/Header.tsx index 48020ad..e4e2567 100644 --- a/src/components/Layouts/Header.tsx +++ b/src/components/Layouts/Header.tsx @@ -91,7 +91,7 @@ export const Header: React.FC = ({ return (
@@ -209,12 +209,6 @@ export const Header: React.FC = ({
- {/* {pathname === "/" && - messages.length > 0 && - !streaming && - shareModeEnabled && ( - - )} */} {messages.length > 0 && !streaming && ( = ({ -
+
diff --git a/src/components/Layouts/Layout.tsx b/src/components/Layouts/Layout.tsx index 3a6b6b8..a5ae02d 100644 --- a/src/components/Layouts/Layout.tsx +++ b/src/components/Layouts/Layout.tsx @@ -36,72 +36,75 @@ export default function OptionLayout({ const { setSystemPrompt } = useStoreChatModelSettings() return ( - <> -
-
-
{children}
-
+
+
+
+
+
+ {/*
*/} + {children} + {/*
*/} + + {t("sidebarTitle")} - - {t("sidebarTitle")} - - - - -
- } - placement="left" - closeIcon={null} - onClose={() => setSidebarOpen(false)} - open={sidebarOpen}> - + + + +
+ } + placement="left" + closeIcon={null} onClose={() => setSidebarOpen(false)} - setMessages={setMessages} - setHistory={setHistory} - setHistoryId={setHistoryId} - setSelectedModel={setSelectedModel} - setSelectedSystemPrompt={setSelectedSystemPrompt} - clearChat={clearChat} - historyId={historyId} - setSystemPrompt={setSystemPrompt} - temporaryChat={temporaryChat} - history={history} - /> - + open={sidebarOpen}> + setSidebarOpen(false)} + setMessages={setMessages} + setHistory={setHistory} + setHistoryId={setHistoryId} + setSelectedModel={setSelectedModel} + setSelectedSystemPrompt={setSelectedSystemPrompt} + clearChat={clearChat} + historyId={historyId} + setSystemPrompt={setSystemPrompt} + temporaryChat={temporaryChat} + history={history} + /> + - - + + +
) } diff --git a/src/components/Layouts/NewChat.tsx b/src/components/Layouts/NewChat.tsx index fa8cab8..0353180 100644 --- a/src/components/Layouts/NewChat.tsx +++ b/src/components/Layouts/NewChat.tsx @@ -20,9 +20,7 @@ export const NewChat: React.FC = ({ clearChat }) => {