level_two.c 10.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482
  1. /*!
  2. \file lib/vector/Vlib/level_two.c
  3. \brief Vector library - topology level functions
  4. (C) 2001-2009, 2011-2012 by the GRASS Development Team
  5. This program is free software under the GNU General Public License
  6. (>=v2). Read the file COPYING that comes with GRASS for details.
  7. \author Original author CERL, probably Dave Gerdes or Mike Higgins.
  8. \author Update to GRASS 5.7 Radim Blazek and David D. Gray.
  9. \author Update to GRASS 7 by Martin Landa <landa.martin gmail.com>
  10. */
  11. #include <stdlib.h>
  12. #include <grass/vector.h>
  13. #include <grass/glocale.h>
  14. static void check_level(const struct Map_info *Map)
  15. {
  16. if (Map->level < 2)
  17. G_fatal_error(_("Vector map <%s> is not open at topological level"),
  18. Vect_get_full_name(Map));
  19. }
  20. /*!
  21. \brief Get number of nodes in vector map
  22. \param Map pointer to Map_info struct
  23. \return number of nodes
  24. */
  25. plus_t Vect_get_num_nodes(const struct Map_info *Map)
  26. {
  27. return (Map->plus.n_nodes);
  28. }
  29. /*!
  30. \brief Get number of primitives in vector map
  31. \param Map pointer to Map_info struct
  32. \param type feature type
  33. \return number of primitives
  34. */
  35. plus_t Vect_get_num_primitives(const struct Map_info *Map, int type)
  36. {
  37. plus_t num = 0;
  38. if (type & GV_POINT)
  39. num += Map->plus.n_plines;
  40. if (type & GV_LINE)
  41. num += Map->plus.n_llines;
  42. if (type & GV_BOUNDARY)
  43. num += Map->plus.n_blines;
  44. if (type & GV_CENTROID)
  45. num += Map->plus.n_clines;
  46. if (type & GV_FACE)
  47. num += Map->plus.n_flines;
  48. if (type & GV_KERNEL)
  49. num += Map->plus.n_klines;
  50. return num;
  51. }
  52. /*!
  53. \brief Fetch number of features (points, lines, boundaries, centroids) in vector map
  54. \param Map pointer to Map_info struct
  55. \return number of features
  56. */
  57. plus_t Vect_get_num_lines(const struct Map_info *Map)
  58. {
  59. return (Map->plus.n_lines);
  60. }
  61. /*!
  62. \brief Get number of areas in vector map
  63. \param Map pointer to Map_info struct
  64. \return number of areas
  65. */
  66. plus_t Vect_get_num_areas(const struct Map_info *Map)
  67. {
  68. return (Map->plus.n_areas);
  69. }
  70. /*!
  71. \brief Fetch number of kernels in vector map
  72. \param Map pointer to Map_info struct
  73. \return number of kernels
  74. */
  75. plus_t Vect_get_num_kernels(const struct Map_info *Map)
  76. {
  77. return (Map->plus.n_klines);
  78. }
  79. /*!
  80. \brief Get number of faces in vector map
  81. \param Map pointer to Map_info struct
  82. \return number of faces
  83. */
  84. plus_t Vect_get_num_faces(const struct Map_info *Map)
  85. {
  86. return (Map->plus.n_flines);
  87. }
  88. /*!
  89. \brief Fetch number of volumes in vector map
  90. \param Map pointer to Map_info struct
  91. \return number of volumes
  92. */
  93. plus_t Vect_get_num_volumes(const struct Map_info *Map)
  94. {
  95. return (Map->plus.n_volumes);
  96. }
  97. /*!
  98. \brief Get number of islands in vector map
  99. \param Map pointer to Map_info struct
  100. \return number of islands
  101. */
  102. plus_t Vect_get_num_islands(const struct Map_info *Map)
  103. {
  104. return (Map->plus.n_isles);
  105. }
  106. /*!
  107. \brief Fetch number of holes in vector map
  108. \param Map pointer to Map_info struct
  109. \return number of holes
  110. */
  111. plus_t Vect_get_num_holes(const struct Map_info *Map)
  112. {
  113. return (Map->plus.n_holes);
  114. }
  115. /*!
  116. \brief Get number of defined dblinks
  117. \param Map pointer to Map_info struct
  118. \return number of dblinks
  119. */
  120. int Vect_get_num_dblinks(const struct Map_info *Map)
  121. {
  122. /* available on level 1 ? */
  123. return (Map->dblnk->n_fields);
  124. }
  125. /*!
  126. \brief Get number of updated features
  127. Note: Vect_set_updated() must be called to maintain list of updated
  128. features
  129. \param Map pointer to Map_info struct
  130. \return number of updated features
  131. */
  132. int Vect_get_num_updated_lines(const struct Map_info *Map)
  133. {
  134. return (Map->plus.uplist.n_uplines);
  135. }
  136. /*!
  137. \brief Get updated line by index
  138. Note: Vect_set_updated() must be called to maintain list of updated
  139. features
  140. \param Map pointer to Map_info struct
  141. \param idx index
  142. \return updated line
  143. */
  144. int Vect_get_updated_line(const struct Map_info *Map, int idx)
  145. {
  146. return (Map->plus.uplist.uplines[idx]);
  147. }
  148. /*!
  149. \brief Get updated line offset by index
  150. Note: Vect_set_updated() must be called to maintain list of updated
  151. features
  152. \param Map pointer to Map_info struct
  153. \param idx index
  154. \return updated line
  155. */
  156. off_t Vect_get_updated_line_offset(const struct Map_info *Map, int idx)
  157. {
  158. return (Map->plus.uplist.uplines_offset[idx]);
  159. }
  160. /*!
  161. \brief Get number of updated nodes
  162. \param Map pointer to Map_info struct
  163. \return number of updated nodes
  164. */
  165. int Vect_get_num_updated_nodes(const struct Map_info *Map)
  166. {
  167. return (Map->plus.uplist.n_upnodes);
  168. }
  169. /*!
  170. \brief Get updated (modified) node by index
  171. Note: Vect_set_updated() must be called to maintain list of updated
  172. features
  173. Negative id:
  174. - if Node[id] is not NULL then the node was added
  175. - if Node[id] is NULL then the node was deleted
  176. Positive id:
  177. - node was updated
  178. \param Map pointer to Map_info struct
  179. \param idx index
  180. \return id of modified node
  181. */
  182. int Vect_get_updated_node(const struct Map_info *Map, int idx)
  183. {
  184. return (Map->plus.uplist.upnodes[idx]);
  185. }
  186. /*!
  187. \brief Get line type
  188. \param Map pointer to Map_info struct
  189. \param line line id
  190. \return line type
  191. */
  192. int Vect_get_line_type(const struct Map_info *Map, int line)
  193. {
  194. check_level(Map);
  195. if (!Vect_line_alive(Map, line))
  196. return 0;
  197. return (Map->plus.Line[line]->type);
  198. }
  199. /*!
  200. \brief Get node coordinates
  201. \param Map pointer to Map_info struct
  202. \param num node id (starts at 1)
  203. \param[out] x,y,z coordinates values (for 2D coordinates z is NULL)
  204. \return 0 on success
  205. \return -1 on error
  206. */
  207. int Vect_get_node_coor(const struct Map_info *Map, int num, double *x, double *y,
  208. double *z)
  209. {
  210. struct P_node *Node;
  211. if (num < 1 || num > Map->plus.n_nodes) {
  212. G_warning(_("Invalid node id: %d"), num);
  213. return -1;
  214. }
  215. Node = Map->plus.Node[num];
  216. *x = Node->x;
  217. *y = Node->y;
  218. if (z != NULL)
  219. *z = Node->z;
  220. return 0;
  221. }
  222. /*!
  223. \brief Get line nodes
  224. \param Map pointer to Map_info struct
  225. \param line line id
  226. \param n1 (start node), n2 (end node) ids of line nodes (or NULL)
  227. \return 1
  228. */
  229. int Vect_get_line_nodes(const struct Map_info *Map, int line, int *n1, int *n2)
  230. {
  231. char type;
  232. check_level(Map);
  233. type = Vect_get_line_type(Map, line);
  234. if (!(type & GV_LINES))
  235. G_fatal_error(_("Nodes not available for line %d"), line);
  236. if (type == GV_LINE) {
  237. struct P_topo_l *topo = (struct P_topo_l *)Map->plus.Line[line]->topo;
  238. if (n1 != NULL)
  239. *n1 = topo->N1;
  240. if (n2 != NULL)
  241. *n2 = topo->N2;
  242. }
  243. else if (type == GV_BOUNDARY) {
  244. struct P_topo_b *topo = (struct P_topo_b *)Map->plus.Line[line]->topo;
  245. if (n1 != NULL)
  246. *n1 = topo->N1;
  247. if (n2 != NULL)
  248. *n2 = topo->N2;
  249. }
  250. return 1;
  251. }
  252. /*!
  253. \brief Get area id on the left and right side of the boundary
  254. Negative area id indicates an isle.
  255. \param Map pointer to Map_info struct
  256. \param line line id
  257. \param[out] left,right area id on the left and right side
  258. \return 1 on success
  259. \return -1 on failure (topology not available, line is not a boundary)
  260. */
  261. int Vect_get_line_areas(const struct Map_info *Map, int line, int *left, int *right)
  262. {
  263. struct P_topo_b *topo;
  264. check_level(Map);
  265. if (!Map->plus.Line[line]->topo) {
  266. G_warning(_("Areas not available for line %d"), line);
  267. return -1;
  268. }
  269. if (Vect_get_line_type(Map, line) != GV_BOUNDARY) {
  270. G_warning(_("Line %d is not a boundary"), line);
  271. return -1;
  272. }
  273. topo = (struct P_topo_b *)Map->plus.Line[line]->topo;
  274. if (left != NULL)
  275. *left = topo->left;
  276. if (right != NULL)
  277. *right = topo->right;
  278. return 1;
  279. }
  280. /*!
  281. \brief Get number of lines for node
  282. \param Map pointer to Map_info struct
  283. \param node node id
  284. \return numbers of lines
  285. */
  286. int Vect_get_node_n_lines(const struct Map_info *Map, int node)
  287. {
  288. check_level(Map);
  289. return (Map->plus.Node[node]->n_lines);
  290. }
  291. /*!
  292. \brief Get line id for node line index
  293. \param Map pointer to Map_info struct
  294. \param node node id
  295. \param line line index (range: 0 - Vect_get_node_n_lines())
  296. \return line id
  297. */
  298. int Vect_get_node_line(const struct Map_info *Map, int node, int line)
  299. {
  300. check_level(Map);
  301. return (Map->plus.Node[node]->lines[line]);
  302. }
  303. /*!
  304. \brief Angle of segment of the line connected to the node
  305. \param Map pointer to Map_info struct
  306. \param node node number
  307. \param line line index (range: 0 - Vect_get_node_n_lines())
  308. \return angle of segment of the line connected to the node
  309. */
  310. float Vect_get_node_line_angle(const struct Map_info *Map, int node, int line)
  311. {
  312. check_level(Map);
  313. return (Map->plus.Node[node]->angles[line]);
  314. }
  315. /*!
  316. \brief Get area id the centroid is within
  317. \param Map pointer to Map_info struct
  318. \param centroid centroid id
  319. \return area id the centroid is within
  320. \return 0 for not in area
  321. \return negative id if centroid is duplicated in the area
  322. */
  323. int Vect_get_centroid_area(const struct Map_info *Map, int centroid)
  324. {
  325. struct P_topo_c *topo;
  326. check_level(Map);
  327. if (Map->plus.Line[centroid]->type != GV_CENTROID)
  328. return 0;
  329. topo = (struct P_topo_c *)Map->plus.Line[centroid]->topo;
  330. if(!topo)
  331. G_fatal_error(_("Topology info not available for feature %d"), centroid);
  332. return (topo->area);
  333. }
  334. /*!
  335. \brief Enable/disable maintanance of list of updated lines/nodes
  336. See Plus_head.uplist for details.
  337. \param Map pointer to Map_info struct
  338. \param enable TRUE/FALSE to enable/disable
  339. */
  340. void Vect_set_updated(struct Map_info *Map, int enable)
  341. {
  342. G_debug(1, "Vect_set_updated(): name = '%s' enabled = %d", Map->name, enable);
  343. check_level(Map);
  344. Map->plus.uplist.do_uplist = enable != 0 ? TRUE : FALSE;
  345. }
  346. /*!
  347. \brief Reset list of updated lines/nodes
  348. \param Map pointer to Map_info struct
  349. */
  350. void Vect_reset_updated(struct Map_info *Map)
  351. {
  352. struct Plus_head *Plus;
  353. check_level(Map);
  354. Plus = &(Map->plus);
  355. dig_line_reset_updated(Plus);
  356. dig_node_reset_updated(Plus);
  357. }