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.
- checksums.yaml +4 -4
- data/.gitignore +7 -3
- data/.rubocop.yml +7 -0
- data/.ruby-version +1 -0
- data/Gemfile +1 -1
- data/History.md +143 -1
- data/README.md +5 -11
- data/Rakefile +2 -60
- data/TODO.md +10 -0
- data/examples/geometries.rb +4 -6
- data/examples/gridding.rb +99 -98
- data/examples/ogr_layer_to_layer.rb +0 -2
- data/examples/raster_erasing.rb +47 -0
- data/examples/remove_small_polygons.rb +62 -0
- data/examples/testing_gdal.rb +0 -3
- data/examples/warping.rb +140 -0
- data/ffi-gdal.gemspec +5 -2
- data/lib/ext/error_symbols.rb +1 -1
- data/lib/ext/ffi_library_function_checks.rb +3 -2
- data/lib/ext/float_ext.rb +2 -2
- data/lib/ext/narray_ext.rb +1 -1
- data/lib/ext/numeric_as_data_type.rb +1 -1
- data/lib/ext/to_bool.rb +2 -2
- data/lib/ffi/cpl/conv.rb +1 -3
- data/lib/ffi/cpl/error.rb +0 -3
- data/lib/ffi/cpl/minixml.rb +17 -21
- data/lib/ffi/cpl/progress.rb +27 -0
- data/lib/ffi/cpl/string.rb +0 -8
- data/lib/ffi/cpl/vsi.rb +0 -1
- data/lib/ffi/cpl/xml_node.rb +0 -1
- data/lib/ffi/cpl.rb +15 -0
- data/lib/ffi/gdal/alg.rb +72 -54
- data/lib/ffi/gdal/gdal.rb +669 -672
- data/lib/ffi/gdal/grid.rb +141 -24
- data/lib/ffi/gdal/grid_data_metrics_options.rb +1 -1
- data/lib/ffi/gdal/grid_moving_average_options.rb +1 -1
- data/lib/ffi/gdal/matching.rb +0 -2
- data/lib/ffi/gdal/transformer_info.rb +1 -1
- data/lib/ffi/gdal/version.rb +1 -1
- data/lib/ffi/gdal/vrt.rb +0 -2
- data/lib/ffi/gdal/warp_options.rb +12 -14
- data/lib/ffi/gdal/warper.rb +61 -6
- data/lib/ffi/gdal.rb +18 -3
- data/lib/ffi/ogr/api.rb +10 -21
- data/lib/ffi/ogr/core.rb +9 -12
- data/lib/ffi/ogr/featurestyle.rb +0 -5
- data/lib/ffi/ogr/geocoding.rb +0 -1
- data/lib/ffi/ogr/srs_api.rb +0 -4
- data/lib/ffi/ogr/style_value.rb +1 -2
- data/lib/ffi/ogr.rb +15 -12
- data/lib/ffi-gdal.rb +5 -3
- data/lib/gdal/color_entry.rb +1 -0
- data/lib/gdal/color_interpretation.rb +2 -2
- data/lib/gdal/color_table.rb +14 -14
- data/lib/gdal/color_table_mixins/extensions.rb +4 -4
- data/lib/gdal/cpl_error_handler.rb +12 -14
- data/lib/gdal/data_type.rb +13 -12
- data/lib/gdal/dataset.rb +170 -94
- data/lib/gdal/dataset_mixins/algorithm_methods.rb +47 -21
- data/lib/gdal/dataset_mixins/extensions.rb +32 -61
- data/lib/gdal/dataset_mixins/matching.rb +0 -2
- data/lib/gdal/dataset_mixins/warp_methods.rb +42 -0
- data/lib/gdal/driver.rb +62 -47
- data/lib/gdal/driver_mixins/extensions.rb +2 -7
- data/lib/gdal/environment_methods.rb +13 -10
- data/lib/gdal/exceptions.rb +24 -2
- data/lib/gdal/geo_transform.rb +10 -16
- data/lib/gdal/geo_transform_mixins/extensions.rb +58 -3
- data/lib/gdal/grid.rb +62 -109
- data/lib/gdal/{grid_types → grid_algorithms}/data_metrics_base.rb +1 -3
- data/lib/gdal/{grid_types → grid_algorithms}/inverse_distance_to_a_power.rb +2 -4
- data/lib/gdal/{grid_types → grid_algorithms}/metric_average_distance.rb +2 -2
- data/lib/gdal/{grid_types → grid_algorithms}/metric_average_distance_pts.rb +2 -2
- data/lib/gdal/{grid_types → grid_algorithms}/metric_count.rb +2 -2
- data/lib/gdal/{grid_types → grid_algorithms}/metric_maximum.rb +2 -2
- data/lib/gdal/{grid_types → grid_algorithms}/metric_minimum.rb +2 -2
- data/lib/gdal/{grid_types → grid_algorithms}/metric_range.rb +2 -2
- data/lib/gdal/{grid_types → grid_algorithms}/moving_average.rb +2 -4
- data/lib/gdal/{grid_types → grid_algorithms}/nearest_neighbor.rb +2 -4
- data/lib/gdal/grid_algorithms.rb +22 -0
- data/lib/gdal/gridder/point_extracting.rb +89 -0
- data/lib/gdal/gridder.rb +294 -0
- data/lib/gdal/gridder_options.rb +273 -0
- data/lib/gdal/internal_helpers.rb +132 -23
- data/lib/gdal/major_object.rb +13 -10
- data/lib/gdal/merger.rb +130 -0
- data/lib/gdal/options.rb +3 -2
- data/lib/gdal/raster_attribute_table.rb +74 -51
- data/lib/gdal/raster_attribute_table_mixins/extensions.rb +21 -3
- data/lib/gdal/raster_band.rb +139 -167
- data/lib/gdal/raster_band_classifier.rb +19 -18
- data/lib/gdal/raster_band_mixins/algorithm_extensions.rb +107 -0
- data/lib/gdal/raster_band_mixins/algorithm_methods.rb +79 -40
- data/lib/gdal/raster_band_mixins/coloring_extensions.rb +84 -0
- data/lib/gdal/raster_band_mixins/extensions.rb +34 -169
- data/lib/gdal/raster_band_mixins/io_extensions.rb +180 -0
- data/lib/gdal/rpc_info.rb +1 -2
- data/lib/gdal/transformer.rb +1 -6
- data/lib/gdal/transformers/approximate_transformer.rb +0 -4
- data/lib/gdal/transformers/base_general_image_projection_transformer.rb +0 -6
- data/lib/gdal/transformers/gcp_transformer.rb +2 -6
- data/lib/gdal/transformers/general_image_projection_transformer.rb +8 -7
- data/lib/gdal/transformers/general_image_projection_transformer2.rb +1 -1
- data/lib/gdal/transformers/geolocation_transformer.rb +0 -4
- data/lib/gdal/transformers/reprojection_transformer.rb +0 -8
- data/lib/gdal/transformers/rpc_transformer.rb +0 -4
- data/lib/gdal/transformers/tps_transformer.rb +1 -3
- data/lib/gdal/version_info.rb +7 -8
- data/lib/gdal/virtual_dataset.rb +2 -4
- data/lib/gdal/warp_operation.rb +17 -14
- data/lib/gdal/warp_options.rb +132 -0
- data/lib/gdal.rb +41 -2
- data/lib/ogr/coordinate_transformation.rb +79 -32
- data/lib/ogr/data_source.rb +17 -14
- data/lib/ogr/data_source_extensions.rb +1 -5
- data/lib/ogr/driver.rb +11 -14
- data/lib/ogr/envelope.rb +1 -1
- data/lib/ogr/envelope_extensions.rb +23 -6
- data/lib/ogr/error_handling.rb +3 -3
- data/lib/ogr/exceptions.rb +6 -0
- data/lib/ogr/feature.rb +25 -38
- data/lib/ogr/feature_definition.rb +6 -8
- data/lib/ogr/feature_definition_extensions.rb +2 -6
- data/lib/ogr/feature_extensions.rb +71 -41
- data/lib/ogr/field.rb +16 -15
- data/lib/ogr/field_definition.rb +4 -4
- data/lib/ogr/geocoder.rb +5 -5
- data/lib/ogr/geometries/geometry_collection.rb +4 -1
- data/lib/ogr/geometries/geometry_collection_25d.rb +12 -0
- data/lib/ogr/geometries/line_string.rb +30 -8
- data/lib/ogr/geometries/line_string_25d.rb +21 -0
- data/lib/ogr/geometries/linear_ring.rb +10 -1
- data/lib/ogr/geometries/multi_line_string.rb +2 -1
- data/lib/ogr/geometries/multi_line_string_25d.rb +13 -0
- data/lib/ogr/geometries/multi_point.rb +2 -1
- data/lib/ogr/geometries/multi_point_25d.rb +14 -0
- data/lib/ogr/geometries/multi_polygon.rb +3 -2
- data/lib/ogr/geometries/multi_polygon_25d.rb +13 -0
- data/lib/ogr/geometries/point.rb +20 -23
- data/lib/ogr/geometries/point_25d.rb +48 -0
- data/lib/ogr/geometries/polygon.rb +4 -1
- data/lib/ogr/geometries/polygon_25d.rb +14 -0
- data/lib/ogr/geometry.rb +125 -93
- data/lib/ogr/geometry_field_definition.rb +7 -5
- data/lib/ogr/geometry_mixins/container_mixins.rb +23 -0
- data/lib/ogr/geometry_mixins/extensions.rb +111 -0
- data/lib/ogr/geometry_types/container.rb +10 -3
- data/lib/ogr/geometry_types/curve.rb +68 -23
- data/lib/ogr/geometry_types/surface.rb +0 -9
- data/lib/ogr/internal_helpers.rb +3 -3
- data/lib/ogr/layer.rb +4 -5
- data/lib/ogr/layer_mixins/extensions.rb +242 -17
- data/lib/ogr/layer_mixins/ogr_feature_methods.rb +11 -11
- data/lib/ogr/layer_mixins/ogr_field_methods.rb +6 -11
- data/lib/ogr/layer_mixins/ogr_layer_method_methods.rb +18 -18
- data/lib/ogr/layer_mixins/ogr_query_filter_methods.rb +0 -2
- data/lib/ogr/layer_mixins/ogr_sql_methods.rb +1 -1
- data/lib/ogr/spatial_reference.rb +12 -37
- data/lib/ogr/spatial_reference_mixins/coordinate_system_getter_setters.rb +53 -55
- data/lib/ogr/spatial_reference_mixins/exporters.rb +18 -49
- data/lib/ogr/spatial_reference_mixins/parameter_getter_setters.rb +10 -29
- data/lib/ogr/style_table.rb +2 -2
- data/lib/ogr/style_table_extensions.rb +3 -1
- data/lib/ogr/style_tool.rb +8 -14
- data/lib/ogr.rb +39 -1
- data/spec/ffi-gdal_spec.rb +18 -1
- data/spec/integration/gdal/color_table_info_spec.rb +49 -33
- data/spec/integration/gdal/dataset_info_spec.rb +294 -45
- data/spec/integration/gdal/driver_info_spec.rb +139 -31
- data/spec/integration/gdal/geo_transform_info_spec.rb +197 -26
- data/spec/integration/gdal/gridder_spec.rb +329 -0
- data/spec/integration/gdal/raster_attribute_table_info_spec.rb +216 -11
- data/spec/integration/gdal/raster_band_algorithms_spec.rb +33 -0
- data/spec/integration/gdal/raster_band_info_spec.rb +240 -271
- data/spec/integration/ogr/layer_spec.rb +3 -1
- data/spec/spec_helper.rb +15 -6
- data/spec/support/images/osgeo/gdal/data/hfa/float-rle.img +0 -0
- data/spec/support/images/osgeo/geotiff/GeogToWGS84GeoKey/GeogToWGS84GeoKey5.lgo +31 -0
- data/spec/support/images/osgeo/geotiff/GeogToWGS84GeoKey/GeogToWGS84GeoKey5.tif +0 -0
- data/spec/support/images/osgeo/geotiff/GeogToWGS84GeoKey/GeogToWGS84GeoKey5.tif.msk +0 -0
- data/spec/support/images/osgeo/geotiff/GeogToWGS84GeoKey/GeogToWGS84GeoKey5.txt +10 -0
- data/spec/support/images/osgeo/geotiff/gdal_eg/cea.tif +0 -0
- data/spec/support/images/osgeo/geotiff/gdal_eg/cea.txt +84 -0
- data/spec/support/images/osgeo/geotiff/zi_imaging/image0.lgo +45 -0
- data/spec/support/images/osgeo/geotiff/zi_imaging/image0.tif +0 -0
- data/spec/support/integration_help.rb +32 -2
- data/spec/support/shared_examples/gdal/major_object_examples.rb +0 -6
- data/spec/support/shared_examples/ogr/a_geometry.rb +1 -1
- data/spec/unit/ffi/gdal_spec.rb +1 -1
- data/spec/unit/gdal/color_entry_spec.rb +1 -0
- data/spec/unit/gdal/color_interpretation_spec.rb +1 -0
- data/spec/unit/gdal/dataset_spec.rb +53 -2
- data/spec/unit/gdal/geo_transform_mixins/extensions_spec.rb +67 -0
- data/spec/unit/gdal/geo_transform_spec.rb +1 -1
- data/spec/unit/gdal/grid_spec.rb +83 -0
- data/spec/unit/gdal/gridder/point_extracting_spec.rb +99 -0
- data/spec/unit/gdal/gridder_options_spec.rb +183 -0
- data/spec/unit/gdal/gridder_spec.rb +140 -0
- data/spec/unit/gdal/internal_helpers_spec.rb +166 -2
- data/spec/unit/gdal/major_object_spec.rb +2 -0
- data/spec/unit/gdal/options_spec.rb +1 -0
- data/spec/unit/gdal/raster_band_classifier_spec.rb +70 -12
- data/spec/unit/gdal/raster_band_mixins/extensions_spec.rb +71 -0
- data/spec/unit/gdal/raster_band_mixins/io_extensions_spec.rb +133 -0
- data/spec/unit/gdal/raster_band_spec.rb +1 -0
- data/spec/unit/gdal/rpc_info_spec.rb +1 -0
- data/spec/unit/gdal/version_info_spec.rb +2 -0
- data/spec/unit/gdal/warp_operation_spec.rb +1 -0
- data/spec/unit/ogr/coordinate_transformation_spec.rb +102 -0
- data/spec/unit/ogr/data_source_spec.rb +12 -0
- data/spec/unit/ogr/feature_extensions_spec.rb +88 -0
- data/spec/unit/ogr/feature_spec.rb +30 -46
- data/spec/unit/ogr/geometries/geometry_collection_25d_spec.rb +23 -0
- data/spec/unit/ogr/geometries/geometry_collection_spec.rb +3 -3
- data/spec/unit/ogr/geometries/line_string_25d_spec.rb +23 -0
- data/spec/unit/ogr/geometries/line_string_spec.rb +2 -2
- data/spec/unit/ogr/geometries/linear_ring_spec.rb +2 -2
- data/spec/unit/ogr/geometries/multi_line_string_25d_spec.rb +23 -0
- data/spec/unit/ogr/geometries/multi_point_25d_spec.rb +23 -0
- data/spec/unit/ogr/geometries/multi_polygon_25d_spec.rb +23 -0
- data/spec/unit/ogr/geometries/point_25d_spec.rb +23 -0
- data/spec/unit/ogr/geometries/point_spec.rb +14 -24
- data/spec/unit/ogr/geometries/polygon_25d_spec.rb +23 -0
- data/spec/unit/ogr/geometries/polygon_spec.rb +1 -1
- data/spec/unit/ogr/geometry_field_definition_spec.rb +1 -1
- data/spec/unit/ogr/geometry_spec.rb +196 -30
- data/spec/unit/ogr/internal_helpers_spec.rb +20 -9
- data/spec/unit/ogr/layer_mixins/ogr_feature_methods_spec.rb +14 -6
- data/spec/unit/ogr/spatial_reference_mixins/exporters_spec.rb +9 -1
- data/spec/unit/ogr/spatial_reference_mixins/parameter_getter_setters_spec.rb +2 -1
- data/spec/unit/ogr/style_table_spec.rb +1 -1
- data/tmp/.keep +0 -0
- metadata +121 -19
- data/examples/points.txt +0 -127
- data/lib/gdal/grid_types.rb +0 -22
- data/lib/ogr/geometries/point_extensions.rb +0 -32
- data/lib/ogr/geometry_extensions.rb +0 -59
@@ -0,0 +1,183 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
require 'gdal/gridder_options'
|
3
|
+
|
4
|
+
RSpec.describe GDAL::GridderOptions do
|
5
|
+
subject(:gridder_options) { described_class.new(:metric_count) }
|
6
|
+
|
7
|
+
describe 'attributes' do
|
8
|
+
it { is_expected.to respond_to :input_clipping_geometry }
|
9
|
+
it { is_expected.to respond_to :input_clipping_geometry= }
|
10
|
+
it { is_expected.to respond_to :input_field_name }
|
11
|
+
it { is_expected.to respond_to :input_field_name= }
|
12
|
+
|
13
|
+
it { is_expected.to respond_to :progress_formatter }
|
14
|
+
it { is_expected.to respond_to :progress_formatter= }
|
15
|
+
it { is_expected.to respond_to :grid }
|
16
|
+
it { is_expected.to respond_to :algorithm_options }
|
17
|
+
|
18
|
+
it { is_expected.to respond_to :output_creation_options }
|
19
|
+
it { is_expected.to respond_to :output_creation_options= }
|
20
|
+
it { is_expected.to respond_to :output_format }
|
21
|
+
it { is_expected.to respond_to :output_format= }
|
22
|
+
it { is_expected.to respond_to :output_x_extent }
|
23
|
+
it { is_expected.to respond_to :output_x_extent= }
|
24
|
+
it { is_expected.to respond_to :output_y_extent }
|
25
|
+
it { is_expected.to respond_to :output_y_extent= }
|
26
|
+
it { is_expected.to respond_to :output_projection }
|
27
|
+
it { is_expected.to respond_to :output_projection= }
|
28
|
+
it { is_expected.to respond_to :output_size }
|
29
|
+
it { is_expected.to respond_to :output_size= }
|
30
|
+
it { is_expected.to respond_to :output_data_type }
|
31
|
+
it { is_expected.to respond_to :output_data_type= }
|
32
|
+
end
|
33
|
+
|
34
|
+
describe 'default values' do
|
35
|
+
describe '#output_data_type' do
|
36
|
+
subject { gridder_options.output_data_type }
|
37
|
+
it { is_expected.to eq :GDT_Float64 }
|
38
|
+
end
|
39
|
+
|
40
|
+
describe '#output_format' do
|
41
|
+
subject { gridder_options.output_format }
|
42
|
+
it { is_expected.to eq 'GTiff' }
|
43
|
+
end
|
44
|
+
|
45
|
+
describe '#output_size' do
|
46
|
+
subject { gridder_options.output_size }
|
47
|
+
it { is_expected.to eq(width: 256, height: 256) }
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
describe '#input_clipping_geometry=' do
|
52
|
+
context 'param is a OGR::Geometry' do
|
53
|
+
it 'sets the attribute' do
|
54
|
+
geom = OGR::Point.new
|
55
|
+
subject.input_clipping_geometry = geom
|
56
|
+
expect(subject.input_clipping_geometry).to eq geom
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
context 'param is not a OGR::Geometry' do
|
61
|
+
it 'raises a OGR::InvalidGeometry exception' do
|
62
|
+
expect { subject.input_clipping_geometry = 'meow' }.
|
63
|
+
to raise_exception OGR::InvalidGeometry
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
describe '#output_data_type=' do
|
69
|
+
context 'param is a FFI::GDAL::GDAL::DataType' do
|
70
|
+
it 'sets the attribute and the grid data type' do
|
71
|
+
subject.output_data_type = :GDT_Byte
|
72
|
+
expect(subject.output_data_type).to eq :GDT_Byte
|
73
|
+
expect(subject.grid.data_type).to eq :GDT_Byte
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
77
|
+
context 'param is not a FFI::GDAL::GDAL::DataType' do
|
78
|
+
it 'raises a OGR::InvalidGeometry exception' do
|
79
|
+
expect { subject.output_data_type = 'meow' }.
|
80
|
+
to raise_exception GDAL::InvalidDataType
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
84
|
+
|
85
|
+
describe '#output_format=' do
|
86
|
+
context 'param is a GDAL::Driver short name' do
|
87
|
+
it 'sets the attribute' do
|
88
|
+
subject.output_format = 'SAGA'
|
89
|
+
expect(subject.output_format).to eq 'SAGA'
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
context 'param is not a GDAL::Driver short name' do
|
94
|
+
it 'raises a GDAL::InvalidDriverName exception' do
|
95
|
+
expect { subject.output_format = 'meow' }.
|
96
|
+
to raise_exception GDAL::InvalidDriverName
|
97
|
+
end
|
98
|
+
end
|
99
|
+
end
|
100
|
+
|
101
|
+
describe '#output_x_extent=' do
|
102
|
+
it 'returns a Hash with min and max keys' do
|
103
|
+
expect(subject).to receive(:extract_min_max).with(%w[some values], :min, :max).
|
104
|
+
and_return(%w[some values])
|
105
|
+
subject.output_x_extent = %w[some values]
|
106
|
+
expect(subject.output_x_extent).to eq(min: 'some', max: 'values')
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
describe '#output_y_extent=' do
|
111
|
+
it 'returns a Hash with min and max keys' do
|
112
|
+
expect(subject).to receive(:extract_min_max).with(%w[some values], :min, :max).
|
113
|
+
and_return(%w[some values])
|
114
|
+
subject.output_y_extent = %w[some values]
|
115
|
+
expect(subject.output_y_extent).to eq(min: 'some', max: 'values')
|
116
|
+
end
|
117
|
+
end
|
118
|
+
|
119
|
+
describe '#output_size=' do
|
120
|
+
it 'returns a Hash with min and max keys' do
|
121
|
+
expect(subject).to receive(:extract_min_max).with(%w[some values], :width, :height).
|
122
|
+
and_return(%w[some values])
|
123
|
+
subject.output_size = %w[some values]
|
124
|
+
expect(subject.output_size).to eq(width: 'some', height: 'values')
|
125
|
+
end
|
126
|
+
end
|
127
|
+
|
128
|
+
describe '#output_projection=' do
|
129
|
+
context 'param is a OGR::SpatialReference' do
|
130
|
+
it 'sets the attribute' do
|
131
|
+
projection = OGR::SpatialReference.new_from_epsg(4326)
|
132
|
+
subject.output_projection = projection
|
133
|
+
expect(subject.output_projection).to eq projection
|
134
|
+
end
|
135
|
+
end
|
136
|
+
|
137
|
+
context 'param is not a OGR::SpatialReference' do
|
138
|
+
it 'raises a OGR::InvalidSpatialReference exception' do
|
139
|
+
expect { subject.output_projection = 'meow' }.
|
140
|
+
to raise_exception OGR::InvalidSpatialReference
|
141
|
+
end
|
142
|
+
end
|
143
|
+
end
|
144
|
+
|
145
|
+
describe '#extract_min_max_from_array' do
|
146
|
+
context 'param is a 2-element Array' do
|
147
|
+
it 'sets the attribute' do
|
148
|
+
expect(subject.send(:extract_min_max_from_array, [1, 20], :foo, :bar)).
|
149
|
+
to eq([1, 20])
|
150
|
+
end
|
151
|
+
end
|
152
|
+
|
153
|
+
context 'param is an Array with not 2 elements' do
|
154
|
+
it 'raises an ArgumentError' do
|
155
|
+
expect { subject.send(:extract_min_max_from_array, [1, 20, 30], :foo, :bar) }.
|
156
|
+
to raise_exception ArgumentError
|
157
|
+
end
|
158
|
+
end
|
159
|
+
end
|
160
|
+
|
161
|
+
describe '#extract_min_max_from_hash' do
|
162
|
+
context 'param is a Hash with :min and :max keys' do
|
163
|
+
it 'sets the attribute' do
|
164
|
+
expect(subject.send(:extract_min_max_from_hash, { min: 1, max: 20 }, :min, :max)).
|
165
|
+
to eq([1, 20])
|
166
|
+
end
|
167
|
+
end
|
168
|
+
|
169
|
+
context 'param is a Hash with :min, :max, and :other' do
|
170
|
+
it 'raises an ArgumentError' do
|
171
|
+
expect { subject.send(:extract_min_max_from_hash, { min: 1, max: 20, other: 30 }, :min, :max) }.
|
172
|
+
to raise_exception ArgumentError
|
173
|
+
end
|
174
|
+
end
|
175
|
+
|
176
|
+
context 'param is a Hash without :min and :max' do
|
177
|
+
it 'raises an ArgumentError' do
|
178
|
+
expect { subject.send(:extract_min_max_from_hash, { things: 1, stuff: 20 }, :min, :max) }.
|
179
|
+
to raise_exception ArgumentError
|
180
|
+
end
|
181
|
+
end
|
182
|
+
end
|
183
|
+
end
|
@@ -0,0 +1,140 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
require 'gdal/gridder'
|
3
|
+
|
4
|
+
RSpec.describe GDAL::Gridder do
|
5
|
+
let(:source_layer) { instance_double 'OGR::Layer' }
|
6
|
+
let(:dest_file_name) { 'blah.docx' }
|
7
|
+
let(:gridder_options) { instance_double 'GDAL::GridderOptions' }
|
8
|
+
|
9
|
+
subject(:gridder) { described_class.new(source_layer, dest_file_name, gridder_options) }
|
10
|
+
|
11
|
+
describe '#build_output_spatial_reference' do
|
12
|
+
let(:spatial_reference) { instance_double 'OGR::SpatialRefernce' }
|
13
|
+
|
14
|
+
context 'no output_projection given, source layer has one set' do
|
15
|
+
before do
|
16
|
+
allow(gridder_options).to receive(:output_projection).and_return nil
|
17
|
+
allow(source_layer).to receive(:spatial_reference).and_return spatial_reference
|
18
|
+
allow(spatial_reference).to receive(:to_wkt).and_return 'BLAH'
|
19
|
+
end
|
20
|
+
|
21
|
+
it "returns WKT of the source layer's SpatialReference" do
|
22
|
+
expect(subject.send(:build_output_spatial_reference)).to eq 'BLAH'
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
context 'output_projection given' do
|
27
|
+
before do
|
28
|
+
allow(gridder_options).to receive(:output_projection).and_return spatial_reference
|
29
|
+
allow(spatial_reference).to receive(:to_wkt).and_return 'MEOW'
|
30
|
+
end
|
31
|
+
|
32
|
+
it "returns WKT of the source layer's SpatialReference" do
|
33
|
+
expect(subject.send(:build_output_spatial_reference)).to eq 'MEOW'
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
context 'no output_projection given, source layer does not have one set' do
|
38
|
+
before do
|
39
|
+
allow(gridder_options).to receive(:output_projection).and_return nil
|
40
|
+
allow(source_layer).to receive(:spatial_reference).and_return nil
|
41
|
+
end
|
42
|
+
|
43
|
+
it 'returns nil' do
|
44
|
+
expect(subject.send(:build_output_spatial_reference)).to eq nil
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
describe '#x_min' do
|
50
|
+
context 'output_x_extent is set' do
|
51
|
+
before { allow(gridder_options).to receive(:output_x_extent).and_return(min: 123) }
|
52
|
+
|
53
|
+
it 'sets x_min to that value' do
|
54
|
+
expect(subject.send(:x_min)).to eq 123
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
context 'output_x_extent is not set' do
|
59
|
+
let(:extent) { instance_double 'OGR::Envelope', x_min: 456 }
|
60
|
+
|
61
|
+
before do
|
62
|
+
allow(gridder_options).to receive(:output_x_extent).and_return({})
|
63
|
+
allow(source_layer).to receive(:extent).and_return extent
|
64
|
+
end
|
65
|
+
|
66
|
+
it "sets x_min to the source layer's extent's x_min value" do
|
67
|
+
expect(subject.send(:x_min)).to eq 456
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
describe '#x_max' do
|
73
|
+
context 'output_x_extent is set' do
|
74
|
+
before { allow(gridder_options).to receive(:output_x_extent).and_return(max: 321) }
|
75
|
+
|
76
|
+
it 'sets x_max to that value' do
|
77
|
+
expect(subject.send(:x_max)).to eq 321
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
context 'output_x_extent is not set' do
|
82
|
+
let(:extent) { instance_double 'OGR::Envelope', x_max: 654 }
|
83
|
+
|
84
|
+
before do
|
85
|
+
allow(gridder_options).to receive(:output_x_extent).and_return({})
|
86
|
+
allow(source_layer).to receive(:extent).and_return extent
|
87
|
+
end
|
88
|
+
|
89
|
+
it "sets x_max to the source layer's extent's x_max value" do
|
90
|
+
expect(subject.send(:x_max)).to eq 654
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
|
95
|
+
describe '#y_min' do
|
96
|
+
context 'output_y_extent is set' do
|
97
|
+
before { allow(gridder_options).to receive(:output_y_extent).and_return(min: 123) }
|
98
|
+
|
99
|
+
it 'sets y_min to that value' do
|
100
|
+
expect(subject.send(:y_min)).to eq 123
|
101
|
+
end
|
102
|
+
end
|
103
|
+
|
104
|
+
context 'output_y_extent is not set' do
|
105
|
+
let(:extent) { instance_double 'OGR::Envelope', y_min: 456 }
|
106
|
+
|
107
|
+
before do
|
108
|
+
allow(gridder_options).to receive(:output_y_extent).and_return({})
|
109
|
+
allow(source_layer).to receive(:extent).and_return extent
|
110
|
+
end
|
111
|
+
|
112
|
+
it "sets y_min to the source layer's extent's y_min value" do
|
113
|
+
expect(subject.send(:y_min)).to eq 456
|
114
|
+
end
|
115
|
+
end
|
116
|
+
end
|
117
|
+
|
118
|
+
describe '#y_max' do
|
119
|
+
context 'output_y_extent is set' do
|
120
|
+
before { allow(gridder_options).to receive(:output_y_extent).and_return(max: 321) }
|
121
|
+
|
122
|
+
it 'sets y_max to that value' do
|
123
|
+
expect(subject.send(:y_max)).to eq 321
|
124
|
+
end
|
125
|
+
end
|
126
|
+
|
127
|
+
context 'output_y_extent is not set' do
|
128
|
+
let(:extent) { instance_double 'OGR::Envelope', y_max: 654 }
|
129
|
+
|
130
|
+
before do
|
131
|
+
allow(gridder_options).to receive(:output_y_extent).and_return({})
|
132
|
+
allow(source_layer).to receive(:extent).and_return extent
|
133
|
+
end
|
134
|
+
|
135
|
+
it "sets y_max to the source layer's extent's y_max value" do
|
136
|
+
expect(subject.send(:y_max)).to eq 654
|
137
|
+
end
|
138
|
+
end
|
139
|
+
end
|
140
|
+
end
|
@@ -93,8 +93,58 @@ RSpec.describe GDAL::InternalHelpers do
|
|
93
93
|
end
|
94
94
|
|
95
95
|
context 'data type is not one listed' do
|
96
|
-
|
97
|
-
|
96
|
+
it 'raises a GDAL::InvalidDataType' do
|
97
|
+
expect { tester._gdal_data_type_to_ffi(:blargh) }.
|
98
|
+
to raise_exception(GDAL::InvalidDataType)
|
99
|
+
end
|
100
|
+
end
|
101
|
+
end
|
102
|
+
|
103
|
+
describe '._read_pointer' do
|
104
|
+
context 'length is 1' do
|
105
|
+
let(:pointer) do
|
106
|
+
p = FFI::MemoryPointer.new(:int16)
|
107
|
+
p.write_int16(12_345)
|
108
|
+
|
109
|
+
p
|
110
|
+
end
|
111
|
+
|
112
|
+
it 'returns the data value' do
|
113
|
+
expect(GDAL._read_pointer(pointer, :GDT_Int16)).to eq(12_345)
|
114
|
+
end
|
115
|
+
end
|
116
|
+
|
117
|
+
context 'length is > 1' do
|
118
|
+
let(:pointer) do
|
119
|
+
p = FFI::MemoryPointer.new(:int16, 2)
|
120
|
+
p.write_array_of_int16([12_345, 222])
|
121
|
+
|
122
|
+
p
|
123
|
+
end
|
124
|
+
|
125
|
+
it 'returns the data value' do
|
126
|
+
expect(GDAL._read_pointer(pointer, :GDT_Int16, 2)).to eq([12_345, 222])
|
127
|
+
end
|
128
|
+
end
|
129
|
+
end
|
130
|
+
|
131
|
+
describe '._write_pointer' do
|
132
|
+
context 'data is not an Array' do
|
133
|
+
let(:pointer) { FFI::MemoryPointer.new(:int16) }
|
134
|
+
|
135
|
+
it 'writes the single value to the pointer' do
|
136
|
+
expect(pointer).to receive(:write_int16).with(12_345)
|
137
|
+
GDAL._write_pointer(pointer, :GDT_Int16, 12_345)
|
138
|
+
end
|
139
|
+
end
|
140
|
+
|
141
|
+
context 'data is an Array' do
|
142
|
+
let(:pointer) { FFI::MemoryPointer.new(:int16, 2) }
|
143
|
+
|
144
|
+
it 'writes the values to the pointer' do
|
145
|
+
expect(pointer).to receive(:write_array_of_int16).with([12_345, 222])
|
146
|
+
GDAL._write_pointer(pointer, :GDT_Int16, [12_345, 222])
|
147
|
+
end
|
98
148
|
end
|
99
149
|
end
|
100
150
|
|
@@ -109,4 +159,118 @@ RSpec.describe GDAL::InternalHelpers do
|
|
109
159
|
it { is_expected.to eq false }
|
110
160
|
end
|
111
161
|
end
|
162
|
+
|
163
|
+
describe '._gdal_data_type_to_narray' do
|
164
|
+
subject { GDAL._gdal_data_type_to_narray(data_type) }
|
165
|
+
|
166
|
+
context 'data_type is :GDT_Byte' do
|
167
|
+
let(:data_type) { :GDT_Byte }
|
168
|
+
it { is_expected.to eq(:byte) }
|
169
|
+
end
|
170
|
+
|
171
|
+
context 'data_type is :GDT_Int16' do
|
172
|
+
let(:data_type) { :GDT_Int16 }
|
173
|
+
it { is_expected.to eq(:sint) }
|
174
|
+
end
|
175
|
+
|
176
|
+
context 'data_type is :GDT_UInt16' do
|
177
|
+
let(:data_type) { :GDT_UInt16 }
|
178
|
+
it { is_expected.to eq(:int) }
|
179
|
+
end
|
180
|
+
|
181
|
+
context 'data_type is :GDT_Int32' do
|
182
|
+
let(:data_type) { :GDT_Int32 }
|
183
|
+
it { is_expected.to eq(:int) }
|
184
|
+
end
|
185
|
+
|
186
|
+
context 'data_type is :GDT_UInt32' do
|
187
|
+
let(:data_type) { :GDT_UInt32 }
|
188
|
+
it { is_expected.to eq(:int) }
|
189
|
+
end
|
190
|
+
|
191
|
+
context 'data_type is :GDT_Float32' do
|
192
|
+
let(:data_type) { :GDT_Float32 }
|
193
|
+
it { is_expected.to eq(:float) }
|
194
|
+
end
|
195
|
+
|
196
|
+
context 'data_type is :GDT_Float64' do
|
197
|
+
let(:data_type) { :GDT_Float64 }
|
198
|
+
it { is_expected.to eq(:dfloat) }
|
199
|
+
end
|
200
|
+
|
201
|
+
context 'data_type is :GDT_CInt16' do
|
202
|
+
let(:data_type) { :GDT_CInt16 }
|
203
|
+
it { is_expected.to eq(:scomplex) }
|
204
|
+
end
|
205
|
+
|
206
|
+
context 'data_type is :GDT_CInt32' do
|
207
|
+
let(:data_type) { :GDT_CInt32 }
|
208
|
+
it { is_expected.to eq(:scomplex) }
|
209
|
+
end
|
210
|
+
|
211
|
+
context 'data_type is :GDT_CFloat32' do
|
212
|
+
let(:data_type) { :GDT_CFloat32 }
|
213
|
+
it { is_expected.to eq(:complex) }
|
214
|
+
end
|
215
|
+
|
216
|
+
context 'data_type is :GDT_CFloat64' do
|
217
|
+
let(:data_type) { :GDT_CFloat64 }
|
218
|
+
it { is_expected.to eq(:dcomplex) }
|
219
|
+
end
|
220
|
+
|
221
|
+
context 'unknown data_type' do
|
222
|
+
it 'raises a GDAL::InvalidDataType exception' do
|
223
|
+
expect { GDAL._gdal_data_type_to_narray(:meow) }.
|
224
|
+
to raise_exception(GDAL::InvalidDataType)
|
225
|
+
end
|
226
|
+
end
|
227
|
+
end
|
228
|
+
|
229
|
+
describe '._narray_from_data_type' do
|
230
|
+
context '0 narray_args and known GDAL data_type' do
|
231
|
+
subject { GDAL._narray_from_data_type(:GDT_Byte) }
|
232
|
+
it { is_expected.to be_a NArray }
|
233
|
+
|
234
|
+
it 'has size 0' do
|
235
|
+
expect(subject.size).to be_zero
|
236
|
+
end
|
237
|
+
|
238
|
+
it 'has shape []' do
|
239
|
+
expect(subject.shape).to eq([])
|
240
|
+
end
|
241
|
+
end
|
242
|
+
|
243
|
+
context '1 narray_args and known GDAL data_type' do
|
244
|
+
subject { GDAL._narray_from_data_type(:GDT_Byte, 2) }
|
245
|
+
it { is_expected.to be_a NArray }
|
246
|
+
|
247
|
+
it 'has size of the 2nd param' do
|
248
|
+
expect(subject.size).to eq(2)
|
249
|
+
end
|
250
|
+
|
251
|
+
it 'has 1D shape with size of the 2nd param' do
|
252
|
+
expect(subject.shape).to eq([2])
|
253
|
+
end
|
254
|
+
end
|
255
|
+
|
256
|
+
context '2 narray_args and known GDAL data_type' do
|
257
|
+
subject { GDAL._narray_from_data_type(:GDT_Byte, 2, 3) }
|
258
|
+
it { is_expected.to be_a NArray }
|
259
|
+
|
260
|
+
it 'has size of the 2nd param * 3rd param' do
|
261
|
+
expect(subject.size).to eq(6)
|
262
|
+
end
|
263
|
+
|
264
|
+
it 'has 2D shape with size of each of the params' do
|
265
|
+
expect(subject.shape).to eq([2, 3])
|
266
|
+
end
|
267
|
+
end
|
268
|
+
|
269
|
+
context 'unknown GDAL data_type' do
|
270
|
+
it 'raises a GDAL::InvalidDataType exception' do
|
271
|
+
expect { GDAL._narray_from_data_type(:bobo) }.
|
272
|
+
to raise_exception(GDAL::InvalidDataType)
|
273
|
+
end
|
274
|
+
end
|
275
|
+
end
|
112
276
|
end
|
@@ -6,16 +6,15 @@ RSpec.describe GDAL::RasterBandClassifier do
|
|
6
6
|
let(:driver) { GDAL::Driver.by_name('MEM') }
|
7
7
|
|
8
8
|
let(:dataset) do
|
9
|
-
driver.create_dataset
|
10
|
-
|
11
|
-
|
12
|
-
let(:raster_band) do
|
13
|
-
band = dataset.raster_band 1
|
9
|
+
d = driver.create_dataset('test dataset', 640, 480)
|
10
|
+
band = d.raster_band 1
|
14
11
|
new_values = band.to_na.indgen!
|
15
|
-
band.
|
16
|
-
|
12
|
+
band.write_xy_narray(new_values)
|
13
|
+
|
14
|
+
d
|
17
15
|
end
|
18
16
|
|
17
|
+
let(:raster_band) { dataset.raster_band 1 }
|
19
18
|
subject(:classifier) { described_class.new(raster_band) }
|
20
19
|
|
21
20
|
describe '#add_range' do
|
@@ -70,7 +69,7 @@ RSpec.describe GDAL::RasterBandClassifier do
|
|
70
69
|
let(:raster_band) do
|
71
70
|
band = float_dataset.raster_band 1
|
72
71
|
new_values = band.to_na.indgen!
|
73
|
-
band.
|
72
|
+
band.write_xy_narray(new_values)
|
74
73
|
band
|
75
74
|
end
|
76
75
|
|
@@ -95,6 +94,15 @@ RSpec.describe GDAL::RasterBandClassifier do
|
|
95
94
|
subject { classifier.equal_count_ranges(1_000) }
|
96
95
|
it { is_expected.to be_nil }
|
97
96
|
end
|
97
|
+
|
98
|
+
context 'all nodata pixels' do
|
99
|
+
let(:band_narray) { NArray.byte(0) }
|
100
|
+
before { allow(raster_band).to receive(:to_na).and_return(band_narray) }
|
101
|
+
|
102
|
+
it 'returns an empty Array' do
|
103
|
+
expect(subject.equal_count_ranges(10)).to eq([])
|
104
|
+
end
|
105
|
+
end
|
98
106
|
end
|
99
107
|
|
100
108
|
describe '#classify!' do
|
@@ -103,37 +111,87 @@ RSpec.describe GDAL::RasterBandClassifier do
|
|
103
111
|
subject.add_ranges(ranges)
|
104
112
|
end
|
105
113
|
|
106
|
-
context 'no_data_value is set' do
|
114
|
+
context 'no_data_value is set to 0' do
|
107
115
|
before do
|
108
116
|
raster_band.no_data_value = 0
|
109
|
-
subject.classify!
|
110
117
|
end
|
111
118
|
|
112
119
|
it 'has a max value equal to the number of ranges' do
|
120
|
+
subject.classify!
|
113
121
|
min_max = raster_band.min_max
|
114
122
|
expect(min_max[:max]).to eq 10
|
115
123
|
end
|
116
124
|
|
117
125
|
it 'has a min value of 1' do
|
126
|
+
subject.classify!
|
118
127
|
min_max = raster_band.min_max
|
119
128
|
expect(min_max[:min]).to eq 1
|
120
129
|
end
|
130
|
+
|
131
|
+
it 'retains its NODATA pixels' do
|
132
|
+
expect { subject.classify! }.to_not change { raster_band.to_na.eq(-9999.0).count_true }
|
133
|
+
end
|
121
134
|
end
|
122
135
|
|
123
|
-
|
124
|
-
|
136
|
+
# Relevant because NArray inits its arrays to 0.
|
137
|
+
context 'no_data_value is set to non-0' do
|
138
|
+
let(:dataset) do
|
139
|
+
d = driver.create_dataset('test dataset', 640, 480, data_type: :GDT_Float32)
|
140
|
+
band = d.raster_band 1
|
141
|
+
band.no_data_value = -9999.0
|
142
|
+
new_values = band.to_na.indgen!
|
143
|
+
new_values[true, 0] = -9999.0
|
144
|
+
band.write_xy_narray(new_values)
|
145
|
+
|
146
|
+
d
|
147
|
+
end
|
148
|
+
|
149
|
+
it 'has a max value equal to the number of ranges' do
|
125
150
|
subject.classify!
|
151
|
+
min_max = raster_band.min_max
|
152
|
+
expect(min_max[:max]).to eq 10
|
153
|
+
end
|
154
|
+
|
155
|
+
it 'has a min value of 1' do
|
156
|
+
subject.classify!
|
157
|
+
min_max = raster_band.min_max
|
158
|
+
expect(min_max[:min]).to eq 1
|
126
159
|
end
|
127
160
|
|
161
|
+
it 'retains its NODATA pixels' do
|
162
|
+
expect { subject.classify! }.to_not change { raster_band.to_na.eq(-9999.0).count_true }
|
163
|
+
pixels = raster_band.to_na
|
164
|
+
expect(pixels.eq(-9999).count_true).to eq 640
|
165
|
+
expect(pixels.eq(0).count_true).to eq 0
|
166
|
+
expect(pixels.eq(1).count_true).to eq 30_656
|
167
|
+
expect(pixels.eq(2).count_true).to eq 30_656
|
168
|
+
expect(pixels.eq(3).count_true).to eq 30_656
|
169
|
+
expect(pixels.eq(4).count_true).to eq 30_656
|
170
|
+
expect(pixels.eq(5).count_true).to eq 30_656
|
171
|
+
expect(pixels.eq(6).count_true).to eq 30_656
|
172
|
+
expect(pixels.eq(7).count_true).to eq 30_656
|
173
|
+
expect(pixels.eq(8).count_true).to eq 30_656
|
174
|
+
expect(pixels.eq(9).count_true).to eq 30_656
|
175
|
+
expect(pixels.eq(10).count_true).to eq 30_656
|
176
|
+
end
|
177
|
+
end
|
178
|
+
|
179
|
+
context 'no_data_value is not set' do
|
128
180
|
it 'has a max value equal to the number of ranges' do
|
181
|
+
subject.classify!
|
129
182
|
min_max = raster_band.min_max
|
130
183
|
expect(min_max[:max]).to eq 10
|
131
184
|
end
|
132
185
|
|
133
186
|
it 'has a min value of 0' do
|
187
|
+
subject.classify!
|
134
188
|
min_max = raster_band.min_max
|
135
189
|
expect(min_max[:min]).to eq 0
|
136
190
|
end
|
191
|
+
|
192
|
+
it 'retains its NODATA pixels' do
|
193
|
+
expect { subject.classify! }.to_not change { raster_band.to_na.eq(-9999.0).count_true }
|
194
|
+
end
|
137
195
|
end
|
138
196
|
end
|
139
197
|
end
|