Gazebo Common

API Reference

7.4.0
ImageHeightmap.hh
Go to the documentation of this file.
1/*
2 * Copyright (C) 2022 Open Source Robotics Foundation
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 *
16*/
17#ifndef GZ_COMMON_GEOSPATIAL_IMAGEHEIGHTMAPDATA_HH_
18#define GZ_COMMON_GEOSPATIAL_IMAGEHEIGHTMAPDATA_HH_
19
20#include <limits>
21#include <string>
22#include <vector>
23#include <gz/math/Vector3.hh>
24
25#include <gz/common/geospatial/Export.hh>
27#include <gz/common/Image.hh>
28
29namespace gz
30{
31 namespace common
32 {
34 class GZ_COMMON_GEOSPATIAL_VISIBLE ImageHeightmap
36 {
38 public: ImageHeightmap();
39
43 public: int Load(const std::string &_filename = "");
44
45 // Documentation inherited.
46 public: void FillHeightMap(int _subSampling, unsigned int _vertSize,
47 const gz::math::Vector3d &_size,
48 const gz::math::Vector3d &_scale, bool _flipY,
49 std::vector<float> &_heights) const;
50
51 // Documentation inherited.
52 public: std::string Filename() const;
53
54 // Documentation inherited.
55 public: unsigned int Height() const;
56
57 // Documentation inherited.
58 public: unsigned int Width() const;
59
60 // Documentation inherited.
61 public: float MaxElevation() const;
62
64 private: gz::common::Image img;
65
76 private: template <typename T>
77 void FillHeights(T *_data, int _imgHeight, int _imgWidth,
78 unsigned int _pitch, int _subSampling, unsigned int _vertSize,
79 const gz::math::Vector3d &_size,
80 const gz::math::Vector3d &_scale,
81 bool _flipY, std::vector<float> &_heights) const
82 {
83 // bytes per pixel
84 const unsigned int bpp = _pitch / _imgWidth;
85 // number of channels in a pixel
86 const unsigned int channels = bpp / sizeof(T);
87 // number of pixels in a row of image
88 const unsigned int pitchInPixels = _pitch / bpp;
89
90 const double maxPixelValue =
91 static_cast<double>(std::numeric_limits<T>::max());
92
93 // Iterate over all the vertices
94 for (unsigned int y = 0; y < _vertSize; ++y)
95 {
96 // yf ranges between 0 and 4
97 const double yf = y / static_cast<double>(_subSampling);
98 const int y1 = static_cast<int>(std::floor(yf));
99 int y2 = static_cast<int>(std::ceil(yf));
100 if (y2 >= _imgHeight)
101 y2 = _imgHeight - 1;
102 const double dy = yf - y1;
103
104 for (unsigned int x = 0; x < _vertSize; ++x)
105 {
106 const double xf = x / static_cast<double>(_subSampling);
107 const int x1 = static_cast<int>(std::floor(xf));
108 int x2 = static_cast<int>(std::ceil(xf));
109 if (x2 >= _imgWidth)
110 x2 = _imgWidth - 1;
111 const double dx = xf - x1;
112
113 const double px1 = static_cast<int>(
114 _data[(y1 * pitchInPixels + x1) * channels]) / maxPixelValue;
115 const double px2 = static_cast<int>(
116 _data[(y1 * pitchInPixels + x2) * channels]) / maxPixelValue;
117 const float h1 = (px1 - ((px1 - px2) * dx));
118
119 const double px3 = static_cast<int>(
120 _data[(y2 * pitchInPixels + x1) * channels]) / maxPixelValue;
121 const double px4 = static_cast<int>(
122 _data[(y2 * pitchInPixels + x2) * channels]) / maxPixelValue;
123 const float h2 = (px3 - ((px3 - px4) * dx));
124 float h = (h1 - ((h1 - h2) * dy)) * _scale.Z();
125
126 // invert pixel definition so 1=ground, 0=full height,
127 // if the terrain size has a negative z component
128 // this is mainly for backward compatibility
129 if (_size.Z() < 0)
130 h = 1.0 - h;
131
132 // Store the height for future use
133 if (!_flipY)
134 _heights[y * _vertSize + x] = h;
135 else
136 _heights[(_vertSize - y - 1) * _vertSize + x] = h;
137 }
138 }
139 }
140 };
141 }
142}
143#endif