From b313dd9f2db0952b3c0a2abdfe811b61c4f81700 Mon Sep 17 00:00:00 2001 From: Bborie Park Date: Tue, 16 Oct 2012 20:59:06 +0000 Subject: [PATCH] Added optional interpolate_nodata flag as function parameter to ST_HillShade, ST_Aspect and ST_Slope. git-svn-id: http://svn.osgeo.org/postgis/trunk@10445 b70326c6-7e19-0410-871a-916f4a2858ee --- NEWS | 2 ++ doc/reference_raster.xml | 24 +++++++++++++--- raster/rt_pg/rtpostgis.sql.in.c | 41 ++++++++++++++++++++++------ raster/rt_pg/rtpostgis_drop.sql.in.c | 5 ++++ 4 files changed, 59 insertions(+), 13 deletions(-) diff --git a/NEWS b/NEWS index 539f227d7..018301445 100644 --- a/NEWS +++ b/NEWS @@ -52,6 +52,8 @@ PostGIS 2.1.0 - #2006, better support of ST_Area(geography) over poles and dateline - TopologySummary output now includes unregistered layers and a count of missing TopoGeometry objects from their natural layer. + - ST_HillShade(), ST_Aspect() and ST_Slope() have one new optional parameter to + interpolate NODATA pixels before running the operation. * Fixes * diff --git a/doc/reference_raster.xml b/doc/reference_raster.xml index 13cd542cf..c15b06aad 100644 --- a/doc/reference_raster.xml +++ b/doc/reference_raster.xml @@ -7243,6 +7243,7 @@ FROM dummy_rast; double precision altitude double precision max_bright=255 double precision elevation_scale=1 + boolean interpolate_nodata=FALSE @@ -7251,10 +7252,15 @@ FROM dummy_rast; Description Returns the hypothetical illumination of an elevation raster band using the azimuth, altitude, brightness, and elevation scale inputs. Utilizes map algebra and applies the hill shade equation to neighboring pixels. + + + If interpolate_nodata is TRUE, values for NODATA pixels from the input raster will be interpolated using before computing the hillshade illumination. + + The hill shade equation is: max_bright * ( (cos(zenith)*cos(slope)) + (sin(zenith)*sin(slope)*cos(azimuth - aspect)) ). Availability: 2.0.0 - Enhanced: 2.1.0 Uses and runs before running the hillshade operation - + Enhanced: 2.1.0 Uses and added optional interpolate_nodata function parameter + @@ -7283,6 +7289,7 @@ FROM dummy_rast; raster rast integer band text pixeltype + boolean interpolate_nodata=FALSE @@ -7292,6 +7299,10 @@ FROM dummy_rast; Returns the surface aspect of an elevation raster band. Utilizes map algebra and applies the aspect equation to neighboring pixels. + + If interpolate_nodata is TRUE, values for NODATA pixels from the input raster will be interpolated using before computing the surface aspect. + + Given the following representation of a 3x3 neighborhood of pixels: @@ -7319,7 +7330,7 @@ FROM dummy_rast; The equation for the pixel aspect of cell E is: atan2((((G + 2H + I) - (A + 2B + C)) / 8), -(((C + 2F + I) - (A + 2D + G)) / 8)) Availability: 2.0.0 - Enhanced: 2.1.0 Uses and runs before running the hillshade operation + Enhanced: 2.1.0 Uses and added optional interpolate_nodata function parameter @@ -7349,6 +7360,7 @@ FROM dummy_rast; raster rast integer band text pixeltype + boolean interpolate_nodata=FALSE @@ -7358,6 +7370,10 @@ FROM dummy_rast; Returns the surface slope of an elevation raster band. Utilizes map algebra and applies the slope equation to neighboring pixels. + + If interpolate_nodata is TRUE, values for NODATA pixels from the input raster will be interpolated using before computing the surface slope. + + Given the following representation of a 3x3 neighborhood of pixels: @@ -7385,7 +7401,7 @@ FROM dummy_rast; The equation for the pixel slope of cell E is: atan(sqrt(((c + 2f + i) - (a + 2d + g) / 8)^2 + (((g + 2h + i) - (a + 2b + c)) / 8) ^ 2)) Availability: 2.0.0 - Enhanced: 2.1.0 Uses and runs before running the hillshade operation + Enhanced: 2.1.0 Uses and added optional interpolate_nodata function parameter diff --git a/raster/rt_pg/rtpostgis.sql.in.c b/raster/rt_pg/rtpostgis.sql.in.c index 820e15675..1d496a557 100644 --- a/raster/rt_pg/rtpostgis.sql.in.c +++ b/raster/rt_pg/rtpostgis.sql.in.c @@ -3466,10 +3466,17 @@ CREATE OR REPLACE FUNCTION _st_slope4ma(value double precision[][][], pos intege END; $$ LANGUAGE 'plpgsql' IMMUTABLE; -CREATE OR REPLACE FUNCTION st_slope(rast raster, band integer, pixeltype text) +CREATE OR REPLACE FUNCTION st_slope(rast raster, band integer, pixeltype text, interpolate_nodata boolean DEFAULT FALSE) RETURNS raster - AS $$ SELECT ST_MapAlgebra(ARRAY[ROW(ST_MapAlgebra(ARRAY[ROW($1, $2)]::rastbandarg[], 'st_invdistweight4ma(double precision[][][], integer[][], text[])'::regprocedure, $3, 'FIRST', NULL, 1, 1), 1)]::rastbandarg[], '_st_slope4ma(double precision[][][], integer[][], text[])'::regprocedure, NULL, 'FIRST', NULL, 1, 1, st_pixelwidth($1)::text, st_pixelheight($1)::text) $$ - LANGUAGE 'sql' IMMUTABLE; + AS $$ + SELECT + CASE + WHEN $4 IS FALSE THEN + ST_MapAlgebra(ARRAY[ROW($1, $2)]::rastbandarg[], '_st_slope4ma(double precision[][][], integer[][], text[])'::regprocedure, $3, 'FIRST', NULL, 1, 1, st_pixelwidth($1)::text, st_pixelheight($1)::text) + ELSE + ST_MapAlgebra(ARRAY[ROW(ST_MapAlgebra(ARRAY[ROW($1, $2)]::rastbandarg[], 'st_invdistweight4ma(double precision[][][], integer[][], text[])'::regprocedure, $3, 'FIRST', NULL, 1, 1), 1)]::rastbandarg[], '_st_slope4ma(double precision[][][], integer[][], text[])'::regprocedure, NULL, 'FIRST', NULL, 1, 1, st_pixelwidth($1)::text, st_pixelheight($1)::text) + END + $$ LANGUAGE 'sql' IMMUTABLE; ----------------------------------------------------------------------- -- ST_Aspect @@ -3533,10 +3540,17 @@ CREATE OR REPLACE FUNCTION _st_aspect4ma(value double precision[][][], pos integ END; $$ LANGUAGE 'plpgsql' IMMUTABLE; -CREATE OR REPLACE FUNCTION st_aspect(rast raster, band integer, pixeltype text) +CREATE OR REPLACE FUNCTION st_aspect(rast raster, band integer, pixeltype text, interpolate_nodata boolean DEFAULT FALSE) RETURNS raster - AS $$ SELECT ST_MapAlgebra(ARRAY[ROW(ST_MapAlgebra(ARRAY[ROW($1, $2)]::rastbandarg[], 'st_invdistweight4ma(double precision[][][], integer[][], text[])'::regprocedure, $3, 'FIRST', NULL, 1, 1), 1)]::rastbandarg[], '_st_aspect4ma(double precision[][][], integer[][], text[])'::regprocedure, NULL, 'FIRST', NULL, 1, 1, st_pixelwidth($1)::text, st_pixelheight($1)::text) $$ - LANGUAGE 'sql' IMMUTABLE; + AS $$ + SELECT + CASE + WHEN $4 IS FALSE THEN + ST_MapAlgebra(ARRAY[ROW($1, $2)]::rastbandarg[], '_st_aspect4ma(double precision[][][], integer[][], text[])'::regprocedure, $3, 'FIRST', NULL, 1, 1, st_pixelwidth($1)::text, st_pixelheight($1)::text) + ELSE + ST_MapAlgebra(ARRAY[ROW(ST_MapAlgebra(ARRAY[ROW($1, $2)]::rastbandarg[], 'st_invdistweight4ma(double precision[][][], integer[][], text[])'::regprocedure, $3, 'FIRST', NULL, 1, 1), 1)]::rastbandarg[], '_st_aspect4ma(double precision[][][], integer[][], text[])'::regprocedure, NULL, 'FIRST', NULL, 1, 1, st_pixelwidth($1)::text, st_pixelheight($1)::text) + END + $$ LANGUAGE 'sql' IMMUTABLE; ----------------------------------------------------------------------- -- ST_HillShade @@ -3617,11 +3631,20 @@ CREATE OR REPLACE FUNCTION _st_hillshade4ma(value double precision[][][], pos in CREATE OR REPLACE FUNCTION st_hillshade( rast raster, band integer, pixeltype text, - azimuth double precision, altitude double precision, max_bright double precision DEFAULT 255.0, elevation_scale double precision DEFAULT 1.0 + azimuth double precision, altitude double precision, + max_bright double precision DEFAULT 255.0, elevation_scale double precision DEFAULT 1.0, + interpolate_nodata boolean DEFAULT FALSE ) RETURNS RASTER - AS $$ SELECT ST_MapAlgebra(ARRAY[ROW(ST_MapAlgebra(ARRAY[ROW($1, $2)]::rastbandarg[], 'st_invdistweight4ma(double precision[][][], integer[][], text[])'::regprocedure, $3, 'FIRST', NULL, 1, 1), 1)]::rastbandarg[], '_st_hillshade4ma(double precision[][][], integer[][], text[])'::regprocedure, NULL, 'FIRST', NULL, 1, 1, st_pixelwidth($1)::text, st_pixelheight($1)::text, $4::text, $5::text, $6::text, $7::text) $$ - LANGUAGE 'sql' IMMUTABLE; + AS $$ + SELECT + CASE + WHEN $8 IS FALSE THEN + ST_MapAlgebra(ARRAY[ROW($1, $2)]::rastbandarg[], '_st_hillshade4ma(double precision[][][], integer[][], text[])'::regprocedure, $3, 'FIRST', NULL, 1, 1, st_pixelwidth($1)::text, st_pixelheight($1)::text, $4::text, $5::text, $6::text, $7::text) + ELSE + ST_MapAlgebra(ARRAY[ROW(ST_MapAlgebra(ARRAY[ROW($1, $2)]::rastbandarg[], 'st_invdistweight4ma(double precision[][][], integer[][], text[])'::regprocedure, $3, 'FIRST', NULL, 1, 1), 1)]::rastbandarg[], '_st_hillshade4ma(double precision[][][], integer[][], text[])'::regprocedure, NULL, 'FIRST', NULL, 1, 1, st_pixelwidth($1)::text, st_pixelheight($1)::text, $4::text, $5::text, $6::text, $7::text) + END + $$ LANGUAGE 'sql' IMMUTABLE; ----------------------------------------------------------------------- -- Get information about the raster diff --git a/raster/rt_pg/rtpostgis_drop.sql.in.c b/raster/rt_pg/rtpostgis_drop.sql.in.c index 678439a76..fbcadb334 100644 --- a/raster/rt_pg/rtpostgis_drop.sql.in.c +++ b/raster/rt_pg/rtpostgis_drop.sql.in.c @@ -435,3 +435,8 @@ DROP FUNCTION IF EXISTS _st_contains(geometry, raster, integer); -- function signature changed DROP FUNCTION IF EXISTS st_addband(raster, raster[], integer); + +-- function signatures changed +DROP FUNCTION IF EXISTS st_slope(raster, integer, text); +DROP FUNCTION IF EXISTS st_aspect(raster, integer, text); +DROP FUNCTION IF EXISTS st_hillshade(raster, integer, text, float, float, float, float); -- 2.40.0