/* Copyright (c) 2006-2013 by OpenLayers Contributors (see authors.txt for
 * full list of contributors). Published under the 2-clause BSD license.
 * See license.txt in the OpenLayers distribution or repository for the
 * full text of the license. */

OpenLayers.Events.featureclick=OpenLayers.Class({cache:null,map:null,provides:["featureclick","nofeatureclick","featureover","featureout"],initialize:function(e){this.target=e;if(e.object instanceof OpenLayers.Map)this.setMap(e.object);else{if(!(e.object instanceof OpenLayers.Layer.Vector))throw"Listeners for '"+this.provides.join("', '")+"' events can only be registered for OpenLayers.Layer.Vector "+"or OpenLayers.Map instances";e.object.map?this.setMap(e.object.map):e.object.events.register("added",this,function(t){this.setMap(e.object.map)})}for(var t=this.provides.length-1;t>=0;--t)e.extensions[this.provides[t]]=!0},setMap:function(e){this.map=e,this.cache={},e.events.register("mousedown",this,this.start,{extension:!0}),e.events.register("mouseup",this,this.onClick,{extension:!0}),e.events.register("touchstart",this,this.start,{extension:!0}),e.events.register("touchmove",this,this.cancel,{extension:!0}),e.events.register("touchend",this,this.onClick,{extension:!0}),e.events.register("mousemove",this,this.onMousemove,{extension:!0})},start:function(e){this.startEvt=e},cancel:function(e){delete this.startEvt},onClick:function(e){if(!this.startEvt||e.type!=="touchend"&&!OpenLayers.Event.isLeftClick(e))return;var t=this.getFeatures(this.startEvt);delete this.startEvt;var n,r,i,s={};for(var o=0,u=t.length;o<u;++o){n=t[o],r=n.layer,s[r.id]=!0,i=this.triggerEvent("featureclick",{feature:n});if(i===!1)break}for(o=0,u=this.map.layers.length;o<u;++o)r=this.map.layers[o],r instanceof OpenLayers.Layer.Vector&&!s[r.id]&&this.triggerEvent("nofeatureclick",{layer:r})},onMousemove:function(e){delete this.startEvt;var t=this.getFeatures(e),n={},r=[],i;for(var s=0,o=t.length;s<o;++s)i=t[s],n[i.id]=i,this.cache[i.id]||r.push(i);var u=[];for(var a in this.cache)i=this.cache[a],i.layer&&i.layer.map?n[i.id]||u.push(i):delete this.cache[a];var f;for(s=0,o=r.length;s<o;++s){i=r[s],this.cache[i.id]=i,f=this.triggerEvent("featureover",{feature:i});if(f===!1)break}for(s=0,o=u.length;s<o;++s){i=u[s],delete this.cache[i.id],f=this.triggerEvent("featureout",{feature:i});if(f===!1)break}},triggerEvent:function(e,t){var n=t.feature?t.feature.layer:t.layer,r=this.target.object;if(r instanceof OpenLayers.Map||r===n)return this.target.triggerEvent(e,t)},getFeatures:function(e){var t=e.clientX,n=e.clientY,r=[],i=[],s=[],o,u,a,f,l;for(f=this.map.layers.length-1;f>=0;--f){o=this.map.layers[f];if(o.div.style.display!=="none")if(o.renderer instanceof OpenLayers.Renderer.Elements){if(o instanceof OpenLayers.Layer.Vector){u=document.elementFromPoint(t,n);while(u&&u._featureId)a=o.getFeatureById(u._featureId),a?(r.push(a),u.style.display="none",i.push(u),u=document.elementFromPoint(t,n)):u=!1}s.push(o),o.div.style.display="none"}else o.renderer instanceof OpenLayers.Renderer.Canvas&&(a=o.renderer.getFeatureIdFromEvent(e),a&&(r.push(a),s.push(o)))}for(f=0,l=i.length;f<l;++f)i[f].style.display="";for(f=s.length-1;f>=0;--f)s[f].div.style.display="block";return r},destroy:function(){for(var e=this.provides.length-1;e>=0;--e)delete this.target.extensions[this.provides[e]];this.map.events.un({mousemove:this.onMousemove,mousedown:this.start,mouseup:this.onClick,touchstart:this.start,touchmove:this.cancel,touchend:this.onClick,scope:this}),delete this.cache,delete this.map,delete this.target}}),OpenLayers.Events.nofeatureclick=OpenLayers.Events.featureclick,OpenLayers.Events.featureover=OpenLayers.Events.featureclick,OpenLayers.Events.featureout=OpenLayers.Events.featureclick;