|
@@ -64,9 +64,13 @@ pub use wry::application::window::{Window, WindowBuilder as WryWindowBuilder};
|
|
use wry::webview::WebviewExtWindows;
|
|
use wry::webview::WebviewExtWindows;
|
|
|
|
|
|
use std::{
|
|
use std::{
|
|
- collections::HashMap,
|
|
|
|
|
|
+ collections::{
|
|
|
|
+ hash_map::Entry::{Occupied, Vacant},
|
|
|
|
+ HashMap,
|
|
|
|
+ },
|
|
convert::TryFrom,
|
|
convert::TryFrom,
|
|
fs::read,
|
|
fs::read,
|
|
|
|
+ path::PathBuf,
|
|
sync::{
|
|
sync::{
|
|
atomic::{AtomicBool, Ordering},
|
|
atomic::{AtomicBool, Ordering},
|
|
mpsc::{channel, Sender},
|
|
mpsc::{channel, Sender},
|
|
@@ -83,6 +87,7 @@ use menu::*;
|
|
mod mime_type;
|
|
mod mime_type;
|
|
use mime_type::MimeType;
|
|
use mime_type::MimeType;
|
|
|
|
|
|
|
|
+type WebContextStore = Mutex<HashMap<Option<PathBuf>, WebContext>>;
|
|
type WindowEventHandler = Box<dyn Fn(&WindowEvent) + Send>;
|
|
type WindowEventHandler = Box<dyn Fn(&WindowEvent) + Send>;
|
|
type WindowEventListenersMap = Arc<Mutex<HashMap<Uuid, WindowEventHandler>>>;
|
|
type WindowEventListenersMap = Arc<Mutex<HashMap<Uuid, WindowEventHandler>>>;
|
|
type WindowEventListeners = Arc<Mutex<HashMap<WindowId, WindowEventListenersMap>>>;
|
|
type WindowEventListeners = Arc<Mutex<HashMap<WindowId, WindowEventListenersMap>>>;
|
|
@@ -752,7 +757,9 @@ pub(crate) enum Message {
|
|
#[cfg(feature = "system-tray")]
|
|
#[cfg(feature = "system-tray")]
|
|
Tray(TrayMessage),
|
|
Tray(TrayMessage),
|
|
CreateWebview(
|
|
CreateWebview(
|
|
- Box<dyn FnOnce(&EventLoopWindowTarget<Message>) -> Result<WindowWrapper> + Send>,
|
|
|
|
|
|
+ Box<
|
|
|
|
+ dyn FnOnce(&EventLoopWindowTarget<Message>, &WebContextStore) -> Result<WindowWrapper> + Send,
|
|
|
|
+ >,
|
|
Sender<WindowId>,
|
|
Sender<WindowId>,
|
|
),
|
|
),
|
|
CreateWindow(
|
|
CreateWindow(
|
|
@@ -956,7 +963,9 @@ impl Dispatch for WryDispatcher {
|
|
.context
|
|
.context
|
|
.proxy
|
|
.proxy
|
|
.send_event(Message::CreateWebview(
|
|
.send_event(Message::CreateWebview(
|
|
- Box::new(move |event_loop| create_webview(event_loop, context, pending)),
|
|
|
|
|
|
+ Box::new(move |event_loop, web_context| {
|
|
|
|
+ create_webview(event_loop, web_context, context, pending)
|
|
|
|
+ }),
|
|
tx,
|
|
tx,
|
|
))
|
|
))
|
|
.map_err(|_| Error::FailedToSendMessage)?;
|
|
.map_err(|_| Error::FailedToSendMessage)?;
|
|
@@ -1243,6 +1252,7 @@ pub struct Wry {
|
|
is_event_loop_running: Arc<AtomicBool>,
|
|
is_event_loop_running: Arc<AtomicBool>,
|
|
event_loop: EventLoop<Message>,
|
|
event_loop: EventLoop<Message>,
|
|
windows: Arc<Mutex<HashMap<WindowId, WindowWrapper>>>,
|
|
windows: Arc<Mutex<HashMap<WindowId, WindowWrapper>>>,
|
|
|
|
+ web_context: WebContextStore,
|
|
window_event_listeners: WindowEventListeners,
|
|
window_event_listeners: WindowEventListeners,
|
|
#[cfg(feature = "menu")]
|
|
#[cfg(feature = "menu")]
|
|
menu_event_listeners: MenuEventListeners,
|
|
menu_event_listeners: MenuEventListeners,
|
|
@@ -1288,7 +1298,9 @@ impl RuntimeHandle for WryHandle {
|
|
.dispatcher_context
|
|
.dispatcher_context
|
|
.proxy
|
|
.proxy
|
|
.send_event(Message::CreateWebview(
|
|
.send_event(Message::CreateWebview(
|
|
- Box::new(move |event_loop| create_webview(event_loop, dispatcher_context, pending)),
|
|
|
|
|
|
+ Box::new(move |event_loop, web_context| {
|
|
|
|
+ create_webview(event_loop, web_context, dispatcher_context, pending)
|
|
|
|
+ }),
|
|
tx,
|
|
tx,
|
|
))
|
|
))
|
|
.map_err(|_| Error::FailedToSendMessage)?;
|
|
.map_err(|_| Error::FailedToSendMessage)?;
|
|
@@ -1348,6 +1360,7 @@ impl Runtime for Wry {
|
|
is_event_loop_running,
|
|
is_event_loop_running,
|
|
event_loop,
|
|
event_loop,
|
|
windows: Default::default(),
|
|
windows: Default::default(),
|
|
|
|
+ web_context: Default::default(),
|
|
window_event_listeners: Default::default(),
|
|
window_event_listeners: Default::default(),
|
|
#[cfg(feature = "menu")]
|
|
#[cfg(feature = "menu")]
|
|
menu_event_listeners: Default::default(),
|
|
menu_event_listeners: Default::default(),
|
|
@@ -1382,6 +1395,7 @@ impl Runtime for Wry {
|
|
let proxy = self.event_loop.create_proxy();
|
|
let proxy = self.event_loop.create_proxy();
|
|
let webview = create_webview(
|
|
let webview = create_webview(
|
|
&self.event_loop,
|
|
&self.event_loop,
|
|
|
|
+ &self.web_context,
|
|
DispatcherContext {
|
|
DispatcherContext {
|
|
main_thread_id: self.main_thread_id,
|
|
main_thread_id: self.main_thread_id,
|
|
is_event_loop_running: self.is_event_loop_running.clone(),
|
|
is_event_loop_running: self.is_event_loop_running.clone(),
|
|
@@ -1497,6 +1511,7 @@ impl Runtime for Wry {
|
|
fn run_iteration<F: Fn(RunEvent) + 'static>(&mut self, callback: F) -> RunIteration {
|
|
fn run_iteration<F: Fn(RunEvent) + 'static>(&mut self, callback: F) -> RunIteration {
|
|
use wry::application::platform::run_return::EventLoopExtRunReturn;
|
|
use wry::application::platform::run_return::EventLoopExtRunReturn;
|
|
let windows = self.windows.clone();
|
|
let windows = self.windows.clone();
|
|
|
|
+ let web_context = &self.web_context;
|
|
let window_event_listeners = self.window_event_listeners.clone();
|
|
let window_event_listeners = self.window_event_listeners.clone();
|
|
#[cfg(feature = "menu")]
|
|
#[cfg(feature = "menu")]
|
|
let menu_event_listeners = self.menu_event_listeners.clone();
|
|
let menu_event_listeners = self.menu_event_listeners.clone();
|
|
@@ -1531,6 +1546,7 @@ impl Runtime for Wry {
|
|
#[cfg(feature = "system-tray")]
|
|
#[cfg(feature = "system-tray")]
|
|
tray_context: &tray_context,
|
|
tray_context: &tray_context,
|
|
},
|
|
},
|
|
|
|
+ web_context,
|
|
);
|
|
);
|
|
});
|
|
});
|
|
self.is_event_loop_running.store(false, Ordering::Relaxed);
|
|
self.is_event_loop_running.store(false, Ordering::Relaxed);
|
|
@@ -1541,6 +1557,7 @@ impl Runtime for Wry {
|
|
fn run<F: Fn(RunEvent) + 'static>(self, callback: F) {
|
|
fn run<F: Fn(RunEvent) + 'static>(self, callback: F) {
|
|
self.is_event_loop_running.store(true, Ordering::Relaxed);
|
|
self.is_event_loop_running.store(true, Ordering::Relaxed);
|
|
let windows = self.windows.clone();
|
|
let windows = self.windows.clone();
|
|
|
|
+ let web_context = self.web_context;
|
|
let window_event_listeners = self.window_event_listeners.clone();
|
|
let window_event_listeners = self.window_event_listeners.clone();
|
|
#[cfg(feature = "menu")]
|
|
#[cfg(feature = "menu")]
|
|
let menu_event_listeners = self.menu_event_listeners.clone();
|
|
let menu_event_listeners = self.menu_event_listeners.clone();
|
|
@@ -1567,6 +1584,7 @@ impl Runtime for Wry {
|
|
#[cfg(feature = "system-tray")]
|
|
#[cfg(feature = "system-tray")]
|
|
tray_context: &tray_context,
|
|
tray_context: &tray_context,
|
|
},
|
|
},
|
|
|
|
+ &web_context,
|
|
);
|
|
);
|
|
})
|
|
})
|
|
}
|
|
}
|
|
@@ -1590,6 +1608,7 @@ fn handle_event_loop(
|
|
event_loop: &EventLoopWindowTarget<Message>,
|
|
event_loop: &EventLoopWindowTarget<Message>,
|
|
control_flow: &mut ControlFlow,
|
|
control_flow: &mut ControlFlow,
|
|
context: EventLoopIterationContext<'_>,
|
|
context: EventLoopIterationContext<'_>,
|
|
|
|
+ web_context: &WebContextStore,
|
|
) -> RunIteration {
|
|
) -> RunIteration {
|
|
let EventLoopIterationContext {
|
|
let EventLoopIterationContext {
|
|
callback,
|
|
callback,
|
|
@@ -1892,7 +1911,7 @@ fn handle_event_loop(
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
- Message::CreateWebview(handler, sender) => match handler(event_loop) {
|
|
|
|
|
|
+ Message::CreateWebview(handler, sender) => match handler(event_loop, web_context) {
|
|
Ok(webview) => {
|
|
Ok(webview) => {
|
|
let window_id = webview.inner.window().id();
|
|
let window_id = webview.inner.window().id();
|
|
windows.insert(window_id, webview);
|
|
windows.insert(window_id, webview);
|
|
@@ -1936,6 +1955,7 @@ fn handle_event_loop(
|
|
sender.send(Err(Error::CreateWindow)).unwrap();
|
|
sender.send(Err(Error::CreateWindow)).unwrap();
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
+
|
|
#[cfg(feature = "system-tray")]
|
|
#[cfg(feature = "system-tray")]
|
|
Message::Tray(tray_message) => match tray_message {
|
|
Message::Tray(tray_message) => match tray_message {
|
|
TrayMessage::UpdateItem(menu_id, update) => {
|
|
TrayMessage::UpdateItem(menu_id, update) => {
|
|
@@ -2068,6 +2088,7 @@ fn center_window(window: &Window) -> Result<()> {
|
|
|
|
|
|
fn create_webview(
|
|
fn create_webview(
|
|
event_loop: &EventLoopWindowTarget<Message>,
|
|
event_loop: &EventLoopWindowTarget<Message>,
|
|
|
|
+ web_context: &WebContextStore,
|
|
context: DispatcherContext,
|
|
context: DispatcherContext,
|
|
pending: PendingWindow<Wry>,
|
|
pending: PendingWindow<Wry>,
|
|
) -> Result<WindowWrapper> {
|
|
) -> Result<WindowWrapper> {
|
|
@@ -2134,13 +2155,27 @@ fn create_webview(
|
|
.map_err(|_| wry::Error::InitScriptError)
|
|
.map_err(|_| wry::Error::InitScriptError)
|
|
});
|
|
});
|
|
}
|
|
}
|
|
- let mut context = WebContext::new(webview_attributes.data_directory);
|
|
|
|
- webview_builder = webview_builder.with_web_context(&mut context);
|
|
|
|
|
|
+
|
|
for script in webview_attributes.initialization_scripts {
|
|
for script in webview_attributes.initialization_scripts {
|
|
webview_builder = webview_builder.with_initialization_script(&script);
|
|
webview_builder = webview_builder.with_initialization_script(&script);
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+ let mut web_context = web_context.lock().expect("poisoned WebContext store");
|
|
|
|
+ let is_first_context = web_context.is_empty();
|
|
|
|
+ let web_context = match web_context.entry(webview_attributes.data_directory) {
|
|
|
|
+ Occupied(occupied) => occupied.into_mut(),
|
|
|
|
+ Vacant(vacant) => {
|
|
|
|
+ let mut web_context = WebContext::new(vacant.key().clone());
|
|
|
|
+ web_context.set_allows_automation(match std::env::var("TAURI_AUTOMATION").as_deref() {
|
|
|
|
+ Ok("true") => is_first_context,
|
|
|
|
+ _ => false,
|
|
|
|
+ });
|
|
|
|
+ vacant.insert(web_context)
|
|
|
|
+ }
|
|
|
|
+ };
|
|
|
|
+
|
|
let webview = webview_builder
|
|
let webview = webview_builder
|
|
|
|
+ .with_web_context(web_context)
|
|
.build()
|
|
.build()
|
|
.map_err(|e| Error::CreateWebview(Box::new(e)))?;
|
|
.map_err(|e| Error::CreateWebview(Box::new(e)))?;
|
|
|
|
|