br_code/
qrcode.rs

1use std::{env, fs};
2use std::time::{SystemTime, UNIX_EPOCH};
3use image::{Luma};
4use qrcode::{QrCode};
5use qrcode::render::{svg};
6use image;
7
8/// 生成二维码
9pub fn qrcode_create(text: &str, mode: &str) -> Result<String, String> {
10    let temp_dir = env::temp_dir();
11    let filename = format!("{}.{mode}", SystemTime::now().duration_since(UNIX_EPOCH).unwrap().as_secs());
12    let filepath = temp_dir.join(filename);
13
14    let code = match QrCode::new(text.as_bytes()) {
15        Ok(e) => e,
16        Err(e) => return Err(format!("Error QrCode file: {}", e)),
17    };
18    match mode {
19        "svg" => {
20            let string = code.render().min_dimensions(200, 200).dark_color(svg::Color("#000000")).light_color(svg::Color("#ffffff")).build();
21            match fs::write(filepath.clone(), string) {
22                Ok(_) => Ok(filepath.to_str().unwrap().to_string()),
23                Err(e) => Err(format!("Error writing svg file: {}", e)),
24            }
25        }
26        "png" => {
27            let image = code.render::<Luma<u8>>().build();
28            match image.save(filepath.clone()) {
29                Ok(_) => Ok(filepath.to_str().unwrap().to_string()),
30                Err(e) => Err(format!("Error writing png file: {}", e)),
31            }
32        }
33        _ => {
34            let image = code.render::<Luma<u8>>().min_dimensions(200, 200).build();
35            match image.save(filepath.clone()) {
36                Ok(_) => Ok(filepath.to_str().unwrap().to_string()),
37                Err(e) => Err(format!("Error writing file: {}", e)),
38            }
39        }
40    }
41}
42
43pub fn qrcode_read(filename: &str) -> Vec<String> {
44    let mut qrcode = vec![];
45
46    let img = image::open(filename);
47    let img_gray = match img {
48        Ok(e) => e.into_luma8(),
49        Err(_) => {
50            return qrcode;
51        }
52    };
53
54    let mut decoder = quircs::Quirc::default();
55    let codes = decoder.identify(img_gray.width() as usize, img_gray.height() as usize, &img_gray);
56    for code in codes {
57        let code = match code {
58            Ok(e) => e,
59            Err(_) => {
60                return qrcode;
61            }
62        };
63        let decoded = match code.decode() {
64            Ok(e) => e,
65            Err(_) => {
66                return qrcode;
67            }
68        };
69        qrcode.push(std::str::from_utf8(&decoded.payload.clone()).unwrap().to_string());
70    }
71    qrcode
72}
73
74/// 生成 svg 二维码
75pub fn create_qrcode(code: &str) -> String {
76    let code = QrCode::new(code).unwrap();
77    let string = code.render().min_dimensions(200, 200).dark_color(svg::Color("#000000")).light_color(svg::Color("#ffffff")).build();
78    string.replace("width=\"203\"", "width=\"100%\"").replace("height=\"203\"", "height=\"100%\"")
79}