OpenLayers OpenLayers

Changeset 7589

Show
Ignore:
Timestamp:
07/29/08 14:20:19 (4 months ago)
Author:
tschaub
Message:

Adding a box property to the SelectFeature control for selecting all features within a box. p=pgiraud, r=me,crschmidt (closes #1071)

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • trunk/openlayers/examples/select-feature.html

    r7095 r7589  
    4242                        multiple: false, hover: false, 
    4343                        toggleKey: "ctrlKey", // ctrl key removes from selection 
    44                         multipleKey: "shiftKey" // shift key adds to selection 
     44                        multipleKey: "shiftKey", // shift key adds to selection 
     45                        box: true 
    4546                    } 
    4647                ) 
     
    7071            var hover = document.getElementById("hover").checked; 
    7172            drawControls.select.hover = hover; 
    72             if(hover && drawControls.select.active) { 
    73                 // turn on/off to clear feature property of handler 
     73            drawControls.select.box = document.getElementById("box").checked; 
     74            if(drawControls.select.active) { 
    7475                drawControls.select.deactivate(); 
    7576                drawControls.select.activate(); 
     
    112113            <ul> 
    113114                <li> 
     115                    <input id="box" type="checkbox" checked="checked" 
     116                           name="box" onchange="update()" /> 
     117                    <label for="box">select features in a box</label> 
     118                </li> 
     119                <li> 
    114120                    <input id="clickout" type="checkbox" 
    115121                           name="clickout" onchange="update()" /> 
  • trunk/openlayers/lib/OpenLayers/Control/SelectFeature.js

    r6577 r7589  
    6161     
    6262    /** 
     63     * APIProperty: box 
     64     * {Boolean} Allow feature selection by drawing a box. 
     65     */ 
     66    box: false, 
     67     
     68    /** 
    6369     * APIProperty: onSelect  
    6470     * {Function} Optional function to be called when a feature is selected. 
     
    8995    /** 
    9096     * APIProperty: callbacks 
    91      * {Object} The functions that are sent to the handler for callback 
     97     * {Object} The functions that are sent to the handlers.feature for callback 
    9298     */ 
    9399    callbacks: null, 
     
    107113 
    108114    /** 
    109      * Property: handler 
    110      * {<OpenLayers.Handler.Feature>} 
    111      */ 
    112     handler: null, 
     115     * Property: handlers 
     116     * {Object} Object with references to multiple <OpenLayers.Handler> 
     117     *     instances. 
     118     */ 
     119    handlers: null, 
    113120 
    114121    /** 
     
    128135                                                  out: this.outFeature 
    129136                                                }, this.callbacks); 
    130         var handlerOptions = { geometryTypes: this.geometryTypes}; 
    131         this.handler = new OpenLayers.Handler.Feature(this, layer, 
    132                                                       this.callbacks, 
    133                                                       handlerOptions); 
     137        this.handlers = { 
     138            feature: new OpenLayers.Handler.Feature( 
     139                this, layer, this.callbacks, {geometryTypes: this.geometryTypes} 
     140            ) 
     141        }; 
     142 
     143        if (this.box) { 
     144            this.handlers.box = new OpenLayers.Handler.Box( 
     145                this, {done: this.selectBox}, 
     146                {boxDivClassName: "olHandlerBoxSelectFeature"} 
     147            );  
     148        } 
     149    }, 
     150 
     151    /** 
     152     * Method: activate 
     153     * Activates the control. 
     154     *  
     155     * Returns: 
     156     * {Boolean} The control was effectively activated. 
     157     */ 
     158    activate: function () { 
     159        if (!this.active) { 
     160            this.handlers.feature.activate(); 
     161            if(this.box && this.handlers.box) { 
     162                this.handlers.box.activate(); 
     163            } 
     164        } 
     165        return OpenLayers.Control.prototype.activate.apply( 
     166            this, arguments 
     167        ); 
     168    }, 
     169 
     170    /** 
     171     * Method: deactivate 
     172     * Deactivates the control. 
     173     *  
     174     * Returns: 
     175     * {Boolean} The control was effectively deactivated. 
     176     */ 
     177    deactivate: function () { 
     178        if (this.active) { 
     179            this.handlers.feature.deactivate(); 
     180            if(this.handlers.box) { 
     181                this.handlers.box.deactivate(); 
     182            } 
     183        } 
     184        return OpenLayers.Control.prototype.deactivate.apply( 
     185            this, arguments 
     186        ); 
    134187    }, 
    135188 
     
    189242     */ 
    190243    multipleSelect: function() { 
    191         return this.multiple || this.handler.evt[this.multipleKey]; 
     244        return this.multiple || this.handlers.feature.evt[this.multipleKey]; 
    192245    }, 
    193246     
     
    201254     */ 
    202255    toggleSelect: function() { 
    203         return this.toggle || this.handler.evt[this.toggleKey]; 
     256        return this.toggle || this.handlers.feature.evt[this.toggleKey]; 
    204257    }, 
    205258 
     
    280333        this.onUnselect(feature); 
    281334    }, 
     335     
     336    /** 
     337     * Method: selectBox 
     338     * Callback from the handlers.box set up when <box> selection is true 
     339     *     on. 
     340     * 
     341     * Parameters: 
     342     * position - {<OpenLayers.Bounds> || <OpenLayers.Pixel> }   
     343     */ 
     344    selectBox: function(position) { 
     345        if (position instanceof OpenLayers.Bounds) { 
     346            var minXY = this.map.getLonLatFromPixel( 
     347                new OpenLayers.Pixel(position.left, position.bottom) 
     348            ); 
     349            var maxXY = this.map.getLonLatFromPixel( 
     350                new OpenLayers.Pixel(position.right, position.top) 
     351            ); 
     352            var bounds = new OpenLayers.Bounds( 
     353                minXY.lon, minXY.lat, maxXY.lon, maxXY.lat 
     354            ); 
     355             
     356            // if multiple is false, first deselect currently selected features 
     357            if (!this.multipleSelect()) { 
     358                this.unselectAll(); 
     359            } 
     360             
     361            // because we're using a box, we consider we want multiple selection 
     362            var prevMultiple = this.multiple; 
     363            this.multiple = true; 
     364            for(var i=0, len = this.layer.features.length; i<len; ++i) { 
     365                var feature = this.layer.features[i]; 
     366                if (this.geometryTypes == null || OpenLayers.Util.indexOf( 
     367                        this.geometryTypes, feature.geometry.CLASS_NAME) > -1) { 
     368                    if (bounds.toGeometry().intersects(feature.geometry)) { 
     369                        if (OpenLayers.Util.indexOf(this.layer.selectedFeatures, feature) == -1) { 
     370                            this.select(feature); 
     371                        } 
     372                    } 
     373                } 
     374            } 
     375            this.multiple = prevMultiple; 
     376        } 
     377    }, 
    282378 
    283379    /**  
     
    289385     */ 
    290386    setMap: function(map) { 
    291         this.handler.setMap(map); 
     387        this.handlers.feature.setMap(map); 
     388        if (this.box) { 
     389            this.handlers.box.setMap(map); 
     390        } 
    292391        OpenLayers.Control.prototype.setMap.apply(this, arguments); 
    293392    }, 
  • trunk/openlayers/tests/Control/SelectFeature.html

    r6719 r7589  
    1414        t.eq(control.layer, "bar", 
    1515             "constructor sets layer correctly");         
    16 //        t.eq(control.featureHandler.geometryTypes, "foo", 
     16//        t.eq(control.handlers.feature.geometryTypes, "foo", 
    1717//             "constructor sets options correctly on feature handler"); 
    1818    } 
    1919     
    2020    function test_Control_SelectFeature_destroy(t) { 
    21         t.plan(1); 
    22         var map = new OpenLayers.Map("map"); 
    23         var layer = new OpenLayers.Layer.Vector(); 
    24         map.addLayer(layer); 
    25         var control = new OpenLayers.Control.SelectFeature(layer); 
    26         control.handler.destroy = function() { 
    27             t.ok(true, 
    28                  "control.destroy calls destroy on feature handler"); 
     21        t.plan(2); 
     22        var map = new OpenLayers.Map("map"); 
     23        var layer = new OpenLayers.Layer.Vector(); 
     24        map.addLayer(layer); 
     25        var control = new OpenLayers.Control.SelectFeature(layer, {box: true}); 
     26        control.handlers.feature.deactivate = function() { 
     27            t.ok(true, 
     28                 "control.deactivate calls deactivate on feature handler"); 
     29        } 
     30        control.handlers.box.deactivate = function() { 
     31            t.ok(true, 
     32                 "control.deactivate calls deactivate on box handler"); 
    2933        } 
    3034// should nullify the layer property here 
     
    6266        // mock up active control 
    6367        var control = new OpenLayers.Control.SelectFeature(layer); 
    64         control.handler = { 
     68        control.handlers.feature = { 
    6569            evt: {} 
    6670        }; 
     
    111115    } 
    112116     
     117    function test_box(t) { 
     118        t.plan(5); 
     119        var map = new OpenLayers.Map("map"); 
     120        var layer = new OpenLayers.Layer.Vector(); 
     121        map.addLayer(layer); 
     122        var control = new OpenLayers.Control.SelectFeature(layer, {'multiple': true, box: true }); 
     123        var feature = new OpenLayers.Feature.Vector(new OpenLayers.Geometry.Point(0,0)); 
     124        var feature2 = new OpenLayers.Feature.Vector(new OpenLayers.Geometry.Point(1,1)); 
     125        var feature3 = new OpenLayers.Feature.Vector(new OpenLayers.Geometry.Point(-2,-2)); 
     126        var feature4 = new OpenLayers.Feature.Vector(new OpenLayers.Geometry.LineString([ 
     127            new OpenLayers.Geometry.Point(0, 0), new OpenLayers.Geometry.Point(1, 1) 
     128        ])); 
     129        layer.addFeatures([feature, feature2, feature3, feature4]); 
     130        control.setMap(map); 
     131        map.getLonLatFromPixel = function(arg) { 
     132            return new OpenLayers.LonLat(arg.x, arg.y); 
     133        }     
     134        control.selectBox(new OpenLayers.Bounds(-1, -1, 2, 2)); 
     135        t.eq(layer.selectedFeatures.length, 3, "box around all features selects 3 features"); 
     136         
     137        control.selectBox(new OpenLayers.Bounds(-3, -3, -1, -1)); 
     138        t.eq(layer.selectedFeatures.length, 4, "box around other features doesn't turn off already selected features.");         
     139         
     140        control.multipleSelect = function() { 
     141            return false; 
     142        }; 
     143        control.selectBox(new OpenLayers.Bounds(-3, -3, -1, -1)); 
     144        t.eq(layer.selectedFeatures.length, 1, "box around other features correctly turns off already selected features."); 
     145         
     146        control.geometryTypes = null; 
     147        control.selectBox(new OpenLayers.Bounds(-100, -100, 100, 100)); 
     148        t.eq(layer.selectedFeatures.length, layer.features.length, "all features selected with no geometryTypes filter"); 
     149         
     150        control.geometryTypes = ["OpenLayers.Geometry.Point"]; 
     151        control.selectBox(new OpenLayers.Bounds(-100, -100, 100, 100)); 
     152        t.eq(layer.selectedFeatures.length, 3, "3 features selected with geometryTypes filter"); 
     153         
     154        ["OpenLayers.Geometry.Point"] 
     155         
     156 
     157    } 
     158     
    113159    function test_Control_SelectFeature_activate(t) { 
    114         t.plan(2); 
    115         var map = new OpenLayers.Map("map"); 
    116         var layer = new OpenLayers.Layer.Vector(); 
    117         map.addLayer(layer); 
    118         var control = new OpenLayers.Control.SelectFeature(layer); 
     160        t.plan(4); 
     161        var map = new OpenLayers.Map("map"); 
     162        var layer = new OpenLayers.Layer.Vector(); 
     163        map.addLayer(layer); 
     164        var control = new OpenLayers.Control.SelectFeature(layer, {box: true}); 
    119165        map.addControl(control); 
    120         t.ok(!control.handler.active, 
     166        t.ok(!control.handlers.feature.active, 
    121167             "feature handler is not active prior to activating control"); 
     168        t.ok(!control.handlers.box.active, 
     169             "box handler is not active prior to activating control"); 
    122170        control.activate(); 
    123         t.ok(control.handler.active, 
     171        t.ok(control.handlers.feature.active, 
    124172             "feature handler is active after activating control"); 
     173        t.ok(control.handlers.box.active, 
     174             "box handler is active after activating control"); 
    125175    } 
    126176 
    127177    function test_Control_SelectFeature_deactivate(t) { 
    128         t.plan(1); 
    129         var map = new OpenLayers.Map("map"); 
    130         var layer = new OpenLayers.Layer.Vector(); 
    131         map.addLayer(layer); 
    132         var control = new OpenLayers.Control.SelectFeature(layer); 
     178        t.plan(2); 
     179        var map = new OpenLayers.Map("map"); 
     180        var layer = new OpenLayers.Layer.Vector(); 
     181        map.addLayer(layer); 
     182        var control = new OpenLayers.Control.SelectFeature(layer, {box: true}); 
    133183        map.addControl(control); 
    134          
     184 
    135185        control.activate(); 
    136         control.handler.deactivate = function() { 
     186        control.handlers.feature.deactivate = function() { 
    137187            t.ok(true, 
    138188                 "control.deactivate calls deactivate on feature handler"); 
     189        } 
     190        control.handlers.box.deactivate = function() { 
     191            t.ok(true, 
     192                 "control.deactivate calls deactivate on box handler"); 
    139193        } 
    140194        control.deactivate(); 
  • trunk/openlayers/theme/default/style.css

    r7584 r7589  
    231231    font-size: 1px; 
    232232    filter: alpha(opacity=50); 
     233} 
     234.olHandlerBoxSelectFeature { 
     235    border: 2px solid blue; 
     236    position: absolute; 
     237    background-color: white; 
     238    opacity: 0.50; 
     239    font-size: 1px; 
     240    filter: alpha(opacity=50); 
    233241}    
    234242