feat: switch origin

This commit is contained in:
lencx
2022-12-12 01:32:41 +08:00
parent 3eac43541e
commit 78f8daab86
9 changed files with 150 additions and 29 deletions

View File

@@ -14,11 +14,11 @@ rust-version = "1.57"
tauri-build = {version = "1.2.1", features = [] }
[dependencies]
anyhow = "1.0.66"
serde_json = "1.0"
serde = { version = "1.0", features = ["derive"] }
tauri = { version = "1.2.1", features = ["api-all", "devtools", "system-tray", "updater"] }
tauri = { version = "1.2.2", features = ["api-all", "devtools", "system-tray", "updater"] }
tauri-plugin-positioner = { version = "1.0.4", features = ["system-tray"] }
anyhow = "1.0.66"
[features]
# by default Tauri runs in production mode

View File

@@ -33,3 +33,30 @@ pub fn open_link(app: AppHandle, url: String) {
pub fn get_chat_conf() -> ChatConfJson {
ChatConfJson::get_chat_conf()
}
#[command]
pub fn form_confirm(app: AppHandle, data: serde_json::Value) {
ChatConfJson::amend(&serde_json::json!(data)).unwrap();
tauri::api::process::restart(&app.env());
}
#[command]
pub fn form_cancel(app: AppHandle, label: &str, title: &str, msg: &str) {
let win = app.app_handle().get_window(label).unwrap();
tauri::api::dialog::ask(
app.app_handle().get_window(label).as_ref(),
title,
msg,
move |is_cancel| {
if is_cancel {
win.close().unwrap();
}
},
);
}
#[command]
pub fn form_msg(app: AppHandle, label: &str, title: &str, msg: &str) {
let win = app.app_handle().get_window(label);
tauri::api::dialog::message(win.as_ref(), title, msg);
}

View File

@@ -10,7 +10,8 @@ use tauri::{
use tauri_plugin_positioner::{on_tray_event, Position, WindowExt};
// --- Menu
pub fn init(chat_conf: &conf::ChatConfJson, context: &Context<EmbeddedAssets>) -> Menu {
pub fn init(context: &Context<EmbeddedAssets>) -> Menu {
let chat_conf = ChatConfJson::get_chat_conf();
let name = &context.package_info().name;
let app_menu = Submenu::new(
name,

View File

@@ -5,10 +5,8 @@ use crate::{
};
use tauri::{utils::config::WindowUrl, window::WindowBuilder, App, Manager};
pub fn init(
app: &mut App,
chat_conf: ChatConfJson,
) -> std::result::Result<(), Box<dyn std::error::Error>> {
pub fn init(app: &mut App) -> std::result::Result<(), Box<dyn std::error::Error>> {
let chat_conf = ChatConfJson::get_chat_conf();
let url = chat_conf.origin.to_string();
let theme = ChatConfJson::theme();
window::mini_window(&app.app_handle());

View File

@@ -25,14 +25,17 @@ pub fn mini_window(handle: &tauri::AppHandle) {
}
pub fn origin_window(handle: &tauri::AppHandle) {
let theme = conf::ChatConfJson::theme();
WindowBuilder::new(handle, "main", WindowUrl::External("/".parse().unwrap()))
let chat_conf = conf::ChatConfJson::get_chat_conf();
// tauri://localhost/origin
// let url = chat_conf.origin;
WindowBuilder::new(handle, "origin", WindowUrl::App(chat_conf.origin.into()))
.resizable(false)
.fullscreen(false)
.inner_size(400.0, 300.0)
.always_on_top(true)
.theme(theme)
.decorations(false)
.initialization_script(include_str!("../assets/core.js"))
.initialization_script(include_str!("../assets/origin.js"))
.build()
.unwrap();
}

View File

@@ -2,6 +2,7 @@
// @ref: https://github.com/liady/ChatGPT-pdf/blob/main/src/content_script.js
async function init() {
const chatConf = await invoke('get_chat_conf') || {};
if (window.buttonsInterval) {
clearInterval(window.buttonsInterval);
}
@@ -16,7 +17,7 @@ async function init() {
});
if (hasTryAgainButton && buttons.length === 1) {
const TryAgainButton = actionsArea.querySelector("button");
addActionsButtons(actionsArea, TryAgainButton);
addActionsButtons(actionsArea, TryAgainButton, chatConf);
} else if (!hasTryAgainButton) {
removeButtons();
}
@@ -28,7 +29,7 @@ const Format = {
PDF: "pdf",
};
function addActionsButtons(actionsArea, TryAgainButton) {
function addActionsButtons(actionsArea, TryAgainButton, chatConf) {
const downloadButton = TryAgainButton.cloneNode(true);
downloadButton.id = "download-png-button";
downloadButton.innerText = "Generate PNG";
@@ -36,6 +37,7 @@ function addActionsButtons(actionsArea, TryAgainButton) {
downloadThread();
};
actionsArea.appendChild(downloadButton);
const downloadPdfButton = TryAgainButton.cloneNode(true);
downloadPdfButton.id = "download-pdf-button";
downloadPdfButton.innerText = "Download PDF";
@@ -43,13 +45,16 @@ function addActionsButtons(actionsArea, TryAgainButton) {
downloadThread({ as: Format.PDF });
};
actionsArea.appendChild(downloadPdfButton);
const exportHtml = TryAgainButton.cloneNode(true);
exportHtml.id = "download-html-button";
exportHtml.innerText = "Share Link";
exportHtml.onclick = () => {
sendRequest();
};
actionsArea.appendChild(exportHtml);
if (new RegExp('//chat.openai.com').test(chatConf.origin)) {
const exportHtml = TryAgainButton.cloneNode(true);
exportHtml.id = "download-html-button";
exportHtml.innerText = "Share Link";
exportHtml.onclick = () => {
sendRequest();
};
actionsArea.appendChild(exportHtml);
}
}
function removeButtons() {

View File

@@ -0,0 +1,71 @@
function init() {
document.body.innerHTML = `<style>
body {
height: 100vh;
padding: 0;
margin: 0;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
font-family: Söhne,ui-sans-serif,system-ui,-apple-system,Segoe UI,Roboto,Ubuntu,Cantarell,Noto Sans,sans-serif,Helvetica Neue,Arial,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol,Noto Color Emoji;
}
input {
all: unset;
width: 280px;
height: 30px;
margin-bottom: 10px;
padding: 0 5px;
border: solid 2px #d8d8d8;
}
button {
all: unset;
height: 30px;
font-size: 16px;
padding: 0 10px;
line-height: 30px;
margin: 0 5px;
color: #fff;
border-radius: 5px;
cursor: pointer;
}
#cancel {
background-color: #999;
}
#confirm {
background-color: #10a37f;
}
</style>
<h3>Switch Origin</h3>
<input id="input" type="text" />
<div class="btns">
<button id="cancel">Cancel</button>
<button id="confirm">Confirm</button>
</div>`;
const srcipt = document.createElement('script');
srcipt.innerHTML = `const input = document.getElementById('input');
const cancelBtn = document.getElementById('cancel');
const confirmBtn = document.getElementById('confirm');
cancelBtn.addEventListener('click', () => {
window.invoke('form_cancel', { label: 'origin', title: 'Switch Origin', msg: 'Sure you want to give up the switch?' });
})
confirmBtn.addEventListener('click', () => {
if (/^https?:\\/\\//.test(input.value)) {
window.invoke('form_confirm', { data: { origin: input.value } });
} else {
window.invoke('form_msg', { label: 'origin', title: 'Switch Origin', msg: 'Invalid URL!' });
}
})`;
document.head.appendChild(srcipt);
}
// run init
if (
document.readyState === "complete" ||
document.readyState === "interactive"
) {
init();
} else {
document.addEventListener("DOMContentLoaded", init);
}

View File

@@ -12,7 +12,8 @@ pub const DEFAULT_CHAT_CONF: &str = r#"{
"always_on_top": false,
"theme": "Light",
"titlebar": true,
"origin": "https://chat.openai.com/"
"default_origin": "https://chat.openai.com",
"origin": "https://chat.openai.com"
}"#;
pub struct ChatState {
@@ -32,6 +33,7 @@ pub struct ChatConfJson {
pub always_on_top: bool,
pub theme: String,
pub titlebar: bool,
pub default_origin: String,
pub origin: String,
}
@@ -42,10 +44,22 @@ impl ChatConfJson {
let conf_file = ChatConfJson::conf_path();
if !exists(&conf_file) {
create_file(&conf_file).unwrap();
fs::write(&conf_file, DEFAULT_CHAT_CONF).unwrap();
#[cfg(target_os = "macos")]
ChatConfJson::amend(&serde_json::json!({ "titlebar": false })).unwrap();
fs::write(
&conf_file,
r#"{
"always_on_top": false,
"theme": "Light",
"titlebar": false,
"default_origin": "https://chat.openai.com",
"origin": "https://chat.openai.com"
}"#,
)
.unwrap();
#[cfg(not(target_os = "macos"))]
fs::write(&conf_file, DEFAULT_CHAT_CONF).unwrap();
}
conf_file
}

View File

@@ -8,26 +8,28 @@ mod conf;
mod utils;
use app::{cmd, menu, setup};
use conf::ChatConfJson;
use conf::{ChatConfJson, ChatState};
fn main() {
ChatConfJson::init();
let context = tauri::generate_context!();
let chat_conf = ChatConfJson::get_chat_conf();
let chat_conf2 = chat_conf.clone();
let context = tauri::generate_context!();
tauri::Builder::default()
.manage(conf::ChatState::default(chat_conf.clone()))
.manage(ChatState::default(chat_conf))
.invoke_handler(tauri::generate_handler![
cmd::drag_window,
cmd::fullscreen,
cmd::download,
cmd::open_link,
cmd::get_chat_conf,
cmd::form_cancel,
cmd::form_confirm,
cmd::form_msg,
])
.setup(|app| setup::init(app, chat_conf2))
.setup(setup::init)
.plugin(tauri_plugin_positioner::init())
.menu(menu::init(&chat_conf, &context))
.menu(menu::init(&context))
.system_tray(menu::tray_menu())
.on_menu_event(menu::menu_handler)
.on_system_tray_event(menu::tray_handler)