rust - 将windows剪贴板的截图保存为png

本文提供了将windows系统的截图另存为png格式图片的方法。

添加依赖

rust 复制代码
cargo add clipboard-win
cargo add image
cargo add windows

配置修改windows依赖特性

rust 复制代码
[dependencies]
image = "0.25.0"

[target.'cfg(windows)'.dependencies]
windows = "0.51.1"
clipboard-win = "5.3.0"

[dependencies.windows]
version = "0.51"
features = [
    "Win32_Foundation",
    "Win32_System_DataExchange",
    "Win32_Graphics_Gdi",
    "Win32_System_LibraryLoader",
    "Win32_UI_WindowsAndMessaging",
    "Win32_System_DataExchange",
    "Win32_System_Registry",
]

模拟windows截图并另存为png文件

rust 复制代码
use clipboard_win::formats::Bitmap;
use clipboard_win::{Clipboard, Getter, Setter};
use core::{mem, ptr};
use image::{
    codecs::png::PngEncoder, GenericImageView, ImageEncoder, ImageFormat,
};
use std::env;
use std::io::Write;
use std::{
    fs,
    io::{BufReader, BufWriter, Cursor},
};
use windows::Win32::Graphics::Gdi::{BITMAPFILEHEADER, BITMAPINFOHEADER};

const INFO_HEADER_LEN: usize = mem::size_of::<BITMAPINFOHEADER>();
const FILE_HEADER_LEN: usize = mem::size_of::<BITMAPFILEHEADER>();

#[test]
fn test_to_png() {
    // 读取bitmap文件
    let image_path = env::current_dir().unwrap().join("tests/test-image.bmp");
    let test_image_bytes = std::fs::read(image_path).expect("Read test image");

    // 打开剪贴板
    let _clip = Clipboard::new_attempts(10).expect("Open clipboard");
    // 保存到剪贴板模拟截图
    Bitmap.write_clipboard(&test_image_bytes).expect("To set image");

    // 从剪贴板读取截图
    let mut output: Vec<u8> = Vec::new();
    let _ = Bitmap.read_clipboard(&mut output);

    // 获得位图的大小(在栈上申请一块未初始化内存)
    let mut info_header = mem::MaybeUninit::<BITMAPINFOHEADER>::uninit();
    let info_header = unsafe {
        ptr::copy_nonoverlapping(
            output.as_ptr().add(FILE_HEADER_LEN),
            info_header.as_mut_ptr() as _,
            INFO_HEADER_LEN,
        );
        // 把T的所有权返回,编译器会主动对T调用drop
        info_header.assume_init()
    };
    let bitmap_width = info_header.biWidth;
    let bitmap_height = info_header.biHeight;

    assert_eq!(bitmap_width, 750);
    assert_eq!(bitmap_height, 300);

    // 将数组转换为BufReader对象,并读取位图信息
    let buf_reader = BufReader::new(Cursor::new(output));
    let img = image::load(buf_reader, ImageFormat::Bmp).unwrap();

    // 转换为png格式
    let mut png_file_content = Vec::new();
    let buff_writer = BufWriter::new(&mut png_file_content);
    let encoder = PngEncoder::new(buff_writer);
    let _ = encoder.write_image(
        &img.as_bytes().to_vec(),
        img.dimensions().0,
        img.dimensions().1,
        img.color().into(),
    );

    // 另存为png文件
    let png_path = env::current_dir().unwrap().join("tests/test-image.png");
    let mut file = fs::File::create(png_path).unwrap();
    file.write_all(png_file_content.as_slice()).unwrap();
}
相关推荐
Sylvia33.1 分钟前
火星数据体育API|一站式接入足球篮球电竞等18+项目实时数据
java·开发语言·python·websocket·游戏
Data_Journal27 分钟前
使用 AutoScraper 进行网页抓取:分步教程
大数据·开发语言·数据库·python·scrapy
yume_sibai44 分钟前
12-Rust 性能优化指南(性能分析 + 内存优化 + SIMD + 并发优化 + 编译器优化 + 基准测试)
开发语言·性能优化·rust
萧瑟余晖1 小时前
Hibernate 核心原理与架构详解
开发语言·架构·hibernate
爱喝水的鱼丶1 小时前
SAP-ABAP:SAP MM 模块物料主数据批量导入与增强开发:字段扩展、校验逻辑与批量导入工具开发
开发语言·性能优化·sap·abap·增强·经验交流·mm
geovindu1 小时前
rust:Builder Pattern
开发语言·设计模式·rust·建造者模式
白远山1 小时前
健身场馆无人自动化解决方案:从架构到落地实践
java·开发语言·数据库·数据挖掘·需求分析
Data_Journal2 小时前
如何将网页抓取用于机器学习
大数据·开发语言·数据库·python·scrapy
郝学胜-神的一滴2 小时前
Effective Python 条款 13:善用星号解包,告别下标切片拆分的坑
服务器·开发语言·数据结构·python·程序人生·pycharm
一水鉴天3 小时前
词、术语、概念:从特征集收束到统一拓扑变换的升格与降格模型 20260915(豆包)
开发语言·人工智能