1 /* Copyright (c) 2006-2008 MetaCarta, Inc., published under the Clear BSD
2 * license. See http://svn.openlayers.org/trunk/openlayers/license.txt for the
3 * full text of the license. */
7 * @requires OpenLayers/Util.js
8 * @requires OpenLayers/Console.js
12 * Class: OpenLayers.Tile
13 * This is a class designed to designate a single tile, however
14 * it is explicitly designed to do relatively little. Tiles store
15 * information about themselves -- such as the URL that they are related
16 * to, and their size - but do not add themselves to the layer div
17 * automatically, for example. Create a new tile with the
18 * <OpenLayers.Tile> constructor, or a subclass.
20 * TBD 3.0 - remove reference to url in above paragraph
23 OpenLayers.Tile = OpenLayers.Class({
26 * Constant: EVENT_TYPES
27 * {Array(String)} Supported application event types
29 EVENT_TYPES: [ "loadstart", "loadend", "reload", "unload"],
33 * {<OpenLayers.Events>} An events object that handles all
46 * {<OpenLayers.Layer>} layer the tile is attached to
52 * {String} url of the request.
55 * Deprecated. The base tile class does not need an url. This should be
56 * handled in subclasses. Does not belong here.
62 * {<OpenLayers.Bounds>} null
68 * {<OpenLayers.Size>} null
74 * {<OpenLayers.Pixel>} Top Left pixel of the tile
80 * {Boolean} Is the tile loading?
84 /** TBD 3.0 -- remove 'url' from the list of parameters to the constructor.
85 * there is no need for the base tile class to have a url.
87 * Constructor: OpenLayers.Tile
88 * Constructor for a new <OpenLayers.Tile> instance.
91 * layer - {<OpenLayers.Layer>} layer that the tile will go in.
92 * position - {<OpenLayers.Pixel>}
93 * bounds - {<OpenLayers.Bounds>}
95 * size - {<OpenLayers.Size>}
97 initialize: function(layer, position, bounds, url, size) {
99 this.position = position.clone();
100 this.bounds = bounds.clone();
102 this.size = size.clone();
104 //give the tile a unique id based on its BBOX.
105 this.id = OpenLayers.Util.createUniqueID("Tile_");
107 this.events = new OpenLayers.Events(this, null, this.EVENT_TYPES);
112 * Call immediately before destroying if you are listening to tile
113 * events, so that counters are properly handled if tile is still
114 * loading at destroy-time. Will only fire an event if the tile is
118 if (this.isLoading) {
119 this.isLoading = false;
120 this.events.triggerEvent("unload");
126 * Nullify references to prevent circular references and memory leaks.
132 this.position = null;
134 this.events.destroy();
142 * obj - {<OpenLayers.Tile>} The tile to be cloned
145 * {<OpenLayers.Tile>} An exact clone of this <OpenLayers.Tile>
147 clone: function (obj) {
149 obj = new OpenLayers.Tile(this.layer,
156 // catch any randomly tagged-on properties
157 OpenLayers.Util.applyDefaults(obj, this);
164 * Clear whatever is currently in the tile, then return whether or not
165 * it should actually be re-drawn.
168 * {Boolean} Whether or not the tile should actually be drawn. Note that
169 * this is not really the best way of doing things, but such is
170 * the way the code has been developed. Subclasses call this and
171 * depend on the return to know if they should draw or not.
174 var maxExtent = this.layer.maxExtent;
175 var withinMaxExtent = (maxExtent &&
176 this.bounds.intersectsBounds(maxExtent, false));
178 // The only case where we *wouldn't* want to draw the tile is if the
179 // tile is outside its layer's maxExtent.
180 this.shouldDraw = (withinMaxExtent || this.layer.displayOutsideMaxExtent);
182 //clear tile's contents and mark as not drawn
185 return this.shouldDraw;
190 * Reposition the tile.
193 * bounds - {<OpenLayers.Bounds>}
194 * position - {<OpenLayers.Pixel>}
195 * redraw - {Boolean} Call draw method on tile after moving.
198 moveTo: function (bounds, position, redraw) {
199 if (redraw == null) {
203 this.bounds = bounds.clone();
204 this.position = position.clone();
212 * Clear the tile of any bounds/position-related data so that it can
213 * be reused in a new location. To be implemented by subclasses.
216 // to be implemented by subclasses
220 * Method: getBoundsFromBaseLayer
221 * Take the pixel locations of the corner of the tile, and pass them to
222 * the base layer and ask for the location of those pixels, so that
223 * displaying tiles over Google works fine.
226 * position - {<OpenLayers.Pixel>}
229 * bounds - {<OpenLayers.Bounds>}
231 getBoundsFromBaseLayer: function(position) {
232 var msg = OpenLayers.i18n('reprojectDeprecated',
233 {'layerName':this.layer.name});
234 OpenLayers.Console.warn(msg);
235 var topLeft = this.layer.map.getLonLatFromLayerPx(position);
236 var bottomRightPx = position.clone();
237 bottomRightPx.x += this.size.w;
238 bottomRightPx.y += this.size.h;
239 var bottomRight = this.layer.map.getLonLatFromLayerPx(bottomRightPx);
240 // Handle the case where the base layer wraps around the date line.
241 // Google does this, and it breaks WMS servers to request bounds in
243 if (topLeft.lon > bottomRight.lon) {
244 if (topLeft.lon < 0) {
245 topLeft.lon = -180 - (topLeft.lon+180);
247 bottomRight.lon = 180+bottomRight.lon+180;
250 var bounds = new OpenLayers.Bounds(topLeft.lon,
259 * Show the tile only if it should be drawn.
261 showTile: function() {
262 if (this.shouldDraw) {
269 * Show the tile. To be implemented by subclasses.
271 show: function() { },
275 * Hide the tile. To be implemented by subclasses.
277 hide: function() { },
279 CLASS_NAME: "OpenLayers.Tile"