GRASS 8 Programmer's Manual 8.6.0dev(2026)-1878fdfec5
Loading...
Searching...
No Matches
group.c
Go to the documentation of this file.
1/****************************************************************************
2 *
3 * MODULE: imagery library
4 * AUTHOR(S): Original author(s) name(s) unknown - written by CERL
5 * PURPOSE: Image processing library
6 * SPDX-FileCopyrightText: 1999, 2005 GRASS Development Team
7 * SPDX-License-Identifier: GPL-2.0-or-later
8 *
9 *****************************************************************************/
10
11/**********************************************************
12 * I_get_group (group);
13 * I_put_group (group);
14 *
15 * I_get_group_ref (group, &Ref);
16 * I_put_group_ref (group, &Ref);
17 * I_get_subgroup_ref_file (group, subgroup, &Ref);
18 * I_put_subgroup_ref_file (group, subgroup, &Ref);
19 * I_add_file_to_group_ref (name, mapset, &Ref)
20 * I_transfer_group_ref_file (&Src_ref, n, &Dst_ref)
21 * I_init_group_ref (&Ref);
22 * I_free_group_ref (&Ref);
23 **********************************************************/
24
25#include <string.h>
26#include <stdlib.h>
27#include <grass/imagery.h>
28
29static int get_ref(const char *, const char *, const char *, struct Ref *);
30static int set_color(const char *, const char *, const char *, struct Ref *);
31static int put_ref(const char *, const char *, const struct Ref *);
32
33/* get current group name from file GROUPFILE in current mapset */
34int I_get_group(char *group)
35{
36 FILE *fd;
37 int stat;
38
39 *group = 0;
41 fd = G_fopen_old("", GROUPFILE, G_mapset());
43 if (fd == NULL)
44 return 0;
45 stat = (fscanf(fd, "%255s", group) == 1);
46 fclose(fd);
47 return stat;
48}
49
50/* write group name to file GROUPFILE in current mapset */
51int I_put_group(const char *group)
52{
53 FILE *fd;
54
55 fd = G_fopen_new("", GROUPFILE);
56 if (fd == NULL)
57 return 0;
58 fprintf(fd, "%s\n", group);
59 fclose(fd);
60 return 1;
61}
62
63/* get current subgroup for group in current mapset */
64int I_get_subgroup(const char *group, char *subgroup)
65{
66 FILE *fd;
67 int stat;
68
69 *subgroup = 0;
70 if (!I_find_group(group))
71 return 0;
75 if (fd == NULL)
76 return 0;
77 stat = (fscanf(fd, "%255s", subgroup) == 1);
78 fclose(fd);
79 return stat;
80}
81
82/* write current subgroup to group in current mapset */
83int I_put_subgroup(const char *group, const char *subgroup)
84{
85 FILE *fd;
86
87 if (!I_find_group(group))
88 return 0;
90 if (fd == NULL)
91 return 0;
92 fprintf(fd, "%s\n", subgroup);
93 fclose(fd);
94 return 1;
95}
96
97/*!
98 * \brief read group REF file
99 *
100 * Reads the contents of the REF file for the specified <b>group</b> into
101 * the <b>ref</b> structure.
102 * Returns 1 if successful; 0 otherwise (but no error messages are printed).
103 *
104 * \param group
105 * \param ref
106 * \return int
107 */
108int I_get_group_ref(const char *group, struct Ref *ref)
109{
110 return get_ref(group, "", NULL, ref);
111}
112
113/*!
114 * \brief read group REF file
115 *
116 * Reads the contents of the REF file for the specified <b>group</b> into
117 * the <b>ref</b> structure.
118 * Returns 1 if successful; 0 otherwise (but no error messages are printed).
119 *
120 * \param group
121 * \param mapset
122 * \param ref
123 * \return int
124 */
125int I_get_group_ref2(const char *group, const char *mapset, struct Ref *ref)
126{
127 return get_ref(group, "", mapset, ref);
128}
129
130/*!
131 * \brief read subgroup REF file
132 *
133 * Reads the contents of the REF file for the
134 * specified <b>subgroup</b> of the specified <b>group</b> into the
135 * <b>ref</b> structure.
136 * Returns 1 if successful; 0 otherwise (but no error messages are printed).
137 *
138 * \param group
139 * \param subgroup
140 * \param ref
141 * \return int
142 */
143int I_get_subgroup_ref(const char *group, const char *subgroup, struct Ref *ref)
144{
145 return get_ref(group, subgroup, NULL, ref);
146}
147
148/*!
149 * \brief read subgroup REF file
150 *
151 * Reads the contents of the REF file for the
152 * specified <b>subgroup</b> of the specified <b>group</b> into the
153 * <b>ref</b> structure.
154 * Returns 1 if successful; 0 otherwise (but no error messages are printed).
155 *
156 * \param group
157 * \param subgroup
158 * \param mapset
159 * \param ref
160 * \return int
161 */
162int I_get_subgroup_ref2(const char *group, const char *subgroup,
163 const char *mapset, struct Ref *ref)
164{
165 return get_ref(group, subgroup, mapset, ref);
166}
167
168static int get_ref(const char *group, const char *subgroup, const char *gmapset,
169 struct Ref *ref)
170{
171 char buf[1024];
172 char name[INAME_LEN], mapset[INAME_LEN];
174 char color[20];
175 FILE *fd;
176
178
180 group = xname;
182
183 if (gmapset == NULL || *gmapset == 0)
184 gmapset = G_mapset();
185
187 if (*subgroup == 0)
188 fd = I_fopen_group_ref_old2(group, gmapset);
189 else
192 if (!fd)
193 return 0;
194
195 while (G_getl2(buf, sizeof buf, fd)) {
196 int n = sscanf(buf, "%255s %255s %15s", name, mapset,
197 color); /* better use INAME_LEN */
198 if (n == 2 || n == 3) {
200 if (n == 3)
201 set_color(name, mapset, color, ref);
202 }
203 }
204 /* make sure we have a color assignment */
206
207 fclose(fd);
208 return 1;
209}
210
211static int set_color(const char *name, const char *mapset, const char *color,
212 struct Ref *ref)
213{
214 int n;
215
216 for (n = 0; n < ref->nfiles; n++) {
217 if (strcmp(ref->file[n].name, name) == 0 &&
218 strcmp(ref->file[n].mapset, mapset) == 0)
219 break;
220 }
221
222 if (n < ref->nfiles)
223 while (*color) {
224 switch (*color) {
225 case 'r':
226 case 'R':
227 if (ref->red.n < 0)
228 ref->red.n = n;
229 break;
230 case 'g':
231 case 'G':
232 if (ref->grn.n < 0)
233 ref->grn.n = n;
234 break;
235 case 'b':
236 case 'B':
237 if (ref->blu.n < 0)
238 ref->blu.n = n;
239 break;
240 }
241 color++;
242 }
243
244 return 0;
245}
246
248{
249 ref->red.table = NULL;
250 ref->grn.table = NULL;
251 ref->blu.table = NULL;
252
253 ref->red.index = NULL;
254 ref->grn.index = NULL;
255 ref->blu.index = NULL;
256
257 if (ref->nfiles <= 0 || ref->red.n >= 0 || ref->blu.n >= 0 ||
258 ref->grn.n >= 0)
259 return 1;
260 switch (ref->nfiles) {
261 case 1:
262 ref->red.n = 0;
263 ref->grn.n = 0;
264 ref->blu.n = 0;
265 break;
266 case 2:
267 ref->blu.n = 0;
268 ref->grn.n = 1;
269 break;
270 case 3:
271 ref->blu.n = 0;
272 ref->grn.n = 1;
273 ref->red.n = 2;
274 break;
275 case 4:
276 ref->blu.n = 0;
277 ref->grn.n = 1;
278 ref->red.n = 3;
279 break;
280 default:
281 ref->blu.n = 1;
282 ref->grn.n = 2;
283 ref->red.n = 4;
284 break;
285 }
286
287 return 0;
288}
289
290/*!
291 * \brief write group REF file
292 *
293 * Writes the contents of the <b>ref</b> structure to the REF file for
294 * the specified <b>group.</b>
295 * Returns 1 if successful; 0 otherwise (and prints a diagnostic error).
296 * <b>Note.</b> This routine will create the <b>group</b>, if it does not
297 * already exist.
298 *
299 * \param group
300 * \param ref
301 * \return int
302 */
303int I_put_group_ref(const char *group, const struct Ref *ref)
304{
305 return put_ref(group, "", ref);
306}
307
308/*!
309 * \brief write subgroup REF file
310 *
311 * Writes the contents of the <b>ref</b>
312 * structure into the REF file for the specified <b>subgroup</b> of the
313 * specified <b>group.</b>
314 * Returns 1 if successful; 0 otherwise (and prints a diagnostic error).
315 * <b>Note.</b> This routine will create the <b>subgroup</b>, if it does not
316 * already exist.
317 *
318 * \param group
319 * \param subgroup
320 * \param ref
321 * \return int
322 */
323int I_put_subgroup_ref(const char *group, const char *subgroup,
324 const struct Ref *ref)
325{
326 return put_ref(group, subgroup, ref);
327}
328
329static int put_ref(const char *group, const char *subgroup,
330 const struct Ref *ref)
331{
332 int n;
333 FILE *fd;
334
335 if (*subgroup == 0)
336 fd = I_fopen_group_ref_new(group);
337 else
339 if (!fd)
340 return 0;
341
342 for (n = 0; n < ref->nfiles; n++) {
343 fprintf(fd, "%s %s", ref->file[n].name, ref->file[n].mapset);
344 if (n == ref->red.n || n == ref->grn.n || n == ref->blu.n) {
345 fprintf(fd, " ");
346 if (n == ref->red.n)
347 fprintf(fd, "r");
348 if (n == ref->grn.n)
349 fprintf(fd, "g");
350 if (n == ref->blu.n)
351 fprintf(fd, "b");
352 }
353 fprintf(fd, "\n");
354 }
355 fclose(fd);
356 return 1;
357}
358
359/*!
360 * \brief add file name to Ref structure
361 *
362 * This routine adds the file
363 * <b>name</b> and <b>mapset</b> to the list contained in the <b>ref</b>
364 * structure, if it is not already in the list. The <b>ref</b> structure must
365 * have been properly initialized. This routine is used by programs, such as
366 * <i>i.maxlik</i>, to add to the group new raster maps created from files
367 * already in the group.
368 * Returns the index into the <i>file</i> array within the <b>ref</b>
369 * structure for the file after insertion; see
370 * Imagery_Library_Data_Structures.
371 *
372 * \param name
373 * \param mapset
374 * \param ref
375 * \return int
376 */
377int I_add_file_to_group_ref(const char *name, const char *mapset,
378 struct Ref *ref)
379{
380 int n;
381
382 for (n = 0; n < ref->nfiles; n++) {
383 if (strcmp(ref->file[n].name, name) == 0 &&
384 strcmp(ref->file[n].mapset, mapset) == 0)
385 return n;
386 }
387
388 if ((n = ref->nfiles++))
389 ref->file = (struct Ref_Files *)G_realloc(
390 ref->file, ref->nfiles * sizeof(struct Ref_Files));
391 else
392 ref->file = (struct Ref_Files *)G_malloc(ref->nfiles *
393 sizeof(struct Ref_Files));
394 strcpy(ref->file[n].name, name);
395 strcpy(ref->file[n].mapset, mapset);
396 return n;
397}
398
399/*!
400 * \brief copy Ref lists
401 *
402 * This routine is used to copy file names from one
403 * <i>Ref</i> structure to another. The name and mapset for file <b>n</b>
404 * from the <b>src</b> structure are copied into the <b>dst</b> structure
405 * (which must be properly initialized).
406 * For example, the following code copies one <i>Ref</i> structure to another:
407 \code
408 struct Ref src,dst;
409 int n;
410 // some code to get information into <b>src</b>
411 ...
412 I_init_group_ref (&dst);
413 for (n = 0; n < src.nfiles; n++)
414 I_transfer_group_ref_file (&src, n, &dst);
415 \endcode
416 * This routine is used by <i>g.gui.gcp</i> to create the REF file for a
417 * subgroup.
418 *
419 * \param ref2 Source
420 * \param n
421 * \param ref1 Destination
422 * \return int 0
423 */
424int I_transfer_group_ref_file(const struct Ref *ref2, int n, struct Ref *ref1)
425{
426 int k;
427
428 /* insert old name into new ref */
429 k = I_add_file_to_group_ref(ref2->file[n].name, ref2->file[n].mapset, ref1);
430
431 /* preserve color assignment */
432 if (n == ref2->red.n)
433 ref1->red.n = k;
434 if (n == ref2->grn.n)
435 ref1->grn.n = k;
436 if (n == ref2->blu.n)
437 ref1->blu.n = k;
438
439 return 0;
440}
441
442/*!
443 * \brief initialize Ref
444 * structure
445 *
446 * This routine initializes the <b>ref</b> structure for other
447 * library calls which require a <i>Ref</i> structure. This routine must be
448 * called before any use of the structure can be made.
449 * <b>Note.</b> The routines I_get_group_ref and I_get_subgroup_ref call
450 * this routine automatically.
451 *
452 * \param ref
453 * \return int
454 */
456{
457 ref->nfiles = 0;
458 ref->red.n = ref->grn.n = ref->blu.n = -1;
459 ref->red.table = ref->grn.table = ref->blu.table = NULL;
460
461 return 0;
462}
463
464/*!
465 * \brief free Ref structure
466 *
467 * This routine frees memory allocated to the <b>ref</b> structure.
468 *
469 * \param ref
470 * \return int
471 */
473{
474 if (ref->nfiles > 0)
475 free(ref->file);
476 ref->nfiles = 0;
477
478 return 0;
479}
#define NULL
Definition ccmath.h:32
AMI_err name(char **stream_name)
Definition ami_stream.h:426
int G_getl2(char *, int, FILE *)
Gets a line of text from a file of any pedigree.
Definition getl.c:58
#define G_realloc(p, n)
Definition defs/gis.h:138
int G_unqualified_name(const char *, const char *, char *, char *)
Returns unqualified map name (without @ mapset)
Definition nme_in_mps.c:132
FILE * G_fopen_new(const char *, const char *)
Open a new database file.
Definition gis/open.c:218
#define G_malloc(n)
Definition defs/gis.h:136
FILE * G_fopen_old(const char *, const char *, const char *)
Open a database file for reading.
Definition gis/open.c:250
void int G_suppress_warnings(int)
Suppress printing a warning message to stderr.
Definition gis/error.c:219
const char * G_mapset(void)
Get current mapset name.
Definition gis/mapset.c:31
FILE * I_fopen_group_file_old(const char *, const char *)
Open group file for reading.
Definition fopen.c:102
FILE * I_fopen_group_ref_new(const char *)
Definition ref.c:22
FILE * I_fopen_group_ref_old2(const char *, const char *)
Definition ref.c:32
int I_find_group(const char *)
does group exist?
FILE * I_fopen_group_file_new(const char *, const char *)
Definition fopen.c:69
FILE * I_fopen_subgroup_ref_new(const char *, const char *)
Definition ref.c:46
FILE * I_fopen_subgroup_ref_old2(const char *, const char *, const char *)
Definition ref.c:59
#define GMAPSET_MAX
Definition gis.h:194
#define GNAME_MAX
Definition gis.h:193
int I_get_subgroup(const char *group, char *subgroup)
Definition group.c:64
int I_put_subgroup_ref(const char *group, const char *subgroup, const struct Ref *ref)
write subgroup REF file
Definition group.c:323
int I_add_file_to_group_ref(const char *name, const char *mapset, struct Ref *ref)
add file name to Ref structure
Definition group.c:377
int I_put_subgroup(const char *group, const char *subgroup)
Definition group.c:83
int I_get_subgroup_ref2(const char *group, const char *subgroup, const char *mapset, struct Ref *ref)
read subgroup REF file
Definition group.c:162
int I_get_group_ref(const char *group, struct Ref *ref)
read group REF file
Definition group.c:108
int I_transfer_group_ref_file(const struct Ref *ref2, int n, struct Ref *ref1)
copy Ref lists
Definition group.c:424
int I_init_ref_color_nums(struct Ref *ref)
Definition group.c:247
int I_free_group_ref(struct Ref *ref)
free Ref structure
Definition group.c:472
int I_get_subgroup_ref(const char *group, const char *subgroup, struct Ref *ref)
read subgroup REF file
Definition group.c:143
int I_get_group_ref2(const char *group, const char *mapset, struct Ref *ref)
read group REF file
Definition group.c:125
int I_put_group_ref(const char *group, const struct Ref *ref)
write group REF file
Definition group.c:303
int I_init_group_ref(struct Ref *ref)
initialize Ref structure
Definition group.c:455
int I_get_group(char *group)
Definition group.c:34
int I_put_group(const char *group)
Definition group.c:51
#define INAME_LEN
Definition imagery.h:8
#define GROUPFILE
Definition imagery.h:203
#define SUBGROUPFILE
Definition imagery.h:204
const char * name
Definition named_colr.c:6
#define strcpy
Definition parson.c:66
void free(void *)
char mapset[256]
Definition imagery.h:21
Definition imagery.h:24