formatting
This commit is contained in:
parent
8159124a48
commit
44e5352c16
41
IV/wm.sql
41
IV/wm.sql
@ -1,9 +1,9 @@
|
|||||||
\set ON_ERROR_STOP on
|
\set ON_ERROR_STOP on
|
||||||
SET plpgsql.extra_errors TO 'all';
|
SET plpgsql.extra_errors TO 'all';
|
||||||
|
|
||||||
|
-- detect_bends detects bends using the inflection angles. No corrections.
|
||||||
drop function if exists detect_bends;
|
drop function if exists detect_bends;
|
||||||
-- detect_bends detects bends using the inflection angles. It does not do corrections.
|
create function detect_bends(line geometry, OUT bends geometry[]) as $$
|
||||||
create or replace function detect_bends(line geometry, OUT bends geometry[]) as $$
|
|
||||||
declare
|
declare
|
||||||
pi real;
|
pi real;
|
||||||
p geometry;
|
p geometry;
|
||||||
@ -16,8 +16,8 @@ declare
|
|||||||
begin
|
begin
|
||||||
pi = radians(180);
|
pi = radians(180);
|
||||||
|
|
||||||
-- the last vertex is iterated over twice, because the algorithm uses 3 vertices
|
-- the last vertex is iterated over twice, because the algorithm uses 3
|
||||||
-- to calculate the angle between them.
|
-- vertices to calculate the angle between them.
|
||||||
--
|
--
|
||||||
-- Given 3 vertices p1, p2, p3:
|
-- Given 3 vertices p1, p2, p3:
|
||||||
--
|
--
|
||||||
@ -97,7 +97,8 @@ $$ language plpgsql;
|
|||||||
|
|
||||||
-- fix_gentle_inflections1 fixes gentle inflections of an array of lines in
|
-- fix_gentle_inflections1 fixes gentle inflections of an array of lines in
|
||||||
-- one direction. This is an implementation detail of fix_gentle_inflections.
|
-- one direction. This is an implementation detail of fix_gentle_inflections.
|
||||||
create or replace function fix_gentle_inflections1(INOUT bends geometry[]) as $$
|
drop function if exists fix_gentle_inflections1;
|
||||||
|
create function fix_gentle_inflections1(INOUT bends geometry[]) as $$
|
||||||
declare
|
declare
|
||||||
pi real;
|
pi real;
|
||||||
small_angle real;
|
small_angle real;
|
||||||
@ -145,13 +146,14 @@ begin
|
|||||||
-- if the bend got too short, stop processing it
|
-- if the bend got too short, stop processing it
|
||||||
exit when array_length(phead, 1) < 3;
|
exit when array_length(phead, 1) < 3;
|
||||||
|
|
||||||
-- if inflection angle between ptail[1:3] "large", stop processing this bend
|
-- inflection angle between ptail[1:3] is "large", stop processing
|
||||||
exit when abs(st_angle(phead[1], phead[2], phead[3]) - pi) > small_angle;
|
exit when abs(st_angle(phead[1], phead[2], phead[3]) - pi) > small_angle;
|
||||||
|
|
||||||
-- distance from head's first vertex should be larger than from second vertex
|
-- distance from head's 1st vertex should be larger than from 2nd vertex
|
||||||
exit when st_distance(ptail, phead[2]) < st_distance(ptail, phead[3]);
|
exit when st_distance(ptail, phead[2]) < st_distance(ptail, phead[3]);
|
||||||
|
|
||||||
-- detected a gentle inflection. Move head of the tail to the tail of head
|
-- Detected a gentle inflection.
|
||||||
|
-- Move head of the tail to the tail of head
|
||||||
bends[i] = st_removepoint(bends[i], 0);
|
bends[i] = st_removepoint(bends[i], 0);
|
||||||
bends[i-1] = st_addpoint(bends[i-1], phead[3]);
|
bends[i-1] = st_addpoint(bends[i-1], phead[3]);
|
||||||
end loop;
|
end loop;
|
||||||
@ -162,7 +164,8 @@ $$ language plpgsql;
|
|||||||
|
|
||||||
-- self_crossing eliminates self-crossing from the bends, following the
|
-- self_crossing eliminates self-crossing from the bends, following the
|
||||||
-- article's section "Self-line Crossing When Cutting a Bend".
|
-- article's section "Self-line Crossing When Cutting a Bend".
|
||||||
create or replace function self_crossing(INOUT bends geometry[]) as $$
|
drop function if exists self_crossing;
|
||||||
|
create function self_crossing(INOUT bends geometry[]) as $$
|
||||||
declare
|
declare
|
||||||
i int4;
|
i int4;
|
||||||
j int4;
|
j int4;
|
||||||
@ -189,7 +192,9 @@ begin
|
|||||||
p1 = null;
|
p1 = null;
|
||||||
p2 = null;
|
p2 = null;
|
||||||
p3 = null;
|
p3 = null;
|
||||||
for p0 in (select geom from st_dumppoints(bends[i]) order by path[1] asc) loop
|
for p0 in (
|
||||||
|
select geom from st_dumppoints(bends[i]) order by path[1] asc
|
||||||
|
) loop
|
||||||
p3 = p2;
|
p3 = p2;
|
||||||
p2 = p1;
|
p2 = p1;
|
||||||
p1 = p0;
|
p1 = p0;
|
||||||
@ -219,8 +224,10 @@ begin
|
|||||||
|
|
||||||
-- are p2 and p3 on the different sides of line(p0,p1)? vector
|
-- are p2 and p3 on the different sides of line(p0,p1)? vector
|
||||||
-- multiplication; https://stackoverflow.com/questions/1560492/
|
-- multiplication; https://stackoverflow.com/questions/1560492/
|
||||||
s2 = (st_x(p0)-st_x(p1)*(st_y(p2)-st_y(p1))-(st_y(p0)-st_y(p1))*(st_x(p2)-st_x(p1)));
|
s2 = (st_x(p0)-st_x(p1)*(st_y(p2)-st_y(p1))-
|
||||||
s3 = (st_x(p0)-st_x(p1)*(st_y(p3)-st_y(p1))-(st_y(p0)-st_y(p1))*(st_x(p3)-st_x(p1)));
|
(st_y(p0)-st_y(p1))*(st_x(p2)-st_x(p1)));
|
||||||
|
s3 = (st_x(p0)-st_x(p1)*(st_y(p3)-st_y(p1))-
|
||||||
|
(st_y(p0)-st_y(p1))*(st_x(p3)-st_x(p1)));
|
||||||
continue when sign(s2) = sign(s3);
|
continue when sign(s2) = sign(s3);
|
||||||
|
|
||||||
-- do end vertices of bend[i] cross bend[j]?
|
-- do end vertices of bend[i] cross bend[j]?
|
||||||
@ -228,12 +235,13 @@ begin
|
|||||||
b = st_pointn(bends[i], -1);
|
b = st_pointn(bends[i], -1);
|
||||||
multi = st_split(bends[j], st_makeline(a, b));
|
multi = st_split(bends[j], st_makeline(a, b));
|
||||||
continue when st_numgeometries(multi) = 1;
|
continue when st_numgeometries(multi) = 1;
|
||||||
continue when st_numgeometries(multi) = 2 and (st_contains(bends[j], a) or st_contains(bends[j], b));
|
continue when st_numgeometries(multi) = 2 and
|
||||||
|
(st_contains(bends[j], a) or st_contains(bends[j], b));
|
||||||
|
|
||||||
-- real self-crossing detected! Remove it.
|
-- real self-crossing detected! Remove it.
|
||||||
-- if j < i:
|
-- if j < i:
|
||||||
-- bends[j] = multi[1][1...n-1]; that will have all the vertices of bends[j],
|
-- bends[j] = multi[1][1...n-1]; that will have all the vertices of
|
||||||
-- except the crossing and what comes after it.
|
-- bends[j], except the crossing and what comes after it.
|
||||||
-- bends[j] = append(bends[j], bends[i][-1])
|
-- bends[j] = append(bends[j], bends[i][-1])
|
||||||
-- remove bends from bends[j+1] to bends[i] inclusive.
|
-- remove bends from bends[j+1] to bends[i] inclusive.
|
||||||
-- j := i+1
|
-- j := i+1
|
||||||
@ -253,7 +261,8 @@ begin
|
|||||||
prev_length = array_length(bends, 1);
|
prev_length = array_length(bends, 1);
|
||||||
if j < i then
|
if j < i then
|
||||||
bends[j] = st_geometryn(multi, 1);
|
bends[j] = st_geometryn(multi, 1);
|
||||||
bends[j] = st_setpoint(bends[j], st_npoints(bends[j])-1, st_pointn(bends[i], st_npoints(bends[i])));
|
bends[j] = st_setpoint(bends[j], st_npoints(bends[j])-1,
|
||||||
|
st_pointn(bends[i], st_npoints(bends[i])));
|
||||||
bends = bends[1:j] || bends[i+1:prev_length];
|
bends = bends[1:j] || bends[i+1:prev_length];
|
||||||
j = i;
|
j = i;
|
||||||
else
|
else
|
||||||
|
Loading…
Reference in New Issue
Block a user