166 lines
4.9 KiB
JavaScript
166 lines
4.9 KiB
JavaScript
import {Class} from '../../core/Class';
|
|
import {setOptions} from '../../core/Util';
|
|
import {toPoint as point} from '../../geometry/Point';
|
|
import Browser from '../../core/Browser';
|
|
|
|
/*
|
|
* @class Icon
|
|
* @aka L.Icon
|
|
*
|
|
* Represents an icon to provide when creating a marker.
|
|
*
|
|
* @example
|
|
*
|
|
* ```js
|
|
* var myIcon = L.icon({
|
|
* iconUrl: 'my-icon.png',
|
|
* iconRetinaUrl: 'my-icon@2x.png',
|
|
* iconSize: [38, 95],
|
|
* iconAnchor: [22, 94],
|
|
* popupAnchor: [-3, -76],
|
|
* shadowUrl: 'my-icon-shadow.png',
|
|
* shadowRetinaUrl: 'my-icon-shadow@2x.png',
|
|
* shadowSize: [68, 95],
|
|
* shadowAnchor: [22, 94]
|
|
* });
|
|
*
|
|
* L.marker([50.505, 30.57], {icon: myIcon}).addTo(map);
|
|
* ```
|
|
*
|
|
* `L.Icon.Default` extends `L.Icon` and is the blue icon Leaflet uses for markers by default.
|
|
*
|
|
*/
|
|
|
|
export var Icon = Class.extend({
|
|
|
|
/* @section
|
|
* @aka Icon options
|
|
*
|
|
* @option iconUrl: String = null
|
|
* **(required)** The URL to the icon image (absolute or relative to your script path).
|
|
*
|
|
* @option iconRetinaUrl: String = null
|
|
* The URL to a retina sized version of the icon image (absolute or relative to your
|
|
* script path). Used for Retina screen devices.
|
|
*
|
|
* @option iconSize: Point = null
|
|
* Size of the icon image in pixels.
|
|
*
|
|
* @option iconAnchor: Point = null
|
|
* The coordinates of the "tip" of the icon (relative to its top left corner). The icon
|
|
* will be aligned so that this point is at the marker's geographical location. Centered
|
|
* by default if size is specified, also can be set in CSS with negative margins.
|
|
*
|
|
* @option popupAnchor: Point = [0, 0]
|
|
* The coordinates of the point from which popups will "open", relative to the icon anchor.
|
|
*
|
|
* @option tooltipAnchor: Point = [0, 0]
|
|
* The coordinates of the point from which tooltips will "open", relative to the icon anchor.
|
|
*
|
|
* @option shadowUrl: String = null
|
|
* The URL to the icon shadow image. If not specified, no shadow image will be created.
|
|
*
|
|
* @option shadowRetinaUrl: String = null
|
|
*
|
|
* @option shadowSize: Point = null
|
|
* Size of the shadow image in pixels.
|
|
*
|
|
* @option shadowAnchor: Point = null
|
|
* The coordinates of the "tip" of the shadow (relative to its top left corner) (the same
|
|
* as iconAnchor if not specified).
|
|
*
|
|
* @option className: String = ''
|
|
* A custom class name to assign to both icon and shadow images. Empty by default.
|
|
*/
|
|
|
|
options: {
|
|
popupAnchor: [0, 0],
|
|
tooltipAnchor: [0, 0],
|
|
|
|
// @option crossOrigin: Boolean|String = false
|
|
// Whether the crossOrigin attribute will be added to the tiles.
|
|
// If a String is provided, all tiles will have their crossOrigin attribute set to the String provided. This is needed if you want to access tile pixel data.
|
|
// Refer to [CORS Settings](https://developer.mozilla.org/en-US/docs/Web/HTML/CORS_settings_attributes) for valid String values.
|
|
crossOrigin: false
|
|
},
|
|
|
|
initialize: function (options) {
|
|
setOptions(this, options);
|
|
},
|
|
|
|
// @method createIcon(oldIcon?: HTMLElement): HTMLElement
|
|
// Called internally when the icon has to be shown, returns a `<img>` HTML element
|
|
// styled according to the options.
|
|
createIcon: function (oldIcon) {
|
|
return this._createIcon('icon', oldIcon);
|
|
},
|
|
|
|
// @method createShadow(oldIcon?: HTMLElement): HTMLElement
|
|
// As `createIcon`, but for the shadow beneath it.
|
|
createShadow: function (oldIcon) {
|
|
return this._createIcon('shadow', oldIcon);
|
|
},
|
|
|
|
_createIcon: function (name, oldIcon) {
|
|
var src = this._getIconUrl(name);
|
|
|
|
if (!src) {
|
|
if (name === 'icon') {
|
|
throw new Error('iconUrl not set in Icon options (see the docs).');
|
|
}
|
|
return null;
|
|
}
|
|
|
|
var img = this._createImg(src, oldIcon && oldIcon.tagName === 'IMG' ? oldIcon : null);
|
|
this._setIconStyles(img, name);
|
|
|
|
if (this.options.crossOrigin || this.options.crossOrigin === '') {
|
|
img.crossOrigin = this.options.crossOrigin === true ? '' : this.options.crossOrigin;
|
|
}
|
|
|
|
return img;
|
|
},
|
|
|
|
_setIconStyles: function (img, name) {
|
|
var options = this.options;
|
|
var sizeOption = options[name + 'Size'];
|
|
|
|
if (typeof sizeOption === 'number') {
|
|
sizeOption = [sizeOption, sizeOption];
|
|
}
|
|
|
|
var size = point(sizeOption),
|
|
anchor = point(name === 'shadow' && options.shadowAnchor || options.iconAnchor ||
|
|
size && size.divideBy(2, true));
|
|
|
|
img.className = 'leaflet-marker-' + name + ' ' + (options.className || '');
|
|
|
|
if (anchor) {
|
|
img.style.marginLeft = (-anchor.x) + 'px';
|
|
img.style.marginTop = (-anchor.y) + 'px';
|
|
}
|
|
|
|
if (size) {
|
|
img.style.width = size.x + 'px';
|
|
img.style.height = size.y + 'px';
|
|
}
|
|
},
|
|
|
|
_createImg: function (src, el) {
|
|
el = el || document.createElement('img');
|
|
el.src = src;
|
|
return el;
|
|
},
|
|
|
|
_getIconUrl: function (name) {
|
|
return Browser.retina && this.options[name + 'RetinaUrl'] || this.options[name + 'Url'];
|
|
}
|
|
});
|
|
|
|
|
|
// @factory L.icon(options: Icon options)
|
|
// Creates an icon instance with the given options.
|
|
export function icon(options) {
|
|
return new Icon(options);
|
|
}
|