diff --git a/.github/workflows/cross-platform-testing.yml b/.github/workflows/cross-platform-testing.yml index 2138ca3..c28d1ca 100644 --- a/.github/workflows/cross-platform-testing.yml +++ b/.github/workflows/cross-platform-testing.yml @@ -72,6 +72,9 @@ jobs: echo "target flag is: ${{ env.TARGET_FLAGS }}" echo "target dir is: ${{ env.TARGET_DIR }}" + - name: Build with all features + if: startsWith(matrix.os, 'windows') + run: ${{ env.CARGO }} build ${{ env.TARGET_FLAGS }} --all-features - name: Build (and link) run: ${{ env.CARGO }} build ${{ env.TARGET_FLAGS }} - name: Run tests diff --git a/Cargo.toml b/Cargo.toml index fd7e36d..8eb39a0 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -12,6 +12,16 @@ keywords = ["open", "xdg-open", "start", "launch"] include = ["src/**/*", "LICENSE.md", "README.md", "changelog.md"] rust-version = "1.62" +[features] +## If enabled, link to `shell32` on Windows and use `ShellExecuteW` intead of a command invocation. +## That way, it should be possible to open currently opened (for writing) files as well. +## +## However, if the `flate2` crate with zlib-ng backend is also used in the same tree, it maybe that +## linkage fails. +## +## This feature is only effective on Windows. +shellexecute-on-windows = [] + [[bin]] test = false doc = false diff --git a/src/lib.rs b/src/lib.rs index 9afcd8c..2c6a43c 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -237,7 +237,7 @@ pub fn with_in_background>( /// /// See documentation of [`that()`] for more details. pub fn that_detached(path: impl AsRef) -> io::Result<()> { - #[cfg(not(windows))] + #[cfg(any(not(feature = "shellexecute-on-windows"), not(windows)))] { let mut last_err = None; for mut cmd in commands(path) { @@ -251,7 +251,7 @@ pub fn that_detached(path: impl AsRef) -> io::Result<()> { Err(last_err.expect("no launcher worked, at least one error")) } - #[cfg(windows)] + #[cfg(all(windows, feature = "shellexecute-on-windows"))] { windows::that_detached(path) } @@ -263,13 +263,13 @@ pub fn that_detached(path: impl AsRef) -> io::Result<()> { /// /// See documentation of [`with()`] for more details. pub fn with_detached>(path: T, app: impl Into) -> io::Result<()> { - #[cfg(not(windows))] + #[cfg(any(not(feature = "shellexecute-on-windows"), not(windows)))] { let mut cmd = with_command(path, app); cmd.spawn_detached() } - #[cfg(windows)] + #[cfg(all(windows, feature = "shellexecute-on-windows"))] { windows::with_detached(path, app) } diff --git a/src/windows.rs b/src/windows.rs index 2977c78..c58db74 100644 --- a/src/windows.rs +++ b/src/windows.rs @@ -39,6 +39,7 @@ fn wrap_in_quotes>(path: T) -> OsString { result } +#[cfg(feature = "shellexecute-on-windows")] pub fn that_detached>(path: T) -> std::io::Result<()> { let path = wide(path); @@ -54,6 +55,7 @@ pub fn that_detached>(path: T) -> std::io::Result<()> { } } +#[cfg(feature = "shellexecute-on-windows")] pub fn with_detached>(path: T, app: impl Into) -> std::io::Result<()> { let app = wide(app.into()); let path = wide(path); @@ -79,6 +81,7 @@ fn wide>(input: T) -> Vec { /// /// #[allow(non_snake_case)] +#[cfg(feature = "shellexecute-on-windows")] pub unsafe fn ShellExecuteW( hwnd: isize, lpoperation: *const u16, @@ -105,6 +108,7 @@ pub unsafe fn ShellExecuteW( } } +#[cfg(feature = "shellexecute-on-windows")] mod ffi { /// Activates the window and displays it in its current size and position. ///