Visual Servoing Platform  version 3.6.1 under development (2024-05-18)
vpImageIoOpenCV.cpp
1 /*
2  * ViSP, open source Visual Servoing Platform software.
3  * Copyright (C) 2005 - 2023 by Inria. All rights reserved.
4  *
5  * This software is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation; either version 2 of the License, or
8  * (at your option) any later version.
9  * See the file LICENSE.txt at the root directory of this source
10  * distribution for additional information about the GNU GPL.
11  *
12  * For using ViSP with software that can not be combined with the GNU
13  * GPL, please contact Inria about acquiring a ViSP Professional
14  * Edition License.
15  *
16  * See https://visp.inria.fr for more information.
17  *
18  * This software was developed at:
19  * Inria Rennes - Bretagne Atlantique
20  * Campus Universitaire de Beaulieu
21  * 35042 Rennes Cedex
22  * France
23  *
24  * If you have questions regarding the use of this file, please contact
25  * Inria at visp@inria.fr
26  *
27  * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
28  * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
29  *
30  * Description:
31  * OpenCV backend for image I/O operations.
32  */
33 
39 #include <visp3/core/vpConfig.h>
40 
41 #include "vpImageIoBackend.h"
42 
43 #ifdef VISP_HAVE_OPENCV
44 #if (VISP_HAVE_OPENCV_VERSION >= 0x030000) // Require opencv >= 3.0.0
45 #if defined(HAVE_OPENCV_IMGCODECS)
46 #include <opencv2/imgcodecs.hpp>
47 #endif
48 #else // Require opencv >= 2.4.8
49 #if defined(HAVE_OPENCV_HIGHGUI) && defined(HAVE_OPENCV_IMGPROC)
50 #include <opencv2/core/core.hpp>
51 #include <opencv2/highgui/highgui.hpp>
52 #include <opencv2/imgproc/imgproc.hpp>
53 #endif
54 #endif
55 #endif
56 
57 #include <visp3/core/vpImageConvert.h>
58 
59 #if ((VISP_HAVE_OPENCV_VERSION >= 0x030000) && defined(HAVE_OPENCV_IMGCODECS)) || ((VISP_HAVE_OPENCV_VERSION < 0x030000) \
60  && defined(HAVE_OPENCV_HIGHGUI) && defined(HAVE_OPENCV_IMGPROC))
61 
77 void readOpenCV(vpImage<unsigned char> &I, const std::string &filename)
78 {
79 #if defined(VISP_HAVE_OPENCV)
80 #if VISP_HAVE_OPENCV_VERSION >= 0x030200
81  int flags = cv::IMREAD_GRAYSCALE | cv::IMREAD_IGNORE_ORIENTATION;
82 #elif VISP_HAVE_OPENCV_VERSION >= 0x030000
83  int flags = cv::IMREAD_GRAYSCALE;
84 #else
85  int flags = CV_LOAD_IMAGE_GRAYSCALE;
86 #endif
87  cv::Mat Ip = cv::imread(filename.c_str(), flags);
88  if (!Ip.empty())
90  else
91  throw(vpImageException(vpImageException::ioError, "Can't read the image"));
92 #endif
93 }
94 
112 void readOpenCV(vpImage<vpRGBa> &I, const std::string &filename)
113 {
114 #if defined(VISP_HAVE_OPENCV)
115 #if VISP_HAVE_OPENCV_VERSION >= 0x030200
116  int flags = cv::IMREAD_COLOR | cv::IMREAD_IGNORE_ORIENTATION;
117 #elif VISP_HAVE_OPENCV_VERSION >= 0x030000
118  int flags = cv::IMREAD_COLOR;
119 #else
120  int flags = CV_LOAD_IMAGE_COLOR;
121 #endif
122  cv::Mat Ip = cv::imread(filename.c_str(), flags);
123  if (!Ip.empty())
125  else
126  throw(vpImageException(vpImageException::ioError, "Can't read the image"));
127 #endif
128 }
129 
130 void readOpenCV(vpImage<float> &I, const std::string &filename)
131 {
132 #if defined(VISP_HAVE_OPENCV)
133 #if VISP_HAVE_OPENCV_VERSION >= 0x030200
134  int flags = cv::IMREAD_COLOR | cv::IMREAD_IGNORE_ORIENTATION;
135 #elif VISP_HAVE_OPENCV_VERSION >= 0x030000
136  int flags = cv::IMREAD_COLOR;
137 #else
138  int flags = CV_LOAD_IMAGE_COLOR;
139 #endif
140  cv::Mat Ip = cv::imread(filename.c_str(), flags);
141  if (!Ip.empty())
143  else
144  throw(vpImageException(vpImageException::ioError, "Can't read the image"));
145 #else
146  throw(vpImageException(vpImageException::ioError, "Can't read the image"));
147 #endif
148 }
149 
150 void readOpenCV(vpImage<vpRGBf> &I, const std::string &filename)
151 {
152 #if defined(VISP_HAVE_OPENCV)
153 #if VISP_HAVE_OPENCV_VERSION >= 0x030200
154  int flags = cv::IMREAD_COLOR | cv::IMREAD_IGNORE_ORIENTATION;
155 #elif VISP_HAVE_OPENCV_VERSION >= 0x030000
156  int flags = cv::IMREAD_COLOR;
157 #else
158  int flags = CV_LOAD_IMAGE_COLOR;
159 #endif
160  cv::Mat Ip = cv::imread(filename.c_str(), flags);
161  if (!Ip.empty())
163  else
164  throw(vpImageException(vpImageException::ioError, "Can't read the image"));
165 #else
166  throw(vpImageException(vpImageException::ioError, "Can't read the image"));
167 #endif
168 }
169 
176 void readPNGfromMemOpenCV(const std::vector<unsigned char> &buffer, vpImage<unsigned char> &I)
177 {
178  cv::Mat1b buf(static_cast<int>(buffer.size()), 1, const_cast<unsigned char *>(buffer.data()));
179  cv::Mat1b img = cv::imdecode(buf, cv::IMREAD_GRAYSCALE);
180  I.resize(img.rows, img.cols);
181  std::copy(img.begin(), img.end(), I.bitmap);
182 }
183 
190 void readPNGfromMemOpenCV(const std::vector<unsigned char> &buffer, vpImage<vpRGBa> &I_color)
191 {
192  cv::Mat1b buf(static_cast<int>(buffer.size()), 1, const_cast<unsigned char *>(buffer.data()));
193  cv::Mat3b img = cv::imdecode(buf, cv::IMREAD_COLOR);
194  vpImageConvert::convert(img, I_color);
195 }
196 
204 void writeOpenCV(const vpImage<unsigned char> &I, const std::string &filename, int quality)
205 {
206  cv::Mat Ip;
208 
209  std::vector<int> compression_params;
210  compression_params.push_back(cv::IMWRITE_JPEG_QUALITY);
211  compression_params.push_back(quality);
212  cv::imwrite(filename.c_str(), Ip, compression_params);
213 }
214 
222 void writeOpenCV(const vpImage<vpRGBa> &I, const std::string &filename, int quality)
223 {
224  cv::Mat Ip;
226 
227  std::vector<int> compression_params;
228  compression_params.push_back(cv::IMWRITE_JPEG_QUALITY);
229  compression_params.push_back(quality);
230  cv::imwrite(filename.c_str(), Ip, compression_params);
231 }
232 
233 void writeOpenCV(const vpImage<float> &I, const std::string &filename)
234 {
235  cv::Mat Ip;
237 
238  cv::imwrite(filename.c_str(), Ip);
239 }
240 
241 void writeOpenCV(const vpImage<vpRGBf> &I, const std::string &filename)
242 {
243  cv::Mat Ip;
245 
246  cv::imwrite(filename.c_str(), Ip);
247 }
248 
255 void writePNGtoMemOpenCV(const vpImage<unsigned char> &I, std::vector<unsigned char> &buffer)
256 {
257  cv::Mat1b img(I.getRows(), I.getCols(), I.bitmap);
258  bool result = cv::imencode(".png", img, buffer);
259 
260  if (!result) {
261  std::string message = "Cannot write png to memory";
263  }
264 }
265 
273 void writePNGtoMemOpenCV(const vpImage<vpRGBa> &I_color, std::vector<unsigned char> &buffer, bool saveAlpha)
274 {
275  const int height = I_color.getRows();
276  const int width = I_color.getCols();
277  const int channels = saveAlpha ? 4 : 3;
278 
279  if (saveAlpha) {
280  cv::Mat4b img(height, width, reinterpret_cast<cv::Vec4b *>(I_color.bitmap));
281  // No need to perform RGB to BGR conversion
282  bool result = cv::imencode(".png", img, buffer);
283 
284  if (!result) {
285  std::string message = "Cannot write png to memory";
287  }
288  }
289  else {
290  unsigned char *bitmap = new unsigned char[height * width * channels];
291  vpImageConvert::RGBaToRGB(reinterpret_cast<unsigned char *>(I_color.bitmap), bitmap, height*width);
292 
293  cv::Mat3b img(height, width, reinterpret_cast<cv::Vec3b *>(bitmap));
294  // No need to perform RGB to BGR conversion
295  bool result = cv::imencode(".png", img, buffer);
296  delete[] bitmap;
297 
298  if (!result) {
299  std::string message = "Cannot write png to memory";
301  }
302  }
303 }
304 
305 #endif
static void convert(const vpImage< unsigned char > &src, vpImage< vpRGBa > &dest)
static void RGBaToRGB(unsigned char *rgba, unsigned char *rgb, unsigned int size)
Error that can be emitted by the vpImage class and its derivatives.
@ ioError
Image io error.
void resize(unsigned int h, unsigned int w)
resize the image : Image initialization
Definition: vpImage.h:798
unsigned int getCols() const
Definition: vpImage.h:175
Type * bitmap
points toward the bitmap
Definition: vpImage.h:139
unsigned int getRows() const
Definition: vpImage.h:215