2016-08-16 5 views
0

Я ищу процедуру, которая позволяет мне генерировать последовательность эквидистантных точек (координат) вдоль сторон произвольного многоугольника.Создание последовательности эквидистантных точек на границе полигона

создания изображения в многоугольник, заданный координатами его вершин:

poly.mat <- matrix(c(0,0, 
        0,1, 
        0.5,1.5, 
        0.5,0, 
        0,0 # last row included to close the polygon 
        ), byrow = T, ncol = 2) 
colnames(poly.mat) <- c("x", "y") 
plot(poly.mat, type = "l") 

Если длина последовательности Я хочу, чтобы генерировать это n (регулируемое), как можно производить последовательность, начиная с (0, 0), эквидистантных координат.

я добрался до расчета по периметру формы с geosphere пакет (который я считаю, мне нужно)

library(geosphere) 
n <- 50 # sequence of length set to be 50 
perim <- perimeter(poly.mat) 
perim/n # looks like every section needs to be 8210.768 something in length 
+0

эквидистантный каждый из следующего? Прямое расстояние или движение вдоль границы? –

+0

Эквидистант каждый из следующего, да. Путешествие по границе. – crubba

+0

Итак, вы хотите развернуть периметр полигона и разбить его на равные сегменты? или вы хотите равные промежуточные точки между каждой вершиной – MichaelChirico

ответ

0

Вот решение, которое я придумал.

pointDistance <- function(p1, p2){ 
    sqrt((p2[,1]-p1[,1])^2) + sqrt((p2[,2]-p1[,2])^2) 
} 

getPos <- function(shp.mat, ll){ 
    greaterLL <- shp.mat$cumdis > ll 
    if(all(greaterLL == FALSE)) return(poly.mat[nrow(poly.mat), c("x", "y")]) 
    smallRow <- min(which(greaterLL)) # the smallest coordinate that has greater length 
    p.start <- shp.mat[smallRow-1, c("x","y")] 
    p.end <- shp.mat[smallRow, c("x","y")] 
    cumVal <- shp.mat$cumdis[smallRow] 
    prop <- (ll-shp.mat$cumdis[smallRow-1])/(shp.mat$cumdis[smallRow]-shp.mat$cumdis[smallRow-1]) 

    p.start + (prop)* (p.end-p.start) 
} 

# shp1 
poly.mat <- matrix(c(0,0, 
       0,1, 
       0.5,1.5, 
       0.5,0, 
       0,0 
),byrow = T, ncol = 2) 
colnames(poly.mat) <- c("x", "y") 
poly.mat <- as.data.frame(poly.mat) 


# Main fun 
pointsOnPath <- function(shp.mat, n){ 

dist <- vector(mode = "numeric", length = nrow(shp.mat)-1) 

for(i in 2:nrow(shp.mat)){ 
    dist[i] <- pointDistance(p1 = shp.mat[i,], p2 = shp.mat[i-1,]) 
} 
shp.mat$dist <- dist 
shp.mat$cumdis <- cumsum(shp.mat$dist) 


dis <- matrix(seq(from = 0, to = max(shp.mat$cumdis), length.out = n+1), ncol = 1) 

out <- lapply(dis, function(x) getPos(shp.mat = shp.mat, ll = x)) 
out <- do.call("rbind", out) 
out$dis <- dis 

out[-nrow(out),] 
} 

df <- pointsOnPath(shp.mat = poly.mat, 5) 

# Plot 
plot(poly.mat$x, poly.mat$y, type = "l", xlim = c(0,1.5), ylim = c(0,1.5)) 
points(df$x, df$y, col = "red", lwd = 2) 

pointsonpath-plot

Существует возможность для улучшения кода, но он должен возвращать правильный результат

0

Вы должны будете написать код самостоятельно. К сожалению, для каждой последней детали каждого последнего назначения нет функции библиотеки. Предполагая, что каждая пара точек определяет отрезок линии, вы можете просто генерировать N точек вдоль каждого сегмента, как в

begin = [xbegin, ybegin];
end = [xend, yend];

xdist = (xend - xbegin)/nintervals;
ydist = (yend - ybegin)/nintervals;

тогда ваши точки определяются [xbegin + я * xdist, ybegin + я * ydist]

Смежные вопросы