Changeset 81 for trunk


Ignore:
Timestamp:
Jan 18, 2011, 10:19:20 AM (14 years ago)
Author:
reluc
Message:

Adding getGeodesicLength
Adding getGeodesicArea
Adding ZOO.Geometry.Polygon.createRegularPolygon
Adding more documentation, need to be ended

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/zoo-api/js/ZOO-api.js

    r74 r81  
    115115  },
    116116  /**
     117   * Function: rad
     118   *
     119   * Parameters:
     120   * x - {Float}
     121   *
     122   * Returns:
     123   * {Float}
     124   */
     125  rad: function(x) {return x*Math.PI/180;},
     126  /**
     127   * Function: distVincenty
     128   * Given two objects representing points with geographic coordinates, this
     129   *     calculates the distance between those points on the surface of an
     130   *     ellipsoid.
     131   *
     132   * Parameters:
     133   * p1 - {<ZOO.Geometry.Point>} (or any object with both .x, .y properties)
     134   * p2 - {<ZOO.Geometry.Point>} (or any object with both .x, .y properties)
     135   *
     136   * Returns:
     137   * {Float} The distance (in km) between the two input points as measured on an
     138   *     ellipsoid.  Note that the input point objects must be in geographic
     139   *     coordinates (decimal degrees) and the return distance is in kilometers.
     140   */
     141  distVincenty: function(p1, p2) {
     142    var a = 6378137, b = 6356752.3142,  f = 1/298.257223563;
     143    var L = ZOO.rad(p2.x - p1.y);
     144    var U1 = Math.atan((1-f) * Math.tan(ZOO.rad(p1.y)));
     145    var U2 = Math.atan((1-f) * Math.tan(ZOO.rad(p2.y)));
     146    var sinU1 = Math.sin(U1), cosU1 = Math.cos(U1);
     147    var sinU2 = Math.sin(U2), cosU2 = Math.cos(U2);
     148    var lambda = L, lambdaP = 2*Math.PI;
     149    var iterLimit = 20;
     150    while (Math.abs(lambda-lambdaP) > 1e-12 && --iterLimit>0) {
     151        var sinLambda = Math.sin(lambda), cosLambda = Math.cos(lambda);
     152        var sinSigma = Math.sqrt((cosU2*sinLambda) * (cosU2*sinLambda) +
     153        (cosU1*sinU2-sinU1*cosU2*cosLambda) * (cosU1*sinU2-sinU1*cosU2*cosLambda));
     154        if (sinSigma==0) {
     155            return 0;  // co-incident points
     156        }
     157        var cosSigma = sinU1*sinU2 + cosU1*cosU2*cosLambda;
     158        var sigma = Math.atan2(sinSigma, cosSigma);
     159        var alpha = Math.asin(cosU1 * cosU2 * sinLambda / sinSigma);
     160        var cosSqAlpha = Math.cos(alpha) * Math.cos(alpha);
     161        var cos2SigmaM = cosSigma - 2*sinU1*sinU2/cosSqAlpha;
     162        var C = f/16*cosSqAlpha*(4+f*(4-3*cosSqAlpha));
     163        lambdaP = lambda;
     164        lambda = L + (1-C) * f * Math.sin(alpha) *
     165        (sigma + C*sinSigma*(cos2SigmaM+C*cosSigma*(-1+2*cos2SigmaM*cos2SigmaM)));
     166    }
     167    if (iterLimit==0) {
     168        return NaN;  // formula failed to converge
     169    }
     170    var uSq = cosSqAlpha * (a*a - b*b) / (b*b);
     171    var A = 1 + uSq/16384*(4096+uSq*(-768+uSq*(320-175*uSq)));
     172    var B = uSq/1024 * (256+uSq*(-128+uSq*(74-47*uSq)));
     173    var deltaSigma = B*sinSigma*(cos2SigmaM+B/4*(cosSigma*(-1+2*cos2SigmaM*cos2SigmaM)-
     174        B/6*cos2SigmaM*(-3+4*sinSigma*sinSigma)*(-3+4*cos2SigmaM*cos2SigmaM)));
     175    var s = b*A*(sigma-deltaSigma);
     176    var d = s.toFixed(3)/1000; // round to 1mm precision
     177    return d;
     178  },
     179  /**
    117180   * Function: Class
    118181   * Method used to create ZOO classes. Includes support for
     
    669732  projCode: null,
    670733  /**
    671    * Constructor: OpenLayers.Projection
     734   * Constructor: ZOO.Projection
    672735   * This class offers several methods for interacting with a wrapped
    673736   *     zoo-pro4js projection object.
     
    750813 * point - {{ZOO.Geometry.Point> | Object} An object with x and y
    751814 *     properties representing coordinates in those dimensions.
    752  * sourceProj - {OpenLayers.Projection} Source map coordinate system
    753  * destProj - {OpenLayers.Projection} Destination map coordinate system
     815 * sourceProj - {ZOO.Projection} Source map coordinate system
     816 * destProj - {ZOO.Projection} Destination map coordinate system
    754817 *
    755818 * Returns:
     
    9731036  },
    9741037  /**
     1038   * Property: extract
    9751039   * Object with properties corresponding to the geometry types.
    9761040   * Property values are functions that do the actual data extraction.
     
    10571121  },
    10581122  /**
     1123   * Property: parse
    10591124   * Object with properties corresponding to the geometry types.
    1060    * Property values are functions that do the actual parsing.
     1125   *     Property values are functions that do the actual parsing.
    10611126   */
    10621127  parse: {
    10631128    /**
     1129     * Method: parse.point
    10641130     * Return point feature given a point WKT fragment.
    1065      * @param {String} str A WKT fragment representing the point
    1066      * @returns {<ZOO.Feature>} A point feature
     1131     *
     1132     * Parameters:
     1133     * str - {String} A WKT fragment representing the point
     1134     * Returns:
     1135     * {<ZOO.Feature>} A point feature
    10671136     */
    10681137    'point': function(str) {
     
    10731142    },
    10741143    /**
     1144     * Method: parse.multipoint
    10751145     * Return a multipoint feature given a multipoint WKT fragment.
    1076      * @param {String} A WKT fragment representing the multipoint
    1077      * @returns {<ZOO.Feature>} A multipoint feature
     1146     *
     1147     * Parameters:
     1148     * str - {String} A WKT fragment representing the multipoint
     1149     *
     1150     * Returns:
     1151     * {<ZOO.Feature>} A multipoint feature
    10781152     */
    10791153    'multipoint': function(str) {
     
    10881162    },
    10891163    /**
     1164     * Method: parse.linestring
    10901165     * Return a linestring feature given a linestring WKT fragment.
    1091      * @param {String} A WKT fragment representing the linestring
    1092      * @returns {<ZOO.Feature>} A linestring feature
     1166     *
     1167     * Parameters:
     1168     * str - {String} A WKT fragment representing the linestring
     1169     *
     1170     * Returns:
     1171     * {<ZOO.Feature>} A linestring feature
    10931172     */
    10941173    'linestring': function(str) {
     
    11031182    },
    11041183    /**
     1184     * Method: parse.multilinestring
    11051185     * Return a multilinestring feature given a multilinestring WKT fragment.
    1106      * @param {String} A WKT fragment representing the multilinestring
    1107      * @returns {<ZOO.Feature>} A multilinestring feature
     1186     *
     1187     * Parameters:
     1188     * str - {String} A WKT fragment representing the multilinestring
     1189     *
     1190     * Returns:
     1191     * {<ZOO.Feature>} A multilinestring feature
    11081192     */
    11091193    'multilinestring': function(str) {
     
    11201204    },
    11211205    /**
     1206     * Method: parse.polygon
    11221207     * Return a polygon feature given a polygon WKT fragment.
    1123      * @param {String} A WKT fragment representing the polygon
    1124      * @returns {<ZOO.Feature>} A polygon feature
     1208     *
     1209     * Parameters:
     1210     * str - {String} A WKT fragment representing the polygon
     1211     *
     1212     * Returns:
     1213     * {<ZOO.Feature>} A polygon feature
    11251214     */
    11261215    'polygon': function(str) {
     
    11391228    },
    11401229    /**
     1230     * Method: parse.multipolygon
    11411231     * Return a multipolygon feature given a multipolygon WKT fragment.
    1142      * @param {String} A WKT fragment representing the multipolygon
    1143      * @returns {<ZOO.Feature>} A multipolygon feature
    1144      * @private
     1232     *
     1233     * Parameters:
     1234     * str - {String} A WKT fragment representing the multipolygon
     1235     *
     1236     * Returns:
     1237     * {<ZOO.Feature>} A multipolygon feature
    11451238     */
    11461239    'multipolygon': function(str) {
     
    11571250    },
    11581251    /**
     1252     * Method: parse.geometrycollection
    11591253     * Return an array of features given a geometrycollection WKT fragment.
    1160      * @param {String} A WKT fragment representing the geometrycollection
    1161      * @returns {Array} An array of ZOO.Feature
     1254     *
     1255     * Parameters:
     1256     * str - {String} A WKT fragment representing the geometrycollection
     1257     *
     1258     * Returns:
     1259     * {Array} An array of ZOO.Feature
    11621260     */
    11631261    'geometrycollection': function(str) {
     
    11801278 *
    11811279 * Inherits from:
    1182  *  - <OpenLayers.Format>
     1280 *  - <ZOO.Format>
    11831281 */
    11841282ZOO.Format.JSON = ZOO.Class(ZOO.Format, {
     1283  /**
     1284   * Property: indent
     1285   * {String} For "pretty" printing, the indent string will be used once for
     1286   *     each indentation level.
     1287   */
    11851288  indent: "    ",
     1289  /**
     1290   * Property: space
     1291   * {String} For "pretty" printing, the space string will be used after
     1292   *     the ":" separating a name/value pair.
     1293   */
    11861294  space: " ",
     1295  /**
     1296   * Property: newline
     1297   * {String} For "pretty" printing, the newline string will be used at the
     1298   *     end of each name/value pair or array item.
     1299   */
    11871300  newline: "\n",
     1301  /**
     1302   * Property: level
     1303   * {Integer} For "pretty" printing, this is incremented/decremented during
     1304   *     serialization.
     1305   */
    11881306  level: 0,
     1307  /**
     1308   * Property: pretty
     1309   * {Boolean} Serialize with extra whitespace for structure.  This is set
     1310   *     by the <write> method.
     1311   */
    11891312  pretty: false,
     1313  /**
     1314   * Constructor: ZOO.Format.JSON
     1315   * Create a new parser for JSON.
     1316   *
     1317   * Parameters:
     1318   * options - {Object} An optional object whose properties will be set on
     1319   *     this instance.
     1320   */
    11901321  initialize: function(options) {
    11911322    ZOO.Format.prototype.initialize.apply(this, [options]);
    11921323  },
     1324  /**
     1325   * Method: read
     1326   * Deserialize a json string.
     1327   *
     1328   * Parameters:
     1329   * json - {String} A JSON string
     1330   * filter - {Function} A function which will be called for every key and
     1331   *     value at every level of the final result. Each value will be
     1332   *     replaced by the result of the filter function. This can be used to
     1333   *     reform generic objects into instances of classes, or to transform
     1334   *     date strings into Date objects.
     1335   *     
     1336   * Returns:
     1337   * {Object} An object, array, string, or number .
     1338   */
    11931339  read: function(json, filter) {
     1340    /**
     1341     * Parsing happens in three stages. In the first stage, we run the text
     1342     *     against a regular expression which looks for non-JSON
     1343     *     characters. We are especially concerned with '()' and 'new'
     1344     *     because they can cause invocation, and '=' because it can cause
     1345     *     mutation. But just to be safe, we will reject all unexpected
     1346     *     characters.
     1347     */
    11941348    try {
    11951349      if (/^[\],:{}\s]*$/.test(json.replace(/\\["\\\/bfnrtu]/g, '@').
    11961350                          replace(/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g, ']').
    11971351                          replace(/(?:^|:|,)(?:\s*\[)+/g, ''))) {
     1352        /**
     1353         * In the second stage we use the eval function to compile the
     1354         *     text into a JavaScript structure. The '{' operator is
     1355         *     subject to a syntactic ambiguity in JavaScript - it can
     1356         *     begin a block or an object literal. We wrap the text in
     1357         *     parens to eliminate the ambiguity.
     1358         */
    11981359        var object = eval('(' + json + ')');
     1360        /**
     1361         * In the optional third stage, we recursively walk the new
     1362         *     structure, passing each name/value pair to a filter
     1363         *     function for possible transformation.
     1364         */
    11991365        if(typeof filter === 'function') {
    12001366          function walk(k, v) {
     
    12201386    return null;
    12211387  },
     1388  /**
     1389   * Method: write
     1390   * Serialize an object into a JSON string.
     1391   *
     1392   * Parameters:
     1393   * value - {String} The object, array, string, number, boolean or date
     1394   *     to be serialized.
     1395   * pretty - {Boolean} Structure the output with newlines and indentation.
     1396   *     Default is false.
     1397   *
     1398   * Returns:
     1399   * {String} The JSON string representation of the input value.
     1400   */
    12221401  write: function(value, pretty) {
    12231402    this.pretty = !!pretty;
     
    12331412    return json;
    12341413  },
     1414  /**
     1415   * Method: writeIndent
     1416   * Output an indentation string depending on the indentation level.
     1417   *
     1418   * Returns:
     1419   * {String} An appropriate indentation string.
     1420   */
    12351421  writeIndent: function() {
    12361422    var pieces = [];
     
    12421428    return pieces.join('');
    12431429  },
     1430  /**
     1431   * Method: writeNewline
     1432   * Output a string representing a newline if in pretty printing mode.
     1433   *
     1434   * Returns:
     1435   * {String} A string representing a new line.
     1436   */
    12441437  writeNewline: function() {
    12451438    return (this.pretty) ? this.newline : '';
    12461439  },
     1440  /**
     1441   * Method: writeSpace
     1442   * Output a string representing a space if in pretty printing mode.
     1443   *
     1444   * Returns:
     1445   * {String} A space.
     1446   */
    12471447  writeSpace: function() {
    12481448    return (this.pretty) ? this.space : '';
    12491449  },
     1450  /**
     1451   * Property: serialize
     1452   * Object with properties corresponding to the serializable data types.
     1453   *     Property values are functions that do the actual serializing.
     1454   */
    12501455  serialize: {
     1456    /**
     1457     * Method: serialize.object
     1458     * Transform an object into a JSON string.
     1459     *
     1460     * Parameters:
     1461     * object - {Object} The object to be serialized.
     1462     *
     1463     * Returns:
     1464     * {String} A JSON string representing the object.
     1465     */
    12511466    'object': function(object) {
    12521467       // three special objects that we want to treat differently
     
    12821497       return pieces.join('');
    12831498    },
     1499    /**
     1500     * Method: serialize.array
     1501     * Transform an array into a JSON string.
     1502     *
     1503     * Parameters:
     1504     * array - {Array} The array to be serialized
     1505     *
     1506     * Returns:
     1507     * {String} A JSON string representing the array.
     1508     */
    12841509    'array': function(array) {
    12851510      var json;
     
    13001525      return pieces.join('');
    13011526    },
     1527    /**
     1528     * Method: serialize.string
     1529     * Transform a string into a JSON string.
     1530     *
     1531     * Parameters:
     1532     * string - {String} The string to be serialized
     1533     *
     1534     * Returns:
     1535     * {String} A JSON string representing the string.
     1536     */
    13021537    'string': function(string) {
    13031538      var m = {
     
    13231558      return '"' + string + '"';
    13241559    },
     1560    /**
     1561     * Method: serialize.number
     1562     * Transform a number into a JSON string.
     1563     *
     1564     * Parameters:
     1565     * number - {Number} The number to be serialized.
     1566     *
     1567     * Returns:
     1568     * {String} A JSON string representing the number.
     1569     */
    13251570    'number': function(number) {
    13261571      return isFinite(number) ? String(number) : "null";
    13271572    },
     1573    /**
     1574     * Method: serialize.boolean
     1575     * Transform a boolean into a JSON string.
     1576     *
     1577     * Parameters:
     1578     * bool - {Boolean} The boolean to be serialized.
     1579     *
     1580     * Returns:
     1581     * {String} A JSON string representing the boolean.
     1582     */
    13281583    'boolean': function(bool) {
    13291584      return String(bool);
    13301585    },
     1586    /**
     1587     * Method: serialize.date
     1588     * Transform a date into a JSON string.
     1589     *
     1590     * Parameters:
     1591     * date - {Date} The date to be serialized.
     1592     *
     1593     * Returns:
     1594     * {String} A JSON string representing the date.
     1595     */
    13311596    'date': function(date) {   
    13321597      function format(number) {
     
    13441609  CLASS_NAME: 'ZOO.Format.JSON'
    13451610});
     1611/**
     1612 * Class: ZOO.Format.GeoJSON
     1613 * Read and write GeoJSON. Create a new parser with the
     1614 *     <ZOO.Format.GeoJSON> constructor.
     1615 *
     1616 * Inherits from:
     1617 *  - <ZOO.Format.JSON>
     1618 */
    13461619ZOO.Format.GeoJSON = ZOO.Class(ZOO.Format.JSON, {
     1620  /**
     1621   * Constructor: ZOO.Format.GeoJSON
     1622   * Create a new parser for GeoJSON.
     1623   *
     1624   * Parameters:
     1625   * options - {Object} An optional object whose properties will be set on
     1626   *     this instance.
     1627   */
    13471628  initialize: function(options) {
    13481629    ZOO.Format.JSON.prototype.initialize.apply(this, [options]);
    13491630  },
     1631  /**
     1632   * Method: read
     1633   * Deserialize a GeoJSON string.
     1634   *
     1635   * Parameters:
     1636   * json - {String} A GeoJSON string
     1637   * type - {String} Optional string that determines the structure of
     1638   *     the output.  Supported values are "Geometry", "Feature", and
     1639   *     "FeatureCollection".  If absent or null, a default of
     1640   *     "FeatureCollection" is assumed.
     1641   * filter - {Function} A function which will be called for every key and
     1642   *     value at every level of the final result. Each value will be
     1643   *     replaced by the result of the filter function. This can be used to
     1644   *     reform generic objects into instances of classes, or to transform
     1645   *     date strings into Date objects.
     1646   *
     1647   * Returns:
     1648   * {Object} The return depends on the value of the type argument. If type
     1649   *     is "FeatureCollection" (the default), the return will be an array
     1650   *     of <ZOO.Feature>. If type is "Geometry", the input json
     1651   *     must represent a single geometry, and the return will be an
     1652   *     <ZOO.Geometry>.  If type is "Feature", the input json must
     1653   *     represent a single feature, and the return will be an
     1654   *     <ZOO.Feature>.
     1655   */
    13501656  read: function(json, type, filter) {
    13511657    type = (type) ? type : "FeatureCollection";
     
    13571663      obj = json;
    13581664    if(!obj) {
    1359       //OpenLayers.Console.error("Bad JSON: " + json);
     1665      //ZOO.Console.error("Bad JSON: " + json);
    13601666    } else if(typeof(obj.type) != "string") {
    1361       //OpenLayers.Console.error("Bad GeoJSON - no type: " + json);
     1667      //ZOO.Console.error("Bad GeoJSON - no type: " + json);
    13621668    } else if(this.isValidType(obj, type)) {
    13631669      switch(type) {
     
    13661672            results = this.parseGeometry(obj);
    13671673          } catch(err) {
    1368             //OpenLayers.Console.error(err);
     1674            //ZOO.Console.error(err);
    13691675          }
    13701676          break;
     
    13741680            results.type = "Feature";
    13751681          } catch(err) {
    1376             //OpenLayers.Console.error(err);
     1682            //ZOO.Console.error(err);
    13771683          }
    13781684          break;
     
    13861692              } catch(err) {
    13871693                results = null;
    1388                 //OpenLayers.Console.error(err);
     1694                //ZOO.Console.error(err);
    13891695              }
    13901696              break;
     
    13951701                } catch(err) {
    13961702                  results = null;
    1397                   //OpenLayers.Console.error(err);
     1703                  //ZOO.Console.error(err);
    13981704                }
    13991705              }
     
    14051711              } catch(err) {
    14061712                results = null;
    1407                 //OpenLayers.Console.error(err);
     1713                //ZOO.Console.error(err);
    14081714              }
    14091715          }
     
    14131719    return results;
    14141720  },
     1721  /**
     1722   * Method: isValidType
     1723   * Check if a GeoJSON object is a valid representative of the given type.
     1724   *
     1725   * Returns:
     1726   * {Boolean} The object is valid GeoJSON object of the given type.
     1727   */
    14151728  isValidType: function(obj, type) {
    14161729    var valid = false;
     
    14221735              obj.type) == -1) {
    14231736          // unsupported geometry type
    1424           //OpenLayers.Console.error("Unsupported geometry type: " +obj.type);
     1737          //ZOO.Console.error("Unsupported geometry type: " +obj.type);
    14251738        } else {
    14261739          valid = true;
     
    14361749          valid = true;
    14371750        } else {
    1438           //OpenLayers.Console.error("Cannot convert types from " +obj.type + " to " + type);
     1751          //ZOO.Console.error("Cannot convert types from " +obj.type + " to " + type);
    14391752        }
    14401753    }
    14411754    return valid;
    14421755  },
     1756  /**
     1757   * Method: parseFeature
     1758   * Convert a feature object from GeoJSON into an
     1759   *     <ZOO.Feature>.
     1760   *
     1761   * Parameters:
     1762   * obj - {Object} An object created from a GeoJSON object
     1763   *
     1764   * Returns:
     1765   * {<ZOO.Feature>} A feature.
     1766   */
    14431767  parseFeature: function(obj) {
    14441768    var feature, geometry, attributes, bbox;
     
    14581782    return feature;
    14591783  },
     1784  /**
     1785   * Method: parseGeometry
     1786   * Convert a geometry object from GeoJSON into an <ZOO.Geometry>.
     1787   *
     1788   * Parameters:
     1789   * obj - {Object} An object created from a GeoJSON object
     1790   *
     1791   * Returns:
     1792   * {<ZOO.Geometry>} A geometry.
     1793   */
    14601794  parseGeometry: function(obj) {
    14611795    if (obj == null)
     
    14991833    return geometry;
    15001834  },
     1835  /**
     1836   * Property: parseCoords
     1837   * Object with properties corresponding to the GeoJSON geometry types.
     1838   *     Property values are functions that do the actual parsing.
     1839   */
    15011840  parseCoords: {
     1841    /**
     1842     * Method: parseCoords.point
     1843     * Convert a coordinate array from GeoJSON into an
     1844     *     <ZOO.Geometry.Point>.
     1845     *
     1846     * Parameters:
     1847     * array - {Object} The coordinates array from the GeoJSON fragment.
     1848     *
     1849     * Returns:
     1850     * {<ZOO.Geometry.Point>} A geometry.
     1851     */
    15021852    "point": function(array) {
    15031853      if(array.length != 2) {
     
    15061856      return new ZOO.Geometry.Point(array[0], array[1]);
    15071857    },
     1858    /**
     1859     * Method: parseCoords.multipoint
     1860     * Convert a coordinate array from GeoJSON into an
     1861     *     <ZOO.Geometry.MultiPoint>.
     1862     *
     1863     * Parameters:
     1864     * array - {Object} The coordinates array from the GeoJSON fragment.
     1865     *
     1866     * Returns:
     1867     * {<ZOO.Geometry.MultiPoint>} A geometry.
     1868     */
    15081869    "multipoint": function(array) {
    15091870      var points = [];
     
    15191880      return new ZOO.Geometry.MultiPoint(points);
    15201881    },
     1882    /**
     1883     * Method: parseCoords.linestring
     1884     * Convert a coordinate array from GeoJSON into an
     1885     *     <ZOO.Geometry.LineString>.
     1886     *
     1887     * Parameters:
     1888     * array - {Object} The coordinates array from the GeoJSON fragment.
     1889     *
     1890     * Returns:
     1891     * {<ZOO.Geometry.LineString>} A geometry.
     1892     */
    15211893    "linestring": function(array) {
    15221894      var points = [];
     
    15321904      return new ZOO.Geometry.LineString(points);
    15331905    },
     1906    /**
     1907     * Method: parseCoords.multilinestring
     1908     * Convert a coordinate array from GeoJSON into an
     1909     *     <ZOO.Geometry.MultiLineString>.
     1910     *
     1911     * Parameters:
     1912     * array - {Object} The coordinates array from the GeoJSON fragment.
     1913     *
     1914     * Returns:
     1915     * {<ZOO.Geometry.MultiLineString>} A geometry.
     1916     */
    15341917    "multilinestring": function(array) {
    15351918      var lines = [];
     
    15451928      return new ZOO.Geometry.MultiLineString(lines);
    15461929    },
     1930    /**
     1931     * Method: parseCoords.polygon
     1932     * Convert a coordinate array from GeoJSON into an
     1933     *     <ZOO.Geometry.Polygon>.
     1934     *
     1935     * Parameters:
     1936     * array - {Object} The coordinates array from the GeoJSON fragment.
     1937     *
     1938     * Returns:
     1939     * {<ZOO.Geometry.Polygon>} A geometry.
     1940     */
    15471941    "polygon": function(array) {
    15481942      var rings = [];
     
    15591953      return new ZOO.Geometry.Polygon(rings);
    15601954    },
     1955    /**
     1956     * Method: parseCoords.multipolygon
     1957     * Convert a coordinate array from GeoJSON into an
     1958     *     <ZOO.Geometry.MultiPolygon>.
     1959     *
     1960     * Parameters:
     1961     * array - {Object} The coordinates array from the GeoJSON fragment.
     1962     *
     1963     * Returns:
     1964     * {<ZOO.Geometry.MultiPolygon>} A geometry.
     1965     */
    15611966    "multipolygon": function(array) {
    15621967      var polys = [];
     
    15721977      return new ZOO.Geometry.MultiPolygon(polys);
    15731978    },
     1979    /**
     1980     * Method: parseCoords.box
     1981     * Convert a coordinate array from GeoJSON into an
     1982     *     <ZOO.Geometry.Polygon>.
     1983     *
     1984     * Parameters:
     1985     * array - {Object} The coordinates array from the GeoJSON fragment.
     1986     *
     1987     * Returns:
     1988     * {<ZOO.Geometry.Polygon>} A geometry.
     1989     */
    15741990    "box": function(array) {
    15751991      if(array.length != 2) {
     
    15872003    }
    15882004  },
     2005  /**
     2006   * Method: write
     2007   * Serialize a feature, geometry, array of features into a GeoJSON string.
     2008   *
     2009   * Parameters:
     2010   * obj - {Object} An <ZOO.Feature>, <ZOO.Geometry>,
     2011   *     or an array of features.
     2012   * pretty - {Boolean} Structure the output with newlines and indentation.
     2013   *     Default is false.
     2014   *
     2015   * Returns:
     2016   * {String} The GeoJSON string representation of the input geometry,
     2017   *     features, or array of features.
     2018   */
    15892019  write: function(obj, pretty) {
    15902020    var geojson = {
     
    16172047                                                 [geojson, pretty]);
    16182048  },
     2049  /**
     2050   * Method: createCRSObject
     2051   * Create the CRS object for an object.
     2052   *
     2053   * Parameters:
     2054   * object - {<ZOO.Feature>}
     2055   *
     2056   * Returns:
     2057   * {Object} An object which can be assigned to the crs property
     2058   * of a GeoJSON object.
     2059   */
    16192060  createCRSObject: function(object) {
    16202061    //var proj = object.layer.projection.toString();
     
    16412082    return crs;
    16422083  },
     2084  /**
     2085   * Property: extract
     2086   * Object with properties corresponding to the GeoJSON types.
     2087   *     Property values are functions that do the actual value extraction.
     2088   */
    16432089  extract: {
     2090    /**
     2091     * Method: extract.feature
     2092     * Return a partial GeoJSON object representing a single feature.
     2093     *
     2094     * Parameters:
     2095     * feature - {<ZOO.Feature>}
     2096     *
     2097     * Returns:
     2098     * {Object} An object representing the point.
     2099     */
    16442100    'feature': function(feature) {
    16452101      var geom = this.extract.geometry.apply(this, [feature.geometry]);
     
    16512107      };
    16522108    },
     2109    /**
     2110     * Method: extract.geometry
     2111     * Return a GeoJSON object representing a single geometry.
     2112     *
     2113     * Parameters:
     2114     * geometry - {<ZOO.Geometry>}
     2115     *
     2116     * Returns:
     2117     * {Object} An object representing the geometry.
     2118     */
    16532119    'geometry': function(geometry) {
    16542120      if (geometry == null)
     
    16742140      return json;
    16752141    },
     2142    /**
     2143     * Method: extract.point
     2144     * Return an array of coordinates from a point.
     2145     *
     2146     * Parameters:
     2147     * point - {<ZOO.Geometry.Point>}
     2148     *
     2149     * Returns:
     2150     * {Array} An array of coordinates representing the point.
     2151     */
    16762152    'point': function(point) {
    16772153      return [point.x, point.y];
    16782154    },
     2155    /**
     2156     * Method: extract.multipoint
     2157     * Return an array of coordinates from a multipoint.
     2158     *
     2159     * Parameters:
     2160     * multipoint - {<ZOO.Geometry.MultiPoint>}
     2161     *
     2162     * Returns:
     2163     * {Array} An array of point coordinate arrays representing
     2164     *     the multipoint.
     2165     */
    16792166    'multipoint': function(multipoint) {
    16802167      var array = [];
     
    16842171      return array;
    16852172    },
     2173    /**
     2174     * Method: extract.linestring
     2175     * Return an array of coordinate arrays from a linestring.
     2176     *
     2177     * Parameters:
     2178     * linestring - {<ZOO.Geometry.LineString>}
     2179     *
     2180     * Returns:
     2181     * {Array} An array of coordinate arrays representing
     2182     *     the linestring.
     2183     */
    16862184    'linestring': function(linestring) {
    16872185      var array = [];
     
    16912189      return array;
    16922190    },
     2191    /**
     2192     * Method: extract.multilinestring
     2193     * Return an array of linestring arrays from a linestring.
     2194     *
     2195     * Parameters:
     2196     * multilinestring - {<ZOO.Geometry.MultiLineString>}
     2197     *
     2198     * Returns:
     2199     * {Array} An array of linestring arrays representing
     2200     *     the multilinestring.
     2201     */
    16932202    'multilinestring': function(multilinestring) {
    16942203      var array = [];
     
    16982207      return array;
    16992208    },
     2209    /**
     2210     * Method: extract.polygon
     2211     * Return an array of linear ring arrays from a polygon.
     2212     *
     2213     * Parameters:
     2214     * polygon - {<ZOO.Geometry.Polygon>}
     2215     *
     2216     * Returns:
     2217     * {Array} An array of linear ring arrays representing the polygon.
     2218     */
    17002219    'polygon': function(polygon) {
    17012220      var array = [];
     
    17052224      return array;
    17062225    },
     2226    /**
     2227     * Method: extract.multipolygon
     2228     * Return an array of polygon arrays from a multipolygon.
     2229     *
     2230     * Parameters:
     2231     * multipolygon - {<ZOO.Geometry.MultiPolygon>}
     2232     *
     2233     * Returns:
     2234     * {Array} An array of polygon arrays representing
     2235     *     the multipolygon
     2236     */
    17072237    'multipolygon': function(multipolygon) {
    17082238      var array = [];
     
    17122242      return array;
    17132243    },
     2244    /**
     2245     * Method: extract.collection
     2246     * Return an array of geometries from a geometry collection.
     2247     *
     2248     * Parameters:
     2249     * collection - {<ZOO.Geometry.Collection>}
     2250     *
     2251     * Returns:
     2252     * {Array} An array of geometry objects representing the geometry
     2253     *     collection.
     2254     */
    17142255    'collection': function(collection) {
    17152256      var len = collection.components.length;
     
    17252266  CLASS_NAME: 'ZOO.Format.GeoJSON'
    17262267});
     2268/**
     2269 * Class: ZOO.Format.KML
     2270 * Read/Write KML. Create a new instance with the <ZOO.Format.KML>
     2271 *     constructor.
     2272 *
     2273 * Inherits from:
     2274 *  - <ZOO.Format>
     2275 */
    17272276ZOO.Format.KML = ZOO.Class(ZOO.Format, {
     2277  /**
     2278   * Property: kmlns
     2279   * {String} KML Namespace to use. Defaults to 2.2 namespace.
     2280   */
    17282281  kmlns: "http://www.opengis.net/kml/2.2",
     2282  /**
     2283   * Property: foldersName
     2284   * {String} Name of the folders.  Default is "ZOO export".
     2285   *          If set to null, no name element will be created.
     2286   */
    17292287  foldersName: "ZOO export",
     2288  /**
     2289   * Property: foldersDesc
     2290   * {String} Description of the folders. Default is "Exported on [date]."
     2291   *          If set to null, no description element will be created.
     2292   */
    17302293  foldersDesc: "Created on " + new Date(),
     2294  /**
     2295   * Property: placemarksDesc
     2296   * {String} Name of the placemarks.  Default is "No description available".
     2297   */
    17312298  placemarksDesc: "No description available",
     2299  /**
     2300   * Property: extractAttributes
     2301   * {Boolean} Extract attributes from KML.  Default is true.
     2302   *           Extracting styleUrls requires this to be set to true
     2303   */
    17322304  extractAttributes: true,
     2305  /**
     2306   * Constructor: ZOO.Format.KML
     2307   * Create a new parser for KML.
     2308   *
     2309   * Parameters:
     2310   * options - {Object} An optional object whose properties will be set on
     2311   *     this instance.
     2312   */
    17332313  initialize: function(options) {
    17342314    // compile regular expressions once instead of every time they are used
     
    17422322           straightBracket: (/\$\[(.*?)\]/g)
    17432323    };
     2324    // KML coordinates are always in longlat WGS84
     2325    this.externalProjection = new ZOO.Projection("EPSG:4326");
    17442326    ZOO.Format.prototype.initialize.apply(this, [options]);
    17452327  },
     2328  /**
     2329   * APIMethod: read
     2330   * Read data from a string, and return a list of features.
     2331   *
     2332   * Parameters:
     2333   * data    - {String} data to read/parse.
     2334   *
     2335   * Returns:
     2336   * {Array(<ZOO.Feature>)} List of features.
     2337   */
    17462338  read: function(data) {
    17472339    this.features = [];
     
    17522344    return this.features;
    17532345  },
     2346  /**
     2347   * Method: parseFeatures
     2348   * Loop through all Placemark nodes and parse them.
     2349   * Will create a list of features
     2350   *
     2351   * Parameters:
     2352   * nodes    - {Array} of {E4XElement} data to read/parse.
     2353   * options  - {Object} Hash of options
     2354   *
     2355   */
    17542356  parseFeatures: function(nodes) {
    17552357    var features = new Array(nodes.length());
     
    17612363    this.features = this.features.concat(features);
    17622364  },
     2365  /**
     2366   * Method: parseFeature
     2367   * This function is the core of the KML parsing code in ZOO.
     2368   *     It creates the geometries that are then attached to the returned
     2369   *     feature, and calls parseAttributes() to get attribute data out.
     2370   *
     2371   * Parameters:
     2372   * node - {E4XElement}
     2373   *
     2374   * Returns:
     2375   * {<ZOO.Feature>} A vector feature.
     2376   */
    17632377  parseFeature: function(node) {
     2378    // only accept one geometry per feature - look for highest "order"
    17642379    var order = ["MultiGeometry", "Polygon", "LineString", "Point"];
    17652380    var type, nodeList, geometry, parser;
     
    17762391          }                       
    17772392        }
     2393        // stop looking for different geometry types
    17782394        break;
    17792395      }
    17802396    }
     2397    // construct feature (optionally with attributes)
    17812398    var attributes;
    17822399    if(this.extractAttributes) {
     
    17892406    return feature;
    17902407  },
     2408  /**
     2409   * Property: parseGeometry
     2410   * Properties of this object are the functions that parse geometries based
     2411   *     on their type.
     2412   */
    17912413  parseGeometry: {
     2414    /**
     2415     * Method: parseGeometry.point
     2416     * Given a KML node representing a point geometry, create a ZOO
     2417     *     point geometry.
     2418     *
     2419     * Parameters:
     2420     * node - {E4XElement} A KML Point node.
     2421     *
     2422     * Returns:
     2423     * {<ZOO.Geometry.Point>} A point geometry.
     2424     */
    17922425    'point': function(node) {
    17932426      var coordString = node.*::coordinates.toString();
     
    18042437      return point;
    18052438    },
     2439    /**
     2440     * Method: parseGeometry.linestring
     2441     * Given a KML node representing a linestring geometry, create a
     2442     *     ZOO linestring geometry.
     2443     *
     2444     * Parameters:
     2445     * node - {E4XElement} A KML LineString node.
     2446     *
     2447     * Returns:
     2448     * {<ZOO.Geometry.LineString>} A linestring geometry.
     2449     */
    18062450    'linestring': function(node, ring) {
    18072451      var line = null;
     
    18382482      return line;
    18392483    },
     2484    /**
     2485     * Method: parseGeometry.polygon
     2486     * Given a KML node representing a polygon geometry, create a
     2487     *     ZOO polygon geometry.
     2488     *
     2489     * Parameters:
     2490     * node - {E4XElement} A KML Polygon node.
     2491     *
     2492     * Returns:
     2493     * {<ZOO.Geometry.Polygon>} A polygon geometry.
     2494     */
    18402495    'polygon': function(node) {
    18412496      var nodeList = node..*::LinearRing;
     
    18572512      return new ZOO.Geometry.Polygon(components);
    18582513    },
    1859     multigeometry: function(node) {
     2514    /**
     2515     * Method: parseGeometry.multigeometry
     2516     * Given a KML node representing a multigeometry, create a
     2517     *     ZOO geometry collection.
     2518     *
     2519     * Parameters:
     2520     * node - {E4XElement} A KML MultiGeometry node.
     2521     *
     2522     * Returns:
     2523     * {<ZOO.Geometry.Collection>} A geometry collection.
     2524     */
     2525    'multigeometry': function(node) {
    18602526      var child, parser;
    18612527      var parts = [];
     
    18722538    }
    18732539  },
     2540  /**
     2541   * Method: parseAttributes
     2542   *
     2543   * Parameters:
     2544   * node - {E4XElement}
     2545   *
     2546   * Returns:
     2547   * {Object} An attributes object.
     2548   */
    18742549  parseAttributes: function(node) {
    18752550    var attributes = {};
     
    18942569    return attributes;
    18952570  },
     2571  /**
     2572   * Method: parseExtendedData
     2573   * Parse ExtendedData from KML. Limited support for schemas/datatypes.
     2574   *     See http://code.google.com/apis/kml/documentation/kmlreference.html#extendeddata
     2575   *     for more information on extendeddata.
     2576   *
     2577   * Parameters:
     2578   * node - {E4XElement}
     2579   *
     2580   * Returns:
     2581   * {Object} An attributes object.
     2582   */
    18962583  parseExtendedData: function(node) {
    18972584    var attributes = {};
     
    19112598    return attributes;
    19122599  },
     2600  /**
     2601   * Method: write
     2602   * Accept Feature Collection, and return a string.
     2603   *
     2604   * Parameters:
     2605   * features - {Array(<ZOO.Feature>} An array of features.
     2606   *
     2607   * Returns:
     2608   * {String} A KML string.
     2609   */
    19132610  write: function(features) {
    19142611    if(!(features instanceof Array))
     
    19192616    folder.description = this.foldersDesc;
    19202617    for(var i=0, len=features.length; i<len; ++i) {
    1921       //folder.appendChild(this.createPlacemarkXML(features[i]));
    19222618      folder.Placemark[i] = this.createPlacemark(features[i]);
    19232619    }
    19242620    return kml.toXMLString();
    19252621  },
     2622  /**
     2623   * Method: createPlacemark
     2624   * Creates and returns a KML placemark node representing the given feature.
     2625   *
     2626   * Parameters:
     2627   * feature - {<ZOO.Feature>}
     2628   *
     2629   * Returns:
     2630   * {E4XElement}
     2631   */
    19262632  createPlacemark: function(feature) {
    19272633    var placemark = new XML('<Placemark xmlns="'+this.kmlns+'"></Placemark>');
     
    19352641    return placemark;
    19362642  },
     2643  /**
     2644   * Method: buildGeometryNode
     2645   * Builds and returns a KML geometry node with the given geometry.
     2646   *
     2647   * Parameters:
     2648   * geometry - {<ZOO.Geometry>}
     2649   *
     2650   * Returns:
     2651   * {E4XElement}
     2652   */
    19372653  buildGeometryNode: function(geometry) {
    19382654    if (this.internalProjection && this.externalProjection) {
     
    19502666    return node;
    19512667  },
     2668  /**
     2669   * Property: buildGeometry
     2670   * Object containing methods to do the actual geometry node building
     2671   *     based on geometry type.
     2672   */
    19522673  buildGeometry: {
     2674    /**
     2675     * Method: buildGeometry.point
     2676     * Given a ZOO point geometry, create a KML point.
     2677     *
     2678     * Parameters:
     2679     * geometry - {<ZOO.Geometry.Point>} A point geometry.
     2680     *
     2681     * Returns:
     2682     * {E4XElement} A KML point node.
     2683     */
    19532684    'point': function(geometry) {
    19542685      var kml = new XML('<Point xmlns="'+this.kmlns+'"></Point>');
     
    19562687      return kml;
    19572688    },
     2689    /**
     2690     * Method: buildGeometry.multipoint
     2691     * Given a ZOO multipoint geometry, create a KML
     2692     *     GeometryCollection.
     2693     *
     2694     * Parameters:
     2695     * geometry - {<ZOO.Geometry.MultiPoint>} A multipoint geometry.
     2696     *
     2697     * Returns:
     2698     * {E4XElement} A KML GeometryCollection node.
     2699     */
    19582700    'multipoint': function(geometry) {
    19592701      return this.buildGeometry.collection.apply(this, [geometry]);
    19602702    },
     2703    /**
     2704     * Method: buildGeometry.linestring
     2705     * Given a ZOO linestring geometry, create a KML linestring.
     2706     *
     2707     * Parameters:
     2708     * geometry - {<ZOO.Geometry.LineString>} A linestring geometry.
     2709     *
     2710     * Returns:
     2711     * {E4XElement} A KML linestring node.
     2712     */
    19612713    'linestring': function(geometry) {
    19622714      var kml = new XML('<LineString xmlns="'+this.kmlns+'"></LineString>');
     
    19642716      return kml;
    19652717    },
     2718    /**
     2719     * Method: buildGeometry.multilinestring
     2720     * Given a ZOO multilinestring geometry, create a KML
     2721     *     GeometryCollection.
     2722     *
     2723     * Parameters:
     2724     * geometry - {<ZOO.Geometry.MultiLineString>} A multilinestring geometry.
     2725     *
     2726     * Returns:
     2727     * {E4XElement} A KML GeometryCollection node.
     2728     */
    19662729    'multilinestring': function(geometry) {
    19672730      return this.buildGeometry.collection.apply(this, [geometry]);
    19682731    },
     2732    /**
     2733     * Method: buildGeometry.linearring
     2734     * Given a ZOO linearring geometry, create a KML linearring.
     2735     *
     2736     * Parameters:
     2737     * geometry - {<ZOO.Geometry.LinearRing>} A linearring geometry.
     2738     *
     2739     * Returns:
     2740     * {E4XElement} A KML linearring node.
     2741     */
    19692742    'linearring': function(geometry) {
    19702743      var kml = new XML('<LinearRing xmlns="'+this.kmlns+'"></LinearRing>');
     
    19722745      return kml;
    19732746    },
     2747    /**
     2748     * Method: buildGeometry.polygon
     2749     * Given a ZOO polygon geometry, create a KML polygon.
     2750     *
     2751     * Parameters:
     2752     * geometry - {<ZOO.Geometry.Polygon>} A polygon geometry.
     2753     *
     2754     * Returns:
     2755     * {E4XElement} A KML polygon node.
     2756     */
    19742757    'polygon': function(geometry) {
    19752758      var kml = new XML('<Polygon xmlns="'+this.kmlns+'"></Polygon>');
     
    19842767      return kml;
    19852768    },
     2769    /**
     2770     * Method: buildGeometry.multipolygon
     2771     * Given a ZOO multipolygon geometry, create a KML
     2772     *     GeometryCollection.
     2773     *
     2774     * Parameters:
     2775     * geometry - {<ZOO.Geometry.Point>} A multipolygon geometry.
     2776     *
     2777     * Returns:
     2778     * {E4XElement} A KML GeometryCollection node.
     2779     */
    19862780    'multipolygon': function(geometry) {
    19872781      return this.buildGeometry.collection.apply(this, [geometry]);
    19882782    },
     2783    /**
     2784     * Method: buildGeometry.collection
     2785     * Given a ZOO geometry collection, create a KML MultiGeometry.
     2786     *
     2787     * Parameters:
     2788     * geometry - {<ZOO.Geometry.Collection>} A geometry collection.
     2789     *
     2790     * Returns:
     2791     * {E4XElement} A KML MultiGeometry node.
     2792     */
    19892793    'collection': function(geometry) {
    19902794      var kml = new XML('<MultiGeometry xmlns="'+this.kmlns+'"></MultiGeometry>');
     
    19962800    }
    19972801  },
     2802  /**
     2803   * Method: buildCoordinatesNode
     2804   * Builds and returns the KML coordinates node with the given geometry
     2805   *     <coordinates>...</coordinates>
     2806   *
     2807   * Parameters:
     2808   * geometry - {<ZOO.Geometry>}
     2809   *
     2810   * Return:
     2811   * {E4XElement}
     2812   */
    19982813  buildCoordinatesNode: function(geometry) {
    19992814    var cooridnates = new XML('<coordinates xmlns="'+this.kmlns+'"></coordinates>');
     
    20172832  CLASS_NAME: 'ZOO.Format.KML'
    20182833});
     2834/**
     2835 * Class: ZOO.Format.GML
     2836 * Read/Write GML. Create a new instance with the <ZOO.Format.GML>
     2837 *     constructor.  Supports the GML simple features profile.
     2838 *
     2839 * Inherits from:
     2840 *  - <ZOO.Format>
     2841 */
    20192842ZOO.Format.GML = ZOO.Class(ZOO.Format, {
     2843  /**
     2844   * Property: schemaLocation
     2845   * {String} Schema location for a particular minor version.
     2846   */
    20202847  schemaLocation: "http://www.opengis.net/gml http://schemas.opengis.net/gml/2.1.2/feature.xsd",
     2848  /**
     2849   * Property: namespaces
     2850   * {Object} Mapping of namespace aliases to namespace URIs.
     2851   */
    20212852  namespaces: {
    20222853    ogr: "http://ogr.maptools.org/",
     
    20262857    wfs: "http://www.opengis.net/wfs" // this is a convenience for reading wfs:FeatureCollection
    20272858  },
     2859  /**
     2860   * Property: defaultPrefix
     2861   */
    20282862  defaultPrefix: 'ogr',
     2863  /**
     2864   * Property: collectionName
     2865   * {String} Name of featureCollection element.
     2866   */
    20292867  collectionName: "FeatureCollection",
     2868  /*
     2869   * Property: featureName
     2870   * {String} Element name for features. Default is "sql_statement".
     2871   */
    20302872  featureName: "sql_statement",
     2873  /**
     2874   * Property: geometryName
     2875   * {String} Name of geometry element.  Defaults to "geometryProperty".
     2876   */
    20312877  geometryName: "geometryProperty",
     2878  /**
     2879   * Property: xy
     2880   * {Boolean} Order of the GML coordinate true:(x,y) or false:(y,x)
     2881   * Changing is not recommended, a new Format should be instantiated.
     2882   */
    20322883  xy: true,
     2884  /**
     2885   * Constructor: ZOO.Format.GML
     2886   * Create a new parser for GML.
     2887   *
     2888   * Parameters:
     2889   * options - {Object} An optional object whose properties will be set on
     2890   *     this instance.
     2891   */
    20332892  initialize: function(options) {
    20342893    // compile regular expressions once instead of every time they are used
     
    20412900    ZOO.Format.prototype.initialize.apply(this, [options]);
    20422901  },
     2902  /**
     2903   * Method: read
     2904   * Read data from a string, and return a list of features.
     2905   *
     2906   * Parameters:
     2907   * data - {String} data to read/parse.
     2908   *
     2909   * Returns:
     2910   * {Array(<ZOO.Feature>)} An array of features.
     2911   */
    20432912  read: function(data) {
    20442913    this.features = [];
     
    20572926    return features;
    20582927  },
     2928  /**
     2929   * Method: parseFeature
     2930   * This function is the core of the GML parsing code in ZOO.
     2931   *    It creates the geometries that are then attached to the returned
     2932   *    feature, and calls parseAttributes() to get attribute data out.
     2933   *   
     2934   * Parameters:
     2935   * node - {E4XElement} A GML feature node.
     2936   */
    20592937  parseFeature: function(node) {
    20602938    // only accept one geometry per feature - look for highest "order"
     
    20762954          }                       
    20772955        }
     2956        // stop looking for different geometry types
    20782957        break;
    20792958      }
     
    20812960    var attributes;
    20822961    if(this.extractAttributes) {
    2083       //attributes = this.parseAttributes(node);
     2962      attributes = this.parseAttributes(node);
    20842963    }
    20852964    var feature = new ZOO.Feature(geometry, attributes);
    20862965    return feature;
    20872966  },
     2967  /**
     2968   * Property: parseGeometry
     2969   * Properties of this object are the functions that parse geometries based
     2970   *     on their type.
     2971   */
    20882972  parseGeometry: {
     2973    /**
     2974     * Method: parseGeometry.point
     2975     * Given a GML node representing a point geometry, create a ZOO
     2976     *     point geometry.
     2977     *
     2978     * Parameters:
     2979     * node - {E4XElement} A GML node.
     2980     *
     2981     * Returns:
     2982     * {<ZOO.Geometry.Point>} A point geometry.
     2983     */
    20892984    'point': function(node) {
    20902985      /**
     
    21313026        return new ZOO.Geometry.Point(coords[1],coords[0],coords[2]);
    21323027    },
     3028    /**
     3029     * Method: parseGeometry.multipoint
     3030     * Given a GML node representing a multipoint geometry, create a
     3031     *     ZOO multipoint geometry.
     3032     *
     3033     * Parameters:
     3034     * node - {E4XElement} A GML node.
     3035     *
     3036     * Returns:
     3037     * {<ZOO.Geometry.MultiPoint>} A multipoint geometry.
     3038     */
    21333039    'multipoint': function(node) {
    21343040      var nodeList = node..*::Point;
     
    21443050      return new ZOO.Geometry.MultiPoint(components);
    21453051    },
     3052    /**
     3053     * Method: parseGeometry.linestring
     3054     * Given a GML node representing a linestring geometry, create a
     3055     *     ZOO linestring geometry.
     3056     *
     3057     * Parameters:
     3058     * node - {E4XElement} A GML node.
     3059     *
     3060     * Returns:
     3061     * {<ZOO.Geometry.LineString>} A linestring geometry.
     3062     */
    21463063    'linestring': function(node, ring) {
    21473064      /**
     
    22003117      return line;
    22013118    },
     3119    /**
     3120     * Method: parseGeometry.multilinestring
     3121     * Given a GML node representing a multilinestring geometry, create a
     3122     *     ZOO multilinestring geometry.
     3123     *
     3124     * Parameters:
     3125     * node - {E4XElement} A GML node.
     3126     *
     3127     * Returns:
     3128     * {<ZOO.Geometry.MultiLineString>} A multilinestring geometry.
     3129     */
    22023130    'multilinestring': function(node) {
    22033131      var nodeList = node..*::LineString;
     
    22133141      return new ZOO.Geometry.MultiLineString(components);
    22143142    },
     3143    /**
     3144     * Method: parseGeometry.polygon
     3145     * Given a GML node representing a polygon geometry, create a
     3146     *     ZOO polygon geometry.
     3147     *
     3148     * Parameters:
     3149     * node - {E4XElement} A GML node.
     3150     *
     3151     * Returns:
     3152     * {<ZOO.Geometry.Polygon>} A polygon geometry.
     3153     */
    22153154    'polygon': function(node) {
    22163155      nodeList = node..*::LinearRing;
     
    22273166      return new ZOO.Geometry.Polygon(components);
    22283167    },
     3168    /**
     3169     * Method: parseGeometry.multipolygon
     3170     * Given a GML node representing a multipolygon geometry, create a
     3171     *     ZOO multipolygon geometry.
     3172     *
     3173     * Parameters:
     3174     * node - {E4XElement} A GML node.
     3175     *
     3176     * Returns:
     3177     * {<ZOO.Geometry.MultiPolygon>} A multipolygon geometry.
     3178     */
    22293179    'multipolygon': function(node) {
    22303180      var nodeList = node..*::Polygon;
     
    22403190      return new ZOO.Geometry.MultiPolygon(components);
    22413191    },
     3192    /**
     3193     * Method: parseGeometry.polygon
     3194     * Given a GML node representing an envelope, create a
     3195     *     ZOO polygon geometry.
     3196     *
     3197     * Parameters:
     3198     * node - {E4XElement} A GML node.
     3199     *
     3200     * Returns:
     3201     * {<ZOO.Geometry.Polygon>} A polygon geometry.
     3202     */
    22423203    'envelope': function(node) {
    22433204      var components = [];
     
    22863247    }
    22873248  },
     3249  /**
     3250   * Method: parseAttributes
     3251   *
     3252   * Parameters:
     3253   * node - {<E4XElement>}
     3254   *
     3255   * Returns:
     3256   * {Object} An attributes object.
     3257   */
     3258  parseAttributes: function(node) {
     3259    var attributes = {};
     3260    // assume attributes are children of the first type 1 child
     3261    var childNode = node.*::*[0];
     3262    var child, grandchildren;
     3263    var children = childNode.*::*;
     3264    for(var i=0, len=children.length(); i<len; ++i) {
     3265      child = children[i];
     3266      grandchildren = child..*::*;
     3267      if(grandchildren.length() == 1) {
     3268        var name = child.localName();
     3269        var value = child.toString();
     3270        if (value) {
     3271          value = value.replace(this.regExes.trimSpace, "");
     3272          attributes[name] = value;
     3273        } else
     3274          attributes[name] = null;
     3275      }
     3276    }
     3277    return attributes;
     3278  },
     3279  /**
     3280   * Method: write
     3281   * Generate a GML document string given a list of features.
     3282   *
     3283   * Parameters:
     3284   * features - {Array(<ZOO.Feature>)} List of features to
     3285   *     serialize into a string.
     3286   *
     3287   * Returns:
     3288   * {String} A string representing the GML document.
     3289   */
    22883290  write: function(features) {
    22893291    if(!(features instanceof Array)) {
     
    22943296    var gml = new XML('<'+name+' xmlns:'+pfx+'="'+this.namespaces[pfx]+'" xmlns:gml="'+this.namespaces['gml']+'" xmlns:xsi="'+this.namespaces['xsi']+'" xsi:schemaLocation="'+this.schemaLocation+'"></'+name+'>');
    22953297    for(var i=0; i<features.length; i++) {
    2296       gml.*::*[i] = this.createFeatureXML(features[i]);
     3298      gml.*::*[i] = this.createFeature(features[i]);
    22973299    }
    22983300    return gml.toXMLString();
    22993301  },
    2300   createFeatureXML: function(feature) {
     3302  /**
     3303   * Method: createFeature
     3304   * Accept an ZOO.Feature, and build a GML node for it.
     3305   *
     3306   * Parameters:
     3307   * feature - {<ZOO.Feature>} The feature to be built as GML.
     3308   *
     3309   * Returns:
     3310   * {E4XElement} A node reprensting the feature in GML.
     3311   */
     3312  createFeature: function(feature) {
    23013313    var pfx = this.defaultPrefix;
    23023314    var name = pfx+':'+this.featureName;
     
    23113323    return gml;
    23123324  },
     3325  /**
     3326   * Method: buildGeometryNode
     3327   *
     3328   * Parameters:
     3329   * geometry - {<ZOO.Geometry>} The geometry to be built as GML.
     3330   *
     3331   * Returns:
     3332   * {E4XElement} A node reprensting the geometry in GML.
     3333   */
    23133334  buildGeometryNode: function(geometry) {
    23143335    if (this.externalProjection && this.internalProjection) {
     
    23273348    return gml;
    23283349  },
     3350  /**
     3351   * Property: buildGeometry
     3352   * Object containing methods to do the actual geometry node building
     3353   *     based on geometry type.
     3354   */
    23293355  buildGeometry: {
     3356    /**
     3357     * Method: buildGeometry.point
     3358     * Given a ZOO point geometry, create a GML point.
     3359     *
     3360     * Parameters:
     3361     * geometry - {<ZOO.Geometry.Point>} A point geometry.
     3362     *
     3363     * Returns:
     3364     * {E4XElement} A GML point node.
     3365     */
    23303366    'point': function(geometry) {
    23313367      var gml = new XML('<gml:Point xmlns:gml="'+this.namespaces['gml']+'"></gml:Point>');
     
    23333369      return gml;
    23343370    },
     3371    /**
     3372     * Method: buildGeometry.multipoint
     3373     * Given a ZOO multipoint geometry, create a GML multipoint.
     3374     *
     3375     * Parameters:
     3376     * geometry - {<ZOO.Geometry.MultiPoint>} A multipoint geometry.
     3377     *
     3378     * Returns:
     3379     * {E4XElement} A GML multipoint node.
     3380     */
    23353381    'multipoint': function(geometry) {
    23363382      var gml = new XML('<gml:MultiPoint xmlns:gml="'+this.namespaces['gml']+'"></gml:MultiPoint>');
     
    23443390      return gml;           
    23453391    },
     3392    /**
     3393     * Method: buildGeometry.linestring
     3394     * Given a ZOO linestring geometry, create a GML linestring.
     3395     *
     3396     * Parameters:
     3397     * geometry - {<ZOO.Geometry.LineString>} A linestring geometry.
     3398     *
     3399     * Returns:
     3400     * {E4XElement} A GML linestring node.
     3401     */
    23463402    'linestring': function(geometry) {
    23473403      var gml = new XML('<gml:LineString xmlns:gml="'+this.namespaces['gml']+'"></gml:LineString>');
     
    23493405      return gml;
    23503406    },
     3407    /**
     3408     * Method: buildGeometry.multilinestring
     3409     * Given a ZOO multilinestring geometry, create a GML
     3410     *     multilinestring.
     3411     *
     3412     * Parameters:
     3413     * geometry - {<ZOO.Geometry.MultiLineString>} A multilinestring
     3414     *     geometry.
     3415     *
     3416     * Returns:
     3417     * {E4XElement} A GML multilinestring node.
     3418     */
    23513419    'multilinestring': function(geometry) {
    23523420      var gml = new XML('<gml:MultiLineString xmlns:gml="'+this.namespaces['gml']+'"></gml:MultiLineString>');
     
    23603428      return gml;           
    23613429    },
     3430    /**
     3431     * Method: buildGeometry.linearring
     3432     * Given a ZOO linearring geometry, create a GML linearring.
     3433     *
     3434     * Parameters:
     3435     * geometry - {<ZOO.Geometry.LinearRing>} A linearring geometry.
     3436     *
     3437     * Returns:
     3438     * {E4XElement} A GML linearring node.
     3439     */
    23623440    'linearring': function(geometry) {
    23633441      var gml = new XML('<gml:LinearRing xmlns:gml="'+this.namespaces['gml']+'"></gml:LinearRing>');
     
    23653443      return gml;
    23663444    },
     3445    /**
     3446     * Method: buildGeometry.polygon
     3447     * Given an ZOO polygon geometry, create a GML polygon.
     3448     *
     3449     * Parameters:
     3450     * geometry - {<ZOO.Geometry.Polygon>} A polygon geometry.
     3451     *
     3452     * Returns:
     3453     * {E4XElement} A GML polygon node.
     3454     */
    23673455    'polygon': function(geometry) {
    23683456      var gml = new XML('<gml:Polygon xmlns:gml="'+this.namespaces['gml']+'"></gml:Polygon>');
     
    23773465      return gml;
    23783466    },
     3467    /**
     3468     * Method: buildGeometry.multipolygon
     3469     * Given a ZOO multipolygon geometry, create a GML multipolygon.
     3470     *
     3471     * Parameters:
     3472     * geometry - {<ZOO.Geometry.MultiPolygon>} A multipolygon
     3473     *     geometry.
     3474     *
     3475     * Returns:
     3476     * {E4XElement} A GML multipolygon node.
     3477     */
    23793478    'multipolygon': function(geometry) {
    23803479      var gml = new XML('<gml:MultiPolygon xmlns:gml="'+this.namespaces['gml']+'"></gml:MultiPolygon>');
     
    23873486      }
    23883487      return gml;           
    2389     },
    2390     'bounds': function(bounds) {
    2391       var gml = new XML('<gml:Box xmlns:gml="'+this.namespaces['gml']+'"></gml:Box>');
    2392       gml.*::*[0] = this.buildCoordinatesNode(bounds);
    2393       return gml;
    2394     }
    2395   },
     3488    }
     3489  },
     3490  /**
     3491   * Method: buildCoordinatesNode
     3492   * builds the coordinates XmlNode
     3493   * (code)
     3494   * <gml:coordinates decimal="." cs="," ts=" ">...</gml:coordinates>
     3495   * (end)
     3496   * Parameters:
     3497   * geometry - {<ZOO.Geometry>}
     3498   *
     3499   * Returns:
     3500   * {E4XElement} created E4XElement
     3501   */
    23963502  buildCoordinatesNode: function(geometry) {
    23973503    var parts = [];
     
    24093515  CLASS_NAME: 'ZOO.Format.GML'
    24103516});
     3517/**
     3518 * Class: ZOO.Format.WPS
     3519 * Read/Write WPS. Create a new instance with the <ZOO.Format.WPS>
     3520 *     constructor. Supports only parseExecuteResponse.
     3521 *
     3522 * Inherits from:
     3523 *  - <ZOO.Format>
     3524 */
    24113525ZOO.Format.WPS = ZOO.Class(ZOO.Format, {
     3526  /**
     3527   * Property: schemaLocation
     3528   * {String} Schema location for a particular minor version.
     3529   */
    24123530  schemaLocation: "http://www.opengis.net/wps/1.0.0/../wpsExecute_request.xsd",
     3531  /**
     3532   * Property: namespaces
     3533   * {Object} Mapping of namespace aliases to namespace URIs.
     3534   */
    24133535  namespaces: {
    24143536    ows: "http://www.opengis.net/ows/1.1",
     
    24173539    xsi: "http://www.w3.org/2001/XMLSchema-instance",
    24183540  },
     3541  /**
     3542   * Method: read
     3543   *
     3544   * Parameters:
     3545   * data - {String} A WPS xml document
     3546   *
     3547   * Returns:
     3548   * {Object} Execute response.
     3549   */
    24193550  read:function(data) {
    24203551    data = data.replace(/^<\?xml\s+version\s*=\s*(["'])[^\1]+\1[^?]*\?>/, "");
     
    24273558    }
    24283559  },
     3560  /**
     3561   * Method: parseExecuteResponse
     3562   *
     3563   * Parameters:
     3564   * node - {E4XElement} A WPS ExecuteResponse document
     3565   *
     3566   * Returns:
     3567   * {Object} Execute response.
     3568   */
    24293569  parseExecuteResponse: function(node) {
    24303570    var outputs = node.*::ProcessOutputs.*::Output;
     
    24393579      return null;
    24403580  },
     3581  /**
     3582   * Property: parseData
     3583   * Object containing methods to analyse data response.
     3584   */
    24413585  parseData: {
     3586    /**
     3587     * Method: parseData.complexdata
     3588     * Given an Object representing the WPS complex data response.
     3589     *
     3590     * Parameters:
     3591     * node - {E4XElement} A WPS node.
     3592     *
     3593     * Returns:
     3594     * {Object} A WPS complex data response.
     3595     */
    24423596    'complexdata': function(node) {
    24433597      var result = {value:node.toString()};
     
    24503604      return result;
    24513605    },
     3606    /**
     3607     * Method: parseData.literaldata
     3608     * Given an Object representing the WPS literal data response.
     3609     *
     3610     * Parameters:
     3611     * node - {E4XElement} A WPS node.
     3612     *
     3613     * Returns:
     3614     * {Object} A WPS literal data response.
     3615     */
    24523616    'literaldata': function(node) {
    24533617      var result = {value:node.toString()};
     
    24623626});
    24633627
    2464 
     3628/**
     3629 * Class: ZOO.Feature
     3630 * Vector features use the ZOO.Geometry classes as geometry description.
     3631 * They have an 'attributes' property, which is the data object
     3632 */
    24653633ZOO.Feature = ZOO.Class({
     3634  /**
     3635   * Property: fid
     3636   * {String}
     3637   */
    24663638  fid: null,
     3639  /**
     3640   * Property: geometry
     3641   * {<ZOO.Geometry>}
     3642   */
    24673643  geometry: null,
     3644  /**
     3645   * Property: attributes
     3646   * {Object} This object holds arbitrary properties that describe the
     3647   *     feature.
     3648   */
    24683649  attributes: null,
     3650  /**
     3651   * Property: bounds
     3652   * {<ZOO.Bounds>} The box bounding that feature's geometry, that
     3653   *     property can be set by an <ZOO.Format> object when
     3654   *     deserializing the feature, so in most cases it represents an
     3655   *     information set by the server.
     3656   */
    24693657  bounds: null,
     3658  /**
     3659   * Constructor: ZOO.Feature
     3660   * Create a vector feature.
     3661   *
     3662   * Parameters:
     3663   * geometry - {<ZOO.Geometry>} The geometry that this feature
     3664   *     represents.
     3665   * attributes - {Object} An optional object that will be mapped to the
     3666   *     <attributes> property.
     3667   */
    24703668  initialize: function(geometry, attributes) {
    24713669    this.geometry = geometry ? geometry : null;
     
    24743672      this.attributes = ZOO.extend(this.attributes,attributes);
    24753673  },
     3674  /**
     3675   * Method: destroy
     3676   * nullify references to prevent circular references and memory leaks
     3677   */
    24763678  destroy: function() {
    24773679    this.geometry = null;
    24783680  },
     3681  /**
     3682   * Method: clone
     3683   * Create a clone of this vector feature.  Does not set any non-standard
     3684   *     properties.
     3685   *
     3686   * Returns:
     3687   * {<ZOO.Feature>} An exact clone of this vector feature.
     3688   */
    24793689  clone: function () {
    24803690    return new ZOO.Feature(this.geometry ? this.geometry.clone() : null,
    24813691            this.attributes);
    24823692  },
     3693  /**
     3694   * Method: move
     3695   * Moves the feature and redraws it at its new location
     3696   *
     3697   * Parameters:
     3698   * x - {Float}
     3699   * y - {Float}
     3700   */
    24833701  move: function(x, y) {
    24843702    if(!this.geometry.move)
     
    24913709});
    24923710
     3711/**
     3712 * Class: ZOO.Geometry
     3713 * A Geometry is a description of a geographic object. Create an instance
     3714 * of this class with the <ZOO.Geometry> constructor. This is a base class,
     3715 * typical geometry types are described by subclasses of this class.
     3716 */
    24933717ZOO.Geometry = ZOO.Class({
     3718  /**
     3719   * Property: id
     3720   * {String} A unique identifier for this geometry.
     3721   */
    24943722  id: null,
     3723  /**
     3724   * Property: parent
     3725   * {<ZOO.Geometry>}This is set when a Geometry is added as component
     3726   * of another geometry
     3727   */
    24953728  parent: null,
     3729  /**
     3730   * Property: bounds
     3731   * {<ZOO.Bounds>} The bounds of this geometry
     3732   */
    24963733  bounds: null,
     3734  /**
     3735   * Constructor: ZOO.Geometry
     3736   * Creates a geometry object. 
     3737   */
    24973738  initialize: function() {
    24983739    //generate unique id
    24993740  },
     3741  /**
     3742   * Method: destroy
     3743   * Destroy this geometry.
     3744   */
    25003745  destroy: function() {
    25013746    this.id = null;
    25023747    this.bounds = null;
    25033748  },
     3749  /**
     3750   * Method: clone
     3751   * Create a clone of this geometry.  Does not set any non-standard
     3752   *     properties of the cloned geometry.
     3753   *
     3754   * Returns:
     3755   * {<ZOO.Geometry>} An exact clone of this geometry.
     3756   */
    25043757  clone: function() {
    25053758    return new ZOO.Geometry();
    25063759  },
     3760  /**
     3761   * Method: extendBounds
     3762   * Extend the existing bounds to include the new bounds.
     3763   * If geometry's bounds is not yet set, then set a new Bounds.
     3764   *
     3765   * Parameters:
     3766   * newBounds - {<ZOO.Bounds>}
     3767   */
    25073768  extendBounds: function(newBounds){
    25083769    var bounds = this.getBounds();
     
    25123773      this.bounds.extend(newBounds);
    25133774  },
     3775  /**
     3776   * Set the bounds for this Geometry.
     3777   *
     3778   * Parameters:
     3779   * bounds - {<ZOO.Bounds>}
     3780   */
    25143781  setBounds: function(bounds) {
    25153782    if (bounds)
    25163783      this.bounds = bounds.clone();
    25173784  },
     3785  /**
     3786   * Method: clearBounds
     3787   * Nullify this components bounds and that of its parent as well.
     3788   */
    25183789  clearBounds: function() {
    25193790    this.bounds = null;
     
    25213792      this.parent.clearBounds();
    25223793  },
     3794  /**
     3795   * Method: getBounds
     3796   * Get the bounds for this Geometry. If bounds is not set, it
     3797   * is calculated again, this makes queries faster.
     3798   *
     3799   * Returns:
     3800   * {<ZOO.Bounds>}
     3801   */
    25233802  getBounds: function() {
    25243803    if (this.bounds == null) {
     
    25273806    return this.bounds;
    25283807  },
     3808  /**
     3809   * Method: calculateBounds
     3810   * Recalculate the bounds for the geometry.
     3811   */
    25293812  calculateBounds: function() {
    2530     return this.bounds = null;
     3813    // This should be overridden by subclasses.
     3814    return this.bounds;
    25313815  },
    25323816  distanceTo: function(geometry, options) {
     
    25433827    return null;
    25443828  },
     3829  /**
     3830   * Method: toString
     3831   * Returns the Well-Known Text representation of a geometry
     3832   *
     3833   * Returns:
     3834   * {String} Well-Known Text
     3835   */
    25453836  toString: function() {
    25463837    return ZOO.Format.WKT.prototype.write(
     
    25503841  CLASS_NAME: 'ZOO.Geometry'
    25513842});
     3843/**
     3844 * Function: OpenLayers.Geometry.fromWKT
     3845 * Generate a geometry given a Well-Known Text string.
     3846 *
     3847 * Parameters:
     3848 * wkt - {String} A string representing the geometry in Well-Known Text.
     3849 *
     3850 * Returns:
     3851 * {<ZOO.Geometry>} A geometry of the appropriate class.
     3852 */
    25523853ZOO.Geometry.fromWKT = function(wkt) {
    25533854  var format = arguments.callee.format;
     
    26833984  };
    26843985};
     3986/**
     3987 * Class: OpenLayers.Geometry.Collection
     3988 * A Collection is exactly what it sounds like: A collection of different
     3989 * Geometries. These are stored in the local parameter <components> (which
     3990 * can be passed as a parameter to the constructor).
     3991 *
     3992 * As new geometries are added to the collection, they are NOT cloned.
     3993 * When removing geometries, they need to be specified by reference (ie you
     3994 * have to pass in the *exact* geometry to be removed).
     3995 *
     3996 * The <getArea> and <getLength> functions here merely iterate through
     3997 * the components, summing their respective areas and lengths.
     3998 *
     3999 * Create a new instance with the <ZOO.Geometry.Collection> constructor.
     4000 *
     4001 * Inerhits from:
     4002 *  - <ZOO.Geometry>
     4003 */
    26854004ZOO.Geometry.Collection = ZOO.Class(ZOO.Geometry, {
     4005  /**
     4006   * Property: components
     4007   * {Array(<ZOO.Geometry>)} The component parts of this geometry
     4008   */
    26864009  components: null,
     4010  /**
     4011   * Property: componentTypes
     4012   * {Array(String)} An array of class names representing the types of
     4013   * components that the collection can include.  A null value means the
     4014   * component types are not restricted.
     4015   */
    26874016  componentTypes: null,
     4017  /**
     4018   * Constructor: ZOO.Geometry.Collection
     4019   * Creates a Geometry Collection -- a list of geoms.
     4020   *
     4021   * Parameters:
     4022   * components - {Array(<ZOO.Geometry>)} Optional array of geometries
     4023   *
     4024   */
    26884025  initialize: function (components) {
    26894026    ZOO.Geometry.prototype.initialize.apply(this, arguments);
     
    26934030    }
    26944031  },
     4032  /**
     4033   * Method: destroy
     4034   * Destroy this geometry.
     4035   */
    26954036  destroy: function () {
    26964037    this.components.length = 0;
    26974038    this.components = null;
    26984039  },
     4040  /**
     4041   * Method: clone
     4042   * Clone this geometry.
     4043   *
     4044   * Returns:
     4045   * {<ZOO.Geometry.Collection>} An exact clone of this collection
     4046   */
    26994047  clone: function() {
    27004048    var geometry = eval("new " + this.CLASS_NAME + "()");
     
    27044052    return geometry;
    27054053  },
     4054  /**
     4055   * Method: getComponentsString
     4056   * Get a string representing the components for this collection
     4057   *
     4058   * Returns:
     4059   * {String} A string representation of the components of this geometry
     4060   */
    27064061  getComponentsString: function(){
    27074062    var strings = [];
     
    27114066    return strings.join(",");
    27124067  },
     4068  /**
     4069   * Method: calculateBounds
     4070   * Recalculate the bounds by iterating through the components and
     4071   * calling calling extendBounds() on each item.
     4072   */
    27134073  calculateBounds: function() {
    27144074    this.bounds = null;
     
    27214081    return this.bounds
    27224082  },
     4083  /**
     4084   * APIMethod: addComponents
     4085   * Add components to this geometry.
     4086   *
     4087   * Parameters:
     4088   * components - {Array(<ZOO.Geometry>)} An array of geometries to add
     4089   */
    27234090  addComponents: function(components){
    27244091    if(!(components instanceof Array))
     
    27284095    }
    27294096  },
     4097  /**
     4098   * Method: addComponent
     4099   * Add a new component (geometry) to the collection.  If this.componentTypes
     4100   * is set, then the component class name must be in the componentTypes array.
     4101   *
     4102   * The bounds cache is reset.
     4103   *
     4104   * Parameters:
     4105   * component - {<ZOO.Geometry>} A geometry to add
     4106   * index - {int} Optional index into the array to insert the component
     4107   *
     4108   * Returns:
     4109   * {Boolean} The component geometry was successfully added
     4110   */
    27304111  addComponent: function(component, index) {
    27314112    var added = false;
     
    27504131    return added;
    27514132  },
     4133  /**
     4134   * Method: removeComponents
     4135   * Remove components from this geometry.
     4136   *
     4137   * Parameters:
     4138   * components - {Array(<ZOO.Geometry>)} The components to be removed
     4139   */
    27524140  removeComponents: function(components) {
    27534141    if(!(components instanceof Array))
     
    27574145    }
    27584146  },
     4147  /**
     4148   * Method: removeComponent
     4149   * Remove a component from this geometry.
     4150   *
     4151   * Parameters:
     4152   * component - {<ZOO.Geometry>}
     4153   */
    27594154  removeComponent: function(component) {     
    27604155    ZOO.removeItem(this.components, component);
     
    27634158    this.clearBounds();
    27644159  },
     4160  /**
     4161   * Method: getLength
     4162   * Calculate the length of this geometry
     4163   *
     4164   * Returns:
     4165   * {Float} The length of the geometry
     4166   */
    27654167  getLength: function() {
    27664168    var length = 0.0;
     
    27704172    return length;
    27714173  },
     4174  /**
     4175   * APIMethod: getArea
     4176   * Calculate the area of this geometry. Note how this function is
     4177   * overridden in <ZOO.Geometry.Polygon>.
     4178   *
     4179   * Returns:
     4180   * {Float} The area of the collection by summing its parts
     4181   */
    27724182  getArea: function() {
    27734183    var area = 0.0;
     
    27774187    return area;
    27784188  },
     4189  /**
     4190   * APIMethod: getGeodesicArea
     4191   * Calculate the approximate area of the polygon were it projected onto
     4192   *     the earth.
     4193   *
     4194   * Parameters:
     4195   * projection - {<ZOO.Projection>} The spatial reference system
     4196   *     for the geometry coordinates.  If not provided, Geographic/WGS84 is
     4197   *     assumed.
     4198   *
     4199   * Reference:
     4200   * Robert. G. Chamberlain and William H. Duquette, "Some Algorithms for
     4201   *     Polygons on a Sphere", JPL Publication 07-03, Jet Propulsion
     4202   *     Laboratory, Pasadena, CA, June 2007 http://trs-new.jpl.nasa.gov/dspace/handle/2014/40409
     4203   *
     4204   * Returns:
     4205   * {float} The approximate geodesic area of the geometry in square meters.
     4206   */
     4207  getGeodesicArea: function(projection) {
     4208    var area = 0.0;
     4209    for(var i=0, len=this.components.length; i<len; i++) {
     4210      area += this.components[i].getGeodesicArea(projection);
     4211    }
     4212    return area;
     4213  },
     4214  /**
     4215   * Method: getCentroid
     4216   *
     4217   * Returns:
     4218   * {<ZOO.Geometry.Point>} The centroid of the collection
     4219   */
    27794220  getCentroid: function() {
    27804221    return this.components.length && this.components[0].getCentroid();
    27814222  },
     4223  /**
     4224   * Method: getGeodesicLength
     4225   * Calculate the approximate length of the geometry were it projected onto
     4226   *     the earth.
     4227   *
     4228   * projection - {<ZOO.Projection>} The spatial reference system
     4229   *     for the geometry coordinates.  If not provided, Geographic/WGS84 is
     4230   *     assumed.
     4231   *
     4232   * Returns:
     4233   * {Float} The appoximate geodesic length of the geometry in meters.
     4234   */
     4235  getGeodesicLength: function(projection) {
     4236    var length = 0.0;
     4237    for(var i=0, len=this.components.length; i<len; i++) {
     4238      length += this.components[i].getGeodesicLength(projection);
     4239    }
     4240    return length;
     4241  },
     4242  /**
     4243   * Method: move
     4244   * Moves a geometry by the given displacement along positive x and y axes.
     4245   *     This modifies the position of the geometry and clears the cached
     4246   *     bounds.
     4247   *
     4248   * Parameters:
     4249   * x - {Float} Distance to move geometry in positive x direction.
     4250   * y - {Float} Distance to move geometry in positive y direction.
     4251   */
    27824252  move: function(x, y) {
    27834253    for(var i=0, len=this.components.length; i<len; i++) {
     
    27854255    }
    27864256  },
     4257  /**
     4258   * Method: rotate
     4259   * Rotate a geometry around some origin
     4260   *
     4261   * Parameters:
     4262   * angle - {Float} Rotation angle in degrees (measured counterclockwise
     4263   *                 from the positive x-axis)
     4264   * origin - {<ZOO.Geometry.Point>} Center point for the rotation
     4265   */
    27874266  rotate: function(angle, origin) {
    27884267    for(var i=0, len=this.components.length; i<len; ++i) {
     
    27904269    }
    27914270  },
     4271  /**
     4272   * Method: resize
     4273   * Resize a geometry relative to some origin.  Use this method to apply
     4274   *     a uniform scaling to a geometry.
     4275   *
     4276   * Parameters:
     4277   * scale - {Float} Factor by which to scale the geometry.  A scale of 2
     4278   *                 doubles the size of the geometry in each dimension
     4279   *                 (lines, for example, will be twice as long, and polygons
     4280   *                 will have four times the area).
     4281   * origin - {<ZOO.Geometry.Point>} Point of origin for resizing
     4282   * ratio - {Float} Optional x:y ratio for resizing.  Default ratio is 1.
     4283   *
     4284   * Returns:
     4285   * {ZOO.Geometry} - The current geometry.
     4286   */
    27924287  resize: function(scale, origin, ratio) {
    27934288    for(var i=0; i<this.components.length; ++i) {
     
    28134308    return best;
    28144309  },
     4310  /**
     4311   * Method: equals
     4312   * Determine whether another geometry is equivalent to this one.  Geometries
     4313   *     are considered equivalent if all components have the same coordinates.
     4314   *
     4315   * Parameters:
     4316   * geom - {<ZOO.Geometry>} The geometry to test.
     4317   *
     4318   * Returns:
     4319   * {Boolean} The supplied geometry is equivalent to this geometry.
     4320   */
    28154321  equals: function(geometry) {
    28164322    var equivalent = true;
     
    28304336    return equivalent;
    28314337  },
     4338  /**
     4339   * Method: transform
     4340   * Reproject the components geometry from source to dest.
     4341   *
     4342   * Parameters:
     4343   * source - {<ZOO.Projection>}
     4344   * dest - {<ZOO.Projection>}
     4345   *
     4346   * Returns:
     4347   * {<ZOO.Geometry>}
     4348   */
    28324349  transform: function(source, dest) {
    28334350    if (source && dest) {
     
    28404357    return this;
    28414358  },
     4359  /**
     4360   * Method: intersects
     4361   * Determine if the input geometry intersects this one.
     4362   *
     4363   * Parameters:
     4364   * geometry - {<ZOO.Geometry>} Any type of geometry.
     4365   *
     4366   * Returns:
     4367   * {Boolean} The input geometry intersects this one.
     4368   */
    28424369  intersects: function(geometry) {
    28434370    var intersect = false;
     
    28494376    return intersect;
    28504377  },
     4378  /**
     4379   * Method: getVertices
     4380   * Return a list of all points in this geometry.
     4381   *
     4382   * Parameters:
     4383   * nodes - {Boolean} For lines, only return vertices that are
     4384   *     endpoints.  If false, for lines, only vertices that are not
     4385   *     endpoints will be returned.  If not provided, all vertices will
     4386   *     be returned.
     4387   *
     4388   * Returns:
     4389   * {Array} A list of all vertices in the geometry.
     4390   */
    28514391  getVertices: function(nodes) {
    28524392    var vertices = [];
     
    28604400  CLASS_NAME: 'ZOO.Geometry.Collection'
    28614401});
     4402/**
     4403 * Class: ZOO.Geometry.Point
     4404 * Point geometry class.
     4405 *
     4406 * Inherits from:
     4407 *  - <ZOO.Geometry>
     4408 */
    28624409ZOO.Geometry.Point = ZOO.Class(ZOO.Geometry, {
     4410  /**
     4411   * Property: x
     4412   * {float}
     4413   */
    28634414  x: null,
     4415  /**
     4416   * Property: y
     4417   * {float}
     4418   */
    28644419  y: null,
     4420  /**
     4421   * Constructor: ZOO.Geometry.Point
     4422   * Construct a point geometry.
     4423   *
     4424   * Parameters:
     4425   * x - {float}
     4426   * y - {float}
     4427   *
     4428   */
    28654429  initialize: function(x, y) {
    28664430    ZOO.Geometry.prototype.initialize.apply(this, arguments);
     
    28684432    this.y = parseFloat(y);
    28694433  },
     4434  /**
     4435   * Method: clone
     4436   *
     4437   * Returns:
     4438   * {<ZOO.Geometry.Point>} An exact clone of this ZOO.Geometry.Point
     4439   */
    28704440  clone: function(obj) {
    28714441    if (obj == null)
    28724442      obj = new ZOO.Geometry.Point(this.x, this.y);
    28734443    // catch any randomly tagged-on properties
    2874     //OpenLayers.Util.applyDefaults(obj, this);
     4444    // ZOO.Util.applyDefaults(obj, this);
    28754445    return obj;
    28764446  },
     4447  /**
     4448   * Method: calculateBounds
     4449   * Create a new Bounds based on the x/y
     4450   */
    28774451  calculateBounds: function () {
    28784452    this.bounds = new ZOO.Bounds(this.x, this.y,
     
    29044478    return result;
    29054479  },
     4480  /**
     4481   * Method: equals
     4482   * Determine whether another geometry is equivalent to this one.  Geometries
     4483   *     are considered equivalent if all components have the same coordinates.
     4484   *
     4485   * Parameters:
     4486   * geom - {<ZOO.Geometry.Point>} The geometry to test.
     4487   *
     4488   * Returns:
     4489   * {Boolean} The supplied geometry is equivalent to this geometry.
     4490   */
    29064491  equals: function(geom) {
    29074492    var equals = false;
     
    29114496    return equals;
    29124497  },
     4498  /**
     4499   * Method: toShortString
     4500   *
     4501   * Returns:
     4502   * {String} Shortened String representation of Point object.
     4503   *         (ex. <i>"5, 42"</i>)
     4504   */
    29134505  toShortString: function() {
    29144506    return (this.x + ", " + this.y);
    29154507  },
     4508  /**
     4509   * Method: move
     4510   * Moves a geometry by the given displacement along positive x and y axes.
     4511   *     This modifies the position of the geometry and clears the cached
     4512   *     bounds.
     4513   *
     4514   * Parameters:
     4515   * x - {Float} Distance to move geometry in positive x direction.
     4516   * y - {Float} Distance to move geometry in positive y direction.
     4517   */
    29164518  move: function(x, y) {
    29174519    this.x = this.x + x;
     
    29194521    this.clearBounds();
    29204522  },
     4523  /**
     4524   * Method: rotate
     4525   * Rotate a point around another.
     4526   *
     4527   * Parameters:
     4528   * angle - {Float} Rotation angle in degrees (measured counterclockwise
     4529   *                 from the positive x-axis)
     4530   * origin - {<ZOO.Geometry.Point>} Center point for the rotation
     4531   */
    29214532  rotate: function(angle, origin) {
    29224533        angle *= Math.PI / 180;
     
    29274538        this.clearBounds();
    29284539  },
     4540  /**
     4541   * Method: getCentroid
     4542   *
     4543   * Returns:
     4544   * {<ZOO.Geometry.Point>} The centroid of the collection
     4545   */
    29294546  getCentroid: function() {
    29304547    return new ZOO.Geometry.Point(this.x, this.y);
    29314548  },
     4549  /**
     4550   * Method: resize
     4551   * Resize a point relative to some origin.  For points, this has the effect
     4552   *     of scaling a vector (from the origin to the point).  This method is
     4553   *     more useful on geometry collection subclasses.
     4554   *
     4555   * Parameters:
     4556   * scale - {Float} Ratio of the new distance from the origin to the old
     4557   *                 distance from the origin.  A scale of 2 doubles the
     4558   *                 distance between the point and origin.
     4559   * origin - {<ZOO.Geometry.Point>} Point of origin for resizing
     4560   * ratio - {Float} Optional x:y ratio for resizing.  Default ratio is 1.
     4561   *
     4562   * Returns:
     4563   * {ZOO.Geometry} - The current geometry.
     4564   */
    29324565  resize: function(scale, origin, ratio) {
    29334566    ratio = (ratio == undefined) ? 1 : ratio;
     
    29374570    return this;
    29384571  },
     4572  /**
     4573   * Method: intersects
     4574   * Determine if the input geometry intersects this one.
     4575   *
     4576   * Parameters:
     4577   * geometry - {<ZOO.Geometry>} Any type of geometry.
     4578   *
     4579   * Returns:
     4580   * {Boolean} The input geometry intersects this one.
     4581   */
    29394582  intersects: function(geometry) {
    29404583    var intersect = false;
     
    29464589    return intersect;
    29474590  },
     4591  /**
     4592   * Method: transform
     4593   * Translate the x,y properties of the point from source to dest.
     4594   *
     4595   * Parameters:
     4596   * source - {<ZOO.Projection>}
     4597   * dest - {<ZOO.Projection>}
     4598   *
     4599   * Returns:
     4600   * {<ZOO.Geometry>}
     4601   */
    29484602  transform: function(source, dest) {
    29494603    if ((source && dest)) {
     
    29544608    return this;
    29554609  },
     4610  /**
     4611   * Method: getVertices
     4612   * Return a list of all points in this geometry.
     4613   *
     4614   * Parameters:
     4615   * nodes - {Boolean} For lines, only return vertices that are
     4616   *     endpoints.  If false, for lines, only vertices that are not
     4617   *     endpoints will be returned.  If not provided, all vertices will
     4618   *     be returned.
     4619   *
     4620   * Returns:
     4621   * {Array} A list of all vertices in the geometry.
     4622   */
    29564623  getVertices: function(nodes) {
    29574624    return [this];
     
    29594626  CLASS_NAME: 'ZOO.Geometry.Point'
    29604627});
     4628/**
     4629 * Class: ZOO.Geometry.Surface
     4630 * Surface geometry class.
     4631 *
     4632 * Inherits from:
     4633 *  - <ZOO.Geometry>
     4634 */
    29614635ZOO.Geometry.Surface = ZOO.Class(ZOO.Geometry, {
    29624636  initialize: function() {
     
    29654639  CLASS_NAME: "ZOO.Geometry.Surface"
    29664640});
     4641/**
     4642 * Class: ZOO.Geometry.MultiPoint
     4643 * MultiPoint is a collection of Points. Create a new instance with the
     4644 * <ZOO.Geometry.MultiPoint> constructor.
     4645 *
     4646 * Inherits from:
     4647 *  - <ZOO.Geometry.Collection>
     4648 */
    29674649ZOO.Geometry.MultiPoint = ZOO.Class(
    29684650  ZOO.Geometry.Collection, {
     4651  /**
     4652   * Property: componentTypes
     4653   * {Array(String)} An array of class names representing the types of
     4654   * components that the collection can include.  A null value means the
     4655   * component types are not restricted.
     4656   */
    29694657  componentTypes: ["ZOO.Geometry.Point"],
     4658  /**
     4659   * Constructor: ZOO.Geometry.MultiPoint
     4660   * Create a new MultiPoint Geometry
     4661   *
     4662   * Parameters:
     4663   * components - {Array(<ZOO.Geometry.Point>)}
     4664   *
     4665   * Returns:
     4666   * {<ZOO.Geometry.MultiPoint>}
     4667   */
    29704668  initialize: function(components) {
    29714669    ZOO.Geometry.Collection.prototype.initialize.apply(this,arguments);
    29724670  },
     4671  /**
     4672   * Method: addPoint
     4673   * Wrapper for <ZOO.Geometry.Collection.addComponent>
     4674   *
     4675   * Parameters:
     4676   * point - {<ZOO.Geometry.Point>} Point to be added
     4677   * index - {Integer} Optional index
     4678   */
    29734679  addPoint: function(point, index) {
    29744680    this.addComponent(point, index);
    29754681  },
     4682  /**
     4683   * Method: removePoint
     4684   * Wrapper for <ZOO.Geometry.Collection.removeComponent>
     4685   *
     4686   * Parameters:
     4687   * point - {<ZOO.Geometry.Point>} Point to be removed
     4688   */
    29764689  removePoint: function(point){
    29774690    this.removeComponent(point);
     
    29794692  CLASS_NAME: "ZOO.Geometry.MultiPoint"
    29804693});
     4694/**
     4695 * Class: ZOO.Geometry.Curve
     4696 * A Curve is a MultiPoint, whose points are assumed to be connected. To
     4697 * this end, we provide a "getLength()" function, which iterates through
     4698 * the points, summing the distances between them.
     4699 *
     4700 * Inherits:
     4701 *  - <ZOO.Geometry.MultiPoint>
     4702 */
    29814703ZOO.Geometry.Curve = ZOO.Class(ZOO.Geometry.MultiPoint, {
     4704  /**
     4705   * Property: componentTypes
     4706   * {Array(String)} An array of class names representing the types of
     4707   *                 components that the collection can include.  A null
     4708   *                 value means the component types are not restricted.
     4709   */
    29824710  componentTypes: ["ZOO.Geometry.Point"],
     4711  /**
     4712   * Constructor: ZOO.Geometry.Curve
     4713   *
     4714   * Parameters:
     4715   * point - {Array(<ZOO.Geometry.Point>)}
     4716   */
    29834717  initialize: function(points) {
    29844718    ZOO.Geometry.MultiPoint.prototype.initialize.apply(this,arguments);
    29854719  },
     4720  /**
     4721   * Method: getLength
     4722   *
     4723   * Returns:
     4724   * {Float} The length of the curve
     4725   */
    29864726  getLength: function() {
    29874727    var length = 0.0;
     
    29934733    return length;
    29944734  },
     4735  /**
     4736     * APIMethod: getGeodesicLength
     4737     * Calculate the approximate length of the geometry were it projected onto
     4738     *     the earth.
     4739     *
     4740     * projection - {<ZOO.Projection>} The spatial reference system
     4741     *     for the geometry coordinates.  If not provided, Geographic/WGS84 is
     4742     *     assumed.
     4743     *
     4744     * Returns:
     4745     * {Float} The appoximate geodesic length of the geometry in meters.
     4746     */
     4747    getGeodesicLength: function(projection) {
     4748      var geom = this;  // so we can work with a clone if needed
     4749      if(projection) {
     4750        var gg = new ZOO.Projection("EPSG:4326");
     4751        if(!gg.equals(projection)) {
     4752          geom = this.clone().transform(projection, gg);
     4753       }
     4754     }
     4755     var length = 0.0;
     4756     if(geom.components && (geom.components.length > 1)) {
     4757       var p1, p2;
     4758       for(var i=1, len=geom.components.length; i<len; i++) {
     4759         p1 = geom.components[i-1];
     4760         p2 = geom.components[i];
     4761        // this returns km and requires x/y properties
     4762        length += ZOO.distVincenty(p1,p2);
     4763      }
     4764    }
     4765    // convert to m
     4766    return length * 1000;
     4767  },
    29954768  CLASS_NAME: "ZOO.Geometry.Curve"
    29964769});
     4770/**
     4771 * Class: ZOO.Geometry.LineString
     4772 * A LineString is a Curve which, once two points have been added to it, can
     4773 * never be less than two points long.
     4774 *
     4775 * Inherits from:
     4776 *  - <ZOO.Geometry.Curve>
     4777 */
    29974778ZOO.Geometry.LineString = ZOO.Class(ZOO.Geometry.Curve, {
     4779  /**
     4780   * Constructor: ZOO.Geometry.LineString
     4781   * Create a new LineString geometry
     4782   *
     4783   * Parameters:
     4784   * points - {Array(<ZOO.Geometry.Point>)} An array of points used to
     4785   *          generate the linestring
     4786   *
     4787   */
    29984788  initialize: function(points) {
    29994789    ZOO.Geometry.Curve.prototype.initialize.apply(this, arguments);       
    30004790  },
     4791  /**
     4792   * Method: removeComponent
     4793   * Only allows removal of a point if there are three or more points in
     4794   * the linestring. (otherwise the result would be just a single point)
     4795   *
     4796   * Parameters:
     4797   * point - {<ZOO.Geometry.Point>} The point to be removed
     4798   */
    30014799  removeComponent: function(point) {
    30024800    if ( this.components && (this.components.length > 2))
    30034801      ZOO.Geometry.Collection.prototype.removeComponent.apply(this,arguments);
    30044802  },
     4803  /**
     4804   * Method: intersects
     4805   * Test for instersection between two geometries.  This is a cheapo
     4806   *     implementation of the Bently-Ottmann algorigithm.  It doesn't
     4807   *     really keep track of a sweep line data structure.  It is closer
     4808   *     to the brute force method, except that segments are sorted and
     4809   *     potential intersections are only calculated when bounding boxes
     4810   *     intersect.
     4811   *
     4812   * Parameters:
     4813   * geometry - {<ZOO.Geometry>}
     4814   *
     4815   * Returns:
     4816   * {Boolean} The input geometry intersects this geometry.
     4817   */
    30054818  intersects: function(geometry) {
    30064819    var intersect = false;
     
    30504863    return intersect;
    30514864  },
     4865  /**
     4866   * Method: getSortedSegments
     4867   *
     4868   * Returns:
     4869   * {Array} An array of segment objects.  Segment objects have properties
     4870   *     x1, y1, x2, and y2.  The start point is represented by x1 and y1.
     4871   *     The end point is represented by x2 and y2.  Start and end are
     4872   *     ordered so that x1 < x2.
     4873   */
    30524874  getSortedSegments: function() {
    30534875    var numSeg = this.components.length - 1;
     
    30774899    return segments.sort(byX1);
    30784900  },
     4901  /**
     4902   * Method: splitWithSegment
     4903   * Split this geometry with the given segment.
     4904   *
     4905   * Parameters:
     4906   * seg - {Object} An object with x1, y1, x2, and y2 properties referencing
     4907   *     segment endpoint coordinates.
     4908   * options - {Object} Properties of this object will be used to determine
     4909   *     how the split is conducted.
     4910   *
     4911   * Valid options:
     4912   * edge - {Boolean} Allow splitting when only edges intersect.  Default is
     4913   *     true.  If false, a vertex on the source segment must be within the
     4914   *     tolerance distance of the intersection to be considered a split.
     4915   * tolerance - {Number} If a non-null value is provided, intersections
     4916   *     within the tolerance distance of one of the source segment's
     4917   *     endpoints will be assumed to occur at the endpoint.
     4918   *
     4919   * Returns:
     4920   * {Object} An object with *lines* and *points* properties.  If the given
     4921   *     segment intersects this linestring, the lines array will reference
     4922   *     geometries that result from the split.  The points array will contain
     4923   *     all intersection points.  Intersection points are sorted along the
     4924   *     segment (in order from x1,y1 to x2,y2).
     4925   */
    30794926  splitWithSegment: function(seg, options) {
    30804927    var edge = !(options && options.edge === false);
     
    31374984    return result;
    31384985  },
     4986  /**
     4987   * Method: split
     4988   * Use this geometry (the source) to attempt to split a target geometry.
     4989   *
     4990   * Parameters:
     4991   * target - {<ZOO.Geometry>} The target geometry.
     4992   * options - {Object} Properties of this object will be used to determine
     4993   *     how the split is conducted.
     4994   *
     4995   * Valid options:
     4996   * mutual - {Boolean} Split the source geometry in addition to the target
     4997   *     geometry.  Default is false.
     4998   * edge - {Boolean} Allow splitting when only edges intersect.  Default is
     4999   *     true.  If false, a vertex on the source must be within the tolerance
     5000   *     distance of the intersection to be considered a split.
     5001   * tolerance - {Number} If a non-null value is provided, intersections
     5002   *     within the tolerance distance of an existing vertex on the source
     5003   *     will be assumed to occur at the vertex.
     5004   *
     5005   * Returns:
     5006   * {Array} A list of geometries (of this same type as the target) that
     5007   *     result from splitting the target with the source geometry.  The
     5008   *     source and target geometry will remain unmodified.  If no split
     5009   *     results, null will be returned.  If mutual is true and a split
     5010   *     results, return will be an array of two arrays - the first will be
     5011   *     all geometries that result from splitting the source geometry and
     5012   *     the second will be all geometries that result from splitting the
     5013   *     target geometry.
     5014   */
    31395015  split: function(target, options) {
    31405016    var results = null;
     
    32055081    return results;
    32065082  },
     5083  /**
     5084   * Method: splitWith
     5085   * Split this geometry (the target) with the given geometry (the source).
     5086   *
     5087   * Parameters:
     5088   * geometry - {<ZOO.Geometry>} A geometry used to split this
     5089   *     geometry (the source).
     5090   * options - {Object} Properties of this object will be used to determine
     5091   *     how the split is conducted.
     5092   *
     5093   * Valid options:
     5094   * mutual - {Boolean} Split the source geometry in addition to the target
     5095   *     geometry.  Default is false.
     5096   * edge - {Boolean} Allow splitting when only edges intersect.  Default is
     5097   *     true.  If false, a vertex on the source must be within the tolerance
     5098   *     distance of the intersection to be considered a split.
     5099   * tolerance - {Number} If a non-null value is provided, intersections
     5100   *     within the tolerance distance of an existing vertex on the source
     5101   *     will be assumed to occur at the vertex.
     5102   *
     5103   * Returns:
     5104   * {Array} A list of geometries (of this same type as the target) that
     5105   *     result from splitting the target with the source geometry.  The
     5106   *     source and target geometry will remain unmodified.  If no split
     5107   *     results, null will be returned.  If mutual is true and a split
     5108   *     results, return will be an array of two arrays - the first will be
     5109   *     all geometries that result from splitting the source geometry and
     5110   *     the second will be all geometries that result from splitting the
     5111   *     target geometry.
     5112   */
    32075113  splitWith: function(geometry, options) {
    32085114    return geometry.split(this, options);
    32095115  },
     5116  /**
     5117   * Method: getVertices
     5118   * Return a list of all points in this geometry.
     5119   *
     5120   * Parameters:
     5121   * nodes - {Boolean} For lines, only return vertices that are
     5122   *     endpoints.  If false, for lines, only vertices that are not
     5123   *     endpoints will be returned.  If not provided, all vertices will
     5124   *     be returned.
     5125   *
     5126   * Returns:
     5127   * {Array} A list of all vertices in the geometry.
     5128   */
    32105129  getVertices: function(nodes) {
    32115130    var vertices;
     
    33235242  CLASS_NAME: "ZOO.Geometry.LineString"
    33245243});
     5244/**
     5245 * Class: ZOO.Geometry.LinearRing
     5246 *
     5247 * A Linear Ring is a special LineString which is closed. It closes itself
     5248 * automatically on every addPoint/removePoint by adding a copy of the first
     5249 * point as the last point.
     5250 *
     5251 * Also, as it is the first in the line family to close itself, a getArea()
     5252 * function is defined to calculate the enclosed area of the linearRing
     5253 *
     5254 * Inherits:
     5255 *  - <OpenLayers.Geometry.LineString>
     5256 */
    33255257ZOO.Geometry.LinearRing = ZOO.Class(
    33265258  ZOO.Geometry.LineString, {
     5259  /**
     5260   * Property: componentTypes
     5261   * {Array(String)} An array of class names representing the types of
     5262   *                 components that the collection can include.  A null
     5263   *                 value means the component types are not restricted.
     5264   */
    33275265  componentTypes: ["ZOO.Geometry.Point"],
     5266  /**
     5267   * Constructor: OpenLayers.Geometry.LinearRing
     5268   * Linear rings are constructed with an array of points.  This array
     5269   *     can represent a closed or open ring.  If the ring is open (the last
     5270   *     point does not equal the first point), the constructor will close
     5271   *     the ring.  If the ring is already closed (the last point does equal
     5272   *     the first point), it will be left closed.
     5273   *
     5274   * Parameters:
     5275   * points - {Array(<ZOO.Geometry.Point>)} points
     5276   */
    33285277  initialize: function(points) {
    33295278    ZOO.Geometry.LineString.prototype.initialize.apply(this,arguments);
    33305279  },
     5280  /**
     5281   * Method: addComponent
     5282   * Adds a point to geometry components.  If the point is to be added to
     5283   *     the end of the components array and it is the same as the last point
     5284   *     already in that array, the duplicate point is not added.  This has
     5285   *     the effect of closing the ring if it is not already closed, and
     5286   *     doing the right thing if it is already closed.  This behavior can
     5287   *     be overridden by calling the method with a non-null index as the
     5288   *     second argument.
     5289   *
     5290   * Parameter:
     5291   * point - {<ZOO.Geometry.Point>}
     5292   * index - {Integer} Index into the array to insert the component
     5293   *
     5294   * Returns:
     5295   * {Boolean} Was the Point successfully added?
     5296   */
    33315297  addComponent: function(point, index) {
    33325298    var added = false;
     
    33425308    return added;
    33435309  },
     5310  /**
     5311   * APIMethod: removeComponent
     5312   * Removes a point from geometry components.
     5313   *
     5314   * Parameters:
     5315   * point - {<ZOO.Geometry.Point>}
     5316   */
    33445317  removeComponent: function(point) {
    33455318    if (this.components.length > 4) {
     
    33535326    }
    33545327  },
     5328  /**
     5329   * Method: move
     5330   * Moves a geometry by the given displacement along positive x and y axes.
     5331   *     This modifies the position of the geometry and clears the cached
     5332   *     bounds.
     5333   *
     5334   * Parameters:
     5335   * x - {Float} Distance to move geometry in positive x direction.
     5336   * y - {Float} Distance to move geometry in positive y direction.
     5337   */
    33555338  move: function(x, y) {
    33565339    for(var i = 0, len=this.components.length; i<len - 1; i++) {
     
    33585341    }
    33595342  },
     5343  /**
     5344   * Method: rotate
     5345   * Rotate a geometry around some origin
     5346   *
     5347   * Parameters:
     5348   * angle - {Float} Rotation angle in degrees (measured counterclockwise
     5349   *                 from the positive x-axis)
     5350   * origin - {<ZOO.Geometry.Point>} Center point for the rotation
     5351   */
    33605352  rotate: function(angle, origin) {
    33615353    for(var i=0, len=this.components.length; i<len - 1; ++i) {
     
    33635355    }
    33645356  },
     5357  /**
     5358   * Method: resize
     5359   * Resize a geometry relative to some origin.  Use this method to apply
     5360   *     a uniform scaling to a geometry.
     5361   *
     5362   * Parameters:
     5363   * scale - {Float} Factor by which to scale the geometry.  A scale of 2
     5364   *                 doubles the size of the geometry in each dimension
     5365   *                 (lines, for example, will be twice as long, and polygons
     5366   *                 will have four times the area).
     5367   * origin - {<ZOO.Geometry.Point>} Point of origin for resizing
     5368   * ratio - {Float} Optional x:y ratio for resizing.  Default ratio is 1.
     5369   *
     5370   * Returns:
     5371   * {ZOO.Geometry} - The current geometry.
     5372   */
    33655373  resize: function(scale, origin, ratio) {
    33665374    for(var i=0, len=this.components.length; i<len - 1; ++i) {
     
    33695377    return this;
    33705378  },
     5379  /**
     5380   * Method: transform
     5381   * Reproject the components geometry from source to dest.
     5382   *
     5383   * Parameters:
     5384   * source - {<ZOO.Projection>}
     5385   * dest - {<ZOO.Projection>}
     5386   *
     5387   * Returns:
     5388   * {<ZOO.Geometry>}
     5389   */
    33715390  transform: function(source, dest) {
    33725391    if (source && dest) {
     
    33795398    return this;
    33805399  },
     5400  /**
     5401   * Method: getCentroid
     5402   *
     5403   * Returns:
     5404   * {<ZOO.Geometry.Point>} The centroid of the ring
     5405   */
    33815406  getCentroid: function() {
    33825407    if ( this.components && (this.components.length > 2)) {
     
    33955420    return new ZOO.Geometry.Point(x, y);
    33965421  },
     5422  /**
     5423   * Method: getArea
     5424   * Note - The area is positive if the ring is oriented CW, otherwise
     5425   *         it will be negative.
     5426   *
     5427   * Returns:
     5428   * {Float} The signed area for a ring.
     5429   */
    33975430  getArea: function() {
    33985431    var area = 0.0;
     
    34085441    return area;
    34095442  },
     5443  /**
     5444   * Method: getGeodesicArea
     5445   * Calculate the approximate area of the polygon were it projected onto
     5446   *     the earth.  Note that this area will be positive if ring is oriented
     5447   *     clockwise, otherwise it will be negative.
     5448   *
     5449   * Parameters:
     5450   * projection - {<ZOO.Projection>} The spatial reference system
     5451   *     for the geometry coordinates.  If not provided, Geographic/WGS84 is
     5452   *     assumed.
     5453   *
     5454   * Reference:
     5455   * Robert. G. Chamberlain and William H. Duquette, "Some Algorithms for
     5456   *     Polygons on a Sphere", JPL Publication 07-03, Jet Propulsion
     5457   *     Laboratory, Pasadena, CA, June 2007 http://trs-new.jpl.nasa.gov/dspace/handle/2014/40409
     5458   *
     5459   * Returns:
     5460   * {float} The approximate signed geodesic area of the polygon in square
     5461   *     meters.
     5462   */
     5463  getGeodesicArea: function(projection) {
     5464    var ring = this;  // so we can work with a clone if needed
     5465    if(projection) {
     5466      var gg = new ZOO.Projection("EPSG:4326");
     5467      if(!gg.equals(projection)) {
     5468        ring = this.clone().transform(projection, gg);
     5469      }
     5470    }
     5471    var area = 0.0;
     5472    var len = ring.components && ring.components.length;
     5473    if(len > 2) {
     5474      var p1, p2;
     5475      for(var i=0; i<len-1; i++) {
     5476        p1 = ring.components[i];
     5477        p2 = ring.components[i+1];
     5478        area += ZOO.rad(p2.x - p1.x) *
     5479                (2 + Math.sin(ZOO.rad(p1.y)) +
     5480                Math.sin(ZOO.rad(p2.y)));
     5481      }
     5482      area = area * 6378137.0 * 6378137.0 / 2.0;
     5483    }
     5484    return area;
     5485  },
     5486  /**
     5487   * Method: containsPoint
     5488   * Test if a point is inside a linear ring.  For the case where a point
     5489   *     is coincident with a linear ring edge, returns 1.  Otherwise,
     5490   *     returns boolean.
     5491   *
     5492   * Parameters:
     5493   * point - {<ZOO.Geometry.Point>}
     5494   *
     5495   * Returns:
     5496   * {Boolean | Number} The point is inside the linear ring.  Returns 1 if
     5497   *     the point is coincident with an edge.  Returns boolean otherwise.
     5498   */
    34105499  containsPoint: function(point) {
    34115500    var approx = OpenLayers.Number.limitSigDigs;
     
    35065595  CLASS_NAME: "ZOO.Geometry.LinearRing"
    35075596});
     5597/**
     5598 * Class: ZOO.Geometry.MultiLineString
     5599 * A MultiLineString is a geometry with multiple <ZOO.Geometry.LineString>
     5600 * components.
     5601 *
     5602 * Inherits from:
     5603 *  - <ZOO.Geometry.Collection>
     5604 */
    35085605ZOO.Geometry.MultiLineString = ZOO.Class(
    35095606  ZOO.Geometry.Collection, {
    35105607  componentTypes: ["ZOO.Geometry.LineString"],
     5608  /**
     5609   * Constructor: ZOO.Geometry.MultiLineString
     5610   * Constructor for a MultiLineString Geometry.
     5611   *
     5612   * Parameters:
     5613   * components - {Array(<ZOO.Geometry.LineString>)}
     5614   *
     5615   */
    35115616  initialize: function(components) {
    35125617    ZOO.Geometry.Collection.prototype.initialize.apply(this,arguments);       
     
    36635768  CLASS_NAME: "ZOO.Geometry.MultiLineString"
    36645769});
     5770/**
     5771 * Class: ZOO.Geometry.Polygon
     5772 * Polygon is a collection of <ZOO.Geometry.LinearRing>.
     5773 *
     5774 * Inherits from:
     5775 *  - <ZOO.Geometry.Collection>
     5776 */
    36655777ZOO.Geometry.Polygon = ZOO.Class(
    36665778  ZOO.Geometry.Collection, {
    36675779  componentTypes: ["ZOO.Geometry.LinearRing"],
     5780  /**
     5781   * Constructor: OpenLayers.Geometry.Polygon
     5782   * Constructor for a Polygon geometry.
     5783   * The first ring (this.component[0])is the outer bounds of the polygon and
     5784   * all subsequent rings (this.component[1-n]) are internal holes.
     5785   *
     5786   *
     5787   * Parameters:
     5788   * components - {Array(<ZOO.Geometry.LinearRing>)}
     5789   */
    36685790  initialize: function(components) {
    36695791    ZOO.Geometry.Collection.prototype.initialize.apply(this,arguments);
    36705792  },
     5793  /**
     5794   * Method: getArea
     5795   * Calculated by subtracting the areas of the internal holes from the
     5796   *   area of the outer hole.
     5797   *
     5798   * Returns:
     5799   * {float} The area of the geometry
     5800   */
    36715801  getArea: function() {
    36725802    var area = 0.0;
     
    36795809    return area;
    36805810  },
     5811  /**
     5812   * APIMethod: getGeodesicArea
     5813   * Calculate the approximate area of the polygon were it projected onto
     5814   *     the earth.
     5815   *
     5816   * Parameters:
     5817   * projection - {<ZOO.Projection>} The spatial reference system
     5818   *     for the geometry coordinates.  If not provided, Geographic/WGS84 is
     5819   *     assumed.
     5820   *
     5821   * Reference:
     5822   * Robert. G. Chamberlain and William H. Duquette, "Some Algorithms for
     5823   *     Polygons on a Sphere", JPL Publication 07-03, Jet Propulsion
     5824   *     Laboratory, Pasadena, CA, June 2007 http://trs-new.jpl.nasa.gov/dspace/handle/2014/40409
     5825   *
     5826   * Returns:
     5827   * {float} The approximate geodesic area of the polygon in square meters.
     5828   */
     5829  getGeodesicArea: function(projection) {
     5830    var area = 0.0;
     5831    if(this.components && (this.components.length > 0)) {
     5832      area += Math.abs(this.components[0].getGeodesicArea(projection));
     5833      for(var i=1, len=this.components.length; i<len; i++) {
     5834          area -= Math.abs(this.components[i].getGeodesicArea(projection));
     5835      }
     5836    }
     5837    return area;
     5838  },
     5839  /**
     5840   * Method: containsPoint
     5841   * Test if a point is inside a polygon.  Points on a polygon edge are
     5842   *     considered inside.
     5843   *
     5844   * Parameters:
     5845   * point - {<ZOO.Geometry.Point>}
     5846   *
     5847   * Returns:
     5848   * {Boolean | Number} The point is inside the polygon.  Returns 1 if the
     5849   *     point is on an edge.  Returns boolean otherwise.
     5850   */
    36815851  containsPoint: function(point) {
    36825852    var numRings = this.components.length;
     
    37605930  CLASS_NAME: "ZOO.Geometry.Polygon"
    37615931});
     5932/**
     5933 * Method: createRegularPolygon
     5934 * Create a regular polygon around a radius. Useful for creating circles
     5935 * and the like.
     5936 *
     5937 * Parameters:
     5938 * origin - {<ZOO.Geometry.Point>} center of polygon.
     5939 * radius - {Float} distance to vertex, in map units.
     5940 * sides - {Integer} Number of sides. 20 approximates a circle.
     5941 * rotation - {Float} original angle of rotation, in degrees.
     5942 */
     5943OpenLayers.Geometry.Polygon.createRegularPolygon = function(origin, radius, sides, rotation) { 
     5944    var angle = Math.PI * ((1/sides) - (1/2));
     5945    if(rotation) {
     5946        angle += (rotation / 180) * Math.PI;
     5947    }
     5948    var rotatedAngle, x, y;
     5949    var points = [];
     5950    for(var i=0; i<sides; ++i) {
     5951        rotatedAngle = angle + (i * 2 * Math.PI / sides);
     5952        x = origin.x + (radius * Math.cos(rotatedAngle));
     5953        y = origin.y + (radius * Math.sin(rotatedAngle));
     5954        points.push(new ZOO.Geometry.Point(x, y));
     5955    }
     5956    var ring = new ZOO.Geometry.LinearRing(points);
     5957    return new ZOO.Geometry.Polygon([ring]);
     5958};
     5959/**
     5960 * Class: ZOO.Geometry.MultiPolygon
     5961 * MultiPolygon is a geometry with multiple <ZOO.Geometry.Polygon>
     5962 * components.  Create a new instance with the <ZOO.Geometry.MultiPolygon>
     5963 * constructor.
     5964 *
     5965 * Inherits from:
     5966 *  - <ZOO.Geometry.Collection>
     5967 */
    37625968ZOO.Geometry.MultiPolygon = ZOO.Class(
    37635969  ZOO.Geometry.Collection, {
    37645970  componentTypes: ["ZOO.Geometry.Polygon"],
     5971  /**
     5972   * Constructor: OpenLayers.Geometry.MultiPolygon
     5973   * Create a new MultiPolygon geometry
     5974   *
     5975   * Parameters:
     5976   * components - {Array(<ZOO.Geometry.Polygon>)} An array of polygons
     5977   *              used to generate the MultiPolygon
     5978   *
     5979   */
    37655980  initialize: function(components) {
    37665981    ZOO.Geometry.Collection.prototype.initialize.apply(this,arguments);
Note: See TracChangeset for help on using the changeset viewer.

Search

Context Navigation

ZOO Sponsors

http://www.zoo-project.org/trac/chrome/site/img/geolabs-logo.pnghttp://www.zoo-project.org/trac/chrome/site/img/neogeo-logo.png http://www.zoo-project.org/trac/chrome/site/img/apptech-logo.png http://www.zoo-project.org/trac/chrome/site/img/3liz-logo.png http://www.zoo-project.org/trac/chrome/site/img/gateway-logo.png

Become a sponsor !

Knowledge partners

http://www.zoo-project.org/trac/chrome/site/img/ocu-logo.png http://www.zoo-project.org/trac/chrome/site/img/gucas-logo.png http://www.zoo-project.org/trac/chrome/site/img/polimi-logo.png http://www.zoo-project.org/trac/chrome/site/img/fem-logo.png http://www.zoo-project.org/trac/chrome/site/img/supsi-logo.png http://www.zoo-project.org/trac/chrome/site/img/cumtb-logo.png

Become a knowledge partner

Related links

http://zoo-project.org/img/ogclogo.png http://zoo-project.org/img/osgeologo.png