Commit 85a1025ca190c7543076bc92dc43dc682d54e083

Cléo Rebert 2023-09-14T15:40:52

Optimized draw_image Signed-off-by: Cléo Rebert <cleo.rebert@gmail.com>

diff --git a/qrcodegen-image/CHANGELOG.md b/qrcodegen-image/CHANGELOG.md
index 2f299da..076afc9 100644
--- a/qrcodegen-image/CHANGELOG.md
+++ b/qrcodegen-image/CHANGELOG.md
@@ -1,5 +1,12 @@
 # Changelog
 
+## [1.2.0](https://github.com/constantoine/totp-rs/releases/tag/qrcodegen-image%2Fv1.2.0) (14/09/2023)
+
+### What's new
+
+- Added benchmarks for `draw_canvas`.
+- `draw_canvas` is now 150%(!) faster on my machine after optimizing the "border" loop.
+
 ## [1.1.0](https://github.com/constantoine/totp-rs/releases/tag/qrcodegen-image%2Fv1.1.0) (11/09/2023)
 
 ### What's new
diff --git a/qrcodegen-image/Cargo.toml b/qrcodegen-image/Cargo.toml
index 85e2ad9..a7f1f5b 100644
--- a/qrcodegen-image/Cargo.toml
+++ b/qrcodegen-image/Cargo.toml
@@ -1,6 +1,6 @@
 [package]
 name = "qrcodegen-image"
-version = "1.1.0"
+version = "1.2.0"
 edition = "2021"
 authors = ["Cleo Rebert <cleo.rebert@gmail.com>"]
 rust-version = "1.61"
@@ -20,3 +20,10 @@ base64 = ["dep:base64"]
 qrcodegen = "1.8"
 image = { version = "0.24", features = ["png"], default-features = false}
 base64 = { version = "0.21", optional = true }
+
+[dev-dependencies]
+criterion = { version = "0.5", features = ["html_reports"] }
+
+[[bench]]
+name = "benches"
+harness = false
\ No newline at end of file
diff --git a/qrcodegen-image/benches/benches.rs b/qrcodegen-image/benches/benches.rs
new file mode 100644
index 0000000..c29f7fe
--- /dev/null
+++ b/qrcodegen-image/benches/benches.rs
@@ -0,0 +1,17 @@
+use criterion::{black_box, criterion_group, criterion_main, BenchmarkId, Criterion};
+
+fn criterion_benchmark(c: &mut Criterion) {
+    let input = qrcodegen::QrCode::encode_text("otpauth://totp/GitHub:test?issuer=GitHub&secret=KRSXG5CTMVRXEZLUKN2XAZLSKNSWG4TFOQ&digits=8&period=60&algorithm=SHA256", qrcodegen::QrCodeEcc::Medium).unwrap();
+    c.bench_with_input(
+        BenchmarkId::new("qrcodegen-image", "draw_canvas"),
+        black_box(&input),
+        |b, i| {
+            b.iter(|| {
+                let _img = qrcodegen_image::draw_canvas(i.clone());
+            })
+        },
+    );
+}
+
+criterion_group!(benches, criterion_benchmark);
+criterion_main!(benches);
diff --git a/qrcodegen-image/src/lib.rs b/qrcodegen-image/src/lib.rs
index 6ab8552..9e9d3a1 100644
--- a/qrcodegen-image/src/lib.rs
+++ b/qrcodegen-image/src/lib.rs
@@ -14,12 +14,8 @@ pub fn draw_canvas(qr: qrcodegen::QrCode) -> image::ImageBuffer<Luma<u8>, Vec<u8
     let mut canvas = image::GrayImage::new(image_size, image_size);
 
     // Draw the border
-    for x in 0..image_size {
-        for y in 0..image_size {
-            if (y < 8 * 4 || y >= image_size - 8 * 4) || (x < 8 * 4 || x >= image_size - 8 * 4) {
-                canvas.put_pixel(x, y, Luma([255]));
-            }
-        }
+    for pixel in canvas.pixels_mut() {
+        *pixel = Luma([255]);
     }
 
     // The QR inside the white border