Extended Parcel Area Report

I was in need of a custom XML report to calculate a few ‘extended’ statistics when I have defined my parcels and exported the XML info. The items that I needed were a total parcel count, total parcel coverage, minimum parcel size and name (parcel with least area), maximum parcel size and name (parcel with greatest area), and average parcel size for the project.

To start, I am using Dreamweaver 8 to edit my XML and XSL files. You can use any basic text editing program, such as Notepad, to create the same files.

I am going to start with the easiest portion of the tasks, and that is the total parcel count. To count the total number of parcels, you only need the following line of code:

Total Parcel Count:<xsl:text> </xsl:text><xsl:value-of select="count(//lx:Parcel)"/>

The preceding code will format the output line to have a space after the colon, and then reads the XML source file and physically counts the total number of entries in the Parcel category.

Note: If you have parcels defined for your entire site, be sure to exclude those from your XML file. This will give you more parcels than proposed parcels. The same goes for this entire discussion.

The next portion is the total parcel coverage. In order to get the total parcel coverage, you need to add together all of the parcel areas. To do this we will need to do a few items first. We need to define two variables for the code that will follow. Bellow are the two variables:

<xsl:variable name="ParcelSums" select="sum(//lx:Parcels/*/@area)"/> <-- This physically adds all of the @area attributes for all items in Parcels.
<xsl:variable name="ParcelSumFrmt" select="landUtils:FormatNumber(string($ParcelSums), string($SourceAreaUnit), string($SourceAreaUnit), string($Parcel.2D_Area.precision), string($Parcel.2D_Area.rounding))"/><-- This variable actually takes the ParcelSums variable above and properly formats it to match the project settings.

Now that we have gotten our form to be able to at least add the parcel sums, we can have the form output the result simply by:

Total Parcel(s) Area:<xsl:text> </xsl:text><xsl:value-of select=”$ParcelSumFrmt”/>

And now we are able to get output that will look like so if you have a project setup in meters with 3 decimal places of precision. To get the output that I will be display, use the Tutorial1.xml file that is in the LandXML 7 support directory.

Output:
Total Parcel Count: 24
Total Parcel(s) Area: 11007.936

Ok, now on to the average parcel area calculation. The first step is to define a variable that will count the total number of parcels. I did not define this parcel earlier only because it was not truly needed. To do this, we do the following:

<xsl:variable name="ParcelCnts" select="count(//lx:Parcel)"/>

And now we move on to output line, which will perform the division operations between the parcel count variable and the formated parcel sum variable from above.

Average Parcel Area:<xsl:text> </xsl:text><xsl:value-of select="($ParcelSumFrmt div $ParcelCnts)"/>

As a result we end up with an output that now gives us:

Output:
Total Parcel Count: 24
Total Parcel(s) Area: 11007.936
Average Parcel Area: 458.664

Up until now, things have been somewhat easy. The final two items that we need to add to our report are the minimum and maximum lot sizes. We are going to start off with the maximum parcel size, and this is how we do it:

Maximum Parcel Area:<xsl:text> </xsl:text>
<xsl:for-each select="//lx:Parcels/*"> <-- For each item in Parcels...
<xsl:sort select="@area" data-type="number" order="descending"/> <-- Sort items from Parcels in descending order according to @area
<xsl:variable name="ParcelMaxArea" select="position()"/>
<xsl:choose> <-- This is where it gets ready to select the largest parcel
<xsl:when test="$ParcelMaxArea = 1"> <-- This pulls out the entity in the number 1 position (largest area)
<xsl:value-of select="@area"/><xsl:text> ( </xsl:text> <-- This pulls the @area from the largest parcel
<xsl:value-of select="@name"/><xsl:text> )</xsl:text> <-- This pulls the @name of the largest parcel
</xsl:when>
</xsl:choose>
</xsl:for-each>

Finally we move on to the minimum parcel area. This is almost the same as the maximum, but there are a few different items. One item is extremely puzzling to me still to this point, but I will discuss that after the code.

Minimum Parcel Area:<xsl:text> </xsl:text>
<xsl:for-each select="//lx:Parcels/*">
<xsl:sort select="@area" data-type="number" order="ascending"/> <-- Sorts in ascending order this time
<xsl:variable name="ParcelMinArea" select="position()"/>
<xsl:choose>
<xsl:when test="$ParcelMinArea = 2"> <-- Selects the 2 position, this is where I am puzzled ***See below***
<xsl:value-of select="@area"/><xsl:text> ( </xsl:text>
<xsl:value-of select="@name"/><xsl:text> )</xsl:text>
</xsl:when>
</xsl:choose>
</xsl:for-each>

I am puzzled as to why the position of the smallest parcel is 2, but after a few hours of trying other positions such as 0 and 1 repeatedly and rewriting my code over and over, I decided to try moving up to position 2 and it actually worked! If anyone knows the reasoning behind this I would like to know, so please forward it to me.

To completely round out this little tutorial, I have provided the entire code that I have added to my ParcelArea.xsl file in the XSL folder of the LandXML 7 support directory, I have also uploaded a Word document for you to view the code in it’s entire with relation to the original code. I added all of the following code directly after the </table> and before the </div> tags. Hope this helps. Enjoy!

Extended Parcel Output Code:

<br />
<center>
<span style="font-style:italic">Please note that all information provided below is formatted<br />
to show the same units of measurement as shown above.</span>
</center>
<br />
<table bordercolor="black" border="1" cellspacing="0" cellpadding="4" width="95%" align="center"><caption><strong>Extended Parcel Data</strong></caption>
<tr>
<td style="border-bottom:none;" align="left"><strong>Total Parcel Count:<xsl:text> </xsl:text></strong> <xsl:value-of select="count(//lx:Parcel)"/></td>
</tr>
<xsl:variable name="ParcelSums" select="sum(//lx:Parcels/*/@area)"/>
<xsl:variable name="ParcelSumFix" select="landUtils:FormatNumber(string($ParcelSums), string($SourceAreaUnit), string($SourceAreaUnit), string($Parcel.2D_Area.precision), string($Parcel.2D_Area.rounding))"/>
<tr>
<td style="border-bottom:none; border-top:none;" align="left"><strong>Total Parcel(s) Area:<xsl:text> </xsl:text></strong>
<xsl:value-of select="$ParcelSumFix"/>
</td>
</tr>
<xsl:variable name="ParcelCnts" select="count(//lx:Parcel)"/>
<tr>
<td style="border-bottom:none; border-top:none;" align="left"><strong>Average Parcel Area:<xsl:text> </xsl:text></strong>
<xsl:value-of select="($ParcelSumFix div $ParcelCnts)"/>
</td>
</tr>
<tr>
<td style="border-bottom:none; border-top:none;" align="left"><strong>Maximum Parcel Area:<xsl:text> </xsl:text></strong>
<xsl:for-each select="//lx:Parcels/*">
<xsl:sort select="@area" data-type="number" order="descending"/>
<xsl:variable name="ParcelMaxArea" select="position()"/>
<xsl:choose>
<xsl:when test="$ParcelMaxArea = 1">
<xsl:value-of select="@area"/><xsl:text> ( </xsl:text><xsl:value-of select="@name"/><xsl:text> )</xsl:text>
</xsl:when>
</xsl:choose>
</xsl:for-each>
</td>
</tr>
<tr>
<td style="border-bottom:none; border-top:none;" align="left"><strong>Minimum Parcel Area:<xsl:text> </xsl:text></strong>
<xsl:for-each select="//lx:Parcels/*">
<xsl:sort select="@area" data-type="number" order="ascending"/>
<xsl:variable name="ParcelMinArea" select="position()"/>
<xsl:choose>
<xsl:when test="$ParcelMinArea = 2">
<xsl:value-of select="@area"/><xsl:text> ( </xsl:text><xsl:value-of select="@name"/><xsl:text> )</xsl:text>
</xsl:when>
</xsl:choose>
</xsl:for-each>
</td>
</tr>
</table>

Leave a Reply