feat: pass an `AppHandle` to the callback

pull/72/head
amrbashir 3 years ago
parent 98445a8a5f
commit b0052d2da4
No known key found for this signature in database
GPG Key ID: BBD7A47A2003FF33

@ -8,10 +8,10 @@ rust-version = "1.57"
exclude = ["/examples"]
[dependencies]
tauri = { version = "1.0.0-rc.10" }
tauri = { version = "1.0.0-rc.16" }
[target.'cfg(target_os = "windows")'.dependencies.windows-sys]
version = "0.35"
version = "0.36"
features = [
"Win32_System_Threading",
"Win32_System_DataExchange",

@ -9,6 +9,6 @@
"author": "",
"license": "MIT",
"dependencies": {
"@tauri-apps/cli": "^1.0.0-rc.0"
"@tauri-apps/cli": "^1.0.0-rc.15"
}
}

File diff suppressed because it is too large Load Diff

@ -10,11 +10,11 @@ rust-version = "1.57"
[dependencies]
serde_json = "1.0"
serde = { version = "1.0", features = [ "derive" ] }
tauri = { version = "1.0.0-rc.6", features = ["api-all"] }
tauri = { version = "1.0.0-rc.16", features = ["api-all"] }
tauri-plugin-single-instance = { path = "../../../" }
[build-dependencies]
tauri-build = { version = "1.0.0-rc.5", features = [] }
tauri-build = { version = "1.0.0-rc.14", features = [] }
[features]
default = [ "custom-protocol" ]

@ -5,8 +5,8 @@
fn main() {
tauri::Builder::default()
.plugin(tauri_plugin_single_instance::init(|argv, cwd| {
println!("{argv:?}, {cwd}");
.plugin(tauri_plugin_single_instance::init(|app, argv, cwd| {
println!("{}, {argv:?}, {cwd}", app.package_info().name);
}))
.run(tauri::generate_context!())
.expect("error while running tauri application");

@ -1,4 +1,4 @@
use tauri::{plugin::TauriPlugin, Runtime};
use tauri::{plugin::TauriPlugin, AppHandle, Runtime};
#[cfg(target_os = "windows")]
#[path = "platform_impl/windows.rs"]
@ -10,9 +10,10 @@ mod platform_impl;
#[path = "platform_impl/macos.rs"]
mod platform_impl;
pub(crate) type SingleInstanceCallback = dyn FnMut(Vec<String>, String) + Send + Sync + 'static;
pub(crate) type SingleInstanceCallback<R> =
dyn FnMut(&AppHandle<R>, Vec<String>, String) + Send + Sync + 'static;
pub fn init<R: Runtime, F: FnMut(Vec<String>, String) + Send + Sync + 'static>(
pub fn init<R: Runtime, F: FnMut(&AppHandle<R>, Vec<String>, String) + Send + Sync + 'static>(
f: F,
) -> TauriPlugin<R> {
platform_impl::init(Box::new(f))

@ -2,6 +2,7 @@
use crate::SingleInstanceCallback;
use tauri::{
AppHandle,
plugin::{self, TauriPlugin},
Manager, RunEvent, Runtime,
};
@ -12,22 +13,26 @@ use zbus::{
struct ConnectionHandle(Connection);
struct SingleInstanceDBus {
callback: Box<SingleInstanceCallback>,
struct SingleInstanceDBus<R: Runtime> {
callback: Box<SingleInstanceCallback<R>>,
app_handle: AppHandle<R>,
}
#[dbus_interface(name = "org.SingleInstance.DBus")]
impl SingleInstanceDBus {
impl<R:Runtime> SingleInstanceDBus<R> {
fn execute_callback(&mut self, argv: Vec<String>, cwd: String) {
(self.callback)(argv, cwd);
(self.callback)(&self.app_handle, argv, cwd);
}
}
pub fn init<R: Runtime>(f: Box<SingleInstanceCallback>) -> TauriPlugin<R> {
pub fn init<R: Runtime>(f: Box<SingleInstanceCallback<R>>) -> TauriPlugin<R> {
plugin::Builder::new("single-instance")
.setup(|app| {
let app_name = app.package_info().name.clone();
let single_instance_dbus = SingleInstanceDBus { callback: f };
let single_instance_dbus = SingleInstanceDBus {
callback: f,
app_handle: app.clone(),
};
let dbus_name = format!("org.{}.SingleInstance", app_name);
let dbus_path = format!("/org/{}/SingleInstance", app_name);

@ -4,7 +4,7 @@ use crate::SingleInstanceCallback;
use std::ffi::CStr;
use tauri::{
plugin::{self, TauriPlugin},
Manager, RunEvent, Runtime,
AppHandle, Manager, RunEvent, Runtime,
};
use windows_sys::Win32::{
Foundation::{CloseHandle, GetLastError, ERROR_ALREADY_EXISTS, HWND, LPARAM, LRESULT, WPARAM},
@ -26,7 +26,7 @@ struct TargetWindowHandle(isize);
const WMCOPYDATA_SINGLE_INSTANCE_DATA: usize = 1542;
pub fn init<R: Runtime>(f: Box<SingleInstanceCallback>) -> TauriPlugin<R> {
pub fn init<R: Runtime>(f: Box<SingleInstanceCallback<R>>) -> TauriPlugin<R> {
plugin::Builder::new("single-instance")
.setup(|app| {
let app_name = &app.package_info().name;
@ -70,8 +70,14 @@ pub fn init<R: Runtime>(f: Box<SingleInstanceCallback>) -> TauriPlugin<R> {
} else {
app.manage(MutexHandle(hmutex));
let hwnd = create_event_target_window(&class_name, &window_name);
unsafe { SetWindowLongPtrW(hwnd, GWL_USERDATA, Box::into_raw(Box::new(f)) as _) };
let hwnd = create_event_target_window::<R>(&class_name, &window_name);
unsafe {
SetWindowLongPtrW(
hwnd,
GWL_USERDATA,
Box::into_raw(Box::new((app.clone(), f))) as _,
)
};
app.manage(TargetWindowHandle(hwnd));
}
@ -94,13 +100,15 @@ pub fn init<R: Runtime>(f: Box<SingleInstanceCallback>) -> TauriPlugin<R> {
.build()
}
unsafe extern "system" fn single_instance_window_proc(
unsafe extern "system" fn single_instance_window_proc<R: Runtime>(
hwnd: HWND,
msg: u32,
wparam: WPARAM,
lparam: LPARAM,
) -> LRESULT {
let callback_ptr = GetWindowLongPtrW(hwnd, GWL_USERDATA) as *mut Box<SingleInstanceCallback>;
let data_ptr = GetWindowLongPtrW(hwnd, GWL_USERDATA)
as *mut (AppHandle<R>, Box<SingleInstanceCallback<R>>);
let (app_handle, callback) = &mut *data_ptr;
match msg {
WM_COPYDATA => {
@ -110,25 +118,25 @@ unsafe extern "system" fn single_instance_window_proc(
let mut s = data.split("|");
let cwd = s.next().unwrap();
let args = s.into_iter().map(|s| s.to_string()).collect();
(*callback_ptr)(args, cwd.to_string());
callback(&app_handle, args, cwd.to_string());
}
1
}
WM_DESTROY => {
let _ = Box::from_raw(callback_ptr);
let _ = Box::from_raw(data_ptr);
0
}
_ => DefWindowProcW(hwnd, msg, wparam, lparam),
}
}
fn create_event_target_window(class_name: &str, window_name: &str) -> HWND {
fn create_event_target_window<R: Runtime>(class_name: &str, window_name: &str) -> HWND {
unsafe {
let class = WNDCLASSEXW {
cbSize: std::mem::size_of::<WNDCLASSEXW>() as u32,
style: 0,
lpfnWndProc: Some(single_instance_window_proc),
lpfnWndProc: Some(single_instance_window_proc::<R>),
cbClsExtra: 0,
cbWndExtra: 0,
hInstance: GetModuleHandleW(std::ptr::null()),

Loading…
Cancel
Save