# Calculating percent cover from shapefiles

I normally do not work with shapefiles, so I am a bit lost here. I have two shapefiles each with multiple objects. The first is a set of 32 polygons (each one is a plot). The second shapefile has >10,000 objects which represent vegetation clusters of different sizes within each plot. I am trying to figure out:

1) How do I calculate percent cover of total vegetation cover within each site?

2) What percentage of each the vegetation cover is less than 5 meters in area in each plot?

This is what my data looks like in ArcGIS for a single plot. I am open to advice on how to do this in arcGIS too.

This link will take you to the shapefiles in my dropbox: https://www.dropbox.com/sh/wyokxximppexyb3/p7VC-pfF2E

-
Thank you for providing your data. It saved me time needing to simulate some for my answer. – Jeffrey Evans Jan 9 '14 at 20:41

The parts for step three in the first answer are outlined as graphics below. This is what you want to do:

`````` a) Have three attributes in the vegetation poly (a SiteID [Floor], area of the veg poly [Area], area of the associated site [SiteArea]
b) Dissolve the vegetation polygon on the SiteID [Floor].  Calculate statistics on:
i)  Area = SUM
ii) SiteArea = FIRST
c) Add a new field to the dissolved polygon [PercentCov] (Double 6,2)
d) Calculate the cover in PercentCov with the following expression ([SUM_Area] / [FIRST_Site] * 100
``````

-

Since you tagged R, here is a solution in R. It is best to not assume that there a column representing area, which is why I am pulling it from the polygon@area slot. In the loop(s) you may notice an interesting way of pulling the values of a specific column based on indexing a different column.

This code will add "pVeg" and "pVeg5" columns to your plots polygon feature class. The pVeg column represent the percentage of all vegetation in the plot and "pVeg5" is the <= 5m percent.

``````    require(sp)
require(rgdal)

# SET WORKING DIRECTORY AND READ DATA
setwd("D:/TMP/vegplots")

# ASSOCIATE PLOT IDS TO VEG DATA
veg@data <- data.frame(veg@data, LocCode=over(veg, plots[,"LocCode"]))

# CALCULATE POLYGON AREAS AND ADD TO DATA
plots@data <- data.frame(plots@data, pArea=sapply(slot(plots, 'polygons'), function(i) slot(i, 'area')))
veg@data <- data.frame(veg@data, vArea=sapply(slot(veg, 'polygons'), function(i) slot(i, 'area')))

# CALCULATE PERCENT VEG AREA IN EACH PLOT AND ADD TO "plots" data.frame
varea <- vector()
for(i in 1:dim(plots)[1]) {
varea <- append(varea, sum(veg[veg\$LocCode == plots@data[i,]\$LocCode ,]\$vArea) )
}
plots@data <- data.frame(plots@data, pVeg=varea / plots@data\$pArea * 100)

# CALCULATE PERCENT VEG AREA <= 5m IN EACH PLOT AND ADD TO "plots" data.frame
vsub <- veg[veg\$vArea <= 5 ,]
varea5 <- vector()
for(i in 1:dim(plots)[1]) {
varea5 <- append(varea5, sum(vsub[vsub\$LocCode == plots@data[i,]\$LocCode ,]\$vArea) )
}
plots@data <- data.frame(plots@data, pVeg5=varea5 / plots@data\$pArea * 100)

writeOGR(plots, getwd(), "VegPercents", driver="ESRI Shapefile")
``````
-
+1 Excellent open-source solution – Aaron Jan 9 '14 at 22:07

Area is an attribute of polygons. To see it you may need to create a field in your attribute table to hold the value and calculate it (see here).

You can then do a spatial join of the vegetation cover on the plots. When you do this, set the merge rules in the field mapping to SUM for your area. It looks like some of your vegetation cover areas cross the plot boundaries so you may have to clip the vegetation cover areas (but you'll know your data better than I). Calculating the percentage cover is then an easy matter of dividing the sum of the vegetation areas field by the plot area. You can create another field and have Arc do the calculation in one go for all plots.

A simple solution to the second part of your query would be to repeat the process but pre-select the vegetation cover polygons with an area (your new field) less than 5m.

-
Thanks for your comment: It looks like the area of the veg polygons is included in the attributes table. Im a bit lost on the spatial join. How do I set it so that it sums the area values within each plot? – I Del Toro Jan 9 '14 at 17:18

You will have to do the following:

`````` 1) Calculate the area for each veg polygon (using the Field Calculator)
2) Have an attribute in the veg poly table to references the Site areas
a) If you don't have that, do a spatial join with the Site poly that you have in your graphic (also calculate the area for each Site poly)
3) Dissolve the spatial join veg polygon on the Site ID, at the same time add statistics to the get the SUM
4) Calculate the percent cover into a new attribute field by dividing the sum of site veg poly, with the area of the site
``````
-
Can you explain how to do step 3 a bit more. That is where I get lost. Thanks – I Del Toro Jan 9 '14 at 17:18