Skip to content

Commit 554309e

Browse files
committed
rust: add writer API
1 parent 204f0cf commit 554309e

File tree

10 files changed

+357
-101
lines changed

10 files changed

+357
-101
lines changed

.github/workflows/ci.yml

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -186,10 +186,12 @@ jobs:
186186
runs-on: ${{ matrix.os }}
187187
strategy:
188188
matrix:
189-
os: [ubuntu-latest, macos-latest, windows-latest]
189+
os: [ubuntu-latest, macos-13, windows-latest]
190190

191191
steps:
192192
- uses: actions/checkout@v4
193+
with:
194+
submodules: true
193195

194196
- name: Lint
195197
working-directory: wrappers/rust

core/src/WriteBarcode.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ struct CreatorOptions::Data
3535

3636
mutable std::unique_ptr<zint_symbol> zint;
3737

38-
#if __cplusplus <= 201703L
38+
#if __cplusplus <= 201703L || defined(__APPLE__)
3939
Data(BarcodeFormat f) : format(f) {}
4040
#endif
4141
};
@@ -283,7 +283,7 @@ struct SetCommonWriterOptions
283283
zint->output_options |= opts.withQuietZones() ? BARCODE_QUIET_ZONES : BARCODE_NO_QUIET_ZONES;
284284

285285
if (opts.scale())
286-
zint->scale = opts.scale();
286+
zint->scale = opts.scale() / 2.f;
287287
else if (opts.sizeHint()) {
288288
int size = std::max(zint->width, zint->rows);
289289
zint->scale = std::max(1, int(float(opts.sizeHint()) / size)) / 2.f;

wrappers/rust/Cargo.toml

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[package]
22
name = "zxing-cpp"
3-
version = "0.3.0"
3+
version = "0.4.0"
44
edition = "2021"
55
# authors = ["Axel Waggershauser <[email protected]>"]
66
license = "Apache-2.0"
@@ -10,9 +10,8 @@ readme = "README.md"
1010
keywords = ["zxing", "barcode", "barcode_reader", "ffi"]
1111
categories = ["api-bindings", "computer-vision"]
1212
exclude = [
13-
"core/**/*Write*",
13+
"core/**/*Writer*",
1414
"core/**/*Encode*",
15-
"core/src/libzint/**",
1615
]
1716

1817
[lib]

wrappers/rust/README.md

Lines changed: 19 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -15,34 +15,42 @@ In your Cargo.toml:
1515
# `bundled` causes cargo to compile and statically link an up to
1616
# date version of the c++ core library. This is the most convenient
1717
# and safe way to build the library.
18-
zxing-cpp = { version = "0.3.0", features = ["bundled", "image"] }
18+
zxing-cpp = { version = "0.4.0", features = ["bundled", "image"] }
1919
```
2020

21-
Simple example usage:
21+
Simple example reading some barcodes from a jpg file:
2222

2323
```rust
24-
use zxingcpp::{BarcodeFormat, BarcodeReader, ImageView};
24+
use zxingcpp::BarcodeFormat;
2525

2626
fn main() -> anyhow::Result<()> {
2727
let image = image::open("some-image-file.jpg")?;
28-
let reader = BarcodeReader::new()
28+
29+
let read_barcodes = zxingcpp::read()
2930
.formats(BarcodeFormat::QRCode | BarcodeFormat::LinearCodes)
3031
.try_invert(false);
3132

32-
let barcodes = reader.read(&image)?;
33+
let barcodes = read_barcodes.from(&image)?;
3334

34-
if barcodes.is_empty() {
35-
println!("No barcode found.");
36-
} else {
37-
for barcode in barcodes {
38-
println!("{}: {}", barcode.format(), barcode.text());
39-
}
35+
for barcode in barcodes {
36+
println!("{}: {}", barcode.format(), barcode.text());
4037
}
4138

4239
Ok(())
4340
}
4441
```
4542

43+
Simple example creating a barcode and writing it to a svg file:
44+
```rust
45+
fn main() -> anyhow::Result<()> {
46+
let svg = zxingcpp::create(zxingcpp::BarcodeFormat::QRCode)
47+
.from_str("https://github.com/zxing-cpp/zxing-cpp")?
48+
.to_svg_with(&zxingcpp::write().scale(5))?;
49+
std::fs::write("zxingcpp.svg", svg)?;
50+
Ok(())
51+
}
52+
```
53+
4654
Note: This should currently be considered a pre-release. The API may change slightly to be even more
4755
"rusty" depending on community feedback.
4856

wrappers/rust/build.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,10 @@ fn main() -> miette::Result<()> {
66
let mut dst = cmake::Config::new("core")
77
.define("BUILD_SHARED_LIBS", "OFF")
88
.define("BUILD_READERS", "ON")
9-
.define("BUILD_WRITERS", "OFF")
9+
.define("BUILD_WRITERS", "NEW")
10+
.define("BUILD_EXPERIMENTAL_API", "ON")
1011
.define("BUILD_C_API", "ON")
12+
.define("ZXING_USE_BUNDLED_ZINT", "ON")
1113
.define("CMAKE_CXX_STANDARD", "20")
1214
.build();
1315
dst.push("lib");

wrappers/rust/examples/demo.rs renamed to wrappers/rust/examples/demo_reader.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ fn main() -> anyhow::Result<()> {
1818
let iv = ImageView::from_slice(&lum_img, lum_img.width(), lum_img.height(), ImageFormat::Lum)?;
1919

2020
let formats = BarcodeFormats::from_str(formats.unwrap_or_default())?;
21-
let reader = BarcodeReader::new()
21+
let read_barcodes = BarcodeReader::new()
2222
.formats(formats)
2323
.try_harder(!fast)
2424
.try_invert(!fast)
@@ -27,9 +27,9 @@ fn main() -> anyhow::Result<()> {
2727
.return_errors(true);
2828

2929
#[cfg(feature = "image")]
30-
let barcodes = reader.read(&image)?;
30+
let barcodes = read_barcodes.from(&image)?;
3131
#[cfg(not(feature = "image"))]
32-
let barcodes = reader.read(iv)?;
32+
let barcodes = read_barcodes.from(iv)?;
3333

3434
if barcodes.is_empty() {
3535
println!("No barcode found.");

wrappers/rust/examples/demo_writer.rs

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
/*
2+
* Copyright 2024 Axel Waggershauser
3+
*/
4+
// SPDX-License-Identifier: Apache-2.0
5+
6+
use image;
7+
use std::fs;
8+
use zxingcpp::*;
9+
10+
fn main() -> anyhow::Result<()> {
11+
let text = std::env::args().nth(1).expect("no input text provided");
12+
let format = std::env::args().nth(2).expect("no format provided");
13+
let filename = std::env::args().nth(3).expect("no output file name provided");
14+
15+
let create_barcode = create(BarcodeFormat::from_str(format)?);
16+
let bc = create_barcode.from_str(text)?;
17+
18+
if filename.ends_with(".svg") {
19+
fs::write(filename, bc.to_svg_with(&write().with_hrt(true))?).expect("Unable to write file");
20+
} else {
21+
image::GrayImage::from(&bc.to_image_with(&write().scale(4))?).save(filename)?;
22+
}
23+
24+
Ok(())
25+
}

wrappers/rust/src/bindings.rs

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,16 @@ pub struct ZXing_Image {
2525
pub struct ZXing_ReaderOptions {
2626
_unused: [u8; 0],
2727
}
28+
#[repr(C)]
29+
#[derive(Debug, Copy, Clone)]
30+
pub struct ZXing_CreatorOptions {
31+
_unused: [u8; 0],
32+
}
33+
#[repr(C)]
34+
#[derive(Debug, Copy, Clone)]
35+
pub struct ZXing_WriterOptions {
36+
_unused: [u8; 0],
37+
}
2838
pub const ZXing_ImageFormat_None: ZXing_ImageFormat = 0;
2939
pub const ZXing_ImageFormat_Lum: ZXing_ImageFormat = 16777216;
3040
pub const ZXing_ImageFormat_LumA: ZXing_ImageFormat = 33554432;
@@ -188,6 +198,40 @@ extern "C" {
188198
pub fn ZXing_ReaderOptions_getMaxNumberOfSymbols(opts: *const ZXing_ReaderOptions) -> ::core::ffi::c_int;
189199
pub fn ZXing_ReadBarcode(iv: *const ZXing_ImageView, opts: *const ZXing_ReaderOptions) -> *mut ZXing_Barcode;
190200
pub fn ZXing_ReadBarcodes(iv: *const ZXing_ImageView, opts: *const ZXing_ReaderOptions) -> *mut ZXing_Barcodes;
201+
pub fn ZXing_CreatorOptions_new(format: ZXing_BarcodeFormat) -> *mut ZXing_CreatorOptions;
202+
pub fn ZXing_CreatorOptions_delete(opts: *mut ZXing_CreatorOptions);
203+
pub fn ZXing_CreatorOptions_setFormat(opts: *mut ZXing_CreatorOptions, format: ZXing_BarcodeFormat);
204+
pub fn ZXing_CreatorOptions_getFormat(opts: *const ZXing_CreatorOptions) -> ZXing_BarcodeFormat;
205+
pub fn ZXing_CreatorOptions_setReaderInit(opts: *mut ZXing_CreatorOptions, readerInit: bool);
206+
pub fn ZXing_CreatorOptions_getReaderInit(opts: *const ZXing_CreatorOptions) -> bool;
207+
pub fn ZXing_CreatorOptions_setForceSquareDataMatrix(opts: *mut ZXing_CreatorOptions, forceSquareDataMatrix: bool);
208+
pub fn ZXing_CreatorOptions_getForceSquareDataMatrix(opts: *const ZXing_CreatorOptions) -> bool;
209+
pub fn ZXing_CreatorOptions_setEcLevel(opts: *mut ZXing_CreatorOptions, ecLevel: *const ::core::ffi::c_char);
210+
pub fn ZXing_CreatorOptions_getEcLevel(opts: *const ZXing_CreatorOptions) -> *mut ::core::ffi::c_char;
211+
pub fn ZXing_WriterOptions_new() -> *mut ZXing_WriterOptions;
212+
pub fn ZXing_WriterOptions_delete(opts: *mut ZXing_WriterOptions);
213+
pub fn ZXing_WriterOptions_setScale(opts: *mut ZXing_WriterOptions, scale: ::core::ffi::c_int);
214+
pub fn ZXing_WriterOptions_getScale(opts: *const ZXing_WriterOptions) -> ::core::ffi::c_int;
215+
pub fn ZXing_WriterOptions_setSizeHint(opts: *mut ZXing_WriterOptions, sizeHint: ::core::ffi::c_int);
216+
pub fn ZXing_WriterOptions_getSizeHint(opts: *const ZXing_WriterOptions) -> ::core::ffi::c_int;
217+
pub fn ZXing_WriterOptions_setRotate(opts: *mut ZXing_WriterOptions, rotate: ::core::ffi::c_int);
218+
pub fn ZXing_WriterOptions_getRotate(opts: *const ZXing_WriterOptions) -> ::core::ffi::c_int;
219+
pub fn ZXing_WriterOptions_setWithHRT(opts: *mut ZXing_WriterOptions, withHRT: bool);
220+
pub fn ZXing_WriterOptions_getWithHRT(opts: *const ZXing_WriterOptions) -> bool;
221+
pub fn ZXing_WriterOptions_setWithQuietZones(opts: *mut ZXing_WriterOptions, withQuietZones: bool);
222+
pub fn ZXing_WriterOptions_getWithQuietZones(opts: *const ZXing_WriterOptions) -> bool;
223+
pub fn ZXing_CreateBarcodeFromText(
224+
data: *const ::core::ffi::c_char,
225+
size: ::core::ffi::c_int,
226+
opts: *const ZXing_CreatorOptions,
227+
) -> *mut ZXing_Barcode;
228+
pub fn ZXing_CreateBarcodeFromBytes(
229+
data: *const ::core::ffi::c_void,
230+
size: ::core::ffi::c_int,
231+
opts: *const ZXing_CreatorOptions,
232+
) -> *mut ZXing_Barcode;
233+
pub fn ZXing_WriteBarcodeToSVG(barcode: *const ZXing_Barcode, opts: *const ZXing_WriterOptions) -> *mut ::core::ffi::c_char;
234+
pub fn ZXing_WriteBarcodeToImage(barcode: *const ZXing_Barcode, opts: *const ZXing_WriterOptions) -> *mut ZXing_Image;
191235
pub fn ZXing_LastErrorMsg() -> *mut ::core::ffi::c_char;
192236
pub fn ZXing_free(ptr: *mut ::core::ffi::c_void);
193237
}

0 commit comments

Comments
 (0)