2013-07-10 86 views
1

因此,我創建的繪圖函數用點繪製各個端口的座標。我想創建一個功能,允許用戶選擇他們想要標記哪個端口,然後更改標籤位置。獲取一個參數以獲取多個值 - R

這裏有各種端口和它們的座標:

  Labels  Lon  Lat 
1  Halifax, NS -63.59341 44.68068 
2 St. John's, NL -52.73304 47.59341 
3 Saint John, NB -66.05236 45.27925 
4 Portland, ME -70.24435 43.68068 
5 Woods Hole, MA -70.68068 41.62832 
6 Nuuk, Greenland -51.75049 64.17453 
7  Boston, MA -71.08727 42.36652 

我的功能:

port.label <- function (pos1, cex1 = 0.6, offset1 = 0.2, col1 = "deeppink") { 
     port.file<-read.csv("V:/Science/Finalised Map Files/Ports.csv") 
     Lon <- port.file$Lon 
     Lat <- port.file$Lat 
     Lab <- paste(port.file$Lab) 
     a <- locator() 
     ay <- unlist(a[2]) 
     aylab <- sapply (ay, function (x) which.min (abs (x - Lat))) 
     b <- for (i in (1:length (aylab))) { 
     text (x = Lon [aylab[i]], y = Lat [aylab[i]], labels = Lab [aylab[i]], 
     pos = pos1, cex = cex1, offset = offset1, col = col1) 
     } 
    } 

現在,當我嘗試運行它:點擊四點後port.label(pos1=c(1,2,3,4))返回標籤只使用第一個值(1),因此低於該點。所以它只取第一個價值。我試着預先設置pos1的長度與點擊的端口數有關,但這也沒有幫助。

任何想法爲什麼它只會取第一個pos1值而不是整個向量? 謝謝。

+0

你有看看識別功能的幫助嗎?也許它可以幫助你 – droopy

+0

我想過識別,但不是它只是繪製標籤相對於你點擊的位置而不是你能夠設置標籤的位置 – Tom

回答

1

嗯,因爲對於每次調用text(),你都用完整的向量調用它。由於每個呼叫僅用於一個標籤,因此您需要撥打pos=pos1[i]。不幸的是,然後調用只有1個參數的port.label需要額外檢查pos1()長度。說,你想要所有的標籤在同一個位置,底部,所以你打電話port.label(pos1= 1)。用i=2pos1[i]將取值NA。因此,你將不得不擴大pos1如果它的長度等於1

這將是更有效地調用它像:

port.label <- function (pos1, cex1 = 0.6, offset1 = 0.2, col1 = "deeppink") { 
    port.file<-read.csv("V:/Science/Finalised Map Files/Ports.csv") 
    Lon <- port.file$Lon 
    Lat <- port.file$Lat 
    Lab <- paste(port.file$Lab) 
    a <- locator() 
    ay <- unlist(a[2]) 
    aylab <- sapply (ay, function (x) which.min (abs (x - Lat))) 
    text(x= Lon[aylab], y= Lat[aylab], labels= Lab[aylab], 
     pos= pos1, cex= cex1, offset= offset1, col= col1) 
} 
+0

我只是剔除了代碼,但我不明白爲什麼如果您提出了更改,則需要進行額外的檢查。同樣在你的代碼中,你有'po1'而不是'pos1' – Dason

+0

我試圖在上面的編輯中提出要點。 – January

0

這是有幫助的形式使用dput輸出數據讀者更容易在R中運行。

mydat <- structure(list(Lab = c("Halifax, NS", "St. John's, NL", "Saint John, NB", 
    "Portland, ME", "Woods Hole, MA", "Nuuk, Greenland", "Boston, MA"), 
    Lon = c(-63.59341, -52.73304, -66.05236, -70.24435, -70.68068, -51.75049, -71.08727), 
    Lat = c(44.68068, 47.59341, 45.27925, 43.68068, 41.62832, 64.17453, 42.36652)), 
    .Names = c("Labels", "Lon", "Lat"), class = "data.frame", row.names = c(NA, -7L)) 

對此我一點也不清楚爲什麼你會想要一個這樣做的函數。我想可能有更好的方法去做你真正想做的事。但是,這裏試圖修改你的代碼,以便它能做到你想要的。我建議使用@Droopy的identify()函數。

port.label <- function (data, posn, cex1=0.6, offset1=0.2, col1="deeppink") { 
    j <- identify(mydat$Lon, mydat$Lat, mydat$Lab, plot=FALSE) 
    for(i in 1:length(j)) { 
     text(x=data$Lon[j[i]], y=data$Lat[j[i]], labels=data$Lab[j[i]], pos=posn[i], cex=cex1, offset=offset1, col=col1) 
     } 
    } 

plot(mydat$Lon, mydat$Lat) 
port.label(mydat, posn=c(1, 2, 3, 4))