1 /*!
2 * \file lib/raster/raster.c
3 *
4 * \brief Raster Library - Raster cell value routines.
5 *
6 * (C) 2001-2009 by the GRASS Development Team
7 *
8 * This program is free software under the GNU General Public License
9 * (>=v2). Read the file COPYING that comes with GRASS for details.
10 *
11 * \author Original author CERL
12 */
13
14 #include <stdlib.h>
15 #include <string.h>
16 #include <grass/gis.h>
17 #include <grass/raster.h>
18
19 /*!
20 * \brief Compares raster values.
21 *
22 * \param v1,v2 values to be compared
23 * \param data_type raster type (CELL, FCELL, DCELL)
24 *
25 * \return 1 if p > q or only q is null value
26 * \return -1 if p < q or only p is null value
27 * \return 0 if p == q or p==q==null value
28 */
Rast_raster_cmp(const void * v1,const void * v2,RASTER_MAP_TYPE data_type)29 int Rast_raster_cmp(const void *v1, const void *v2, RASTER_MAP_TYPE data_type)
30 {
31 if (Rast_is_null_value(v1, data_type)) {
32 if (Rast_is_null_value(v2, data_type))
33 return 0;
34 else
35 return -1;
36 }
37 else if (Rast_is_null_value(v2, data_type))
38 return 1;
39
40 switch (data_type) {
41 case CELL_TYPE:
42 if (*((const CELL *)v1) > *((const CELL *)v2))
43 return 1;
44 else if (*((const CELL *)v1) == *((const CELL *)v2))
45 return 0;
46 else
47 return -1;
48 case FCELL_TYPE:
49 if (*((const FCELL *)v1) > *((const FCELL *)v2))
50 return 1;
51 else if (*((const FCELL *)v1) == *((const FCELL *)v2))
52 return 0;
53 else
54 return -1;
55 case DCELL_TYPE:
56 if (*((const DCELL *)v1) > *((const DCELL *)v2))
57 return 1;
58 else if (*((const DCELL *)v1) == *((const DCELL *)v2))
59 return 0;
60 else
61 return -1;
62 }
63
64 return 0;
65 }
66
67 /*!
68 * \brief Copies raster values.
69 *
70 * If \p v2 is null value, sets \p v2 to null value.
71 * \p n is typically size of the destination array
72 * and the source array is at least that large.
73 *
74 * \param v1 destination array for raster values
75 * \param v2 source array with raster values
76 * \param n number of values to copy
77 * \param data_type raster type (CELL, FCELL, DCELL)
78 */
Rast_raster_cpy(void * v1,const void * v2,int n,RASTER_MAP_TYPE data_type)79 void Rast_raster_cpy(void *v1, const void *v2, int n,
80 RASTER_MAP_TYPE data_type)
81 {
82 memcpy(v1, v2, n * Rast_cell_size(data_type));
83 }
84
85 /*!
86 * \brief Places a CELL raster value
87 *
88 * If Rast_is_c_null_value() is true, sets p to null value. Converts CELL
89 * val to data_type (type of p) and stores result in p. Used for
90 * assigning CELL values to raster cells of any type.
91 *
92 * \param rast pointer to raster cell value
93 * \param cval value to set
94 * \param data_type raster type (CELL, FCELL, DCELL)
95 */
Rast_set_c_value(void * rast,CELL cval,RASTER_MAP_TYPE data_type)96 void Rast_set_c_value(void *rast, CELL cval, RASTER_MAP_TYPE data_type)
97 {
98 CELL c;
99
100 c = cval;
101 if (Rast_is_c_null_value(&c)) {
102 Rast_set_null_value(rast, 1, data_type);
103 return;
104 }
105 switch (data_type) {
106 case CELL_TYPE:
107 *((CELL *) rast) = cval;
108 break;
109 case FCELL_TYPE:
110 *((FCELL *) rast) = (FCELL) cval;
111 break;
112 case DCELL_TYPE:
113 *((DCELL *) rast) = (DCELL) cval;
114 break;
115 }
116 }
117
118 /*!
119 * \brief Places a FCELL raster value
120 *
121 * If Rast_is_f_null_value() is true, sets p to null value. Converts
122 * FCELL val to data_type (type of p) and stores result in p. Used for
123 * assigning FCELL values to raster cells of any type.
124 *
125 * \param rast pointer to raster cell value
126 * \param fval value to set
127 * \param data_type raster type (CELL, FCELL, DCELL)
128 */
Rast_set_f_value(void * rast,FCELL fval,RASTER_MAP_TYPE data_type)129 void Rast_set_f_value(void *rast, FCELL fval, RASTER_MAP_TYPE data_type)
130 {
131 FCELL f;
132
133 f = fval;
134 if (Rast_is_f_null_value(&f)) {
135 Rast_set_null_value(rast, 1, data_type);
136 return;
137 }
138 switch (data_type) {
139 case CELL_TYPE:
140 *((CELL *) rast) = (CELL) fval;
141 break;
142 case FCELL_TYPE:
143 *((FCELL *) rast) = fval;
144 break;
145 case DCELL_TYPE:
146 *((DCELL *) rast) = (DCELL) fval;
147 break;
148 }
149 }
150
151
152 /*!
153 * \brief Places a DCELL raster value
154 *
155 * If Rast_is_d_null_value() is true, sets p to null value. Converts
156 * DCELL val to data_type (type of p) and stores result in p. Used for
157 * assigning DCELL values to raster cells of any type.
158 *
159 * \param rast pointer to raster cell value
160 * \param fval value to set
161 * \param data_type raster type (CELL, FCELL, DCELL)
162 */
Rast_set_d_value(void * rast,DCELL dval,RASTER_MAP_TYPE data_type)163 void Rast_set_d_value(void *rast, DCELL dval, RASTER_MAP_TYPE data_type)
164 {
165 DCELL d;
166
167 d = dval;
168 if (Rast_is_d_null_value(&d)) {
169 Rast_set_null_value(rast, 1, data_type);
170 return;
171 }
172 switch (data_type) {
173 case CELL_TYPE:
174 *((CELL *) rast) = (CELL) dval;
175 break;
176 case FCELL_TYPE:
177 *((FCELL *) rast) = (FCELL) dval;
178 break;
179 case DCELL_TYPE:
180 *((DCELL *) rast) = dval;
181 break;
182 }
183 }
184
185 /*!
186 * \brief Retrieves the value of give type from pointer p
187 *
188 * Retrieves the value of type data_type from pointer p, converts it
189 * to CELL type and returns the result. If null value is stored in p,
190 * returns CELL null value.
191 *
192 * Used for retrieving CELL values from raster cells of any type.
193 *
194 * Note: when data_type != CELL_TYPE, no quantization is used, only
195 * type conversion.
196 *
197 * \param rast pointer to raster cell value
198 * \param data_type raster type (CELL, FCELL, DCELL)
199 *
200 * \return raster value
201 */
Rast_get_c_value(const void * rast,RASTER_MAP_TYPE data_type)202 CELL Rast_get_c_value(const void *rast, RASTER_MAP_TYPE data_type)
203 {
204 CELL c;
205
206 if (Rast_is_null_value(rast, data_type)) {
207 Rast_set_c_null_value(&c, 1);
208 return c;
209 }
210 switch (data_type) {
211 case CELL_TYPE:
212 return *((const CELL *)rast);
213 case FCELL_TYPE:
214 return (CELL) * ((const FCELL *)rast);
215 case DCELL_TYPE:
216 return (CELL) * ((const DCELL *)rast);
217 }
218
219 return 0;
220 }
221
222 /*!
223 * \brief Retrieves the value of given raster type from pointer p (FCELL)
224 *
225 * Retrieves the value of type data_type from pointer p, converts it
226 * to FCELL type and returns the result. If null value is stored in p,
227 * returns FCELL null value.
228 *
229 * Used for retrieving FCELL values from raster cells of any type.
230 *
231 * \param rast pointer to raster cell value
232 * \param data_type raster type (CELL, FCELL, DCELL)
233 *
234 * \return raster value
235 */
Rast_get_f_value(const void * rast,RASTER_MAP_TYPE data_type)236 FCELL Rast_get_f_value(const void *rast, RASTER_MAP_TYPE data_type)
237 {
238 FCELL f;
239
240 if (Rast_is_null_value(rast, data_type)) {
241 Rast_set_f_null_value(&f, 1);
242 return f;
243 }
244 switch (data_type) {
245 case CELL_TYPE:
246 return (FCELL) * ((const CELL *)rast);
247 case FCELL_TYPE:
248 return *((const FCELL *)rast);
249 case DCELL_TYPE:
250 return (FCELL) * ((const DCELL *)rast);
251 }
252
253 return 0;
254 }
255
256
257 /*!
258 * \brief Retrieves the value of given type from pointer p (DCELL)
259 *
260 * Retrieves the value of type data_type from pointer p, converts it
261 * to DCELL type and returns the result. If null value is stored in p,
262 * returns DCELL null value.
263
264 * Used for retrieving DCELL values from raster cells of any type.
265 *
266 * \param rast pointer to raster cell value
267 * \param data_type raster type (CELL, FCELL, DCELL)
268 *
269 * \return raster value
270 */
Rast_get_d_value(const void * rast,RASTER_MAP_TYPE data_type)271 DCELL Rast_get_d_value(const void *rast, RASTER_MAP_TYPE data_type)
272 {
273 DCELL d;
274
275 if (Rast_is_null_value(rast, data_type)) {
276 Rast_set_d_null_value(&d, 1);
277 return d;
278 }
279 switch (data_type) {
280 case CELL_TYPE:
281 return (DCELL) * ((const CELL *)rast);
282 case FCELL_TYPE:
283 return (DCELL) * ((const FCELL *)rast);
284 case DCELL_TYPE:
285 return *((const DCELL *)rast);
286 }
287
288 return 0;
289 }
290