ffi-gdal 1.0.0.beta5 → 1.0.0.beta6

Sign up to get free protection for your applications and to get access to all the features.
Files changed (237) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +7 -3
  3. data/.rubocop.yml +7 -0
  4. data/.ruby-version +1 -0
  5. data/Gemfile +1 -1
  6. data/History.md +143 -1
  7. data/README.md +5 -11
  8. data/Rakefile +2 -60
  9. data/TODO.md +10 -0
  10. data/examples/geometries.rb +4 -6
  11. data/examples/gridding.rb +99 -98
  12. data/examples/ogr_layer_to_layer.rb +0 -2
  13. data/examples/raster_erasing.rb +47 -0
  14. data/examples/remove_small_polygons.rb +62 -0
  15. data/examples/testing_gdal.rb +0 -3
  16. data/examples/warping.rb +140 -0
  17. data/ffi-gdal.gemspec +5 -2
  18. data/lib/ext/error_symbols.rb +1 -1
  19. data/lib/ext/ffi_library_function_checks.rb +3 -2
  20. data/lib/ext/float_ext.rb +2 -2
  21. data/lib/ext/narray_ext.rb +1 -1
  22. data/lib/ext/numeric_as_data_type.rb +1 -1
  23. data/lib/ext/to_bool.rb +2 -2
  24. data/lib/ffi/cpl/conv.rb +1 -3
  25. data/lib/ffi/cpl/error.rb +0 -3
  26. data/lib/ffi/cpl/minixml.rb +17 -21
  27. data/lib/ffi/cpl/progress.rb +27 -0
  28. data/lib/ffi/cpl/string.rb +0 -8
  29. data/lib/ffi/cpl/vsi.rb +0 -1
  30. data/lib/ffi/cpl/xml_node.rb +0 -1
  31. data/lib/ffi/cpl.rb +15 -0
  32. data/lib/ffi/gdal/alg.rb +72 -54
  33. data/lib/ffi/gdal/gdal.rb +669 -672
  34. data/lib/ffi/gdal/grid.rb +141 -24
  35. data/lib/ffi/gdal/grid_data_metrics_options.rb +1 -1
  36. data/lib/ffi/gdal/grid_moving_average_options.rb +1 -1
  37. data/lib/ffi/gdal/matching.rb +0 -2
  38. data/lib/ffi/gdal/transformer_info.rb +1 -1
  39. data/lib/ffi/gdal/version.rb +1 -1
  40. data/lib/ffi/gdal/vrt.rb +0 -2
  41. data/lib/ffi/gdal/warp_options.rb +12 -14
  42. data/lib/ffi/gdal/warper.rb +61 -6
  43. data/lib/ffi/gdal.rb +18 -3
  44. data/lib/ffi/ogr/api.rb +10 -21
  45. data/lib/ffi/ogr/core.rb +9 -12
  46. data/lib/ffi/ogr/featurestyle.rb +0 -5
  47. data/lib/ffi/ogr/geocoding.rb +0 -1
  48. data/lib/ffi/ogr/srs_api.rb +0 -4
  49. data/lib/ffi/ogr/style_value.rb +1 -2
  50. data/lib/ffi/ogr.rb +15 -12
  51. data/lib/ffi-gdal.rb +5 -3
  52. data/lib/gdal/color_entry.rb +1 -0
  53. data/lib/gdal/color_interpretation.rb +2 -2
  54. data/lib/gdal/color_table.rb +14 -14
  55. data/lib/gdal/color_table_mixins/extensions.rb +4 -4
  56. data/lib/gdal/cpl_error_handler.rb +12 -14
  57. data/lib/gdal/data_type.rb +13 -12
  58. data/lib/gdal/dataset.rb +170 -94
  59. data/lib/gdal/dataset_mixins/algorithm_methods.rb +47 -21
  60. data/lib/gdal/dataset_mixins/extensions.rb +32 -61
  61. data/lib/gdal/dataset_mixins/matching.rb +0 -2
  62. data/lib/gdal/dataset_mixins/warp_methods.rb +42 -0
  63. data/lib/gdal/driver.rb +62 -47
  64. data/lib/gdal/driver_mixins/extensions.rb +2 -7
  65. data/lib/gdal/environment_methods.rb +13 -10
  66. data/lib/gdal/exceptions.rb +24 -2
  67. data/lib/gdal/geo_transform.rb +10 -16
  68. data/lib/gdal/geo_transform_mixins/extensions.rb +58 -3
  69. data/lib/gdal/grid.rb +62 -109
  70. data/lib/gdal/{grid_types → grid_algorithms}/data_metrics_base.rb +1 -3
  71. data/lib/gdal/{grid_types → grid_algorithms}/inverse_distance_to_a_power.rb +2 -4
  72. data/lib/gdal/{grid_types → grid_algorithms}/metric_average_distance.rb +2 -2
  73. data/lib/gdal/{grid_types → grid_algorithms}/metric_average_distance_pts.rb +2 -2
  74. data/lib/gdal/{grid_types → grid_algorithms}/metric_count.rb +2 -2
  75. data/lib/gdal/{grid_types → grid_algorithms}/metric_maximum.rb +2 -2
  76. data/lib/gdal/{grid_types → grid_algorithms}/metric_minimum.rb +2 -2
  77. data/lib/gdal/{grid_types → grid_algorithms}/metric_range.rb +2 -2
  78. data/lib/gdal/{grid_types → grid_algorithms}/moving_average.rb +2 -4
  79. data/lib/gdal/{grid_types → grid_algorithms}/nearest_neighbor.rb +2 -4
  80. data/lib/gdal/grid_algorithms.rb +22 -0
  81. data/lib/gdal/gridder/point_extracting.rb +89 -0
  82. data/lib/gdal/gridder.rb +294 -0
  83. data/lib/gdal/gridder_options.rb +273 -0
  84. data/lib/gdal/internal_helpers.rb +132 -23
  85. data/lib/gdal/major_object.rb +13 -10
  86. data/lib/gdal/merger.rb +130 -0
  87. data/lib/gdal/options.rb +3 -2
  88. data/lib/gdal/raster_attribute_table.rb +74 -51
  89. data/lib/gdal/raster_attribute_table_mixins/extensions.rb +21 -3
  90. data/lib/gdal/raster_band.rb +139 -167
  91. data/lib/gdal/raster_band_classifier.rb +19 -18
  92. data/lib/gdal/raster_band_mixins/algorithm_extensions.rb +107 -0
  93. data/lib/gdal/raster_band_mixins/algorithm_methods.rb +79 -40
  94. data/lib/gdal/raster_band_mixins/coloring_extensions.rb +84 -0
  95. data/lib/gdal/raster_band_mixins/extensions.rb +34 -169
  96. data/lib/gdal/raster_band_mixins/io_extensions.rb +180 -0
  97. data/lib/gdal/rpc_info.rb +1 -2
  98. data/lib/gdal/transformer.rb +1 -6
  99. data/lib/gdal/transformers/approximate_transformer.rb +0 -4
  100. data/lib/gdal/transformers/base_general_image_projection_transformer.rb +0 -6
  101. data/lib/gdal/transformers/gcp_transformer.rb +2 -6
  102. data/lib/gdal/transformers/general_image_projection_transformer.rb +8 -7
  103. data/lib/gdal/transformers/general_image_projection_transformer2.rb +1 -1
  104. data/lib/gdal/transformers/geolocation_transformer.rb +0 -4
  105. data/lib/gdal/transformers/reprojection_transformer.rb +0 -8
  106. data/lib/gdal/transformers/rpc_transformer.rb +0 -4
  107. data/lib/gdal/transformers/tps_transformer.rb +1 -3
  108. data/lib/gdal/version_info.rb +7 -8
  109. data/lib/gdal/virtual_dataset.rb +2 -4
  110. data/lib/gdal/warp_operation.rb +17 -14
  111. data/lib/gdal/warp_options.rb +132 -0
  112. data/lib/gdal.rb +41 -2
  113. data/lib/ogr/coordinate_transformation.rb +79 -32
  114. data/lib/ogr/data_source.rb +17 -14
  115. data/lib/ogr/data_source_extensions.rb +1 -5
  116. data/lib/ogr/driver.rb +11 -14
  117. data/lib/ogr/envelope.rb +1 -1
  118. data/lib/ogr/envelope_extensions.rb +23 -6
  119. data/lib/ogr/error_handling.rb +3 -3
  120. data/lib/ogr/exceptions.rb +6 -0
  121. data/lib/ogr/feature.rb +25 -38
  122. data/lib/ogr/feature_definition.rb +6 -8
  123. data/lib/ogr/feature_definition_extensions.rb +2 -6
  124. data/lib/ogr/feature_extensions.rb +71 -41
  125. data/lib/ogr/field.rb +16 -15
  126. data/lib/ogr/field_definition.rb +4 -4
  127. data/lib/ogr/geocoder.rb +5 -5
  128. data/lib/ogr/geometries/geometry_collection.rb +4 -1
  129. data/lib/ogr/geometries/geometry_collection_25d.rb +12 -0
  130. data/lib/ogr/geometries/line_string.rb +30 -8
  131. data/lib/ogr/geometries/line_string_25d.rb +21 -0
  132. data/lib/ogr/geometries/linear_ring.rb +10 -1
  133. data/lib/ogr/geometries/multi_line_string.rb +2 -1
  134. data/lib/ogr/geometries/multi_line_string_25d.rb +13 -0
  135. data/lib/ogr/geometries/multi_point.rb +2 -1
  136. data/lib/ogr/geometries/multi_point_25d.rb +14 -0
  137. data/lib/ogr/geometries/multi_polygon.rb +3 -2
  138. data/lib/ogr/geometries/multi_polygon_25d.rb +13 -0
  139. data/lib/ogr/geometries/point.rb +20 -23
  140. data/lib/ogr/geometries/point_25d.rb +48 -0
  141. data/lib/ogr/geometries/polygon.rb +4 -1
  142. data/lib/ogr/geometries/polygon_25d.rb +14 -0
  143. data/lib/ogr/geometry.rb +125 -93
  144. data/lib/ogr/geometry_field_definition.rb +7 -5
  145. data/lib/ogr/geometry_mixins/container_mixins.rb +23 -0
  146. data/lib/ogr/geometry_mixins/extensions.rb +111 -0
  147. data/lib/ogr/geometry_types/container.rb +10 -3
  148. data/lib/ogr/geometry_types/curve.rb +68 -23
  149. data/lib/ogr/geometry_types/surface.rb +0 -9
  150. data/lib/ogr/internal_helpers.rb +3 -3
  151. data/lib/ogr/layer.rb +4 -5
  152. data/lib/ogr/layer_mixins/extensions.rb +242 -17
  153. data/lib/ogr/layer_mixins/ogr_feature_methods.rb +11 -11
  154. data/lib/ogr/layer_mixins/ogr_field_methods.rb +6 -11
  155. data/lib/ogr/layer_mixins/ogr_layer_method_methods.rb +18 -18
  156. data/lib/ogr/layer_mixins/ogr_query_filter_methods.rb +0 -2
  157. data/lib/ogr/layer_mixins/ogr_sql_methods.rb +1 -1
  158. data/lib/ogr/spatial_reference.rb +12 -37
  159. data/lib/ogr/spatial_reference_mixins/coordinate_system_getter_setters.rb +53 -55
  160. data/lib/ogr/spatial_reference_mixins/exporters.rb +18 -49
  161. data/lib/ogr/spatial_reference_mixins/parameter_getter_setters.rb +10 -29
  162. data/lib/ogr/style_table.rb +2 -2
  163. data/lib/ogr/style_table_extensions.rb +3 -1
  164. data/lib/ogr/style_tool.rb +8 -14
  165. data/lib/ogr.rb +39 -1
  166. data/spec/ffi-gdal_spec.rb +18 -1
  167. data/spec/integration/gdal/color_table_info_spec.rb +49 -33
  168. data/spec/integration/gdal/dataset_info_spec.rb +294 -45
  169. data/spec/integration/gdal/driver_info_spec.rb +139 -31
  170. data/spec/integration/gdal/geo_transform_info_spec.rb +197 -26
  171. data/spec/integration/gdal/gridder_spec.rb +329 -0
  172. data/spec/integration/gdal/raster_attribute_table_info_spec.rb +216 -11
  173. data/spec/integration/gdal/raster_band_algorithms_spec.rb +33 -0
  174. data/spec/integration/gdal/raster_band_info_spec.rb +240 -271
  175. data/spec/integration/ogr/layer_spec.rb +3 -1
  176. data/spec/spec_helper.rb +15 -6
  177. data/spec/support/images/osgeo/gdal/data/hfa/float-rle.img +0 -0
  178. data/spec/support/images/osgeo/geotiff/GeogToWGS84GeoKey/GeogToWGS84GeoKey5.lgo +31 -0
  179. data/spec/support/images/osgeo/geotiff/GeogToWGS84GeoKey/GeogToWGS84GeoKey5.tif +0 -0
  180. data/spec/support/images/osgeo/geotiff/GeogToWGS84GeoKey/GeogToWGS84GeoKey5.tif.msk +0 -0
  181. data/spec/support/images/osgeo/geotiff/GeogToWGS84GeoKey/GeogToWGS84GeoKey5.txt +10 -0
  182. data/spec/support/images/osgeo/geotiff/gdal_eg/cea.tif +0 -0
  183. data/spec/support/images/osgeo/geotiff/gdal_eg/cea.txt +84 -0
  184. data/spec/support/images/osgeo/geotiff/zi_imaging/image0.lgo +45 -0
  185. data/spec/support/images/osgeo/geotiff/zi_imaging/image0.tif +0 -0
  186. data/spec/support/integration_help.rb +32 -2
  187. data/spec/support/shared_examples/gdal/major_object_examples.rb +0 -6
  188. data/spec/support/shared_examples/ogr/a_geometry.rb +1 -1
  189. data/spec/unit/ffi/gdal_spec.rb +1 -1
  190. data/spec/unit/gdal/color_entry_spec.rb +1 -0
  191. data/spec/unit/gdal/color_interpretation_spec.rb +1 -0
  192. data/spec/unit/gdal/dataset_spec.rb +53 -2
  193. data/spec/unit/gdal/geo_transform_mixins/extensions_spec.rb +67 -0
  194. data/spec/unit/gdal/geo_transform_spec.rb +1 -1
  195. data/spec/unit/gdal/grid_spec.rb +83 -0
  196. data/spec/unit/gdal/gridder/point_extracting_spec.rb +99 -0
  197. data/spec/unit/gdal/gridder_options_spec.rb +183 -0
  198. data/spec/unit/gdal/gridder_spec.rb +140 -0
  199. data/spec/unit/gdal/internal_helpers_spec.rb +166 -2
  200. data/spec/unit/gdal/major_object_spec.rb +2 -0
  201. data/spec/unit/gdal/options_spec.rb +1 -0
  202. data/spec/unit/gdal/raster_band_classifier_spec.rb +70 -12
  203. data/spec/unit/gdal/raster_band_mixins/extensions_spec.rb +71 -0
  204. data/spec/unit/gdal/raster_band_mixins/io_extensions_spec.rb +133 -0
  205. data/spec/unit/gdal/raster_band_spec.rb +1 -0
  206. data/spec/unit/gdal/rpc_info_spec.rb +1 -0
  207. data/spec/unit/gdal/version_info_spec.rb +2 -0
  208. data/spec/unit/gdal/warp_operation_spec.rb +1 -0
  209. data/spec/unit/ogr/coordinate_transformation_spec.rb +102 -0
  210. data/spec/unit/ogr/data_source_spec.rb +12 -0
  211. data/spec/unit/ogr/feature_extensions_spec.rb +88 -0
  212. data/spec/unit/ogr/feature_spec.rb +30 -46
  213. data/spec/unit/ogr/geometries/geometry_collection_25d_spec.rb +23 -0
  214. data/spec/unit/ogr/geometries/geometry_collection_spec.rb +3 -3
  215. data/spec/unit/ogr/geometries/line_string_25d_spec.rb +23 -0
  216. data/spec/unit/ogr/geometries/line_string_spec.rb +2 -2
  217. data/spec/unit/ogr/geometries/linear_ring_spec.rb +2 -2
  218. data/spec/unit/ogr/geometries/multi_line_string_25d_spec.rb +23 -0
  219. data/spec/unit/ogr/geometries/multi_point_25d_spec.rb +23 -0
  220. data/spec/unit/ogr/geometries/multi_polygon_25d_spec.rb +23 -0
  221. data/spec/unit/ogr/geometries/point_25d_spec.rb +23 -0
  222. data/spec/unit/ogr/geometries/point_spec.rb +14 -24
  223. data/spec/unit/ogr/geometries/polygon_25d_spec.rb +23 -0
  224. data/spec/unit/ogr/geometries/polygon_spec.rb +1 -1
  225. data/spec/unit/ogr/geometry_field_definition_spec.rb +1 -1
  226. data/spec/unit/ogr/geometry_spec.rb +196 -30
  227. data/spec/unit/ogr/internal_helpers_spec.rb +20 -9
  228. data/spec/unit/ogr/layer_mixins/ogr_feature_methods_spec.rb +14 -6
  229. data/spec/unit/ogr/spatial_reference_mixins/exporters_spec.rb +9 -1
  230. data/spec/unit/ogr/spatial_reference_mixins/parameter_getter_setters_spec.rb +2 -1
  231. data/spec/unit/ogr/style_table_spec.rb +1 -1
  232. data/tmp/.keep +0 -0
  233. metadata +121 -19
  234. data/examples/points.txt +0 -127
  235. data/lib/gdal/grid_types.rb +0 -22
  236. data/lib/ogr/geometries/point_extensions.rb +0 -32
  237. data/lib/ogr/geometry_extensions.rb +0 -59
@@ -0,0 +1,329 @@
1
+ require 'spec_helper'
2
+ require 'gdal/gridder'
3
+ require 'ogr/data_source'
4
+
5
+ RSpec.describe 'GDAL::Gridder', type: :integration do
6
+ let(:shapefile_path) { File.expand_path('../../../spec/support/shapefiles/states_21basic', __dir__) }
7
+ let(:source_data_source) { OGR::DataSource.open(shapefile_path, 'r') }
8
+ let(:source_layer) { source_data_source.layer(0) }
9
+ let(:dataset) { GDAL::Dataset.open(output_file_name, 'w', true) }
10
+
11
+ after do
12
+ source_data_source.close if source_data_source.c_pointer
13
+ dataset.close if File.exist?(output_file_name)
14
+
15
+ Dir.glob("#{output_file_name}*").each do |file|
16
+ File.unlink(file) if File.exist?(file)
17
+ end
18
+ end
19
+
20
+ describe 'Inverse Distance to a Power' do
21
+ let(:gridder_options) do
22
+ gridder_options = GDAL::GridderOptions.new(:inverse_distance_to_a_power)
23
+
24
+ gridder_options.algorithm_options[:angle] = 10
25
+ gridder_options.algorithm_options[:max_points] = 5
26
+ gridder_options.algorithm_options[:min_points] = 1
27
+ gridder_options.algorithm_options[:no_data_value] = -9999
28
+ gridder_options.algorithm_options[:power] = 2
29
+ gridder_options.algorithm_options[:radius1] = 20
30
+ gridder_options.algorithm_options[:radius2] = 15
31
+ gridder_options.algorithm_options[:smoothing] = 5
32
+
33
+ gridder_options.input_field_name = 'STATE_FIPS'
34
+ gridder_options.output_size = { width: 300, height: 200 }
35
+ gridder_options.output_data_type = :GDT_UInt16
36
+
37
+ gridder_options
38
+ end
39
+
40
+ let(:output_file_name) { File.expand_path('../../../tmp/gridder_spec-idtap.tif', __dir__) }
41
+
42
+ it 'results in a raster with relevant data to the grid algorithm' do
43
+ gridder = GDAL::Gridder.new(source_layer, output_file_name, gridder_options)
44
+ gridder.grid!
45
+
46
+ expect(dataset.spatial_reference.authority_code.to_i).to eq 4269
47
+ expect(dataset.raster_band(1)).to be_a GDAL::RasterBand
48
+ expect(dataset.raster_band(1).no_data_value[:value]).to eq(-9999)
49
+ expect(dataset.raster_band(1).x_size).to eq 300
50
+ expect(dataset.raster_band(1).y_size).to eq 200
51
+ expect(dataset.raster_band(1).data_type).to eq :GDT_UInt16
52
+
53
+ stats = dataset.raster_band(1).statistics
54
+ expect(stats[:minimum]).to eq 0.0
55
+ expect(stats[:maximum]).to eq 55.0
56
+ expect(stats[:mean]).to be_within(0.000000000001).of 25.549166666667
57
+ expect(stats[:standard_deviation]).to be_within(0.000000000001).of 19.127859747926
58
+ end
59
+ end
60
+
61
+ describe 'Nearest Neighbor' do
62
+ let(:gridder_options) do
63
+ gridder_options = GDAL::GridderOptions.new(:nearest_neighbor)
64
+
65
+ gridder_options.algorithm_options[:angle] = 3
66
+ gridder_options.algorithm_options[:no_data_value] = -9999
67
+ gridder_options.algorithm_options[:radius1] = 2
68
+ gridder_options.algorithm_options[:radius2] = 1
69
+
70
+ gridder_options.input_field_name = 'STATE_FIPS'
71
+ gridder_options.output_size = { width: 10, height: 15 }
72
+ gridder_options.output_data_type = :GDT_Int16
73
+
74
+ gridder_options
75
+ end
76
+
77
+ let(:output_file_name) { File.expand_path('../../../tmp/gridder_spec-nearest_neighbor.tif', __dir__) }
78
+
79
+ it 'results in a raster with relevant data to the grid algorithm' do
80
+ gridder = GDAL::Gridder.new(source_layer, output_file_name, gridder_options)
81
+ gridder.grid!
82
+
83
+ expect(dataset.spatial_reference.authority_code.to_i).to eq 4269
84
+ expect(dataset.raster_band(1)).to be_a GDAL::RasterBand
85
+ expect(dataset.raster_band(1).no_data_value[:value]).to eq(-9999)
86
+ expect(dataset.raster_band(1).x_size).to eq 10
87
+ expect(dataset.raster_band(1).y_size).to eq 15
88
+ expect(dataset.raster_band(1).data_type).to eq :GDT_Int16
89
+
90
+ stats = dataset.raster_band(1).statistics
91
+ expect(stats[:minimum]).to eq 2.0
92
+ expect(stats[:maximum]).to eq 56.0
93
+ expect(stats[:mean]).to be_within(0.00000000001).of 16.972222222222
94
+ expect(stats[:standard_deviation]).to be_within(0.00000000001).of 16.308631169331
95
+ end
96
+ end
97
+
98
+ describe 'Metric Average Distance' do
99
+ let(:gridder_options) do
100
+ gridder_options = GDAL::GridderOptions.new(:metric_average_distance)
101
+
102
+ gridder_options.algorithm_options[:angle] = 30
103
+ gridder_options.algorithm_options[:no_data_value] = -9999
104
+ gridder_options.algorithm_options[:radius1] = 20
105
+ gridder_options.algorithm_options[:radius2] = 15
106
+ gridder_options.algorithm_options[:min_points] = 1000
107
+
108
+ gridder_options.input_field_name = 'STATE_FIPS'
109
+ gridder_options.output_size = { width: 100, height: 150 }
110
+ gridder_options.output_data_type = :GDT_UInt32
111
+
112
+ gridder_options
113
+ end
114
+
115
+ let(:output_file_name) { File.expand_path('../../../tmp/gridder_spec-metric_average_distance.tif', __dir__) }
116
+
117
+ it 'results in a raster with relevant data to the grid algorithm' do
118
+ gridder = GDAL::Gridder.new(source_layer, output_file_name, gridder_options)
119
+ gridder.grid!
120
+
121
+ expect(dataset.spatial_reference.authority_code.to_i).to eq 4269
122
+ expect(dataset.raster_band(1)).to be_a GDAL::RasterBand
123
+ expect(dataset.raster_band(1).no_data_value[:value]).to eq(-9999)
124
+ expect(dataset.raster_band(1).x_size).to eq 100
125
+ expect(dataset.raster_band(1).y_size).to eq 150
126
+ expect(dataset.raster_band(1).data_type).to eq :GDT_UInt32
127
+
128
+ stats = dataset.raster_band(1).statistics
129
+ expect(stats[:minimum]).to eq 0.0
130
+ expect(stats[:maximum]).to eq 17.0
131
+ expect(stats[:mean]).to be_within(0.000000000001).of 6.211
132
+ expect(stats[:standard_deviation]).to be_within(0.000000000001).of 5.9461944973235
133
+ end
134
+ end
135
+
136
+ describe 'Metric Average Distance Between Points' do
137
+ let(:gridder_options) do
138
+ gridder_options = GDAL::GridderOptions.new(:metric_average_distance_pts)
139
+
140
+ gridder_options.algorithm_options[:angle] = 0.1
141
+ gridder_options.algorithm_options[:no_data_value] = -9999
142
+ gridder_options.algorithm_options[:radius1] = 0.2
143
+ gridder_options.algorithm_options[:radius2] = 0.3
144
+ gridder_options.algorithm_options[:min_points] = 1
145
+
146
+ gridder_options.input_field_name = 'STATE_FIPS'
147
+ gridder_options.output_size = { width: 50, height: 250 }
148
+ gridder_options.output_data_type = :GDT_Float32
149
+
150
+ gridder_options
151
+ end
152
+
153
+ let(:output_file_name) { File.expand_path('../../../tmp/gridder_spec-metric_average_distance_pts.tif', __dir__) }
154
+
155
+ it 'results in a raster with relevant data to the grid algorithm' do
156
+ gridder = GDAL::Gridder.new(source_layer, output_file_name, gridder_options)
157
+ gridder.grid!
158
+
159
+ expect(dataset.spatial_reference.authority_code.to_i).to eq 4269
160
+ expect(dataset.raster_band(1)).to be_a GDAL::RasterBand
161
+ expect(dataset.raster_band(1).no_data_value[:value]).to eq(-9999)
162
+ expect(dataset.raster_band(1).x_size).to eq 50
163
+ expect(dataset.raster_band(1).y_size).to eq 250
164
+ expect(dataset.raster_band(1).data_type).to eq :GDT_Float32
165
+
166
+ stats = dataset.raster_band(1).statistics
167
+ expect(stats[:minimum]).to eq 0.0
168
+ expect(stats[:maximum]).to be_within(0.000000000001).of 0.43194779753685
169
+ expect(stats[:mean]).to be_within(0.000000000001).of 0.11661225064791
170
+ expect(stats[:standard_deviation]).to be_within(0.000000000001).of 0.081518691345895
171
+ end
172
+ end
173
+
174
+ describe 'Metric Count' do
175
+ let(:gridder_options) do
176
+ gridder_options = GDAL::GridderOptions.new(:metric_count)
177
+
178
+ gridder_options.algorithm_options[:angle] = 0.5
179
+ gridder_options.algorithm_options[:no_data_value] = -9999
180
+ gridder_options.algorithm_options[:radius1] = 0.1
181
+ gridder_options.algorithm_options[:radius2] = 0.2
182
+ gridder_options.algorithm_options[:min_points] = 1
183
+
184
+ gridder_options.input_field_name = 'STATE_FIPS'
185
+ gridder_options.output_size = { width: 50, height: 50 }
186
+ gridder_options.output_data_type = :GDT_Int32
187
+
188
+ gridder_options
189
+ end
190
+
191
+ let(:output_file_name) { File.expand_path('../../../tmp/gridder_spec-metric_count.tif', __dir__) }
192
+
193
+ it 'results in a raster with relevant data to the grid algorithm' do
194
+ gridder = GDAL::Gridder.new(source_layer, output_file_name, gridder_options)
195
+ gridder.grid!
196
+
197
+ expect(dataset.spatial_reference.authority_code.to_i).to eq 4269
198
+ expect(dataset.raster_band(1)).to be_a GDAL::RasterBand
199
+ expect(dataset.raster_band(1).no_data_value[:value]).to eq(-9999)
200
+ expect(dataset.raster_band(1).x_size).to eq 50
201
+ expect(dataset.raster_band(1).y_size).to eq 50
202
+ expect(dataset.raster_band(1).data_type).to eq :GDT_Int32
203
+
204
+ stats = dataset.raster_band(1).statistics
205
+ expect(stats[:minimum]).to eq 1.0
206
+ expect(stats[:maximum]).to eq 18.0
207
+ expect(stats[:mean]).to be_within(0.000000000001).of 3.9318181818182
208
+ expect(stats[:standard_deviation]).to be_within(0.000000000001).of 3.7135974182892
209
+ end
210
+ end
211
+
212
+ describe 'Metric Maximum' do
213
+ let(:gridder_options) do
214
+ gridder_options = GDAL::GridderOptions.new(:metric_maximum)
215
+
216
+ gridder_options.algorithm_options[:angle] = 30
217
+ gridder_options.algorithm_options[:no_data_value] = -9999
218
+ gridder_options.algorithm_options[:radius1] = 90
219
+ gridder_options.algorithm_options[:radius2] = 0.1
220
+ gridder_options.algorithm_options[:min_points] = 1
221
+
222
+ gridder_options.input_field_name = 'STATE_FIPS'
223
+ gridder_options.output_size = { width: 50, height: 50 }
224
+ gridder_options.output_data_type = :GDT_Byte
225
+
226
+ gridder_options
227
+ end
228
+
229
+ let(:output_file_name) { File.expand_path('../../../tmp/gridder_spec-metric_maximum.tif', __dir__) }
230
+
231
+ it 'results in a raster with relevant data to the grid algorithm' do
232
+ skip 'AGDEV-13650 figure out why this test causes a crash'
233
+ gridder = GDAL::Gridder.new(source_layer, output_file_name, gridder_options)
234
+ gridder.grid!
235
+
236
+ expect(dataset.spatial_reference.authority_code.to_i).to eq 4269
237
+ expect(dataset.raster_band(1)).to be_a GDAL::RasterBand
238
+ expect(dataset.raster_band(1).no_data_value[:value]).to eq(-9999)
239
+ expect(dataset.raster_band(1).x_size).to eq 50
240
+ expect(dataset.raster_band(1).y_size).to eq 50
241
+ expect(dataset.raster_band(1).data_type).to eq :GDT_Byte
242
+
243
+ stats = dataset.raster_band(1).statistics
244
+ expect(stats[:minimum]).to eq 0.0
245
+ expect(stats[:maximum]).to eq 56.0
246
+ expect(stats[:mean]).to be_within(0.000000000001).of 26.3916
247
+ expect(stats[:standard_deviation]).to be_within(0.000000000001).of 24.779859754244
248
+ end
249
+ end
250
+
251
+ describe 'Metric Minimum' do
252
+ let(:gridder_options) do
253
+ gridder_options = GDAL::GridderOptions.new(:metric_minimum)
254
+
255
+ gridder_options.algorithm_options[:angle] = 30
256
+ gridder_options.algorithm_options[:no_data_value] = -9999
257
+ gridder_options.algorithm_options[:radius1] = 90
258
+ gridder_options.algorithm_options[:radius2] = 0.1
259
+ gridder_options.algorithm_options[:min_points] = 1
260
+
261
+ gridder_options.input_field_name = 'STATE_FIPS'
262
+ gridder_options.output_size = { width: 50, height: 50 }
263
+ gridder_options.output_data_type = :GDT_CInt16
264
+
265
+ gridder_options
266
+ end
267
+
268
+ let(:output_file_name) { File.expand_path('../../../tmp/gridder_spec-metric_minimum.tif', __dir__) }
269
+
270
+ it 'results in a raster with relevant data to the grid algorithm' do
271
+ skip 'AGDEV-13650 figure out why this test causes a crash'
272
+ gridder = GDAL::Gridder.new(source_layer, output_file_name, gridder_options)
273
+ gridder.grid!
274
+
275
+ expect(dataset.spatial_reference.authority_code.to_i).to eq 4269
276
+ expect(dataset.raster_band(1)).to be_a GDAL::RasterBand
277
+ expect(dataset.raster_band(1).no_data_value[:value]).to eq(-9999)
278
+ expect(dataset.raster_band(1).x_size).to eq 50
279
+ expect(dataset.raster_band(1).y_size).to eq 50
280
+ expect(dataset.raster_band(1).data_type).to eq :GDT_CInt16
281
+
282
+ stats = dataset.raster_band(1).statistics
283
+ expect(stats[:minimum]).to eq 1.0
284
+ expect(stats[:maximum]).to eq 53.0
285
+ expect(stats[:mean]).to be_within(0.000000000001).of 9.1150793650794
286
+ expect(stats[:standard_deviation]).to be_within(0.000000000001).of 12.575393694871
287
+ end
288
+ end
289
+
290
+ # TODO: This test seems particularly prone to ruby malloc errors.
291
+ describe 'Metric Range' do
292
+ let(:gridder_options) do
293
+ gridder_options = GDAL::GridderOptions.new(:metric_range)
294
+
295
+ gridder_options.algorithm_options[:angle] = 10
296
+ gridder_options.algorithm_options[:no_data_value] = -9999
297
+ gridder_options.algorithm_options[:radius1] = 40
298
+ gridder_options.algorithm_options[:radius2] = 10
299
+ gridder_options.algorithm_options[:min_points] = 1
300
+
301
+ gridder_options.input_field_name = 'STATE_FIPS'
302
+ gridder_options.output_size = { width: 50, height: 50 }
303
+ gridder_options.output_data_type = :GDT_CFloat64
304
+
305
+ gridder_options
306
+ end
307
+
308
+ let(:output_file_name) { File.expand_path('../../../tmp/gridder_spec-metric_range.tif', __dir__) }
309
+
310
+ it 'results in a raster with relevant data to the grid algorithm' do
311
+ skip 'AGDEV-13650 figure out why this test causes a crash'
312
+ gridder = GDAL::Gridder.new(source_layer, output_file_name, gridder_options)
313
+ gridder.grid!
314
+
315
+ expect(dataset.spatial_reference.authority_code.to_i).to eq 4269
316
+ expect(dataset.raster_band(1)).to be_a GDAL::RasterBand
317
+ expect(dataset.raster_band(1).no_data_value[:value]).to eq(-9999)
318
+ expect(dataset.raster_band(1).x_size).to eq 50
319
+ expect(dataset.raster_band(1).y_size).to eq 50
320
+ expect(dataset.raster_band(1).data_type).to eq :GDT_CFloat64
321
+
322
+ stats = dataset.raster_band(1).statistics
323
+ expect(stats[:minimum]).to eq 0.0
324
+ expect(stats[:maximum]).to eq 55.0
325
+ expect(stats[:mean]).to be_within(0.000000000001).of 28.216176470588234
326
+ expect(stats[:standard_deviation]).to be_within(0.000000000001).of 24.681864682477947
327
+ end
328
+ end
329
+ end
@@ -1,22 +1,227 @@
1
1
  require 'spec_helper'
2
- require 'support/integration_help'
3
2
  require 'ffi-gdal'
3
+ require 'gdal'
4
4
 
5
- TIF_FILES.each do |file|
6
- dataset = GDAL::Dataset.open(file, 'r')
5
+ RSpec.describe 'Raster Attribute Table Info', type: :integration do
6
+ let(:file) { make_temp_test_file(original_source_tiff) }
7
7
 
8
- RSpec.describe 'Raster Band Info' do
9
- after :all do
10
- dataset.close
8
+ let(:original_source_tiff) do
9
+ path = '../../../spec/support/images/osgeo/gdal/data/hfa/float-rle.img'
10
+ File.expand_path(path, __dir__)
11
+ end
12
+
13
+ let(:dataset) { GDAL::Dataset.open(file, 'r') }
14
+ after { dataset.close }
15
+
16
+ subject do
17
+ band = dataset.raster_band(1)
18
+ band.default_raster_attribute_table
19
+ end
20
+
21
+ describe '#changes_written_to_file?' do
22
+ context 'no changes to file' do
23
+ it 'is true' do
24
+ expect(subject.changes_written_to_file?).to eq true
25
+ end
26
+ end
27
+ end
28
+
29
+ describe '#column_count' do
30
+ it 'retrieves the column count' do
31
+ expect(subject.column_count).to eq 1
32
+ end
33
+ end
34
+
35
+ describe '#column_name' do
36
+ it 'retrieves the column name' do
37
+ expect(subject.column_name(0)).to eq 'Histogram'
38
+ end
39
+ end
40
+
41
+ describe '#column_usage' do
42
+ it 'retrieves the column usage' do
43
+ expect(subject.column_usage(0)).to eq :GFU_PixelCount
44
+ end
45
+ end
46
+
47
+ describe '#column_type' do
48
+ context 'column number exists' do
49
+ it 'retrieves the column type' do
50
+ expect(subject.column_type(0)).to eq :GFT_Real
51
+ end
52
+ end
53
+
54
+ context 'column number does not exist' do
55
+ it 'returns :GFT_Integer' do
56
+ expect(subject.column_type(110)).to eq :GFT_Integer
57
+ end
58
+ end
59
+ end
60
+
61
+ describe '#column_of_usage' do
62
+ context 'column with usage type exists' do
63
+ it 'retrieves the index of column' do
64
+ expect(subject.column_of_usage(:GFU_PixelCount)).to eq 0
65
+ end
66
+ end
67
+
68
+ context 'column with usage type does not exist' do
69
+ it 'returns nil' do
70
+ expect(subject.column_of_usage(:GFU_Name)).to be_nil
71
+ end
72
+ end
73
+
74
+ context 'column with invalid usage type' do
75
+ it 'returns nil' do
76
+ expect { subject.column_of_usage(:GFU_Meow) }.to raise_exception ArgumentError
77
+ end
78
+ end
79
+ end
80
+
81
+ describe '#create_column' do
82
+ context 'valid params, dataset not opened in write mode' do
83
+ it 'raises a GDAL::NoWriteAccess' do
84
+ expect { subject.create_column('things', :GFT_String, :GFU_Name) }.
85
+ to raise_exception GDAL::NoWriteAccess
86
+ end
87
+ end
88
+
89
+ context 'valid params' do
90
+ let(:dataset) { GDAL::Dataset.open(file, 'w') }
91
+
92
+ it 'adds the column' do
93
+ subject.create_column('things', :GFT_Integer, :GFU_Red)
94
+ expect(subject.column_name(1)).to eq 'Red'
95
+ expect(subject.column_usage(1)).to eq :GFU_Red
96
+ expect(subject.column_type(1)).to eq :GFT_Integer
97
+ end
98
+ end
99
+ end
100
+
101
+ describe '#row_count' do
102
+ it 'returns the number of rows' do
103
+ expect(subject.row_count).to eq 256
104
+ end
105
+ end
106
+
107
+ describe '#row_count=' do
108
+ context 'dataset not opened in write mode' do
109
+ it 'raises a GDAL::NoWriteAccess' do
110
+ expect { subject.row_count = 1 }.to raise_exception GDAL::NoWriteAccess
111
+ end
11
112
  end
12
113
 
13
- subject do
14
- band = dataset.raster_band(1)
15
- band.default_raster_attribute_table
114
+ context 'dataset opened in write mode' do
115
+ let(:dataset) { GDAL::Dataset.open(file, 'w') }
116
+
117
+ it 'sets the number of rows' do
118
+ subject.row_count = 2
119
+ expect(subject.row_count).to eq 2
120
+ end
121
+ end
122
+ end
123
+
124
+ describe '#row_of_value' do
125
+ context 'a row exists for the given pixel value' do
126
+ it 'returns the row index' do
127
+ expect(subject.row_of_value(58_595)).to eq 253
128
+ end
129
+ end
130
+
131
+ context 'a row does not exist for the given pixel value' do
132
+ it 'returns nil' do
133
+ expect(subject.row_of_value(123_456)).to eq nil
134
+ end
135
+ end
136
+ end
137
+
138
+ describe '#set_value_as_string' do
139
+ context 'dataset not opened in write mode' do
140
+ it 'raises a GDAL::NoWriteAccess' do
141
+ expect { subject.set_value_as_string(0, 0, 'test') }.to raise_exception GDAL::NoWriteAccess
142
+ end
143
+ end
144
+
145
+ context 'column is a double' do
146
+ let(:dataset) { GDAL::Dataset.open(file, 'w') }
147
+
148
+ it 'sets the value' do
149
+ subject.set_value_as_string(0, 0, 'test')
150
+ expect(subject.value_as_string(0, 0)).to eq '0'
151
+ end
152
+ end
153
+ end
154
+
155
+ describe '#set_value_as_double' do
156
+ context 'dataset not opened in write mode' do
157
+ it 'raises a GDAL::NoWriteAccess' do
158
+ expect { subject.set_value_as_double(0, 0, 1.2) }.to raise_exception GDAL::NoWriteAccess
159
+ end
160
+ end
161
+
162
+ context 'column is a double' do
163
+ let(:dataset) { GDAL::Dataset.open(file, 'w') }
164
+
165
+ it 'sets the value' do
166
+ subject.set_value_as_double(0, 0, 1.2)
167
+ expect(subject.value_as_double(0, 0)).to eq 1.2
168
+ end
169
+ end
170
+ end
171
+
172
+ describe '#set_value_as_integer' do
173
+ context 'dataset not opened in write mode' do
174
+ it 'raises a GDAL::NoWriteAccess' do
175
+ expect { subject.set_value_as_integer(0, 0, 1) }.to raise_exception GDAL::NoWriteAccess
176
+ end
177
+ end
178
+
179
+ context 'column is a double' do
180
+ let(:dataset) { GDAL::Dataset.open(file, 'w') }
181
+
182
+ it 'sets the value' do
183
+ subject.set_value_as_integer(0, 0, 1)
184
+ expect(subject.value_as_integer(0, 0)).to eq 1
185
+ end
16
186
  end
187
+ end
188
+
189
+ describe '#linear_binning' do
190
+ it 'returns a Hash that contains binning info' do
191
+ expect(subject.linear_binning).to eq(row_0_minimum: 0.0, bin_size: 230.79607843137254)
192
+ end
193
+ end
194
+
195
+ describe '#set_linear_binning' do
196
+ context 'dataset not opened in write mode' do
197
+ it 'raises a GDAL::NoWriteAccess' do
198
+ expect { subject.set_linear_binning(0, 0) }.to raise_exception GDAL::NoWriteAccess
199
+ end
200
+ end
201
+
202
+ context 'valid binning params' do
203
+ let(:dataset) { GDAL::Dataset.open(file, 'w') }
204
+
205
+ it 'returns a Hash that contains binning info' do
206
+ subject.set_linear_binning(1, 20)
207
+ expect(subject.linear_binning).to eq(row_0_minimum: 1.0, bin_size: 20.0)
208
+ end
209
+ end
210
+ end
211
+
212
+ describe '#to_color_table' do
213
+ it 'returns nil' do
214
+ expect(subject.to_color_table).to be_nil
215
+ end
216
+ end
217
+
218
+ describe '#dump_readable' do
219
+ let(:output_path) { File.expand_path('tmp/raster_attribute_table_info') }
220
+ after { File.unlink(output_path) if File.exist?(output_path) }
17
221
 
18
- describe '#column_count' do
19
- pending 'Test files with RATs'
222
+ it 'writes to the file' do
223
+ subject.dump_readable(output_path)
224
+ expect(File.exist?(output_path)).to eq true
20
225
  end
21
226
  end
22
227
  end
@@ -0,0 +1,33 @@
1
+ require 'spec_helper'
2
+ require 'gdal/dataset'
3
+ require 'gdal/raster_band'
4
+
5
+ RSpec.describe GDAL::RasterBand, type: :integration do
6
+ describe '#sieve_filter!' do
7
+ let(:source_image_path) { 'spec/support/images/osgeo/geotiff/zi_imaging/image0.tif' }
8
+ let(:dest_image_path) { 'tmp/image0.tif' }
9
+
10
+ before do
11
+ FileUtils.rm(dest_image_path) if File.exist?(dest_image_path)
12
+ FileUtils.cp(source_image_path, dest_image_path)
13
+ end
14
+
15
+ it 'removes some polygons' do
16
+ dataset = GDAL::Dataset.open(dest_image_path, 'w')
17
+ band = dataset.raster_band(1)
18
+
19
+ ogr_driver = OGR::Driver.by_name('Memory')
20
+ data_source = ogr_driver.create_data_source('meow')
21
+ layer_before = data_source.create_layer('before', spatial_reference: dataset.spatial_reference)
22
+ band.polygonize(layer_before)
23
+
24
+ band.sieve_filter!(1000, 4)
25
+ layer_after = data_source.create_layer('after', spatial_reference: dataset.spatial_reference)
26
+ band.polygonize(layer_after)
27
+
28
+ expect(layer_before.feature_count).to eq 62
29
+ expect(layer_after.feature_count).to eq 15
30
+ dataset.close
31
+ end
32
+ end
33
+ end