main.c 7.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286
  1. /****************************************************************************
  2. *
  3. * MODULE: d.colortable
  4. * AUTHOR(S): James Westervelt, CERL (original contributor)
  5. * Markus Neteler <neteler itc.it>,
  6. * Bernhard Reiter <bernhard intevation.de>,
  7. * Eric G. Miller <egm2 jps.net>,
  8. * Glynn Clements <glynn gclements.plus.com>,
  9. * Hamish Bowman <hamish_b yahoo.com>,
  10. * Jan-Oliver Wagner <jan intevation.de>
  11. * PURPOSE: display the color table associated with a raster map layer in
  12. * the active frame on the graphics monitor
  13. * COPYRIGHT: (C) 1999-2009 by the GRASS Development Team
  14. *
  15. * This program is free software under the GNU General Public
  16. * License (>=v2). Read the file COPYING that comes with GRASS
  17. * for details.
  18. *
  19. *****************************************************************************/
  20. #include <stdlib.h>
  21. #include <math.h>
  22. #include <grass/display.h>
  23. #include <grass/gis.h>
  24. #include <grass/raster.h>
  25. #include <grass/glocale.h>
  26. int main(int argc, char **argv)
  27. {
  28. char *map_name;
  29. int color;
  30. int lines;
  31. int cols;
  32. struct FPRange fp_range;
  33. struct Colors colors;
  34. double ratio;
  35. DCELL dmin, dmax, dval;
  36. int cats_num;
  37. int cur_dot_row, cur_dot_col;
  38. int dots_per_line, dots_per_col;
  39. int atcat;
  40. int black;
  41. int atcol, atline;
  42. int count, offset;
  43. double t, b, l, r;
  44. int fp, new_colr;
  45. double x_box[5], y_box[5];
  46. struct GModule *module;
  47. struct Option *opt1, *opt2, *opt3, *opt4;
  48. struct Flag *skip_null;
  49. /* Initialize the GIS calls */
  50. G_gisinit(argv[0]);
  51. module = G_define_module();
  52. G_add_keyword(_("display"));
  53. G_add_keyword(_("raster"));
  54. G_add_keyword(_("color table"));
  55. module->description =
  56. _("Displays the color table associated with a raster map layer.");
  57. opt1 = G_define_standard_option(G_OPT_R_MAP);
  58. opt1->description =
  59. _("Name of raster map whose color table is to be displayed");
  60. opt2 = G_define_standard_option(G_OPT_C);
  61. opt2->answer = DEFAULT_BG_COLOR;
  62. opt2->label =
  63. _("Color of lines separating the colors of the color table");
  64. opt3 = G_define_option();
  65. opt3->key = "lines";
  66. opt3->type = TYPE_INTEGER;
  67. opt3->options = "1-1000";
  68. opt3->description = _("Number of lines to appear in the color table");
  69. opt4 = G_define_option();
  70. opt4->key = "columns";
  71. opt4->type = TYPE_INTEGER;
  72. opt4->options = "1-1000";
  73. opt4->description = _("Number of columns to appear in the color table");
  74. skip_null = G_define_flag();
  75. skip_null->key = 'n';
  76. skip_null->description =
  77. _("Do not draw a collar showing the NULL color in FP maps");
  78. /* Check command line */
  79. if (G_parser(argc, argv))
  80. exit(EXIT_FAILURE);
  81. map_name = opt1->answer;
  82. fp = Rast_map_is_fp(map_name, "");
  83. if (opt2->answer != NULL) {
  84. new_colr = D_translate_color(opt2->answer);
  85. color = new_colr;
  86. }
  87. if (fp)
  88. lines = 1;
  89. else
  90. lines = 0;
  91. if (opt3->answer != NULL) {
  92. if (fp)
  93. G_warning(_("<%s> is floating-point; "
  94. "ignoring [lines] and drawing continuous color ramp"),
  95. map_name);
  96. else
  97. sscanf(opt3->answer, "%d", &lines);
  98. }
  99. if (fp)
  100. cols = 1;
  101. else
  102. cols = 0;
  103. if (opt4->answer) {
  104. if (fp)
  105. G_warning(_("<%s> is floating-point; "
  106. "ignoring [cols] and drawing continuous color ramp"),
  107. map_name);
  108. else
  109. sscanf(opt4->answer, "%d", &cols);
  110. }
  111. /* Make sure map is available */
  112. if (Rast_read_colors(map_name, "", &colors) == -1)
  113. G_fatal_error(_("Color file for <%s> not available"), map_name);
  114. if (Rast_read_fp_range(map_name, "", &fp_range) == -1)
  115. G_fatal_error(_("Range file for <%s> not available"), map_name);
  116. D_open_driver();
  117. D_setup_unity(0);
  118. D_get_src(&t, &b, &l, &r);
  119. Rast_get_fp_range_min_max(&fp_range, &dmin, &dmax);
  120. if (Rast_is_d_null_value(&dmin) || Rast_is_d_null_value(&dmax))
  121. G_fatal_error(_("Data range is empty"));
  122. cats_num = (int)dmax - (int)dmin + 1;
  123. if (lines <= 0 && cols <= 0) {
  124. double dx, dy;
  125. dy = (double)(b - t);
  126. dx = (double)(r - l);
  127. ratio = dy / dx;
  128. cols = 1 + sqrt((dmax - dmin + 1.) / ratio);
  129. lines = 1 + cats_num / cols;
  130. }
  131. else if (lines > 0 && cols <= 0) {
  132. cols = 1 + cats_num / lines;
  133. }
  134. else if (cols > 0 && lines <= 0) {
  135. lines = 1 + cats_num / cols;
  136. }
  137. /* otherwise, accept without complaint what the user requests
  138. * It is possible that the number of lines and cols is not
  139. * sufficient for the number of categories.
  140. */
  141. dots_per_line = (b - t) / lines;
  142. dots_per_col = (r - l) / cols;
  143. x_box[0] = 0; y_box[0] = 0;
  144. x_box[1] = 0; y_box[1] = (6 - dots_per_line);
  145. x_box[2] = (dots_per_col - 6); y_box[2] = 0;
  146. x_box[3] = 0; y_box[3] = (dots_per_line - 6);
  147. x_box[4] = (6 - dots_per_col); y_box[4] = 0;
  148. black = D_translate_color("black");
  149. Rast_set_c_null_value(&atcat, 1);
  150. if (!fp) {
  151. for (atcol = 0; atcol < cols; atcol++) {
  152. cur_dot_row = t;
  153. cur_dot_col = l + atcol * dots_per_col;
  154. count = 0;
  155. for (atline = 0; atline < lines; atline++) {
  156. cur_dot_row += dots_per_line;
  157. /* Draw outer border box */
  158. D_use_color(color);
  159. D_begin();
  160. D_move_abs(cur_dot_col + 2, (cur_dot_row - 1));
  161. D_cont_rel(0, (2 - dots_per_line));
  162. D_cont_rel((dots_per_col - 2), 0);
  163. D_cont_rel(0, (dots_per_line - 2));
  164. D_cont_rel((2 - dots_per_col), 0);
  165. D_end();
  166. D_stroke();
  167. /* Draw black box */
  168. D_use_color(black);
  169. D_begin();
  170. D_move_abs(cur_dot_col + 3, (cur_dot_row - 2));
  171. D_cont_rel(0, (4 - dots_per_line));
  172. D_cont_rel((dots_per_col - 4), 0);
  173. D_cont_rel(0, (dots_per_line - 4));
  174. D_cont_rel((4 - dots_per_col), 0);
  175. D_end();
  176. D_stroke();
  177. /* Color box */
  178. D_color((CELL) atcat, &colors);
  179. D_pos_abs(cur_dot_col + 4, (cur_dot_row - 3));
  180. D_polygon_rel(x_box, y_box, 5);
  181. count++;
  182. /* first cat number is null value */
  183. if (count == 1)
  184. atcat = (int)dmin;
  185. else if (++atcat > (int)dmax)
  186. break;
  187. }
  188. if (atcat > (int)dmax)
  189. break;
  190. } /* col loop */
  191. } /* int map */
  192. else {
  193. /*** draw continuous color ramp for fp map ***/
  194. cur_dot_row = t + dots_per_line;
  195. cur_dot_col = l;
  196. /* Draw outer border box */
  197. D_use_color(color);
  198. D_begin();
  199. D_move_abs(cur_dot_col + 1, (cur_dot_row - 1));
  200. D_cont_rel(0, (2 - dots_per_line));
  201. D_cont_rel((dots_per_col - 2), 0);
  202. D_cont_rel(0, (dots_per_line - 2));
  203. D_cont_rel((2 - dots_per_col), 0);
  204. D_end();
  205. D_stroke();
  206. /* Draw black box */
  207. D_use_color(black);
  208. D_begin();
  209. D_move_abs(cur_dot_col + 2, (cur_dot_row - 2));
  210. D_cont_rel(0, (4 - dots_per_line));
  211. D_cont_rel((dots_per_col - 4), 0);
  212. D_cont_rel(0, (dots_per_line - 4));
  213. D_cont_rel((4 - dots_per_col), 0);
  214. D_end();
  215. D_stroke();
  216. /* Color ramp box */
  217. /* get separate color for each pixel */
  218. /* fisrt 5 pixels draw null color */
  219. y_box[1] = -1;
  220. y_box[3] = 1;
  221. x_box[2] = (dots_per_col - 6);
  222. x_box[4] = (6 - dots_per_col);
  223. G_debug(1, "dots_per_line: %d dmin=%.2f dmax=%.2f",
  224. dots_per_line, dmin, dmax);
  225. if (skip_null->answer)
  226. offset = 1;
  227. else
  228. offset = 4;
  229. for (r = 0; r < dots_per_line - 6; r++) {
  230. if ((r <= 4) && !skip_null->answer)
  231. Rast_set_d_null_value(&dval, 1);
  232. else
  233. dval =
  234. dmin + r*(dmax - dmin) / (dots_per_line - 6 - offset);
  235. D_d_color(dval, &colors);
  236. D_pos_abs(cur_dot_col + 3, (cur_dot_row - 3) - r);
  237. D_polygon_rel(x_box, y_box, 5);
  238. }
  239. }
  240. D_save_command(G_recreate_command());
  241. D_close_driver();
  242. exit(EXIT_SUCCESS);
  243. }