Skip to main content

virtual_file_transfer/
windows.rs

1//! Windows OLE integration for virtual-file transfer.
2//!
3//! Most applications should use the crate-level [`crate::begin_drag`]
4//! and [`crate::copy_to_clipboard`] convenience functions.
5//! This module also exposes a lower-level
6//! [`crate::windows::create_data_object`] function for applications
7//! that manage their own drag-and-drop flow.
8mod clipboard;
9mod data_object;
10mod drag_drop;
11mod drop_source;
12mod error;
13mod formats;
14mod stream;
15
16pub(crate) mod validation;
17
18use std::marker::PhantomData;
19use std::rc::Rc;
20
21use windows::Win32::System::Com::IDataObject;
22use windows::Win32::System::Ole::{OleInitialize, OleUninitialize};
23
24use crate::TransferRequest;
25
26pub(crate) use self::clipboard::{ClipboardSession, copy_to_clipboard};
27pub(crate) use self::drag_drop::begin_drag;
28
29/// Creates an OLE `IDataObject` advertising the request's virtual files.
30///
31/// Use this when the application already manages its own `IDropSource`,
32/// `DoDragDrop` invocation, and transfer effects. The caller is responsible
33/// for appropriate COM/OLE initialization, threading, and object lifetimes.
34/// A `Vec<VirtualFile>` can be passed directly.
35///
36/// Unlike [`begin_drag`](crate::begin_drag), this function only constructs
37/// the data object; it does not start a drag operation.
38///
39/// # Errors
40///
41/// Returns [`crate::Error::InvalidInput`] for invalid transfer requests or
42/// [`crate::Error::Platform`] for a platform integration failure.
43pub fn create_data_object(request: impl Into<TransferRequest>) -> crate::Result<IDataObject> {
44    data_object::create_data_object(request.into())
45}
46
47pub(crate) struct OleContext {
48    _thread_affinity: PhantomData<Rc<()>>,
49}
50
51impl OleContext {
52    pub(crate) fn new() -> windows::core::Result<Self> {
53        unsafe {
54            OleInitialize(None)?;
55        }
56
57        Ok(Self {
58            _thread_affinity: PhantomData,
59        })
60    }
61}
62
63impl Drop for OleContext {
64    fn drop(&mut self) {
65        unsafe {
66            OleUninitialize();
67        }
68    }
69}
70
71#[cfg(test)]
72mod tests {
73    use super::*;
74
75    #[test]
76    fn initializes_ole() {
77        let _ole = OleContext::new().unwrap();
78    }
79}