<?xml version="1.0" encoding="utf-8"?>
  Copyright 2009 James Richards
  Licensed under the Creative Commons Attribution 3.0 United States License:
    backgroundGradientColors="[0xFFFFFF, 0xAAAAAA]"
    height="100%" width="100%"  viewSourceURL="srcview/index.html">
    <gm:Map id="map"
        key="(Your API Key Here)"
        mapevent_mapready="map_mapReady(event)" />

            import com.adobe.serialization.json.JSON;

            import com.google.maps.LatLng;    
            import com.google.maps.LatLngBounds;
            import com.google.maps.Map;    
            import com.google.maps.MapMoveEvent;
            import com.google.maps.MapType;
            import com.google.maps.controls.OverviewMapControl;
            import com.google.maps.controls.ScaleControl;
            import com.google.maps.controls.ZoomControl;
            import com.google.maps.controls.PositionControl;
            import com.google.maps.controls.MapTypeControl;

            import com.google.maps.overlays.Polygon;
            import com.google.maps.overlays.PolygonOptions;
            import com.google.maps.styles.FillStyle;
            import com.google.maps.styles.StrokeStyle;
            import mx.controls.Alert;
            import mx.rpc.events.FaultEvent;
            import mx.rpc.events.ResultEvent;
            import mx.rpc.http.HTTPService;
            // Parcels URL and parameters
            private var parcelsUrl:String = "http://sampleserver1.arcgisonline.com/" +
            private var wgs84wkid:String = "4236";
            private var toolTipField:String = "RNO";
            // Parcels map service
            private var parcelsService:HTTPService = new HTTPService();
            // Parcels symbols
            private var transparentFill:FillStyle;
            private var greyStroke:StrokeStyle;
            private var whiteStroke:StrokeStyle;
            private function map_mapReady(event:Event):void { 
                // Setup parcel symbols
                transparentFill = new FillStyle({ 
                    alpha: 0.0 });
                greyStroke = new StrokeStyle({
                    alpha: 1.0,
                    thickness: 1.5,
                    color: 0x333333 });
                whiteStroke = new StrokeStyle({
                    alpha: 1.0,
                    thickness: 1.5,
                    color: 0xffffff });
                // Add map controls
                var mtc:MapTypeControl = new MapTypeControl();
                var pc:PositionControl = new PositionControl();
                var zc:ZoomControl = new ZoomControl();
                var sc:ScaleControl = new ScaleControl();
                var omc:OverviewMapControl = new OverviewMapControl();
                // Add event listeners
                map.addEventListener(MapMoveEvent.MOVE_END, map_moveEnd);

                // Initialize map            
                map.setCenter(new LatLng(45.520211, -122.65553), 17, 
            private function map_moveEnd(event:MapMoveEvent):void {
                // Get zoom level
                var zoom:Number = map.getZoom();
                trace("map_moveEnd - Zoom level: " + zoom.toString());
                // Only draw parcels if zoomed in far enough
                if (zoom < 17) {
                    // This just clears the overlays if we're not zoomed in far enough.
                    // This would be a problem if there are other overlays besides parcels.
                    // We'll deal with that in a future post.
                // Get current extent
                var bnds:LatLngBounds = map.getLatLngBounds();
                // An ESRI envelope is configured as xmin, ymin, xmax, ymax
                var envelope:String = bnds.getWest().toString() + "," +
                                      bnds.getSouth().toString() + "," +
                                      bnds.getEast().toString() + "," +
                trace("map_moveEnd - Envelope: " + envelope);
                // Cancel http service in case a request was sent 
                // that hasn't come back yet
                // Setup http service and add listeners
                parcelsService.url = parcelsUrl;
                parcelsService.addEventListener(ResultEvent.RESULT, onParcelResult);
                parcelsService.addEventListener(FaultEvent.FAULT, onHttpFault);
                // Setup parameters to pass to the service
                var params:Object = new Object();
                params.geometry = envelope;
                params.geometryType = "esriGeometryEnvelope";
                params.inSR = wgs84wkid;
                params.spatialRel = "esriSpatialRelIntersects";
                params.returnGeometry = "true";
                params.outSR = wgs84wkid;
                params.outFields = toolTipField;
                params.f = "json";
                // Send the request
            private function onParcelResult(event:ResultEvent):void {
                //trace(event.result as String);
                // Use ascorelib JSON serializer to decode returned object
                var obj:Object = JSON.decode(event.result as String);
                if (obj.error != null) {
                    Alert.show('An error occured on the server. The response message returned was:\n\n' + 
                        event.result, 'Server Error');
                // Simply clear all the polygons from the map.
                // This would be a problem if there are other overlays.
                // We'll deal with that in a future post.
                // Get the features array from the returned JSON
                var features:Array = obj.features as Array;
                // This code breaks multipolygons into a separate polygon for each
                // ring. Not ideal, but necessary at this zoom level because the only
                // way to create multi ringed polygons in GMaps Flash API (as of v 1.9c)
                // is with the Polyline Encoding Algorithm - and this algorithm rounds
                // to 5 decimal places - thus creating choppy looking polygons. 
                // We'll discuss this further in a future post.
                for each (var feature:Object in features) {
                    for each (var ring:Array in feature.geometry.rings) {
                        var points:Array = new Array();
                        for each (var point:Array in ring) {
                            points.push(new LatLng(point[1], point[0]));
                        var polyOpts:PolygonOptions = new PolygonOptions();
                        polyOpts.fillStyle = transparentFill;
                        polyOpts.strokeStyle = 
                            (map.getCurrentMapType() == MapType.NORMAL_MAP_TYPE ? 
                            greyStroke : whiteStroke);
                        polyOpts.tooltip = feature.attributes[toolTipField];
                        var poly:Polygon = new Polygon(points, polyOpts);
            private function onHttpFault(event:FaultEvent):void {
                Alert.show(event.toString(), "HttpFault");