Bienvenue sur PostGIS.fr

Bienvenue sur PostGIS.fr , le site de la communauté des utilisateurs francophones de PostGIS.

PostGIS ajoute le support d'objets géographique à la base de données PostgreSQL. En effet, PostGIS "spatialise" le serverur PostgreSQL, ce qui permet de l'utiliser comme une base de données SIG.

Maintenu à jour, en fonction de nos disponibilités et des diverses sorties des outils que nous testons, nous vous proposons l'ensemble de nos travaux publiés en langue française.

source: trunk/workshop-routing-foss4g/web/OpenLayers/lib/OpenLayers/Strategy/Cluster.js @ 76

Revision 76, 8.9 KB checked in by djay, 12 years ago (diff)

Ajout du répertoire web

  • Property svn:executable set to *
Line 
1/* Copyright (c) 2006-2010 by OpenLayers Contributors (see authors.txt for
2 * full list of contributors). Published under the Clear BSD license. 
3 * See http://svn.openlayers.org/trunk/openlayers/license.txt for the
4 * full text of the license. */
5
6/**
7 * @requires OpenLayers/Strategy.js
8 */
9
10/**
11 * Class: OpenLayers.Strategy.Cluster
12 * Strategy for vector feature clustering.
13 *
14 * Inherits from:
15 *  - <OpenLayers.Strategy>
16 */
17OpenLayers.Strategy.Cluster = OpenLayers.Class(OpenLayers.Strategy, {
18   
19    /**
20     * APIProperty: distance
21     * {Integer} Pixel distance between features that should be considered a
22     *     single cluster.  Default is 20 pixels.
23     */
24    distance: 20,
25   
26    /**
27     * APIProperty: threshold
28     * {Integer} Optional threshold below which original features will be
29     *     added to the layer instead of clusters.  For example, a threshold
30     *     of 3 would mean that any time there are 2 or fewer features in
31     *     a cluster, those features will be added directly to the layer instead
32     *     of a cluster representing those features.  Default is null (which is
33     *     equivalent to 1 - meaning that clusters may contain just one feature).
34     */
35    threshold: null,
36   
37    /**
38     * Property: features
39     * {Array(<OpenLayers.Feature.Vector>)} Cached features.
40     */
41    features: null,
42   
43    /**
44     * Property: clusters
45     * {Array(<OpenLayers.Feature.Vector>)} Calculated clusters.
46     */
47    clusters: null,
48   
49    /**
50     * Property: clustering
51     * {Boolean} The strategy is currently clustering features.
52     */
53    clustering: false,
54   
55    /**
56     * Property: resolution
57     * {Float} The resolution (map units per pixel) of the current cluster set.
58     */
59    resolution: null,
60
61    /**
62     * Constructor: OpenLayers.Strategy.Cluster
63     * Create a new clustering strategy.
64     *
65     * Parameters:
66     * options - {Object} Optional object whose properties will be set on the
67     *     instance.
68     */
69    initialize: function(options) {
70        OpenLayers.Strategy.prototype.initialize.apply(this, [options]);
71    },
72   
73    /**
74     * APIMethod: activate
75     * Activate the strategy.  Register any listeners, do appropriate setup.
76     *
77     * Returns:
78     * {Boolean} The strategy was successfully activated.
79     */
80    activate: function() {
81        var activated = OpenLayers.Strategy.prototype.activate.call(this);
82        if(activated) {
83            this.layer.events.on({
84                "beforefeaturesadded": this.cacheFeatures,
85                "moveend": this.cluster,
86                scope: this
87            });
88        }
89        return activated;
90    },
91   
92    /**
93     * APIMethod: deactivate
94     * Deactivate the strategy.  Unregister any listeners, do appropriate
95     *     tear-down.
96     *
97     * Returns:
98     * {Boolean} The strategy was successfully deactivated.
99     */
100    deactivate: function() {
101        var deactivated = OpenLayers.Strategy.prototype.deactivate.call(this);
102        if(deactivated) {
103            this.clearCache();
104            this.layer.events.un({
105                "beforefeaturesadded": this.cacheFeatures,
106                "moveend": this.cluster,
107                scope: this
108            });
109        }
110        return deactivated;
111    },
112   
113    /**
114     * Method: cacheFeatures
115     * Cache features before they are added to the layer.
116     *
117     * Parameters:
118     * event - {Object} The event that this was listening for.  This will come
119     *     with a batch of features to be clustered.
120     *     
121     * Returns:
122     * {Boolean} False to stop features from being added to the layer.
123     */
124    cacheFeatures: function(event) {
125        var propagate = true;
126        if(!this.clustering) {
127            this.clearCache();
128            this.features = event.features;
129            this.cluster();
130            propagate = false;
131        }
132        return propagate;
133    },
134   
135    /**
136     * Method: clearCache
137     * Clear out the cached features.
138     */
139    clearCache: function() {
140        this.features = null;
141    },
142   
143    /**
144     * Method: cluster
145     * Cluster features based on some threshold distance.
146     *
147     * Parameters:
148     * event - {Object} The event received when cluster is called as a
149     *     result of a moveend event.
150     */
151    cluster: function(event) {
152        if((!event || event.zoomChanged) && this.features) {
153            var resolution = this.layer.map.getResolution();
154            if(resolution != this.resolution || !this.clustersExist()) {
155                this.resolution = resolution;
156                var clusters = [];
157                var feature, clustered, cluster;
158                for(var i=0; i<this.features.length; ++i) {
159                    feature = this.features[i];
160                    if(feature.geometry) {
161                        clustered = false;
162                        for(var j=clusters.length-1; j>=0; --j) {
163                            cluster = clusters[j];
164                            if(this.shouldCluster(cluster, feature)) {
165                                this.addToCluster(cluster, feature);
166                                clustered = true;
167                                break;
168                            }
169                        }
170                        if(!clustered) {
171                            clusters.push(this.createCluster(this.features[i]));
172                        }
173                    }
174                }
175                this.layer.removeAllFeatures();
176                if(clusters.length > 0) {
177                    if(this.threshold > 1) {
178                        var clone = clusters.slice();
179                        clusters = [];
180                        var candidate;
181                        for(var i=0, len=clone.length; i<len; ++i) {
182                            candidate = clone[i];
183                            if(candidate.attributes.count < this.threshold) {
184                                Array.prototype.push.apply(clusters, candidate.cluster);
185                            } else {
186                                clusters.push(candidate);
187                            }
188                        }
189                    }
190                    this.clustering = true;
191                    // A legitimate feature addition could occur during this
192                    // addFeatures call.  For clustering to behave well, features
193                    // should be removed from a layer before requesting a new batch.
194                    this.layer.addFeatures(clusters);
195                    this.clustering = false;
196                }
197                this.clusters = clusters;
198            }
199        }
200    },
201   
202    /**
203     * Method: clustersExist
204     * Determine whether calculated clusters are already on the layer.
205     *
206     * Returns:
207     * {Boolean} The calculated clusters are already on the layer.
208     */
209    clustersExist: function() {
210        var exist = false;
211        if(this.clusters && this.clusters.length > 0 &&
212           this.clusters.length == this.layer.features.length) {
213            exist = true;
214            for(var i=0; i<this.clusters.length; ++i) {
215                if(this.clusters[i] != this.layer.features[i]) {
216                    exist = false;
217                    break;
218                }
219            }
220        }
221        return exist;
222    },
223   
224    /**
225     * Method: shouldCluster
226     * Determine whether to include a feature in a given cluster.
227     *
228     * Parameters:
229     * cluster - {<OpenLayers.Feature.Vector>} A cluster.
230     * feature - {<OpenLayers.Feature.Vector>} A feature.
231     *
232     * Returns:
233     * {Boolean} The feature should be included in the cluster.
234     */
235    shouldCluster: function(cluster, feature) {
236        var cc = cluster.geometry.getBounds().getCenterLonLat();
237        var fc = feature.geometry.getBounds().getCenterLonLat();
238        var distance = (
239            Math.sqrt(
240                Math.pow((cc.lon - fc.lon), 2) + Math.pow((cc.lat - fc.lat), 2)
241            ) / this.resolution
242        );
243        return (distance <= this.distance);
244    },
245   
246    /**
247     * Method: addToCluster
248     * Add a feature to a cluster.
249     *
250     * Parameters:
251     * cluster - {<OpenLayers.Feature.Vector>} A cluster.
252     * feature - {<OpenLayers.Feature.Vector>} A feature.
253     */
254    addToCluster: function(cluster, feature) {
255        cluster.cluster.push(feature);
256        cluster.attributes.count += 1;
257    },
258   
259    /**
260     * Method: createCluster
261     * Given a feature, create a cluster.
262     *
263     * Parameters:
264     * feature - {<OpenLayers.Feature.Vector>}
265     *
266     * Returns:
267     * {<OpenLayers.Feature.Vector>} A cluster.
268     */
269    createCluster: function(feature) {
270        var center = feature.geometry.getBounds().getCenterLonLat();
271        var cluster = new OpenLayers.Feature.Vector(
272            new OpenLayers.Geometry.Point(center.lon, center.lat),
273            {count: 1}
274        );
275        cluster.cluster = [feature];
276        return cluster;
277    },
278
279    CLASS_NAME: "OpenLayers.Strategy.Cluster" 
280});
Note: See TracBrowser for help on using the repository browser.