多邊形等距縮放

2021-08-21 10:25:50 字數 3082 閱讀 7227

給定乙個簡單多邊形,多邊形按照順時針或者逆時針的數許排列

內部等距離縮小或者外部放大的多邊形,實際上是由距離一系列平行已知多邊形的邊,並且距離為l的線段所構成的。

外圍的是原多邊形,內側是新的多邊形

演算法構造

多邊形的相鄰兩條邊,l1和l2,交於pi點

做平行於l1和l2,平行線間距是l的,並且位於多邊形內部的兩條邊,交於qi

我們要計算出qi的座標

如圖,

piqi向量,顯然是等於平行四邊形的兩個相鄰邊的向量v1和v2的和的

而v1和v2向量的方向,就是組成多邊形的邊的方向,可以用頂點差來表示

v1和v2向量的長度是相同的,等於平行線間距l與兩個線段夾角的sin值的除法。

即: qi = pi + (v1 + v2)

qi = pi + l / sinθ * ( normalize(v2) + normalize(v1))

sin θ = |v1 × v2 | /|v1|/|v2|

計算步驟:

⑴、獲取多邊形頂點陣列plist;

⑵、計算dplist[vi+1-vi];

⑶、單位化normalizedplist,得到ndp[dpi];(用同乙個陣列儲存)

⑷、sinα = dp(i+1) x dp(i);

⑸、qi = pi + d/sinα (ndpi+1-ndpi)

⑹、這樣一次性可以把所有頂點計算完。

注意,交換qi表示式當中ndpi+1-ndpi的順序就可以得到外部多邊形頂點陣列。

用swift實現的**如下,在playground可直接執行

import foundation

class point2d 

init( point:point2d)

//func += (inout left:point2d, right:point2d )    

func +  (left:point2d, right:point2d)->point2d  

func -  (left:point2d, right:point2d)->point2d  

func *  (left:point2d, right:point2d)->double   

func *  (left:point2d, value:double )->point2d  

// 自定義的向量差乘運算符號,

infix operator ** {}

func ** (left:point2d, right:point2d)->double 

var plist   = [point2d]()  // 原始頂點座標, 在initplist函式當中初始化賦值

var dplist  = [point2d]() // 邊向量dplist[i+1]- dplist[i] 在 initdplist函式當中計算後賦值

var ndplist = [point2d]() // 單位化的邊向量, 在ini***plist函式當中計算後膚質,實際使用的時候,完全可以用dplist來儲存他們

var newlist = [point2d]()  // 新的折線頂點,在compute函式當中,賦值

// 初始化頂點佇列

func initplist(){

plist  = [ point2d(0,0),

point2d(0,100),

point2d(100,100),

point2d(50,50),

point2d(100,0),

// 初始化dplist  兩頂點間向量差

func initdplist()->void{

print("計算dplist")

var index  : int

for index=0; indexprint("dplist[\(index)]=(\(dplist[index].x),\(dplist[index].y))")

// 初始化ndplist,單位化兩頂點向量差

func ini***plist()->void{

print("開始計算ndplist")

var index=0;

for ; indexprint("ndplist[\(index)]=(\(ndplist[index].x),\(ndplist[index].y))")

// 計算新頂點, 注意引數為負是向內收縮, 為正是向外擴張

func computeline(dist:double)->void{

print("開始計算新頂點")

var index = 0

let count = plist.count;

for ; indexvar point:point2d

let startindex = index==0 ? count-1 : index-1

let endindex   = index

let sina =ndplist[startindex] **ndplist[endindex]

let length = dist / sina

let vector =ndplist[endindex] -ndplist[startindex]

point = plist[index] + vector*length

print("newlist[\(index)] = (\(point.x),\(point.y))")

// 整個演算法的呼叫順序

func run()->void {

initplist();

initdplist()

ini***plist()

computeline(-5)  // 負數為內縮, 正數為外擴。 需要注意演算法本身並沒有檢測內縮多少後折線會自相交,那不是本**的示範意圖

arcgis for js 根據多邊形自動縮放

交代背景 多邊形已經渲染在圖層上,然後根據多邊形自動縮放值合適的大小 思路 獲取圖層資訊,獲取圖層中的幾何資訊,獲取圖形範圍資訊,在地圖上設定範圍 下面的方法有封裝 記一下思路就好 var polygonsingle map.layerop.getlayersingle layerid 獲取圖層資訊...

求任意多邊形面積(凹多邊形和凸多邊形)

遇到問題 已知多邊形的各個左邊點,要求多邊形的面積 然後我搜尋了下看到這篇文章 這個人說的不多,但是簡單明瞭 首先已知各定點的座標分別為 x1,y1 x2,y2 x3,y3 xn,yn 則該多邊形的面積公式為 s 1 2 x1 y2 x2 y1 x2 y3 x3 y2 xk yk 1 xk 1 yk...

驗證多邊形是否為凸多邊形

驗證多邊形是否為凸多邊形 2108 shape of hdu include define debug 0 int crossmulti int x0,int y0,int x1,int y1,int x2,int y2 int main int n,i int f x,f y 第1個點 int s...