GRASS 8 Programmer's Manual 8.6.0dev(2026)-4bb960b182
Loading...
Searching...
No Matches
iscatt_structs.c
Go to the documentation of this file.
1/*!
2 \file lib/imagery/iscatt_structs.c
3
4 \brief Imagery library - functions for manipulation with structures used
5 by wx.iscatt (wx Interactive Scatter Plot Tool)
6
7 SPDX-FileCopyrightText: 2013 GRASS Development Team
8 SPDX-License-Identifier: GPL-2.0-or-later
9
10 \author Stepan Turek <stepan.turek@seznam.cz> (GSoC 2013, Mentor: Martin
11 Landa)
12 */
13
14#include <math.h>
15
16#include <grass/imagery.h>
17#include <grass/gis.h>
18
19/*!
20 \brief Compute band ids from scatter plot id.
21
22 Scatter plot id describes which bands defines the scatter plot.
23
24 Let say we have 3 bands, their ids are 0, 1 and 2.
25 Scatter plot with id 0 consists of band 1 (b_1_id) 0 and band 2 (b_2_id) 1.
26 All scatter plots:
27 scatt_id b_1_id b_2_id
28 0 0 1
29 1 0 2
30 2 1 2
31
32 \param scatt_id scatter plot id
33 \param n_bands number of bands
34 \param[out] b_1_id id of band1
35 \param[out] b_2_id id of band2
36
37 \return 0
38 */
39int I_id_scatt_to_bands(const int scatt_id, const int n_bands, int *b_1_id,
40 int *b_2_id)
41{
42 int n_b1 = n_bands - 1;
43
44 *b_1_id =
45 (int)((2 * n_b1 + 1 -
46 sqrt((double)((2 * n_b1 + 1) * (2 * n_b1 + 1) - 8 * scatt_id))) /
47 2);
48
49 *b_2_id = scatt_id -
50 ((*b_1_id) * (2 * n_b1 + 1) - (*b_1_id) * (*b_1_id)) / 2 +
51 (*b_1_id) + 1;
52
53 return 0;
54}
55
56/*!
57 \brief Compute scatter plot id from band ids.
58
59 See also I_id_scatt_to_bands
60
61 \param b_1_id id of band1
62 \param b_1_id id of band2
63 \param n_bands number of bands
64 \param[out] scatt_id scatter plot id
65
66 \return 0
67 */
68int I_bands_to_id_scatt(const int b_1_id, const int b_2_id, const int n_bands,
69 int *scatt_id)
70{
71 int n_b1 = n_bands - 1;
72
73 *scatt_id =
74 (b_1_id * (2 * n_b1 + 1) - b_1_id * b_1_id) / 2 + b_2_id - b_1_id - 1;
75
76 return 0;
77}
78
79/*!
80 \brief Initialize structure for storing scatter plots data.
81
82 \param cats pointer to scCats struct
83 \param n_bands number of bands
84 \param type SC_SCATT_DATA - stores scatter plots
85 \param type SC_SCATT_CONDITIONS - stores selected areas in scatter plots
86 */
87void I_sc_init_cats(struct scCats *cats, int n_bands, int type)
88{
89 int i_cat;
90
91 cats->type = type;
92
93 cats->n_cats = 100;
94 cats->n_a_cats = 0;
95
96 cats->n_bands = n_bands;
97 cats->n_scatts = (n_bands - 1) * n_bands / 2;
98
99 cats->cats_arr =
100 (struct scScatts **)G_malloc(cats->n_cats * sizeof(struct scScatts *));
101 G_zero(cats->cats_arr, cats->n_cats * sizeof(struct scScatts *));
102
103 cats->cats_ids = (int *)G_malloc(cats->n_cats * sizeof(int));
104 cats->cats_idxs = (int *)G_malloc(cats->n_cats * sizeof(int));
105
106 for (i_cat = 0; i_cat < cats->n_cats; i_cat++)
107 cats->cats_idxs[i_cat] = -1;
108
109 return;
110}
111
112/*!
113 \brief Free data of struct scCats, the structure itself remains allocated.
114
115 \param cats pointer to existing scCats struct
116 */
117void I_sc_free_cats(struct scCats *cats)
118{
119 int i_cat;
120
121 for (i_cat = 0; i_cat < cats->n_a_cats; i_cat++) {
122 if (cats->cats_arr[i_cat]) {
123 G_free(cats->cats_arr[i_cat]->scatt_idxs);
124 G_free(cats->cats_arr[i_cat]->scatts_bands);
125 G_free(cats->cats_arr[i_cat]->scatts_arr);
126 G_free(cats->cats_arr[i_cat]);
127 }
128 }
129
130 G_free(cats->cats_ids);
131 G_free(cats->cats_idxs);
132 G_free(cats->cats_arr);
133
134 cats->n_cats = 0;
135 cats->n_a_cats = 0;
136 cats->n_bands = 0;
137 cats->n_scatts = 0;
138 cats->type = -1;
139
140 return;
141}
142
143/*!
144 \brief Add category.
145
146 Category represents group of scatter plots.
147
148 \param cats pointer to scCats struct
149
150 \return assigned category id (starts with 0)
151 \return -1 if maximum number of categories was reached
152 */
153int I_sc_add_cat(struct scCats *cats)
154{
155 int i_scatt, i_cat_id, cat_id = 0;
156 int n_a_cats = cats->n_a_cats;
157
158 if (cats->n_a_cats >= cats->n_cats)
159 return -1;
160
161 for (i_cat_id = 0; i_cat_id < cats->n_cats; i_cat_id++)
162 if (cats->cats_idxs[i_cat_id] < 0) {
164 break;
165 }
166
167 cats->cats_ids[n_a_cats] = cat_id;
168 cats->cats_idxs[cat_id] = n_a_cats;
169
170 cats->cats_arr[n_a_cats] =
171 (struct scScatts *)G_malloc(sizeof(struct scScatts));
172
173 cats->cats_arr[n_a_cats]->scatts_arr = (struct scdScattData **)G_malloc(
174 cats->n_scatts * sizeof(struct scdScattData *));
175 G_zero((cats->cats_arr[n_a_cats]->scatts_arr),
176 cats->n_scatts * sizeof(struct scdScattData *));
177
178 cats->cats_arr[n_a_cats]->n_a_scatts = 0;
179
180 cats->cats_arr[n_a_cats]->scatts_bands =
181 (int *)G_malloc(cats->n_scatts * 2 * sizeof(int));
182
183 cats->cats_arr[n_a_cats]->scatt_idxs =
184 (int *)G_malloc(cats->n_scatts * sizeof(int));
185 for (i_scatt = 0; i_scatt < cats->n_scatts; i_scatt++)
186 cats->cats_arr[n_a_cats]->scatt_idxs[i_scatt] = -1;
187
188 ++cats->n_a_cats;
189
190 return cat_id;
191}
192
193/*!
194 \brief Insert scatter plot data .
195 Inserted scatt_data struct must have same type as
196 cats struct (SC_SCATT_DATA or SC_SCATT_CONDITIONS).
197
198 \param cats pointer to scCats struct
199 \param scatt_data pointer to scdScattData struct
200 \param cat_id id number of category
201 \param scatt_id id number of scatter plot
202
203 \return 0 on success
204 \return -1 on failure
205 */
207 int cat_id, int scatt_id)
208{
209 int band_1, band_2, cat_idx, n_a_scatts;
210 struct scScatts *scatts;
211
213 return -1;
214
215 cat_idx = cats->cats_idxs[cat_id];
216 if (cat_idx < 0)
217 return -1;
218
220 return -1;
221
222 scatts = cats->cats_arr[cat_idx];
223 if (scatts->scatt_idxs[scatt_id] >= 0)
224 return -1;
225
226 if (!scatt_data->b_conds_arr && cats->type == SC_SCATT_CONDITIONS)
227 return -1;
228
229 if (!scatt_data->scatt_vals_arr && cats->type == SC_SCATT_DATA)
230 return -1;
231
232 n_a_scatts = scatts->n_a_scatts;
233
234 scatts->scatt_idxs[scatt_id] = n_a_scatts;
235
237
238 scatts->scatts_bands[n_a_scatts * 2] = band_1;
239 scatts->scatts_bands[n_a_scatts * 2 + 1] = band_2;
240
241 scatts->scatts_arr[n_a_scatts] = scatt_data;
242 ++scatts->n_a_scatts;
243
244 return 0;
245}
246
247/*!
248 \brief Insert scatter plot data.
249
250 \param scatt_data pointer to existing struct scdScattData
251 \param type SC_SCATT_DATA for scatter plots or
252 SC_SCATT_CONDITIONS for selected areas in scatter plot
253 \param n_vals number of data values
254 \param data array of values (unsigned char for SC_SCATT_CONDITIONS,
255 unsigned int for SC_SCATT_DATA)
256 */
258 int n_vals, void *data)
259{
260 scatt_data->n_vals = n_vals;
261
262 if (type == SC_SCATT_DATA) {
263 if (data)
264 scatt_data->scatt_vals_arr = (unsigned int *)data;
265 else {
266 scatt_data->scatt_vals_arr =
267 (unsigned int *)G_malloc(n_vals * sizeof(unsigned int));
268 G_zero(scatt_data->scatt_vals_arr, n_vals * sizeof(unsigned int));
269 }
270 scatt_data->b_conds_arr = NULL;
271 }
272 else if (type == SC_SCATT_CONDITIONS) {
273 if (data)
274 scatt_data->b_conds_arr = (unsigned char *)data;
275 else {
276 scatt_data->b_conds_arr =
277 (unsigned char *)G_malloc(n_vals * sizeof(unsigned char));
278 G_zero(scatt_data->b_conds_arr, n_vals * sizeof(unsigned char));
279 }
280 scatt_data->scatt_vals_arr = NULL;
281 }
282
283 return;
284}
#define NULL
Definition ccmath.h:32
void G_zero(void *, int)
Zero out a buffer, buf, of length i.
Definition gis/zero.c:21
void G_free(void *)
Free allocated memory.
Definition gis/alloc.c:145
#define G_malloc(n)
Definition defs/gis.h:136
#define SC_SCATT_CONDITIONS
Definition imagery.h:137
#define SC_SCATT_DATA
Definition imagery.h:136
int I_bands_to_id_scatt(const int b_1_id, const int b_2_id, const int n_bands, int *scatt_id)
Compute scatter plot id from band ids.
void I_sc_free_cats(struct scCats *cats)
Free data of struct scCats, the structure itself remains allocated.
void I_sc_init_cats(struct scCats *cats, int n_bands, int type)
Initialize structure for storing scatter plots data.
int I_sc_insert_scatt_data(struct scCats *cats, struct scdScattData *scatt_data, int cat_id, int scatt_id)
Insert scatter plot data . Inserted scatt_data struct must have same type as cats struct (SC_SCATT_DA...
int I_id_scatt_to_bands(const int scatt_id, const int n_bands, int *b_1_id, int *b_2_id)
Compute band ids from scatter plot id.
int I_sc_add_cat(struct scCats *cats)
Add category.
void I_scd_init_scatt_data(struct scdScattData *scatt_data, int type, int n_vals, void *data)
Insert scatter plot data.
int type
Definition imagery.h:144
int n_cats
Definition imagery.h:147
int * cats_ids
Definition imagery.h:154
struct scScatts ** cats_arr
Definition imagery.h:159
int n_a_cats
Definition imagery.h:153
int * cats_idxs
Definition imagery.h:156
int n_scatts
Definition imagery.h:150
int n_bands
Definition imagery.h:149
int n_a_scatts
Definition imagery.h:165