GRASS 8 Programmer's Manual 8.6.0dev(2026)-1878fdfec5
Loading...
Searching...
No Matches
vinput2d.c
Go to the documentation of this file.
1/*!
2 * \file vinput2d.c
3 *
4 * \author
5 * Written by H. Mitasova, I. Kosinovsky, D. Gerdes Fall 1993
6 * University of Illinois
7 * US Army Construction Engineering Research Lab
8 *
9 * \author
10 * Mitasova (University of Illinois),
11 * I. Kosinovsky, (USA-CERL), and D.Gerdes (USA-CERL)
12 *
13 * \author modified by McCauley in August 1995
14 * \author modified by Mitasova in August 1995
15 * \author modofied by Mitasova in Nov 1999 (dmax fix)
16 *
17 * SPDX-FileCopyrightText: 1993-1999 Helena Mitasova
18 * SPDX-FileCopyrightText: GRASS Development Team
19 * SPDX-License-Identifier: GPL-2.0-or-later
20 */
21
22#include <stdio.h>
23#include <stdlib.h>
24#include <math.h>
25#include <grass/bitmap.h>
26#include <grass/linkm.h>
27#include <grass/gis.h>
28#include <grass/dbmi.h>
29#include <grass/vector.h>
30#include <grass/glocale.h>
31
32#include <grass/interpf.h>
33
34/*!
35 * Insert into a quad tree
36 *
37 * Inserts input data inside the region into a quad tree. Also translates
38 * data. Returns number of segments in the quad tree.
39 *
40 * As z values may be used (in *Map*):
41 * - z coordinates in 3D file -> field = 0
42 * - categories -> field > 0, zcol = NULL
43 * - attributes -> field > 0, zcol != NULL
44 */
46 struct interp_params *params, /*!< interpolation parameters */
47 struct Map_info *Map, /*!< input vector map */
48 int field, /*!< category field number */
49 char *zcol, /*!< name of the column containing z values */
50 char *scol, /*!< name of the column containing smooth values */
51 struct tree_info *info, /*!< quadtree info */
52 double *xmin, double *xmax, double *ymin, double *ymax, double *zmin,
53 double *zmax, int *n_points, /*!< number of points used for interpolation */
54 double *dmax /*!< max distance between points */
55)
56{
57 double dmax2; /* max distance between points squared */
58 double c1, c2, c3, c4;
59 int i, k = 0;
60 double ns_res, ew_res;
61 int npoint, OUTRANGE;
62 int totsegm;
63 struct quaddata *data = (struct quaddata *)info->root->data;
64 double xprev, yprev, zprev, x1, y1, z1, d1, xt, yt, z, sm;
65 struct line_pnts *Points;
66 struct line_cats *Cats;
67 int times, j1, ltype, cat, zctype = 0, sctype = 0;
68 struct field_info *Fi;
70 dbHandle handle;
71 dbString stmt;
73
74 OUTRANGE = 0;
75 npoint = 0;
76
77 G_debug(2, "IL_vector_input_data_2d(): field = %d, zcol = %s, scol = %s",
78 field, zcol, scol);
79 ns_res = (data->ymax - data->y_orig) / data->n_rows;
80 ew_res = (data->xmax - data->x_orig) / data->n_cols;
81 dmax2 = *dmax * *dmax;
82
83 Points = Vect_new_line_struct(); /* init line_pnts struct */
85
86 if (field == 0 && !Vect_is_3d(Map))
87 G_fatal_error(_("Vector map <%s> is not 3D"), Vect_get_full_name(Map));
88
89 if (field > 0 && zcol != NULL) { /* open db driver */
90 G_verbose_message(_("Loading data from attribute table ..."));
91 Fi = Vect_get_field(Map, field);
92 if (Fi == NULL)
93 G_fatal_error(_("Database connection not defined for layer %d"),
94 field);
95 G_debug(3, " driver = %s database = %s table = %s", Fi->driver,
96 Fi->database, Fi->table);
97 db_init_handle(&handle);
98 db_init_string(&stmt);
99 driver = db_start_driver(Fi->driver);
100 db_set_handle(&handle, Fi->database, NULL);
101 if (db_open_database(driver, &handle) != DB_OK)
102 G_fatal_error(_("Unable to open database <%s> by driver <%s>"),
103 Fi->database, Fi->driver);
104
105 zctype = db_column_Ctype(driver, Fi->table, zcol);
106 G_debug(3, " zcol C type = %d", zctype);
107 if (zctype == -1)
108 G_fatal_error(_("Column <%s> not found"), zcol);
110 G_fatal_error(_("Data type of column <%s> must be numeric"), zcol);
111
113 G_debug(3, "RST SQL WHERE: %s", params->wheresql);
114 db_select_CatValArray(driver, Fi->table, Fi->key, zcol,
115 params->wheresql, &zarray);
116
117 if (scol != NULL) {
118 sctype = db_column_Ctype(driver, Fi->table, scol);
119 G_debug(3, " scol C type = %d", sctype);
120 if (sctype == -1)
121 G_fatal_error(_("Column <%s> not found"), scol);
123 G_fatal_error(_("Data type of column <%s> must be numeric"),
124 scol);
125
127 db_select_CatValArray(driver, Fi->table, Fi->key, scol,
128 params->wheresql, &sarray);
129 }
130
132 }
133
134 /* Lines without nodes */
135 G_message(_("Reading features from vector map ..."));
136 sm = 0;
137 while ((ltype = Vect_read_next_line(Map, Points, Cats)) != -2) {
138
139 if (!(ltype & (GV_POINT | GV_LINE | GV_BOUNDARY)))
140 continue;
141
142 if (field > 0) { /* use cat or attribute */
143 Vect_cat_get(Cats, field, &cat);
144
145 if (zcol == NULL) { /* use categories */
146 z = (double)cat;
147 }
148 else { /* read att from db */
149 int ret, intval;
150
151 if (zctype == DB_C_TYPE_INT) {
152 ret = db_CatValArray_get_value_int(&zarray, cat, &intval);
153 z = intval;
154 }
155 else { /* DB_C_TYPE_DOUBLE */
157 }
158
159 if (ret != DB_OK) {
160 if (params->wheresql != NULL)
161 /* G_message(_("Database record for cat %d not used due
162 * to SQL statement")); */
163 /* do nothing in this case to not confuse user. Or
164 * implement second cat list */
165 ;
166 else
167 G_warning(_("Database record for cat %d not found"),
168 cat);
169 continue;
170 }
171
172 if (scol != NULL) {
173 if (sctype == DB_C_TYPE_INT) {
174 ret =
175 db_CatValArray_get_value_int(&sarray, cat, &intval);
176 sm = intval;
177 }
178 else { /* DB_C_TYPE_DOUBLE */
179 ret =
181 }
182 if (sm < 0.0)
183 G_fatal_error(_("Negative value of smoothing detected: "
184 "sm must be >= 0"));
185 }
186 G_debug(5, " z = %f sm = %f", z, sm);
187 }
188 }
189
190 /* Insert all points including nodes (end points) */
191 for (i = 0; i < Points->n_points; i++) {
192 if (field == 0)
193 z = Points->z[i];
194 process_point(Points->x[i], Points->y[i], z, sm, info,
195 params->zmult, xmin, xmax, ymin, ymax, zmin, zmax,
196 &npoint, &OUTRANGE, &k);
197 }
198
199 /* Check all segments */
200 xprev = Points->x[0];
201 yprev = Points->y[0];
202 zprev = Points->z[0];
203 for (i = 1; i < Points->n_points; i++) {
204 /* compare the distance between current and previous */
205 x1 = Points->x[i];
206 y1 = Points->y[i];
207 z1 = Points->z[i];
208
209 xt = x1 - xprev;
210 yt = y1 - yprev;
211 d1 = (xt * xt + yt * yt);
212 if ((d1 > dmax2) && (dmax2 != 0.)) {
213 times = (int)(d1 / dmax2 + 0.5);
214 for (j1 = 0; j1 < times; j1++) {
215 xt = x1 - j1 * ((x1 - xprev) / times);
216 yt = y1 - j1 * ((y1 - yprev) / times);
217 if (field == 0)
218 z = z1 - j1 * ((z1 - zprev) / times);
219
220 process_point(xt, yt, z, sm, info, params->zmult, xmin,
221 xmax, ymin, ymax, zmin, zmax, &npoint,
222 &OUTRANGE, &k);
223 }
224 }
225 xprev = x1;
226 yprev = y1;
227 zprev = z1;
228 }
229 }
230
231 if (field > 0 && zcol != NULL)
233 if (scol != NULL) {
235 }
236
237 c1 = *xmin - data->x_orig;
238 c2 = data->xmax - *xmax;
239 c3 = *ymin - data->y_orig;
240 c4 = data->ymax - *ymax;
241 if ((c1 > 5 * ew_res) || (c2 > 5 * ew_res) || (c3 > 5 * ns_res) ||
242 (c4 > 5 * ns_res)) {
243 static int once = 0;
244
245 if (!once) {
246 once = 1;
247 G_warning(_("Strip exists with insufficient data"));
248 }
249 }
250
251 totsegm = translate_quad(info->root, data->x_orig, data->y_orig, *zmin, 4);
252 if (!totsegm)
253 return 0;
254 data->x_orig = 0;
255 data->y_orig = 0;
256
257 /* G_read_vector_timestamp(name,mapset,ts); */
258
259 if (OUTRANGE > 0)
260 G_warning(_("There are points outside specified 2D/3D region - %d "
261 "points ignored"),
262 OUTRANGE);
263 if (npoint > 0)
264 G_important_message(_("Ignoring %d points (too dense)"), npoint);
265 npoint = k - npoint - OUTRANGE;
266 if (npoint < params->kmin) {
267 if (npoint != 0) {
268 G_warning(_("%d points given for interpolation (after thinning) is "
269 "less than given NPMIN=%d"),
270 npoint, params->kmin);
271 params->kmin = npoint;
272 }
273 else {
274 G_warning(_("Zero points in the given region"));
275 return -1;
276 }
277 }
278 if (npoint > params->KMAX2 && params->kmin <= params->kmax) {
279 G_warning(
280 _("Segmentation parameters set to invalid values: npmin= %d, "
281 "segmax= %d "
282 "for smooth connection of segments, npmin > segmax (see manual)"),
283 params->kmin, params->kmax);
284 return -1;
285 }
286 if (npoint < params->KMAX2 && params->kmax != params->KMAX2)
287 G_warning(_("There are less than %d points for interpolation. No "
288 "segmentation is necessary, to run the program faster set "
289 "segmax=%d (see manual)"),
290 params->KMAX2, params->KMAX2);
291
292 G_verbose_message(_("Number of points from vector map %d"), k);
293 G_verbose_message(_("Number of points outside of 2D/3D region %d"),
294 OUTRANGE);
295 G_verbose_message(_("Number of points being used %d"), npoint);
296
297 *n_points = npoint;
298 return (totsegm);
299}
300
301int process_point(double x, double y, double z, double sm,
302 struct tree_info *info, /* quadtree info */
303 double zmult, /* multiplier for z-values */
304 double *xmin, double *xmax, double *ymin, double *ymax,
305 double *zmin, double *zmax, int *npoint, int *OUTRANGE,
306 int *total)
307{
308 struct triple *point;
309 double c1, c2, c3, c4;
310 int a;
311 static int first_time = 1;
312 struct quaddata *data = (struct quaddata *)info->root->data;
313
314 (*total)++;
315
316 z = z * zmult;
317 c1 = x - data->x_orig;
318 c2 = data->xmax - x;
319 c3 = y - data->y_orig;
320 c4 = data->ymax - y;
321
322 if (!((c1 >= 0) && (c2 >= 0) && (c3 >= 0) && (c4 >= 0))) {
323 if (!(*OUTRANGE)) {
324 G_warning(_("Some points outside of region (ignored)"));
325 }
326 (*OUTRANGE)++;
327 }
328 else {
329 if (!(point = quad_point_new(x, y, z, sm))) {
330 G_warning(_("Unable to allocate memory"));
331 return -1;
332 }
333 a = MT_insert(point, info, info->root, 4);
334 if (a == 0) {
335 (*npoint)++;
336 }
337 if (a < 0) {
338 G_warning(_("Unable to insert %f,%f,%f a = %d"), x, y, z, a);
339 return -1;
340 }
341 free(point);
342 if (first_time) {
343 first_time = 0;
344 *xmin = x;
345 *ymin = y;
346 *zmin = z;
347 *xmax = x;
348 *ymax = y;
349 *zmax = z;
350 }
351 *xmin = amin1(*xmin, x);
352 *ymin = amin1(*ymin, y);
353 *zmin = amin1(*zmin, z);
354 *xmax = amax1(*xmax, x);
355 *ymax = amax1(*ymax, y);
356 *zmax = amax1(*zmax, z);
357 }
358 return 1;
359}
#define NULL
Definition ccmath.h:32
struct triple * quad_point_new(double x, double y, double z, double sm)
Definition dataquad.c:32
Main header of GRASS DataBase Management Interface.
#define DB_C_TYPE_INT
Definition dbmi.h:106
#define DB_C_TYPE_DOUBLE
Definition dbmi.h:107
#define DB_OK
Definition dbmi.h:69
void db_CatValArray_free(dbCatValArray *)
Free allocated dbCatValArray.
Definition value.c:371
int db_CatValArray_get_value_int(dbCatValArray *, int, int *)
Find value (integer) by key.
void db_CatValArray_init(dbCatValArray *)
Initialize dbCatValArray.
Definition value.c:359
int db_column_Ctype(dbDriver *, const char *, const char *)
Get column ctype.
int db_open_database(dbDriver *, dbHandle *)
Open database connection.
Definition c_opendb.c:24
int db_close_database_shutdown_driver(dbDriver *)
Close driver/database connection.
Definition db.c:58
int db_select_CatValArray(dbDriver *, const char *, const char *, const char *, const char *, dbCatValArray *)
Select pairs key/value to array, values are sorted by key (must be integer)
int db_set_handle(dbHandle *, const char *, const char *)
Set handle (database and schema name)
Definition handle.c:36
dbDriver * db_start_driver(const char *)
Initialize a new dbDriver for db transaction.
Definition start.c:48
void db_init_handle(dbHandle *)
Initialize handle (i.e database/schema)
Definition handle.c:20
void db_init_string(dbString *)
Initialize dbString.
Definition string.c:23
int db_CatValArray_get_value_double(dbCatValArray *, int, double *)
Find value (double) by key.
void void void void G_fatal_error(const char *,...) __attribute__((format(printf
void G_warning(const char *,...) __attribute__((format(printf
void void G_verbose_message(const char *,...) __attribute__((format(printf
void void void G_important_message(const char *,...) __attribute__((format(printf
void G_message(const char *,...) __attribute__((format(printf
int G_debug(int, const char *,...) __attribute__((format(printf
int Vect_cat_get(const struct line_cats *, int, int *)
Get first found category of given field.
struct field_info * Vect_get_field(struct Map_info *, int)
Get information about link to database (by layer number)
Definition field.c:508
struct line_cats * Vect_new_cats_struct(void)
Creates and initializes line_cats structure.
const char * Vect_get_full_name(struct Map_info *)
Get fully qualified name of vector map.
int Vect_read_next_line(struct Map_info *, struct line_pnts *, struct line_cats *)
Read next vector feature.
struct line_pnts * Vect_new_line_struct(void)
Creates and initializes a line_pnts structure.
Definition line.c:43
int Vect_is_3d(struct Map_info *)
Check if vector map is 3D.
#define GV_LINE
#define GV_POINT
Feature types used in memory on run time (may change)
#define GV_BOUNDARY
#define _(str)
Definition glocale.h:10
int translate_quad(struct multtree *tree, double numberx, double numbery, double numberz, int n_leafs)
Definition input2d.c:85
double amin1(double, double)
Definition minmax.c:68
double amax1(double, double)
Definition minmax.c:55
int MT_insert(struct triple *point, struct tree_info *info, struct multtree *tree, int n_leafs)
Definition qtree.c:99
void free(void *)
Vector map info.
Layer (old: field) information.
char * driver
Name of DB driver ('sqlite', 'dbf', ...)
double zmult
Definition interpf.h:72
const char * wheresql
Definition interpf.h:142
Feature category info.
int * cat
Array of categories.
Feature geometry info - coordinates.
double * y
Array of Y coordinates.
double * x
Array of X coordinates.
int n_points
Number of points.
double * z
Array of Z coordinates.
double ymax
Definition dataquad.h:45
double y_orig
Definition dataquad.h:43
double x_orig
Definition dataquad.h:42
double xmax
Definition dataquad.h:44
int n_cols
Definition dataquad.h:47
int n_rows
Definition dataquad.h:46
struct multtree * root
Definition qtree.h:45
int process_point(double x, double y, double z, double sm, struct tree_info *info, double zmult, double *xmin, double *xmax, double *ymin, double *ymax, double *zmin, double *zmax, int *npoint, int *OUTRANGE, int *total)
Definition vinput2d.c:301
int IL_vector_input_data_2d(struct interp_params *params, struct Map_info *Map, int field, char *zcol, char *scol, struct tree_info *info, double *xmin, double *xmax, double *ymin, double *ymax, double *zmin, double *zmax, int *n_points, double *dmax)
Definition vinput2d.c:45
#define x