1 /* Copyright (c) 2006-2012 by OpenLayers Contributors (see authors.txt for 
 
   2  * full list of contributors). Published under the 2-clause BSD license.
 
   3  * See license.txt in the OpenLayers distribution or repository for the
 
   4  * full text of the license. */
 
   8  * @requires OpenLayers/Control/PanZoom.js
 
  12  * Class: OpenLayers.Control.PanZoomBar
 
  13  * The PanZoomBar is a visible control composed of a
 
  14  * <OpenLayers.Control.PanPanel> and a <OpenLayers.Control.ZoomBar>. 
 
  15  * By default it is displayed in the upper left corner of the map as 4
 
  16  * directional arrows above a vertical slider.
 
  19  *  - <OpenLayers.Control.PanZoom>
 
  21 OpenLayers.Control.SimplePanZoom = OpenLayers.Class(OpenLayers.Control.PanZoom, {
 
  24      * APIProperty: zoomStopWidth
 
  29      * APIProperty: zoomStopHeight
 
  39      * Property: sliderEvents
 
  40      * {<OpenLayers.Events>}
 
  45      * Property: zoombarDiv
 
  51      * APIProperty: zoomWorldIcon
 
  57      * APIProperty: panIcons
 
  58      * {Boolean} Set this property to false not to display the pan icons. If
 
  59      * false the zoom world icon is placed under the zoom bar. Defaults to
 
  65      * APIProperty: forceFixedZoomLevel
 
  66      * {Boolean} Force a fixed zoom level even though the map has 
 
  69     forceFixedZoomLevel: false,
 
  72      * Property: mouseDragStart
 
  73      * {<OpenLayers.Pixel>}
 
  79      * {Number} The cumulative vertical pixel offset during a zoom bar drag.
 
  85      * {<OpenLayers.Pixel>}
 
  90      * Constructor: OpenLayers.Control.PanZoomBar
 
  99         this._removeZoomBar();
 
 102             "changebaselayer": this.redraw,
 
 103             "updatesize": this.redraw,
 
 107         OpenLayers.Control.PanZoom.prototype.destroy.apply(this, arguments);
 
 109         delete this.mouseDragStart;
 
 110         delete this.zoomStart;
 
 117      * map - {<OpenLayers.Map>} 
 
 119     setMap: function(map) {
 
 120         OpenLayers.Control.PanZoom.prototype.setMap.apply(this, arguments);
 
 122             "changebaselayer": this.redraw,
 
 123             "updatesize": this.redraw,
 
 130      * clear the div and start over.
 
 133         if (this.div !== null) {
 
 134             this.removeButtons();
 
 135             this._removeZoomBar();
 
 145     * px - {<OpenLayers.Pixel>} 
 
 148         // initialize our internal div
 
 149         OpenLayers.Control.prototype.draw.apply(this, arguments);
 
 150         px = this.position.clone();
 
 152         // place the controls
 
 154         var ids = ['panup', 'panleft', 'panright', 'pandown', 'zoomout', 'zoomin'];
 
 156         for (var i = 0; i < ids.length; i++) {
 
 157             var b = document.createElement('div');
 
 160             b.className = 'button olButton';
 
 161             this.div.appendChild(b);
 
 162             this.buttons.push(b);
 
 170     * Method: _addZoomBar
 
 173     * centered - {<OpenLayers.Pixel>} where zoombar drawing is to start.
 
 175     _addZoomBar:function() {
 
 176         var id = this.id + "_" + this.map.id;
 
 177         var zoomsToEnd = this.map.getNumZoomLevels() - 1 - this.map.getZoom();
 
 178         var slider = document.createElement('div');
 
 179         slider.id = 'slider';
 
 180         slider.className = 'button';
 
 181         slider.style.cursor = 'move';
 
 182         this.slider = slider;
 
 184         this.sliderEvents = new OpenLayers.Events(this, slider, null, true,
 
 185             { includeXY: true });
 
 186         this.sliderEvents.on({
 
 187             "touchstart": this.zoomBarDown,
 
 188             "touchmove": this.zoomBarDrag,
 
 189             "touchend": this.zoomBarUp,
 
 190             "mousedown": this.zoomBarDown,
 
 191             "mousemove": this.zoomBarDrag,
 
 192             "mouseup": this.zoomBarUp
 
 195         var height = this.zoomStopHeight * (this.map.getNumZoomLevels());
 
 197         // this is the background image
 
 198         var div = document.createElement('div');
 
 199         div.className = 'button olButton';
 
 201         this.zoombarDiv = div;
 
 203         this.div.appendChild(div);
 
 205         this.div.appendChild(slider);
 
 207         this.map.events.register("zoomend", this, this.moveZoomBar);
 
 211      * Method: _removeZoomBar
 
 213     _removeZoomBar: function() {
 
 214         this.sliderEvents.un({
 
 215             "touchstart": this.zoomBarDown,
 
 216             "touchmove": this.zoomBarDrag,
 
 217             "touchend": this.zoomBarUp,
 
 218             "mousedown": this.zoomBarDown,
 
 219             "mousemove": this.zoomBarDrag,
 
 220             "mouseup": this.zoomBarUp
 
 222         this.sliderEvents.destroy();
 
 224         this.div.removeChild(this.zoombarDiv);
 
 225         this.zoombarDiv = null;
 
 226         this.div.removeChild(this.slider);
 
 229         this.map.events.unregister("zoomend", this, this.moveZoomBar);
 
 233      * Method: onButtonClick
 
 238     onButtonClick: function(evt) {
 
 239         OpenLayers.Control.PanZoom.prototype.onButtonClick.apply(this, arguments);
 
 240         if (evt.buttonElement === this.zoombarDiv) {
 
 241             var levels = evt.buttonXY.y / this.zoomStopHeight;
 
 242             if (this.forceFixedZoomLevel || !this.map.fractionalZoom) {
 
 243                 levels = Math.floor(levels);
 
 245             var zoom = (this.map.getNumZoomLevels() - 1) - levels; 
 
 246             zoom = Math.min(Math.max(zoom, 0), this.map.getNumZoomLevels() - 1);
 
 247             this.map.zoomTo(zoom);
 
 252      * Method: passEventToSlider
 
 253      * This function is used to pass events that happen on the div, or the map,
 
 254      * through to the slider, which then does its moving thing.
 
 257      * evt - {<OpenLayers.Event>} 
 
 259     passEventToSlider:function(evt) {
 
 260         this.sliderEvents.handleBrowserEvent(evt);
 
 264      * Method: zoomBarDown
 
 265      * event listener for clicks on the slider
 
 268      * evt - {<OpenLayers.Event>} 
 
 270     zoomBarDown:function(evt) {
 
 271         if (!OpenLayers.Event.isLeftClick(evt) && !OpenLayers.Event.isSingleTouch(evt)) {
 
 275             "touchmove": this.passEventToSlider,
 
 276             "mousemove": this.passEventToSlider,
 
 277             "mouseup": this.passEventToSlider,
 
 280         this.mouseDragStart = evt.xy.clone();
 
 281         this.zoomStart = evt.xy.clone();
 
 282         this.div.style.cursor = "move";
 
 283         // reset the div offsets just in case the div moved
 
 284         this.zoombarDiv.offsets = null; 
 
 285         OpenLayers.Event.stop(evt);
 
 289      * Method: zoomBarDrag
 
 290      * This is what happens when a click has occurred, and the client is
 
 291      * dragging.  Here we must ensure that the slider doesn't go beyond the
 
 292      * bottom/top of the zoombar div, as well as moving the slider to its new
 
 296      * evt - {<OpenLayers.Event>}
 
 298     zoomBarDrag: function(evt) {
 
 299         if (this.mouseDragStart !== null) {
 
 300             var deltaY = this.mouseDragStart.y - evt.xy.y;
 
 301             var offsets = OpenLayers.Util.pagePosition(this.zoombarDiv);
 
 302             if ((evt.clientY - offsets[1]) > 0 && 
 
 303                 (evt.clientY - offsets[1]) < 140) {
 
 304                 var newTop = parseInt(this.slider.style.top, 10) - deltaY;
 
 305                 this.slider.style.top = newTop + "px";
 
 306                 this.mouseDragStart = evt.xy.clone();
 
 308             // set cumulative displacement
 
 309             this.deltaY = this.zoomStart.y - evt.xy.y;
 
 310             OpenLayers.Event.stop(evt);
 
 316      * Perform cleanup when a mouseup event is received -- discover new zoom
 
 317      * level and switch to it.
 
 320      * evt - {<OpenLayers.Event>}
 
 322     zoomBarUp: function(evt) {
 
 323         if (!OpenLayers.Event.isLeftClick(evt) && evt.type !== "touchend") {
 
 326         if (this.mouseDragStart) {
 
 327             this.div.style.cursor = "";
 
 329                 "touchmove": this.passEventToSlider,
 
 330                 "mouseup": this.passEventToSlider,
 
 331                 "mousemove": this.passEventToSlider,
 
 334             var zoomLevel = this.map.zoom;
 
 335             zoomLevel += this.deltaY/this.zoomStopHeight;
 
 336             zoomLevel = Math.max(Math.round(zoomLevel), 0);
 
 337             this.map.zoomTo(zoomLevel);
 
 338             this.mouseDragStart = null;
 
 339             this.zoomStart = null;
 
 341             OpenLayers.Event.stop(evt);
 
 346     * Method: moveZoomBar
 
 347     * Change the location of the slider to match the current zoom level.
 
 349     moveZoomBar:function() {
 
 351             ((this.map.getNumZoomLevels()-1) - this.map.getZoom()) *
 
 352             this.zoomStopHeight + this.startTop;
 
 353         this.slider.style.top = newTop + "px";
 
 355     CLASS_NAME: "OpenLayers.Control.SimplePanZoom"