From bc29dab968fa40022c36aa2701ed23db1b4fb1a2 Mon Sep 17 00:00:00 2001 From: sageTheDM <info@photofuel.tech> Date: Tue, 24 Sep 2024 07:42:39 +0200 Subject: [PATCH 1/4] Fixed the responsive design --- app/components/Settings.tsx | 1 + app/styles/responsive.css | 8 ++++++-- 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/app/components/Settings.tsx b/app/components/Settings.tsx index 2f8b5d8..220e34f 100644 --- a/app/components/Settings.tsx +++ b/app/components/Settings.tsx @@ -579,6 +579,7 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( <li onClick={() => setActiveSection('theme')}>Theme</li> <li onClick={() => setActiveSection('foss')}>FOSS</li> <li onClick={() => setActiveSection('account')}>Account</li> + {/* Make something that can export and import all settings */} </ul> </div> <div className="settings-main"> diff --git a/app/styles/responsive.css b/app/styles/responsive.css index 31f563d..08818cf 100644 --- a/app/styles/responsive.css +++ b/app/styles/responsive.css @@ -12,7 +12,7 @@ position: relative; top: 0; left: 0; - margin-top: 5px; + margin-top: 0px; padding-top: 0; width: 100%; } @@ -23,7 +23,7 @@ flex-direction: column; align-items: center; width: 100vw; - overflow: hidden; + overflow: scroll; margin: 0; padding: 0; } @@ -111,6 +111,10 @@ background-color: var(--input-button-color); /* Use variable for button color */ color: var(--user-message-text-color); /* Use variable for button text color */ } + + .login-button button{ + margin: 20px 0; + } } /* Responsive adjustments for the settings */ From 7010be84ea7cb1569105b5e27e616c23d0524398 Mon Sep 17 00:00:00 2001 From: Patrick_Pluto <patrick_pluto@noreply.codeberg.org> Date: Tue, 24 Sep 2024 09:24:31 +0200 Subject: [PATCH 2/4] Uhmm fixed --- py/ai.py | 29 +++++++++++++++++++++++++++++ py/api.py | 13 ++++++++++--- py/requirements.txt | 3 +-- py/run.py | 7 ------- py/webapp.py | 1 - 5 files changed, 40 insertions(+), 13 deletions(-) delete mode 100644 py/run.py delete mode 100644 py/webapp.py diff --git a/py/ai.py b/py/ai.py index a8c5537..f78b3b7 100644 --- a/py/ai.py +++ b/py/ai.py @@ -1,5 +1,6 @@ from mistralai import Mistral from openai import OpenAI +import google.generativeai as genai import anthropic import ollama @@ -72,3 +73,31 @@ class AI: for text in stream.text_stream: with return_class.ai_response_lock: return_class.ai_response[access_token] += text + + @staticmethod + def process_google(model, messages, return_class, access_token, api_key): + + message = messages[-1]['content'] + messages.pop() + + system = None + if messages and messages[0]['role'] == 'system': + system = messages[0]['content'] + messages.pop(0) + + for msg in messages: + msg['parts'] = msg.pop('content') + + for msg in messages: + if msg['role'] == 'assistant': + msg['role'] = 'model' + + genai.configure(api_key=api_key) + model = genai.GenerativeModel("gemini-1.5-flash") + chat = model.start_chat( + system_instruction=system, + history=[ + {"role": "user", "parts": "Hello"}, + {"role": "model", "parts": "Great to meet you. What would you like to know?"}, + ] + ) diff --git a/py/api.py b/py/api.py index be44561..6c2d243 100644 --- a/py/api.py +++ b/py/api.py @@ -42,19 +42,22 @@ class API: return jsonify({'status': 200}) elif model_type == "mistral": api_key = data.get('api_key') - thread = threading.Thread(target=self.ai.process_mistralai, args=(ai_model, messages, self, access_token, api_key)) + thread = threading.Thread(target=self.ai.process_mistralai, + args=(ai_model, messages, self, access_token, api_key)) thread.start() thread.join() return jsonify({'status': 200}) elif model_type == "openai": api_key = data.get('api_key') - thread = threading.Thread(target=self.ai.process_openai, args=(ai_model, messages, self, access_token, api_key)) + thread = threading.Thread(target=self.ai.process_openai, + args=(ai_model, messages, self, access_token, api_key)) thread.start() thread.join() return jsonify({'status': 200}) elif model_type == "anthropic": api_key = data.get('api_key') - thread = threading.Thread(target=self.ai.process_anthropic, args=(ai_model, messages, self, access_token, api_key)) + thread = threading.Thread(target=self.ai.process_anthropic, + args=(ai_model, messages, self, access_token, api_key)) thread.start() thread.join() return jsonify({'status': 200}) @@ -118,3 +121,7 @@ class API: ssl_context = ("cert.pem", "key.pem") self.app.run(debug=True, host='0.0.0.0', port=5000) + + +api = API() +api.run() diff --git a/py/requirements.txt b/py/requirements.txt index 8a79dc1..bd93ad7 100644 --- a/py/requirements.txt +++ b/py/requirements.txt @@ -4,5 +4,4 @@ ollama mistralai openai anthropic -pyOpenSSL -pywebview \ No newline at end of file +pyOpenSSL \ No newline at end of file diff --git a/py/run.py b/py/run.py deleted file mode 100644 index 612d72e..0000000 --- a/py/run.py +++ /dev/null @@ -1,7 +0,0 @@ -import os -import webview - -os.system("python api.py") -webview.create_window('Hello world', 'http://localhost:3000') -webview.start() - diff --git a/py/webapp.py b/py/webapp.py deleted file mode 100644 index 8b13789..0000000 --- a/py/webapp.py +++ /dev/null @@ -1 +0,0 @@ - From 778bfd632e8a7ae4d1595237d88edd7d33780716 Mon Sep 17 00:00:00 2001 From: Patrick_Pluto <patrick_pluto@noreply.codeberg.org> Date: Tue, 24 Sep 2024 09:27:36 +0200 Subject: [PATCH 3/4] Thanks Google for not using standards. --- py/ai.py | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/py/ai.py b/py/ai.py index f78b3b7..5879e9d 100644 --- a/py/ai.py +++ b/py/ai.py @@ -93,11 +93,14 @@ class AI: msg['role'] = 'model' genai.configure(api_key=api_key) - model = genai.GenerativeModel("gemini-1.5-flash") + + model = genai.GenerativeModel(model) + chat = model.start_chat( system_instruction=system, - history=[ - {"role": "user", "parts": "Hello"}, - {"role": "model", "parts": "Great to meet you. What would you like to know?"}, - ] + history=messages ) + + response = chat.send_message(message, stream=True) + for chunk in response: + return_class.ai_response[access_token] += chunk.text From bb4095a3360591933e32da17b8887dd757381665 Mon Sep 17 00:00:00 2001 From: sageTheDM <info@photofuel.tech> Date: Tue, 24 Sep 2024 09:27:49 +0200 Subject: [PATCH 4/4] Broke the responsive once again and edited the settings --- app/components/Settings.tsx | 390 ++++++++++++++++++++++++--------- app/components/settingUtils.ts | 22 ++ tailwind.config.ts | 21 -- 3 files changed, 311 insertions(+), 122 deletions(-) create mode 100644 app/components/settingUtils.ts diff --git a/app/components/Settings.tsx b/app/components/Settings.tsx index 220e34f..ecc8a34 100644 --- a/app/components/Settings.tsx +++ b/app/components/Settings.tsx @@ -1,9 +1,22 @@ -import React, { useState, useEffect } from 'react'; +import React, { useState } from 'react'; +import { exportSettings, importSettings } from './settingUtils'; // Import utility functions const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ({ closeSettings, accountName }) => { const [activeSection, setActiveSection] = useState('general'); + const [preferredLanguage, setPreferredLanguage] = useState('en'); + const [preferredCurrency, setPreferredCurrency] = useState('usd'); + const [dateFormat, setDateFormat] = useState('mm/dd/yyyy'); + const [timeFormat, setTimeFormat] = useState('12-hour'); + const [timeZone, setTimeZone] = useState('GMT'); + const [disableOnlineAI, setDisableOnlineAI] = useState(false); + const [disableChatHistory, setDisableChatHistory] = useState(false); + const [disableAIMemory, setDisableAIMemory] = useState(false); + const [openSourceMode, setOpenSourceMode] = useState(false); + const [newName, setNewName] = useState(''); + const [newEmail, setNewEmail] = useState(''); + const [newPassword, setNewPassword] = useState(''); - // Theme settings state + // Theme settings state const [backgroundColor, setBackgroundColor] = useState<string>(getComputedStyle(document.documentElement).getPropertyValue('--background-color').trim()); const [textColor, setTextColor] = useState<string>(getComputedStyle(document.documentElement).getPropertyValue('--text-color').trim()); const [inputBackgroundColor, setInputBackgroundColor] = useState<string>(getComputedStyle(document.documentElement).getPropertyValue('--input-background-color').trim()); @@ -24,73 +37,111 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( const [fontFamily, setFontFamily] = useState<string>(getComputedStyle(document.documentElement).getPropertyValue('--font-family').trim()); const [fontSize, setFontSize] = useState<string>(getComputedStyle(document.documentElement).getPropertyValue('--font-size').trim()); - // General settings state - const [preferredLanguage, setPreferredLanguage] = useState<string>('English'); - const [preferredCurrency, setPreferredCurrency] = useState<string>('USD'); - const [dateFormat, setDateFormat] = useState<string>('MM/DD/YYYY'); - const [timeFormat, setTimeFormat] = useState<string>('12-hour'); - const [timeZone, setTimeZone] = useState<string>('UTC'); + // Theme selection + const [selectedTheme, setSelectedTheme] = useState<string>('default'); - // Privacy settings state - const [disableOnlineAI, setDisableOnlineAI] = useState<boolean>(false); - const [disableChatHistory, setDisableChatHistory] = useState<boolean>(false); - const [disableAIMemory, setDisableAIMemory] = useState<boolean>(false); + // Apply imported settings to the CSS variables + const applySettings = (settings: any) => { + if (settings.backgroundColor) { + setBackgroundColor(settings.backgroundColor); + document.documentElement.style.setProperty('--background-color', settings.backgroundColor); + } + + if (settings.textColor) { + setTextColor(settings.textColor); + document.documentElement.style.setProperty('--text-color', settings.textColor); + } + + if (settings.inputBackgroundColor) { + setInputBackgroundColor(settings.inputBackgroundColor); + document.documentElement.style.setProperty('--input-background-color', settings.inputBackgroundColor); + } + + if (settings.inputButtonColor) { + setInputButtonColor(settings.inputButtonColor); + document.documentElement.style.setProperty('--input-button-color', settings.inputButtonColor); + } + + if (settings.inputButtonHoverColor) { + setInputButtonHoverColor(settings.inputButtonHoverColor); + document.documentElement.style.setProperty('--input-button-hover-color', settings.inputButtonHoverColor); + } + + if (settings.userMessageBackgroundColor) { + setUserMessageBackgroundColor(settings.userMessageBackgroundColor); + document.documentElement.style.setProperty('--user-message-background-color', settings.userMessageBackgroundColor); + } + + if (settings.userMessageTextColor) { + setUserMessageTextColor(settings.userMessageTextColor); + document.documentElement.style.setProperty('--user-message-text-color', settings.userMessageTextColor); + } + + if (settings.aiMessageBackgroundColor) { + setAiMessageBackgroundColor(settings.aiMessageBackgroundColor); + document.documentElement.style.setProperty('--ai-message-background-color', settings.aiMessageBackgroundColor); + } + + if (settings.aiMessageTextColor) { + setAiMessageTextColor(settings.aiMessageTextColor); + document.documentElement.style.setProperty('--ai-message-text-color', settings.aiMessageTextColor); + } + + if (settings.buttonBackgroundColor) { + setButtonBackgroundColor(settings.buttonBackgroundColor); + document.documentElement.style.setProperty('--button-background-color', settings.buttonBackgroundColor); + } + + if (settings.buttonHoverBackgroundColor) { + setButtonHoverBackgroundColor(settings.buttonHoverBackgroundColor); + document.documentElement.style.setProperty('--button-hover-background-color', settings.buttonHoverBackgroundColor); + } + + if (settings.modelsBackgroundColor) { + setModelsBackgroundColor(settings.modelsBackgroundColor); + document.documentElement.style.setProperty('--models-background-color', settings.modelsBackgroundColor); + } + + if (settings.historyBackgroundColor) { + setHistoryBackgroundColor(settings.historyBackgroundColor); + document.documentElement.style.setProperty('--history-background-color', settings.historyBackgroundColor); + } + + if (settings.leftPanelBackgroundColor) { + setLeftPanelBackgroundColor(settings.leftPanelBackgroundColor); + document.documentElement.style.setProperty('--left-panel-background-color', settings.leftPanelBackgroundColor); + } + + if (settings.conversationBackgroundColor) { + setConversationBackgroundColor(settings.conversationBackgroundColor); + document.documentElement.style.setProperty('--conversation-background-color', settings.conversationBackgroundColor); + } + + if (settings.popUpTextColor) { + setPopUpTextColor(settings.popUpTextColor); + document.documentElement.style.setProperty('--pop-up-text', settings.popUpTextColor); + } + + if (settings.inputBorderColor) { + setInputBorderColor(settings.inputBorderColor); + document.documentElement.style.setProperty('--input-border-color', settings.inputBorderColor); + } + + if (settings.fontFamily) { + setFontFamily(settings.fontFamily); + document.documentElement.style.setProperty('--font-family', settings.fontFamily); + } + + if (settings.fontSize) { + setFontSize(settings.fontSize); + document.documentElement.style.setProperty('--font-size', settings.fontSize); + } + }; - // FOSS settings state - const [openSourceMode, setOpenSourceMode] = useState<boolean>(false); - - // Account settings state - const [newName, setNewName] = useState<string>(''); - const [newEmail, setNewEmail] = useState<string>(''); - const [newPassword, setNewPassword] = useState<string>(''); - - // Theme selection - const [selectedTheme, setSelectedTheme] = useState<string>('default'); + - // Effect to update CSS variables on theme state change - useEffect(() => { - document.documentElement.style.setProperty('--background-color', backgroundColor); - document.documentElement.style.setProperty('--text-color', textColor); - document.documentElement.style.setProperty('--input-background-color', inputBackgroundColor); - document.documentElement.style.setProperty('--input-button-color', inputButtonColor); - document.documentElement.style.setProperty('--input-button-hover-color', inputButtonHoverColor); - document.documentElement.style.setProperty('--user-message-background-color', userMessageBackgroundColor); - document.documentElement.style.setProperty('--user-message-text-color', userMessageTextColor); - document.documentElement.style.setProperty('--ai-message-background-color', aiMessageBackgroundColor); - document.documentElement.style.setProperty('--ai-message-text-color', aiMessageTextColor); - document.documentElement.style.setProperty('--button-background-color', buttonBackgroundColor); - document.documentElement.style.setProperty('--button-hover-background-color', buttonHoverBackgroundColor); - document.documentElement.style.setProperty('--models-background-color', modelsBackgroundColor); - document.documentElement.style.setProperty('--history-background-color', historyBackgroundColor); - document.documentElement.style.setProperty('--left-panel-background-color', leftPanelBackgroundColor); - document.documentElement.style.setProperty('--conversation-background-color', conversationBackgroundColor); - document.documentElement.style.setProperty('--pop-up-text', popUpTextColor); - document.documentElement.style.setProperty('--input-border-color', inputBorderColor); - document.documentElement.style.setProperty('--font-family', fontFamily); - document.documentElement.style.setProperty('--font-size', fontSize); - }, [ - backgroundColor, - textColor, - inputBackgroundColor, - inputButtonColor, - inputButtonHoverColor, - userMessageBackgroundColor, - userMessageTextColor, - aiMessageBackgroundColor, - aiMessageTextColor, - buttonBackgroundColor, - buttonHoverBackgroundColor, - modelsBackgroundColor, - historyBackgroundColor, - leftPanelBackgroundColor, - conversationBackgroundColor, - popUpTextColor, - inputBorderColor, - fontFamily, - fontSize, - ]); - + // Render settings content based on the active section const renderSettingsContent = () => { switch (activeSection) { case 'general': @@ -113,7 +164,6 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( <option value="ja">Japanese</option> <option value="ru">Russian</option> <option value="ar">Arabic</option> - {/* Add more languages as needed */} </select> </div> <div className="settings-option"> @@ -131,7 +181,6 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( <option value="chf">CHF</option> <option value="cny">CNY</option> <option value="inr">INR</option> - {/* Add more currencies as needed */} </select> </div> <div className="settings-option"> @@ -145,7 +194,6 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( <option value="yyyy-mm-dd">YYYY-MM-DD</option> <option value="mm-dd-yyyy">MM-DD-YYYY</option> <option value="dd-mm-yyyy">DD-MM-YYYY</option> - {/* Add more formats as needed */} </select> </div> <div className="settings-option"> @@ -156,8 +204,6 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( > <option value="12-hour">12 Hour</option> <option value="24-hour">24 Hour</option> - <option value="am-pm">AM/PM Format</option> - {/* Add more formats if necessary */} </select> </div> <div className="settings-option"> @@ -176,7 +222,6 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( <option value="IST">IST</option> <option value="CET">CET</option> <option value="JST">JST</option> - {/* Add more time zones as needed */} </select> </div> </div> @@ -203,7 +248,7 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( checked={disableChatHistory} onChange={() => setDisableChatHistory(!disableChatHistory)} /> - Disable Chat History Save + Disable Chat History </label> </div> <div className="settings-option"> @@ -216,9 +261,6 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( Disable AI Memory </label> </div> - <div className="settings-option"> - <button onClick={() => { /* Export data logic */ }}>Export My Data</button> - </div> </div> ); @@ -356,152 +398,242 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( onChange={(e) => { const newSize = `${e.target.value}px`; setFontSize(newSize); - document.documentElement.style.setProperty('--font-size', newSize); // Update the CSS variable + document.documentElement.style.setProperty('--font-size', newSize); }} /> <span>{fontSize}</span> </div> + <div className="settings-option"> <p>Background Color</p> <input type="color" value={backgroundColor} - onChange={(e) => setBackgroundColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setBackgroundColor(newColor); + document.documentElement.style.setProperty('--background-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Text Color</p> <input type="color" value={textColor} - onChange={(e) => setTextColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setTextColor(newColor); + document.documentElement.style.setProperty('--text-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Input Background Color</p> <input type="color" value={inputBackgroundColor} - onChange={(e) => setInputBackgroundColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setInputBackgroundColor(newColor); + document.documentElement.style.setProperty('--input-background-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Input Button Color</p> <input type="color" value={inputButtonColor} - onChange={(e) => setInputButtonColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setInputButtonColor(newColor); + document.documentElement.style.setProperty('--input-button-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Input Button Hover Color</p> <input type="color" value={inputButtonHoverColor} - onChange={(e) => setInputButtonHoverColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setInputButtonHoverColor(newColor); + document.documentElement.style.setProperty('--input-button-hover-color', newColor); + }} /> </div> + <div className="settings-option"> <p>User Message Background Color</p> <input type="color" value={userMessageBackgroundColor} - onChange={(e) => setUserMessageBackgroundColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setUserMessageBackgroundColor(newColor); + document.documentElement.style.setProperty('--user-message-background-color', newColor); + }} /> </div> + <div className="settings-option"> <p>User Message Text Color</p> <input type="color" value={userMessageTextColor} - onChange={(e) => setUserMessageTextColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setUserMessageTextColor(newColor); + document.documentElement.style.setProperty('--user-message-text-color', newColor); + }} /> </div> + <div className="settings-option"> <p>AI Message Background Color</p> <input type="color" value={aiMessageBackgroundColor} - onChange={(e) => setAiMessageBackgroundColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setAiMessageBackgroundColor(newColor); + document.documentElement.style.setProperty('--ai-message-background-color', newColor); + }} /> </div> + <div className="settings-option"> <p>AI Message Text Color</p> <input type="color" value={aiMessageTextColor} - onChange={(e) => setAiMessageTextColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setAiMessageTextColor(newColor); + document.documentElement.style.setProperty('--ai-message-text-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Button Background Color</p> <input type="color" value={buttonBackgroundColor} - onChange={(e) => setButtonBackgroundColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setButtonBackgroundColor(newColor); + document.documentElement.style.setProperty('--button-background-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Button Hover Background Color</p> <input type="color" value={buttonHoverBackgroundColor} - onChange={(e) => setButtonHoverBackgroundColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setButtonHoverBackgroundColor(newColor); + document.documentElement.style.setProperty('--button-hover-background-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Models Background Color</p> <input type="color" value={modelsBackgroundColor} - onChange={(e) => setModelsBackgroundColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setModelsBackgroundColor(newColor); + document.documentElement.style.setProperty('--models-background-color', newColor); + }} /> </div> + <div className="settings-option"> <p>History Background Color</p> <input type="color" value={historyBackgroundColor} - onChange={(e) => setHistoryBackgroundColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setHistoryBackgroundColor(newColor); + document.documentElement.style.setProperty('--history-background-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Left Panel Background Color</p> <input type="color" value={leftPanelBackgroundColor} - onChange={(e) => setLeftPanelBackgroundColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setLeftPanelBackgroundColor(newColor); + document.documentElement.style.setProperty('--left-panel-background-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Conversation Background Color</p> <input type="color" value={conversationBackgroundColor} - onChange={(e) => setConversationBackgroundColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setConversationBackgroundColor(newColor); + document.documentElement.style.setProperty('--conversation-background-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Pop-up Text Color</p> <input type="color" value={popUpTextColor} - onChange={(e) => setPopUpTextColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setPopUpTextColor(newColor); + document.documentElement.style.setProperty('--pop-up-text', newColor); + }} /> </div> + <div className="settings-option"> <p>Input Border Color</p> <input type="color" value={inputBorderColor} - onChange={(e) => setInputBorderColor(e.target.value)} + onChange={(e) => { + const newColor = e.target.value; + setInputBorderColor(newColor); + document.documentElement.style.setProperty('--input-border-color', newColor); + }} /> </div> + <div className="settings-option"> <p>Font Family</p> <select value={fontFamily} - onChange={(e) => setFontFamily(e.target.value)} + onChange={(e) => { + const newFont = e.target.value; + setFontFamily(newFont); + document.documentElement.style.setProperty('--font-family', newFont); + }} > <option value="'Poppins', sans-serif">Poppins</option> <option value="'Arial', sans-serif">Arial</option> @@ -510,15 +642,17 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( <option value="'Times New Roman', serif">Times New Roman</option> </select> </div> + </> )} </div> ); - + + case 'foss': return ( <div className="settings-section"> - <h2>Free and Open Source Software (FOSS) Settings</h2> + <h2>Open Source Settings</h2> <div className="settings-option"> <label> <input @@ -537,7 +671,7 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( <div className="settings-section"> <h2>Account Settings</h2> <div className="settings-option"> - <label>Change Name</label> + <label>New Name</label> <input type="text" value={newName} @@ -545,7 +679,7 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( /> </div> <div className="settings-option"> - <label>Change Email</label> + <label>New Email</label> <input type="email" value={newEmail} @@ -553,7 +687,7 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( /> </div> <div className="settings-option"> - <label>Change Password</label> + <label>New Password</label> <input type="password" value={newPassword} @@ -563,11 +697,66 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( </div> ); + case 'im/export': + return ( + <div className="settings-section"> + <h2>Import & Export</h2> + <div className="settings-option"> + <h3>Export the settings</h3> + <button onClick={() => exportSettings(currentSettings)}>Export Settings</button> + </div> + <div className="settings-option"> + <h3>Import the settings</h3> + <input type="file" onChange={handleImport} accept=".json" /> + </div> + </div> + ); + default: return null; } }; + // Handle file import + const handleImport = (event: React.ChangeEvent<HTMLInputElement>) => { + if (event.target.files && event.target.files.length > 0) { + const file = event.target.files[0]; + importSettings(file, applySettings); + } + }; + + // Gather all settings into an object + const currentSettings = { + backgroundColor, + textColor, + inputBackgroundColor, + inputButtonColor, + inputButtonHoverColor, + userMessageBackgroundColor, + userMessageTextColor, + aiMessageBackgroundColor, + aiMessageTextColor, + buttonBackgroundColor, + buttonHoverBackgroundColor, + modelsBackgroundColor, + historyBackgroundColor, + leftPanelBackgroundColor, + conversationBackgroundColor, + popUpTextColor, + inputBorderColor, + fontFamily, + fontSize, + preferredLanguage, + preferredCurrency, + dateFormat, + timeFormat, + timeZone, + disableOnlineAI, + disableChatHistory, + disableAIMemory, + openSourceMode, + }; + return ( <div className="popup-overlay"> <div className="settings-content"> @@ -579,7 +768,7 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( <li onClick={() => setActiveSection('theme')}>Theme</li> <li onClick={() => setActiveSection('foss')}>FOSS</li> <li onClick={() => setActiveSection('account')}>Account</li> - {/* Make something that can export and import all settings */} + <li onClick={() => setActiveSection('im/export')}>Import/Export</li> </ul> </div> <div className="settings-main"> @@ -590,7 +779,6 @@ const Settings: React.FC<{ closeSettings: () => void; accountName: string }> = ( </div> </div> </div> - ); }; diff --git a/app/components/settingUtils.ts b/app/components/settingUtils.ts new file mode 100644 index 0000000..e327524 --- /dev/null +++ b/app/components/settingUtils.ts @@ -0,0 +1,22 @@ +// settingsUtils.ts + +// Export the current settings as a JSON file +export const exportSettings = (settings: any) => { + const blob = new Blob([JSON.stringify(settings)], { type: 'application/json' }); + const link = document.createElement('a'); + link.href = URL.createObjectURL(blob); + link.download = 'settings.json'; + link.click(); + }; + + // Import settings from a JSON file + export const importSettings = (file: File, applySettings: (settings: any) => void) => { + const reader = new FileReader(); + reader.onload = (e) => { + const content = e.target?.result as string; + const importedSettings = JSON.parse(content); + applySettings(importedSettings); + }; + reader.readAsText(file); + }; + \ No newline at end of file diff --git a/tailwind.config.ts b/tailwind.config.ts index a883ff7..e69de29 100644 --- a/tailwind.config.ts +++ b/tailwind.config.ts @@ -1,21 +0,0 @@ -import type { Config } from "tailwindcss"; - -const config: Config = { - content: [ - "./pages/**/*.{js,ts,jsx,tsx,mdx}", - "./components/**/*.{js,ts,jsx,tsx,mdx}", - "./app/**/*.{js,ts,jsx,tsx,mdx}", - ], - theme: { - extend: { - colors: { - 'history-background': 'var(--history-background-color)', - 'text-color': 'var(--text-color)', - 'input-button-hover-color': 'var(--input-button-hover-color)', - }, - }, - }, - plugins: [], -}; - -export default config;