OGS
ConvertSHPToGLI.cpp File Reference

Detailed Description

Implementation of the shp to gli converter tool.

Author
Thomas Fischer
Date
2010-05-03

Definition in file ConvertSHPToGLI.cpp.

#include <shapefil.h>
#include <tclap/CmdLine.h>
#include <fstream>
#include <vector>
#include "BaseLib/Logging.h"
#include "BaseLib/MPI.h"
#include "BaseLib/TCLAPArguments.h"
#include "GeoLib/GEOObjects.h"
#include "GeoLib/IO/XmlIO/Qt/XmlGmlInterface.h"
#include "GeoLib/IO/XmlIO/Qt/XmlStnInterface.h"
#include "GeoLib/Point.h"
#include "GeoLib/Station.h"
#include "InfoLib/GitInfo.h"
Include dependency graph for ConvertSHPToGLI.cpp:

Go to the source code of this file.

Functions

void convertPoints (DBFHandle dbf_handle, std::string const &out_fname, std::size_t x_id, std::size_t y_id, std::size_t z_id, std::vector< std::size_t > const &name_component_ids, std::string &points_group_name, bool station)
 
void printFieldInformationTable (DBFHandle const &dbf_handle, std::size_t n_fields)
 
int main (int argc, char *argv[])
 

Function Documentation

◆ convertPoints()

void convertPoints ( DBFHandle dbf_handle,
std::string const & out_fname,
std::size_t x_id,
std::size_t y_id,
std::size_t z_id,
std::vector< std::size_t > const & name_component_ids,
std::string & points_group_name,
bool station )

Definition at line 30 of file ConvertSHPToGLI.cpp.

38{
39 int n_records(DBFGetRecordCount(dbf_handle));
40 INFO("Reading {:d} records.", n_records);
41
42 std::vector<GeoLib::Point*> points;
43 points.reserve(n_records);
44
45 std::string name;
46 for (int k = 0; k < n_records; k++)
47 {
48 double x(DBFReadDoubleAttribute(dbf_handle, k, x_id));
49 double y(DBFReadDoubleAttribute(dbf_handle, k, y_id));
50 double z(0.0);
51 if (z_id != std::numeric_limits<std::size_t>::max())
52 {
53 z = DBFReadDoubleAttribute(dbf_handle, k, z_id);
54 }
55
56 name.clear();
57 if (!name_component_ids.empty())
58 {
59 for (unsigned long name_component_id : name_component_ids)
60 {
61 if (name_component_id !=
62 std::numeric_limits<std::size_t>::max())
63 {
64 name += DBFReadStringAttribute(dbf_handle, k,
65 name_component_id);
66 name += " ";
67 }
68 }
69 }
70 else
71 {
72 name = std::to_string(k);
73 }
74
75 if (station)
76 {
78 points.push_back(pnt);
79 }
80 else
81 {
82 GeoLib::Point* pnt(new GeoLib::Point(x, y, z));
83 points.push_back(pnt);
84 }
85 }
86
87 GeoLib::GEOObjects geo_objs;
88 if (station)
89 {
90 geo_objs.addStationVec(std::move(points), points_group_name);
91 }
92 else
93 {
94 geo_objs.addPointVec(std::move(points), points_group_name,
96 }
97
98 if (station)
99 {
100 GeoLib::IO::XmlStnInterface xml(geo_objs);
101 xml.export_name = points_group_name;
102 BaseLib::IO::writeStringToFile(xml.writeToString(), out_fname);
103 }
104 else
105 {
106 GeoLib::IO::XmlGmlInterface xml(geo_objs);
107 xml.export_name = points_group_name;
108 BaseLib::IO::writeStringToFile(xml.writeToString(), out_fname);
109 }
110}
void INFO(fmt::format_string< Args... > fmt, Args &&... args)
Definition Logging.h:36
Container class for geometric objects.
Definition GEOObjects.h:57
void addPointVec(std::vector< Point * > &&points, std::string &name, PointVec::NameIdMap &&pnt_id_name_map, double const eps=std::sqrt(std::numeric_limits< double >::epsilon()))
void addStationVec(std::vector< Point * > &&stations, std::string &name)
Adds a vector of stations with the given name and colour to GEOObjects.
Reads and writes GeoObjects to and from XML files.
Reads and writes Observation Sites to and from XML files.
A Station (observation site) is basically a Point with some additional information.
Definition Station.h:37
static Station * createStation(const std::string &line)
Definition Station.cpp:46
std::map< std::string, std::size_t > NameIdMap
Definition TemplateVec.h:41
int writeStringToFile(std::string_view content, std::filesystem::path const &file_path)
Definition Writer.cpp:45

References GeoLib::GEOObjects::addPointVec(), GeoLib::GEOObjects::addStationVec(), GeoLib::Station::createStation(), BaseLib::IO::XMLInterface::export_name, INFO(), BaseLib::IO::writeStringToFile(), and BaseLib::IO::Writer::writeToString().

Referenced by main().

◆ main()

int main ( int argc,
char * argv[] )

Definition at line 163 of file ConvertSHPToGLI.cpp.

164{
165 TCLAP::CmdLine cmd(
166 "Converts points contained in shape file\n\n"
167 "OpenGeoSys-6 software, version " +
169 ".\n"
170 "Copyright (c) 2012-2025, OpenGeoSys Community "
171 "(http://www.opengeosys.org)",
173 TCLAP::ValueArg<std::string> shapefile_arg(
174 "s",
175 "shape-file",
176 "Input (.shp). The name of the input shape "
177 "file",
178 true,
179 "",
180 "INPUT_FILE");
181 cmd.add(shapefile_arg);
182
183 auto log_level_arg = BaseLib::makeLogLevelArg();
184 cmd.add(log_level_arg);
185 cmd.parse(argc, argv);
186
187 BaseLib::MPI::Setup mpi_setup(argc, argv);
188 BaseLib::initOGSLogger(log_level_arg.getValue());
189
190 std::string fname(shapefile_arg.getValue());
191
192 int shape_type;
193 int number_of_elements;
194
195 SHPHandle hSHP = SHPOpen(fname.c_str(), "rb");
196 if (hSHP)
197 {
198 SHPGetInfo(hSHP, &number_of_elements, &shape_type,
199 nullptr /*padfMinBound*/, nullptr /*padfMinBound*/);
200
201 if ((shape_type - 1) % 10 == 0)
202 INFO("Shape file contains {:d} points.", number_of_elements);
203 if (((shape_type - 3) % 10 == 0 || (shape_type - 5) % 10 == 0))
204 {
205 ERR("Shape file contains {:d} polylines.", number_of_elements);
206 ERR("This programme only handles only files containing points.");
207 SHPClose(hSHP);
208 return EXIT_SUCCESS;
209 }
210 SHPClose(hSHP);
211 }
212 else
213 {
214 ERR("Could not open shapefile {:s}.", fname);
215 }
216
217 DBFHandle dbf_handle = DBFOpen(fname.c_str(), "rb");
218 if (dbf_handle)
219 {
220 std::size_t n_fields(DBFGetFieldCount(dbf_handle));
221 printFieldInformationTable(dbf_handle, n_fields);
222
223 std::size_t x_id;
224 std::size_t y_id;
225 std::size_t z_id;
226 INFO(
227 "Please give the field idx that should be used for reading the x "
228 "coordinate: ");
229 std::cin >> x_id;
230 INFO(
231 "Please give the field idx that should be used for reading the y "
232 "coordinate: ");
233 std::cin >> y_id;
234 INFO(
235 "Please give the field idx that should be used for reading the z "
236 "coordinate: ");
237 std::cin >> z_id;
238
239 if (z_id > n_fields)
240 {
241 z_id = std::numeric_limits<std::size_t>::max();
242 }
243
244 std::size_t n_name_components;
245 INFO("Please give the number of fields that should be added to name: ");
246 std::cin >> n_name_components;
247
248 std::vector<std::size_t> name_component_ids(
249 n_name_components, std::numeric_limits<std::size_t>::max());
250 if (n_name_components != 0)
251 {
252 for (std::size_t j(0); j < n_name_components; j++)
253 {
254 INFO(
255 "- please give the field idx that should be used for "
256 "reading the name: ");
257 std::cin >> name_component_ids[j];
258 }
259 }
260 for (std::size_t j(0); j < n_name_components; j++)
261 {
262 if (name_component_ids[j] > n_fields)
263 {
264 name_component_ids[j] = std::numeric_limits<std::size_t>::max();
265 }
266 }
267
268 std::size_t station(0);
269
270 INFO(
271 "Should I read the information as GeoLib::Station (0) or as "
272 "GeoLib::Point (1)? Please give the number: ");
273 std::cin >> station;
274
275 std::string fname_base(fname);
276 if (station == 0)
277 {
278 fname += ".stn";
279 }
280 else
281 {
282 fname += ".gml";
283 }
284
285 INFO("Writing to {:s}.", fname);
286 convertPoints(dbf_handle,
287 fname,
288 x_id,
289 y_id,
290 z_id,
291 name_component_ids,
292 fname_base,
293 station == 0);
294 DBFClose(dbf_handle);
295 INFO("\tok.");
296 }
297 else
298 {
299 ERR("Could not open the database file.");
300 }
301
302 return EXIT_SUCCESS;
303}
void convertPoints(DBFHandle dbf_handle, std::string const &out_fname, std::size_t x_id, std::size_t y_id, std::size_t z_id, std::vector< std::size_t > const &name_component_ids, std::string &points_group_name, bool station)
void printFieldInformationTable(DBFHandle const &dbf_handle, std::size_t n_fields)
void ERR(fmt::format_string< Args... > fmt, Args &&... args)
Definition Logging.h:48
TCLAP::ValueArg< std::string > makeLogLevelArg()
void initOGSLogger(std::string const &log_level)
Definition Logging.cpp:64
GITINFOLIB_EXPORT const std::string ogs_version

References convertPoints(), ERR(), INFO(), BaseLib::initOGSLogger(), BaseLib::makeLogLevelArg(), GitInfoLib::GitInfo::ogs_version, and printFieldInformationTable().

◆ printFieldInformationTable()

void printFieldInformationTable ( DBFHandle const & dbf_handle,
std::size_t n_fields )

Definition at line 112 of file ConvertSHPToGLI.cpp.

114{
115 char* field_name(new char[256]);
116 int width(0);
117 int n_decimals(0);
118 std::stringstream out;
119 out << std::endl;
120 out << "************************************************" << std::endl;
121 out << "field idx | name of field | data type of field " << std::endl;
122 out << "------------------------------------------------" << std::endl;
123 for (std::size_t field_idx(0); field_idx < n_fields; field_idx++)
124 {
125 DBFGetFieldInfo(dbf_handle, field_idx, field_name, &width, &n_decimals);
126 if (field_idx < 10)
127 {
128 out << " " << field_idx << " |";
129 }
130 else
131 {
132 out << " " << field_idx << " |";
133 }
134 std::string field_name_str(field_name);
135 for (int k(0); k < (14 - static_cast<int>(field_name_str.size())); k++)
136 {
137 out << " ";
138 }
139 out << field_name_str << " |";
140
141 char native_field_type(DBFGetNativeFieldType(dbf_handle, field_idx));
142 switch (native_field_type)
143 {
144 case 'C':
145 out << " string" << std::endl;
146 break;
147 case 'F':
148 out << " float" << std::endl;
149 break;
150 case 'N':
151 out << " numeric" << std::endl;
152 break;
153 default:
154 out << " n_decimal " << n_decimals << std::endl;
155 break;
156 }
157 }
158 delete[] field_name;
159 out << "************************************************" << std::endl;
160 INFO("{:s}", out.str());
161}

References INFO().

Referenced by main().