OpenLayers Features – Resizing and Reshaping Features in OpenLayers

geocodingjavascriptmapsopenlayers-2

Resizing and Reshaping features in Openlayers. I have a map with Openlayers and some controls to draw and modify Features.

I need to activate the Resize and Drag and Rotate check button fields as defaults when i push the modify button. Currently i have to push the check fields for this.

When i push the modify button it lets me modify all points in my circle without the resize,rotate and drag check buttons checked,

I dont want to be able to modify points just resize, drag and rotate.

Please run the code below to get a better understanding:

                              <html xmlns="http://www.w3.org/1999/xhtml">
  <head>
  <!--CSS for Map -->
  <style type="text/css">
     html, body, #map {
         margin: 0;
         width: 100%;
         height: 100%;
        }
 </style>
 <!-- END of CSS for Map -->

<!--CSS for Controls to draw circle and navigate -->
<style type="text/css">
    #controls {
        position: absolute;
        bottom: 1em;
        left: 100px;
        width: 400px;
        z-index: 20000;
        padding: 0 0.5em 0.5em 0.5em;
    }

    #controlToggle {
        padding-left: 1em;
    }

    #controlToggle li {
        list-style: none;
    }

    #form {
        position: absolute;
        bottom: 1em;
        left: 400px;
        width: 200px;
        z-index: 20000;
        padding: 0 0.5em 0.5em 0.5em;
    }
  </style>
  <!-- END CSS for Controls to draw circle -->

  <link href="css/style.css" rel="stylesheet" type="text/css" />
  <script src="js/firebug.js"></script>
  <script src="js/OpenLayers.js"></script>

  <script type="text/javascript">
    var lon = 24.0000000000; 
    var lat = -29.000000000000;

    var zoom = 4;
    var map, layer, vectors, controls;

    function init(){

       // Because the Streetmaps system uses 300x300 tiles, we need to set up the scaling variables to work with these
 var aRes = [90,45,22.500000,11.250000,5.625000,2.812500,1.406250,0.703125,0.351563,0.175781,0.087891,0.043945,0.021973,0.010986,0.005493,0.002747,0.001373,0.000687,0.000343];
 for (var l=0;l<aRes.length;l++) { aRes[l] = aRes[l]/300; }

      // Normal init, but we pass through the info about the zoom/scaling as options
      map = new OpenLayers.Map( 'map', { tileSize: new OpenLayers.Size(300, 300), projection: 'CRS:84', numZoomLevels:aRes.length, resolutions:aRes, maxResolution:360/300 } );

      // At this point the control is used as per normal            
        layer1 = new OpenLayers.Layer.WMS( 
                          'Streetmaps Streets',
                          'http://www.streetmaps.co.za/WMS/?',
                          {
                          key:                                    'HZPGNWPNDYPREPTIKSIHWKYKQYYOQVYX',
                          service:                                'WMS',
                          request:                                'GetMap',
                          version:                                '1.3.0',
                          layers:                                 'sm.maps.tiled',
                          format:                                 'image/png'
                        }
                );

        layer2 = new OpenLayers.Layer.WMS( 
                          'Streetmaps Imagery',
                          'http://www.streetmaps.co.za/WMS/?',
                          {
                          key:                                    'HZPGNWPNDYPREPTIKSIHWKYKQYYOQVYX',
                          service:                                'WMS',
                          request:                                'GetMap',
                          version:                                '1.3.0',
                          layers:                                 'sm.imagery',
                          format:                                 'image/png'
                        }
                );

        // This loads the map
        map.addLayer(layer1);
        map.addLayer(layer2);

        map.setCenter(new OpenLayers.LonLat(lon, lat), zoom);
        map.addControl( new OpenLayers.Control.LayerSwitcher() );
        var vectors = new OpenLayers.Layer.Vector("vector", {isBaseLayer: true});
        map.addLayers([vectors]);



       // This loads the overlays
       var wms = new OpenLayers.Layer.WMS( "OpenLayers WMS", 
            "http://vmap0.tiles.osgeo.org/wms/vmap0?", {layers: 'basic'}); 
        OpenLayers.Feature.Vector.style['default']['strokeWidth'] = '2';

        // allow testing of specific renderers via "?renderer=Canvas", etc
        var renderer =   OpenLayers.Util.getParameters(window.location.href).renderer;
        renderer = (renderer) ? [renderer] : OpenLayers.Layer.Vector.prototype.renderers;

        vectors = new OpenLayers.Layer.Vector("Vector Layer", {
            renderers: renderer
        });

        map.addLayers([wms, vectors]);
        map.addControl(new OpenLayers.Control.LayerSwitcher());
        map.addControl(new OpenLayers.Control.MousePosition());
        map.setCenter(new OpenLayers.LonLat(lon, lat), zoom);


        if (console && console.log) {
            function report(event) {
                console.log(event.type, event.feature ? event.feature.id : event.components);
            }
            vectors.events.on({
                "beforefeaturemodified": report,
                "featuremodified": report,
                "afterfeaturemodified": report,
                "vertexmodified": report,
                "sketchmodified": report,
                "sketchstarted": report,
                "sketchcomplete": report
            });
        }

        // Now we call an alert to get the bounds or coordinates from a circle or vector we have drawn 
        vectors.events.on({
        featuresadded: onFeaturesAdded
        });

        function onFeaturesAdded(event){
        var bounds = event.features[0].geometry.getBounds();
        var answer = "bottom: " + bounds.bottom  + "\n";
        answer += "left: " + bounds.left  + "\n";
        answer += "right: " + bounds.right  + "\n";
        answer += "top: " + bounds.top  + "\n";
        alert(answer);
        }


        controls = {
            regular: new OpenLayers.Control.DrawFeature(vectors,
                        OpenLayers.Handler.RegularPolygon,
                        {handlerOptions: {sides: 40}}),
            modify: new OpenLayers.Control.ModifyFeature(vectors)
        };

        for(var key in controls) {
            map.addControl(controls[key]);
        }

        map.setCenter(new OpenLayers.LonLat(0, 0), 3);
        document.getElementById('noneToggle').checked = true;
    }

    activate:function update() {
        // reset modification mode
        controls.modify.mode = OpenLayers.Control.ModifyFeature.RESHAPE;
        var rotate = document.getElementById("rotate").checked;
        if(rotate) {
            controls.modify.mode |= OpenLayers.Control.ModifyFeature.ROTATE;
        }
        var resize = document.getElementById("resize").checked;
        if(resize) {
            controls.modify.mode |= OpenLayers.Control.ModifyFeature.RESIZE;
            var keepAspectRatio = document.getElementById("keepAspectRatio").checked;
            if (keepAspectRatio) {
                controls.modify.mode &= ~OpenLayers.Control.ModifyFeature.RESHAPE;
            }
        }
        var drag = document.getElementById("drag").checked;
        if(drag) {
            controls.modify.mode |= OpenLayers.Control.ModifyFeature.DRAG;
        }

        if (rotate || drag) {
            controls.modify.mode &= ~OpenLayers.Control.ModifyFeature.RESHAPE;
        }
        var sides = parseInt(document.getElementById("sides").value);
        sides = Math.max(3, isNaN(sides) ? 0 : sides);
        controls.regular.handler.sides = sides;
        var irregular =  document.getElementById("irregular").checked;
        controls.regular.handler.irregular = irregular;
    }


    function toggleControl(element) {
        for(key in controls) {
            var control = controls[key];
            if(element.value == key && element.checked) {
                control.activate();
            } else {
                control.deactivate();
            }
        }
    }
  </script>
  </head>
  <body onLoad="init()">
  <div id="map" class="smallmap"></div>
  <div id="controls">
    <ul id="controlToggle">
        <li>
            <input type="radio" name="type" value="none" id="noneToggle"
                   onclick="toggleControl(this);" checked="checked" />
            <label for="noneToggle">navigate</label>
        </li>
        <li>
            <input type="radio" name="type" value="regular" id="regularToggle" onClick="toggleControl(this);" />
            <label for="regularToggle">draw regular polygon</label>
    </li>
        <li>
            <input type="radio" name="type" value="modify" id="modifyToggle"
                   onclick="toggleControl(this);" />
            <label for="modifyToggle">modify feature</label>
            <ul>
                <li>
                    <input id="rotate" type="checkbox" 
                           name="rotate" onChange="update()" />
                    <label for="rotate">allow rotation</label>
                </li>
                <li>
                    <input id="resize" type="checkbox"
                           name="resize" onChange="update()" />
                    <label for="resize">allow resizing</label>
                    <input id="keepAspectRatio" type="hidden"
                           name="keepAspectRatio" onChange="update()" checked="checked" />
                    <label for="keepAspectRatio"></label>
                </li>
                <li>
                    <input id="drag" type="checkbox"
                           name="drag" onChange="update()" />
                    <label for="drag">allow dragging</label>
                </li>
            </ul>
        </li>
    </ul>
</div>

Best Answer

This must be a typo on your code, but change activate: function update() { to function update() {.

now add checked="checked" to the checkboxes you want on by default, in the demo case i'll have them all checked. (thought rotating a circle is pointless, I left it in.)

<input id="drag" type="checkbox" name="drag" onChange="update();"  checked="checked"/>

change the "modify feature" radio option to call update() intead of toggleControl(this):

<input type="radio" name="type" value="modify" id="modifyToggle" onclick="update();" />

And activate the modify control:

controls["modify"].activate();

DEMO:

Here's the demo. You can View Source on it.