Skip to content

Commit 7219f9d

Browse files
committed
add support for output string arguments
1 parent 4745beb commit 7219f9d

File tree

4 files changed

+103
-4
lines changed

4 files changed

+103
-4
lines changed

gen_rust.py

Lines changed: 40 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1695,19 +1695,55 @@ def __init__(self, gen, typeid):
16951695
self.c_safe_id = "char_X"
16961696
self.rust_extern = "*mut c_char"
16971697

1698-
def cpp_arg_func_call(self, var_name, is_output=False):
1699-
return "{}({})".format(self.cpptype, var_name)
1698+
def is_output(self):
1699+
return self.is_by_ref and not self.is_const
1700+
1701+
def rust_arg_func_decl(self, var_name, is_output=False):
1702+
if self.is_output():
1703+
return "{}: &mut String".format(var_name)
1704+
return "{}: &str".format(var_name)
17001705

17011706
def rust_arg_pre_call(self, var_name, is_output=False):
1707+
if self.is_output():
1708+
return "string_arg_output_send!(via {}_via)".format(var_name)
17021709
return "string_arg!({}{})".format("" if self.is_const else "mut ", var_name)
17031710

17041711
def rust_arg_func_call(self, var_name, is_output=False):
1712+
if self.is_output():
1713+
return "&mut {}_via".format(var_name)
17051714
if self.is_const:
17061715
return "{}.as_ptr()".format(var_name)
17071716
return "{}.as_ptr() as _".format(var_name) # fixme: use as_mut_ptr() when it's stabilized
17081717

1709-
def rust_arg_func_decl(self, var_name, is_output=False):
1710-
return "{}: &str".format(var_name)
1718+
def rust_extern_arg_func_decl(self, var_name, is_output=False):
1719+
if self.is_output():
1720+
return "{}: *mut {}".format(var_name, self.rust_extern)
1721+
return super(StringTypeInfo, self).rust_extern_arg_func_decl(var_name, is_output)
1722+
1723+
def rust_arg_post_call(self, var_name, is_output=False):
1724+
if self.is_output():
1725+
return "string_arg_output_receive!({}_via => {})".format(var_name, var_name)
1726+
return super(StringTypeInfo, self).rust_arg_post_call(var_name, is_output)
1727+
1728+
def cpp_arg_func_decl(self, var_name, is_output=False):
1729+
if self.is_output():
1730+
return "{}* {}".format(self.cpp_extern, var_name)
1731+
return super(StringTypeInfo, self).cpp_arg_func_decl(var_name, is_output)
1732+
1733+
def cpp_arg_pre_call(self, var_name, is_output=False):
1734+
if self.is_output():
1735+
return "std::string {}_out".format(var_name)
1736+
return super(StringTypeInfo, self).cpp_arg_pre_call(var_name, is_output)
1737+
1738+
def cpp_arg_func_call(self, var_name, is_output=False):
1739+
if self.is_output():
1740+
return "{}_out".format(var_name)
1741+
return "{}({})".format(self.cpptype, var_name)
1742+
1743+
def cpp_arg_post_call(self, var_name, is_output=False):
1744+
if self.is_output():
1745+
return "*{} = strdup({}_out.c_str())".format(var_name, var_name)
1746+
return super(StringTypeInfo, self).cpp_arg_post_call(var_name, is_output)
17111747

17121748
def cpp_method_return(self, is_constructor):
17131749
return "return { Error::Code::StsOk, NULL, strdup(ret.c_str()) };"

src/templ.rs

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,18 @@ macro_rules! string_arg {
1212
};
1313
}
1414

15+
macro_rules! string_arg_output_send {
16+
(via $name_via: ident) => {
17+
let mut $name_via = ::std::ptr::null_mut();
18+
};
19+
}
20+
21+
macro_rules! string_arg_output_receive {
22+
($name_via: ident => $name: ident) => {
23+
*$name = $crate::templ::receive_string_mut($name_via);
24+
};
25+
}
26+
1527
macro_rules! callback_arg {
1628
($callback_name: ident($($tr_arg_name: ident: $tr_arg_type: ty),*) via $userdata_name: ident => ($($fw_arg_name: ident: $fw_arg_type: ty),*)) => {
1729
::lazy_static::lazy_static!(

tests/objdetect.rs

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
use std::path::PathBuf;
2+
3+
use opencv::{
4+
core::Mat,
5+
imgcodecs,
6+
objdetect,
7+
types::VectorOfPoint,
8+
};
9+
10+
#[test]
11+
fn qr_code() {
12+
let qr_path = PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("tests/qr.png");
13+
14+
{
15+
let mut detector = objdetect::QRCodeDetector::new().unwrap();
16+
let src = imgcodecs::imread(qr_path.to_str().unwrap(), imgcodecs::IMREAD_COLOR).unwrap();
17+
let mut pts = VectorOfPoint::new();
18+
let mut straight = Mat::default();
19+
let res = detector.detect_and_decode(&src, &mut pts, &mut straight).unwrap();
20+
assert_eq!(res, "https://crates.io/crates/opencv");
21+
assert_eq!(4, pts.len());
22+
assert!(!straight.empty().unwrap());
23+
}
24+
25+
{
26+
let mut detector = objdetect::QRCodeDetector::new().unwrap();
27+
let src = imgcodecs::imread(qr_path.to_str().unwrap(), imgcodecs::IMREAD_COLOR).unwrap();
28+
let mut pts = VectorOfPoint::new();
29+
let res = detector.detect(&src, &mut pts).unwrap();
30+
assert!(res);
31+
assert_eq!(4, pts.len());
32+
let mut straight = Mat::default();
33+
let res = detector.decode(&src, &pts, &mut straight).unwrap();
34+
assert_eq!(res, "https://crates.io/crates/opencv");
35+
assert!(!straight.empty().unwrap());
36+
}
37+
38+
{
39+
let src = imgcodecs::imread(qr_path.to_str().unwrap(), imgcodecs::IMREAD_COLOR).unwrap();
40+
let mut pts = VectorOfPoint::new();
41+
let res = objdetect::detect_qr_code(&src, &mut pts, 0.2, 0.1).unwrap();
42+
assert!(res);
43+
assert_eq!(4, pts.len());
44+
let mut out = String::new();
45+
let mut straight = Mat::default();
46+
let res = objdetect::decode_qr_code(&src, &pts, &mut out, &mut straight).unwrap();
47+
assert!(res);
48+
assert_eq!(out, "https://crates.io/crates/opencv");
49+
assert!(!straight.empty().unwrap());
50+
}
51+
}

tests/qr.png

542 Bytes
Loading

0 commit comments

Comments
 (0)