cv_convert/
with_opencv.rs1use crate::opencv::{core as core_cv, prelude::*};
2use crate::{common::*, TryFromCv};
3use half::f16;
4
5pub use element_type::*;
6mod element_type {
7 use super::*;
8
9 pub trait OpenCvElement {
10 const DEPTH: i32;
11 }
12
13 impl OpenCvElement for u8 {
14 const DEPTH: i32 = core_cv::CV_8U;
15 }
16
17 impl OpenCvElement for i8 {
18 const DEPTH: i32 = core_cv::CV_8S;
19 }
20
21 impl OpenCvElement for u16 {
22 const DEPTH: i32 = core_cv::CV_16U;
23 }
24
25 impl OpenCvElement for i16 {
26 const DEPTH: i32 = core_cv::CV_16S;
27 }
28
29 impl OpenCvElement for i32 {
30 const DEPTH: i32 = core_cv::CV_32S;
31 }
32
33 impl OpenCvElement for f16 {
34 const DEPTH: i32 = core_cv::CV_16F;
35 }
36
37 impl OpenCvElement for f32 {
38 const DEPTH: i32 = core_cv::CV_32F;
39 }
40
41 impl OpenCvElement for f64 {
42 const DEPTH: i32 = core_cv::CV_64F;
43 }
44}
45
46pub(crate) use mat_ext::*;
47mod mat_ext {
48 use super::*;
49
50 pub trait MatExt {
51 fn size_with_depth(&self) -> Vec<usize>;
52
53 fn numel(&self) -> usize {
54 self.size_with_depth().iter().product()
55 }
56
57 fn as_slice<T>(&self) -> Result<&[T]>
58 where
59 T: OpenCvElement;
60
61 fn type_name(&self) -> String;
62
63 #[cfg(test)]
64 fn new_randn_2d(rows: i32, cols: i32, typ: i32) -> Result<Self>
65 where
66 Self: Sized;
67
68 #[cfg(test)]
69 fn new_randn_nd<T>(shape: &[usize]) -> Result<Self>
70 where
71 Self: Sized,
72 T: OpenCvElement;
73 }
74
75 impl MatExt for core_cv::Mat {
76 fn size_with_depth(&self) -> Vec<usize> {
77 let size = self.mat_size();
78 let size = size.iter().map(|&dim| dim as usize);
79 let channels = self.channels() as usize;
80 size.chain([channels]).collect()
81 }
82
83 fn as_slice<T>(&self) -> Result<&[T]>
84 where
85 T: OpenCvElement,
86 {
87 ensure!(self.depth() == T::DEPTH, "element type mismatch");
88 ensure!(self.is_continuous(), "Mat data must be continuous");
89
90 let numel = self.numel();
91 let ptr = self.ptr(0)? as *const T;
92
93 let slice = unsafe { slice::from_raw_parts(ptr, numel) };
94 Ok(slice)
95 }
96
97 fn type_name(&self) -> String {
98 core_cv::type_to_string(self.typ()).unwrap()
99 }
100
101 #[cfg(test)]
102 fn new_randn_2d(rows: i32, cols: i32, typ: i32) -> Result<Self>
103 where
104 Self: Sized,
105 {
106 let mut mat = Self::zeros(rows, cols, typ)?.to_mat()?;
107 core_cv::randn(&mut mat, &0.0, &1.0)?;
108 Ok(mat)
109 }
110
111 #[cfg(test)]
112 fn new_randn_nd<T>(shape: &[usize]) -> Result<Self>
113 where
114 T: OpenCvElement,
115 {
116 let shape: Vec<_> = shape.iter().map(|&val| val as i32).collect();
117 let mut mat = Self::zeros_nd(&shape, T::DEPTH)?.to_mat()?;
118 core_cv::randn(&mut mat, &0.0, &1.0)?;
119 Ok(mat)
120 }
121 }
122}
123
124impl<T> TryFromCv<&core_cv::Mat> for core_cv::Point_<T>
125where
126 T: core_cv::DataType,
127{
128 type Error = Error;
129
130 fn try_from_cv(from: &core_cv::Mat) -> Result<Self> {
131 let slice = from.data_typed::<T>()?;
132 ensure!(slice.len() == 2, "invalid length");
133 let point = Self {
134 x: slice[0],
135 y: slice[1],
136 };
137 Ok(point)
138 }
139}
140
141impl<T> TryFromCv<core_cv::Mat> for core_cv::Point_<T>
142where
143 T: core_cv::DataType,
144{
145 type Error = Error;
146
147 fn try_from_cv(from: core_cv::Mat) -> Result<Self> {
148 TryFromCv::try_from_cv(&from)
149 }
150}
151
152impl<T> TryFromCv<&core_cv::Mat> for core_cv::Point3_<T>
153where
154 T: core_cv::DataType,
155{
156 type Error = Error;
157
158 fn try_from_cv(from: &core_cv::Mat) -> Result<Self> {
159 let slice = from.data_typed::<T>()?;
160 ensure!(slice.len() == 3, "invalid length");
161 let point = Self {
162 x: slice[0],
163 y: slice[1],
164 z: slice[2],
165 };
166 Ok(point)
167 }
168}
169
170impl<T> TryFromCv<core_cv::Mat> for core_cv::Point3_<T>
171where
172 T: core_cv::DataType,
173{
174 type Error = Error;
175
176 fn try_from_cv(from: core_cv::Mat) -> Result<Self> {
177 TryFromCv::try_from_cv(&from)
178 }
179}
180
181impl<T> TryFromCv<&core_cv::Point_<T>> for core_cv::Mat
182where
183 T: core_cv::DataType,
184{
185 type Error = Error;
186
187 fn try_from_cv(from: &core_cv::Point_<T>) -> Result<Self> {
188 let core_cv::Point_ { x, y, .. } = *from;
189 let mat = core_cv::Mat::from_slice(&[x, y])?;
190 Ok(mat)
191 }
192}
193
194impl<T> TryFromCv<core_cv::Point_<T>> for core_cv::Mat
195where
196 T: core_cv::DataType,
197{
198 type Error = Error;
199
200 fn try_from_cv(from: core_cv::Point_<T>) -> Result<Self> {
201 TryFromCv::try_from_cv(&from)
202 }
203}
204
205impl<T> TryFromCv<&core_cv::Point3_<T>> for core_cv::Mat
206where
207 T: core_cv::DataType,
208{
209 type Error = Error;
210
211 fn try_from_cv(from: &core_cv::Point3_<T>) -> Result<Self> {
212 let core_cv::Point3_ { x, y, z, .. } = *from;
213 let mat = core_cv::Mat::from_slice(&[x, y, z])?;
214 Ok(mat)
215 }
216}
217
218impl<T> TryFromCv<core_cv::Point3_<T>> for core_cv::Mat
219where
220 T: core_cv::DataType,
221{
222 type Error = Error;
223
224 fn try_from_cv(from: core_cv::Point3_<T>) -> Result<Self> {
225 TryFromCv::try_from_cv(&from)
226 }
227}