Convert some leaflet things to typescript
This commit is contained in:
parent
91c78ecd68
commit
a33b50cb03
@ -1,9 +1,11 @@
|
|||||||
import L from 'leaflet';
|
import L, {ControlOptions} from 'leaflet';
|
||||||
|
|
||||||
const LinkControl = L.Control.extend({
|
export interface LinkControlOptions extends ControlOptions {}
|
||||||
options: {position: 'bottomleft'},
|
|
||||||
|
|
||||||
onAdd: function (map) {
|
export class LinkControl extends L.Control {
|
||||||
|
options: LinkControlOptions
|
||||||
|
|
||||||
|
onAdd(map) {
|
||||||
this._map = map;
|
this._map = map;
|
||||||
this._container = L.DomUtil.create('div', 'dynmap-link');
|
this._container = L.DomUtil.create('div', 'dynmap-link');
|
||||||
|
|
||||||
@ -12,18 +14,18 @@ const LinkControl = L.Control.extend({
|
|||||||
|
|
||||||
this._container.appendChild(this._linkButton);
|
this._container.appendChild(this._linkButton);
|
||||||
return this._container;
|
return this._container;
|
||||||
},
|
}
|
||||||
|
|
||||||
getContainer: function () {
|
getContainer() {
|
||||||
return this._container;
|
return this._container;
|
||||||
},
|
}
|
||||||
|
|
||||||
getPosition: function () {
|
getPosition() {
|
||||||
return this.options.position;
|
return this.options.position;
|
||||||
},
|
}
|
||||||
|
|
||||||
_createButton: function (title, className, fn, context) {
|
_createButton(title, className, fn, context) {
|
||||||
var link = document.createElement('a');
|
const link = document.createElement('a');
|
||||||
link.href = '#';
|
link.href = '#';
|
||||||
link.title = title;
|
link.title = title;
|
||||||
link.className = className;
|
link.className = className;
|
||||||
@ -36,16 +38,14 @@ const LinkControl = L.Control.extend({
|
|||||||
L.DomEvent.addListener(link, 'click', fn, context);
|
L.DomEvent.addListener(link, 'click', fn, context);
|
||||||
|
|
||||||
return link;
|
return link;
|
||||||
},
|
}
|
||||||
|
|
||||||
_follow: function () {
|
_follow() {
|
||||||
// var url = dynmap.getLink();
|
// var url = dynmap.getLink();
|
||||||
// window.location = url;
|
// window.location = url;
|
||||||
}
|
}
|
||||||
});
|
}
|
||||||
|
|
||||||
// var link = new dynmapLink();
|
// var link = new dynmapLink();
|
||||||
// dynmap.map.addControl(link);
|
// dynmap.map.addControl(link);
|
||||||
// }
|
// }
|
||||||
|
|
||||||
export default LinkControl;
|
|
116
src/leaflet/icon/PlayerIcon.ts
Normal file
116
src/leaflet/icon/PlayerIcon.ts
Normal file
@ -0,0 +1,116 @@
|
|||||||
|
import L, {DivIconOptions} from 'leaflet';
|
||||||
|
import {DynmapPlayer} from "@/dynmap";
|
||||||
|
|
||||||
|
export interface PlayerIconOptions extends DivIconOptions {
|
||||||
|
smallFace: boolean,
|
||||||
|
showSkinFace: boolean,
|
||||||
|
showBody: boolean,
|
||||||
|
showHealth: boolean,
|
||||||
|
}
|
||||||
|
|
||||||
|
export class PlayerIcon extends L.DivIcon {
|
||||||
|
private readonly _player: DynmapPlayer;
|
||||||
|
private _container?: HTMLDivElement;
|
||||||
|
private _playerImage?: HTMLImageElement;
|
||||||
|
private _playerName?: HTMLSpanElement;
|
||||||
|
|
||||||
|
private _playerHealth?: HTMLDivElement;
|
||||||
|
private _playerHealthBg?: HTMLDivElement;
|
||||||
|
private _playerHealthBar?: HTMLDivElement;
|
||||||
|
private _playerArmourBg?: HTMLDivElement;
|
||||||
|
private _playerArmourBar?: HTMLDivElement;
|
||||||
|
|
||||||
|
// @ts-ignore
|
||||||
|
options: PlayerIconOptions;
|
||||||
|
|
||||||
|
constructor(player: DynmapPlayer, options: PlayerIconOptions) {
|
||||||
|
super(options);
|
||||||
|
this._player = player;
|
||||||
|
}
|
||||||
|
|
||||||
|
createIcon(oldIcon: HTMLElement) {
|
||||||
|
if (oldIcon) {
|
||||||
|
L.DomUtil.remove(oldIcon);
|
||||||
|
}
|
||||||
|
|
||||||
|
const player = this._player;
|
||||||
|
|
||||||
|
this._container = document.createElement('div');
|
||||||
|
|
||||||
|
// var markerPosition = dynmap.getProjection().fromLocationToLatLng(player.location);
|
||||||
|
// player.marker.setLatLng(markerPosition);
|
||||||
|
|
||||||
|
this._container.classList.add('Marker', 'playerMarker', 'leaflet-marker-icon');
|
||||||
|
|
||||||
|
this._playerImage = document.createElement('img');
|
||||||
|
this._playerImage.classList.add(this.options.smallFace ? 'playerIconSm' : 'playerIcon');
|
||||||
|
this._playerImage.src = 'images/player.png';
|
||||||
|
|
||||||
|
this._playerName = document.createElement('span');
|
||||||
|
this._playerName.classList.add(this.options.smallFace ? 'playerNameSm' : 'playerName');
|
||||||
|
this._playerName.innerText = player.name;
|
||||||
|
|
||||||
|
this._container.insertAdjacentElement('beforeend', this._playerImage);
|
||||||
|
this._container.insertAdjacentElement('beforeend', this._playerName);
|
||||||
|
|
||||||
|
if (this.options.showSkinFace) {
|
||||||
|
|
||||||
|
// if (this.options.smallFace) {
|
||||||
|
// getMinecraftHead(player.account, 16, head => {
|
||||||
|
// this._playerImage!.src = head.src;
|
||||||
|
// });
|
||||||
|
// } else if (this.options.showBody) {
|
||||||
|
// getMinecraftHead(player.account, 'body', head => {
|
||||||
|
// this._playerImage!.src = head.src;
|
||||||
|
// });
|
||||||
|
// } else {
|
||||||
|
// getMinecraftHead(player.account, 32, head => {
|
||||||
|
// this._playerImage!.src = head.src;
|
||||||
|
// });
|
||||||
|
// }
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.options.showHealth) {
|
||||||
|
this._playerHealth = document.createElement('div');
|
||||||
|
|
||||||
|
this._playerHealth.classList.add(this.options.smallFace ? 'healthContainerSm' : 'healthContainer');
|
||||||
|
this._container.insertAdjacentElement('beforeend', this._playerHealth)
|
||||||
|
|
||||||
|
this._playerHealthBar = document.createElement('div');
|
||||||
|
this._playerHealthBar.classList.add('playerHealth');
|
||||||
|
|
||||||
|
this._playerArmourBar = document.createElement('div');
|
||||||
|
this._playerArmourBar.classList.add('playerHealth');
|
||||||
|
|
||||||
|
this._playerHealthBg = document.createElement('div');
|
||||||
|
this._playerArmourBg = document.createElement('div');
|
||||||
|
|
||||||
|
this._playerHealthBg.classList.add('playerHealthBackground');
|
||||||
|
this._playerArmourBar.classList.add('playerArmorBackground');
|
||||||
|
|
||||||
|
this._playerHealthBg.insertAdjacentElement('beforeend', this._playerHealthBar);
|
||||||
|
this._playerArmourBg.insertAdjacentElement('beforeend', this._playerArmourBar);
|
||||||
|
|
||||||
|
this._playerHealth.insertAdjacentElement('beforeend', this._playerHealthBg);
|
||||||
|
this._playerHealth.insertAdjacentElement('beforeend', this._playerArmourBg);
|
||||||
|
|
||||||
|
this._playerHealth.hidden = true;
|
||||||
|
} else {
|
||||||
|
this._playerName.classList.add('playerNameNoHealth');
|
||||||
|
}
|
||||||
|
|
||||||
|
return this._container;
|
||||||
|
}
|
||||||
|
|
||||||
|
update() {
|
||||||
|
this._playerName!.innerText = this._player!.name;
|
||||||
|
|
||||||
|
if (this._player.health !== undefined && this._player.armor !== undefined) {
|
||||||
|
this._playerHealth!.hidden = false;
|
||||||
|
this._playerHealthBar!.style.width = Math.ceil(this._player.health * 2.5) + 'px';
|
||||||
|
this._playerArmourBar!.style.width = Math.ceil(this._player.armor * 2.5) + 'px';
|
||||||
|
} else {
|
||||||
|
this._playerHealth!.hidden = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -1,47 +0,0 @@
|
|||||||
import DynmapTileLayer from "@/leaflet/tileLayer/DynmapTileLayer";
|
|
||||||
import HDProjection from "@/leaflet/projection/HDProjection";
|
|
||||||
import L from 'leaflet';
|
|
||||||
|
|
||||||
const HDMapType = DynmapTileLayer.extend({
|
|
||||||
projection: undefined,
|
|
||||||
options: {
|
|
||||||
maxZoom: 1,
|
|
||||||
maxNativeZoom: 1,
|
|
||||||
worldName: '',
|
|
||||||
prefix: '',
|
|
||||||
errorTileUrl: 'images/blank.png',
|
|
||||||
},
|
|
||||||
initialize(options) {
|
|
||||||
DynmapTileLayer.prototype.initialize.call(this, options);
|
|
||||||
options.zoomReverse = true;
|
|
||||||
options.tileSize = 128;
|
|
||||||
options.minZoom = 0;
|
|
||||||
L.Util.setOptions(this, options);
|
|
||||||
this.projection = new HDProjection(Object.assign(options, {map: this}));
|
|
||||||
},
|
|
||||||
|
|
||||||
getTileName: function(coords) {
|
|
||||||
let info = this.getTileInfo(coords);
|
|
||||||
// Y is inverted for HD-map.
|
|
||||||
info.y = -info.y;
|
|
||||||
info.scaledy = info.y >> 5;
|
|
||||||
return `${info.prefix}${info.nightday}/${info.scaledx}_${info.scaledy}/${info.zoom}${info.x}_${info.y}.${info.fmt}`;
|
|
||||||
},
|
|
||||||
zoomprefix: function(amount) {
|
|
||||||
// amount == 0 -> ''
|
|
||||||
// amount == 1 -> 'z_'
|
|
||||||
// amount == 2 -> 'zz_'
|
|
||||||
return 'zzzzzzzzzzzzzzzzzzzzzz'.substr(0, amount) + (amount === 0 ? '' : '_');
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
// maptypes.HDMapType = function(options) { return new HDMapType(options); };
|
|
||||||
|
|
||||||
const hdMapType = (options) => {
|
|
||||||
return new HDMapType(options);
|
|
||||||
}
|
|
||||||
|
|
||||||
export {
|
|
||||||
HDMapType,
|
|
||||||
hdMapType
|
|
||||||
};
|
|
43
src/leaflet/mapType/HDMapType.ts
Normal file
43
src/leaflet/mapType/HDMapType.ts
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
import L from 'leaflet';
|
||||||
|
import HDProjection from "@/leaflet/projection/HDProjection";
|
||||||
|
import {Coordinate} from "@/dynmap";
|
||||||
|
import {DynmapTileLayer, DynmapTileLayerOptions} from "@/leaflet/tileLayer/DynmapTileLayer";
|
||||||
|
|
||||||
|
export interface HDMapTypeOptions extends DynmapTileLayerOptions {}
|
||||||
|
|
||||||
|
export interface HDMapType extends DynmapTileLayer {
|
||||||
|
}
|
||||||
|
|
||||||
|
export class HDMapType extends DynmapTileLayer {
|
||||||
|
constructor(options: DynmapTileLayerOptions) {
|
||||||
|
super(options);
|
||||||
|
|
||||||
|
options.maxZoom = this._mapSettings.nativeZoomLevels + this._mapSettings.extraZoomLevels;
|
||||||
|
options.maxNativeZoom = this._mapSettings.nativeZoomLevels;
|
||||||
|
options.zoomReverse = true;
|
||||||
|
options.tileSize = 128;
|
||||||
|
options.minZoom = 0;
|
||||||
|
|
||||||
|
L.Util.setOptions(this, options);
|
||||||
|
this._projection = new HDProjection({
|
||||||
|
mapToWorld: this._mapSettings.mapToWorld,
|
||||||
|
worldToMap: this._mapSettings.worldToMap,
|
||||||
|
nativeZoomLevels: this._mapSettings.nativeZoomLevels,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
getTileName(coords: Coordinate) {
|
||||||
|
const info = super.getTileInfo(coords);
|
||||||
|
// Y is inverted for HD-map.
|
||||||
|
info.y = -info.y;
|
||||||
|
info.scaledy = info.y >> 5;
|
||||||
|
return `${info.prefix}${info.nightday}/${info.scaledx}_${info.scaledy}/${info.zoom}${info.x}_${info.y}.${info.fmt}`;
|
||||||
|
}
|
||||||
|
|
||||||
|
zoomprefix(amount: number) {
|
||||||
|
// amount == 0 -> ''
|
||||||
|
// amount == 1 -> 'z_'
|
||||||
|
// amount == 2 -> 'zz_'
|
||||||
|
return 'z'.repeat(amount) + (amount === 0 ? '' : '_');
|
||||||
|
}
|
||||||
|
}
|
@ -1,156 +0,0 @@
|
|||||||
import L from 'leaflet';
|
|
||||||
|
|
||||||
const PlayerMarker = L.Marker.extend({
|
|
||||||
options: {
|
|
||||||
smallFace: true,
|
|
||||||
showSkinFace: false,
|
|
||||||
showBody: false,
|
|
||||||
showHealth: false,
|
|
||||||
},
|
|
||||||
|
|
||||||
initialize: function (player, options) {
|
|
||||||
this._player = player;
|
|
||||||
options.draggable = false;
|
|
||||||
options.icon = new PlayerIcon(player, {
|
|
||||||
smallFace: options.smallFace,
|
|
||||||
showSkinFace: options.showSkinFace,
|
|
||||||
showBody: options.showBody,
|
|
||||||
showHealth: options.showHealth,
|
|
||||||
});
|
|
||||||
|
|
||||||
L.Util.setOptions(this, options);
|
|
||||||
//this._latlng = toLatLng(latlng); //TODO
|
|
||||||
},
|
|
||||||
});
|
|
||||||
|
|
||||||
var PlayerIcon = L.DivIcon.extend({
|
|
||||||
_player: null,
|
|
||||||
_container: null,
|
|
||||||
_playerImage: null,
|
|
||||||
_playerName: null,
|
|
||||||
|
|
||||||
_playerHealth: null,
|
|
||||||
_playerHealthBg: null,
|
|
||||||
_playerHealthBar: null,
|
|
||||||
_playerArmourBg: null,
|
|
||||||
_playerArmourBar: null,
|
|
||||||
|
|
||||||
options: {
|
|
||||||
smallFace: true,
|
|
||||||
showSkinFace: false,
|
|
||||||
showBody: false,
|
|
||||||
showHealth: false,
|
|
||||||
},
|
|
||||||
|
|
||||||
initialize: function (player, options) {
|
|
||||||
this._player = player;
|
|
||||||
L.Util.setOptions(this, options);
|
|
||||||
},
|
|
||||||
|
|
||||||
createIcon: function (oldIcon) {
|
|
||||||
if (oldIcon) {
|
|
||||||
L.DomUtil.remove(oldIcon);
|
|
||||||
}
|
|
||||||
|
|
||||||
var player = this._player;
|
|
||||||
|
|
||||||
this._container = document.createElement('div');
|
|
||||||
|
|
||||||
// var markerPosition = dynmap.getProjection().fromLocationToLatLng(player.location);
|
|
||||||
// player.marker.setLatLng(markerPosition);
|
|
||||||
|
|
||||||
this._container.classList.add('Marker', 'playerMarker', 'leaflet-marker-icon');
|
|
||||||
|
|
||||||
this._playerImage = document.createElement('img');
|
|
||||||
this._playerImage.classList.add(this.options.smallFace ? 'playerIconSm' : 'playerIcon');
|
|
||||||
this._playerImage.src = 'images/player.png';
|
|
||||||
|
|
||||||
this._playerName = document.createElement('span');
|
|
||||||
this._playerName.classList.add(this.options.smallFace ? 'playerNameSm' : 'playerName');
|
|
||||||
this._playerName.innerText = player.name;
|
|
||||||
|
|
||||||
this._container.insertAdjacentElement('beforeend', this._playerImage);
|
|
||||||
this._container.insertAdjacentElement('beforeend', this._playerName);
|
|
||||||
|
|
||||||
if (this.options.showSkinFace) {
|
|
||||||
var that = this;
|
|
||||||
|
|
||||||
if (this.options.smallFace) {
|
|
||||||
getMinecraftHead(player.account, 16, function (head) {
|
|
||||||
that._playerImage.src = head.src;
|
|
||||||
});
|
|
||||||
} else if (this.options.showBody) {
|
|
||||||
getMinecraftHead(player.account, 'body', function (head) {
|
|
||||||
that._playerImage.src = head.src;
|
|
||||||
});
|
|
||||||
} else {
|
|
||||||
getMinecraftHead(player.account, 32, function (head) {
|
|
||||||
that._playerImage.src = head.src;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (this.options.showHealth) {
|
|
||||||
this._playerHealth = document.createElement('div');
|
|
||||||
|
|
||||||
this._playerHealth.classList.add(this.options.smallFace ? 'healthContainerSm' : 'healthContainer');
|
|
||||||
this._container.insertAdjacentElement('beforeend', this._playerHealth)
|
|
||||||
|
|
||||||
this._playerHealthBar = document.createElement('div');
|
|
||||||
this._playerHealthBar.classList.add('playerHealth');
|
|
||||||
|
|
||||||
this._playerArmourBar = document.createElement('div');
|
|
||||||
this._playerArmourBar.classList.add('playerHealth');
|
|
||||||
|
|
||||||
this._playerHealthBg = document.createElement('div');
|
|
||||||
this._playerArmourBg = document.createElement('div');
|
|
||||||
|
|
||||||
this._playerHealthBg.classList.add('playerHealthBackground');
|
|
||||||
this._playerArmourBar.classList.add('playerArmorBackground');
|
|
||||||
|
|
||||||
this._playerHealthBg.insertAdjacentElement('beforeend', this._playerHealthBar);
|
|
||||||
this._playerArmourBg.insertAdjacentElement('beforeend', this._playerArmourBar);
|
|
||||||
|
|
||||||
this._playerHealth.insertAdjacentElement('beforeend', this._playerHealthBg);
|
|
||||||
this._playerHealth.insertAdjacentElement('beforeend', this._playerArmourBg);
|
|
||||||
|
|
||||||
this._playerHealth.hidden = true;
|
|
||||||
} else {
|
|
||||||
this._playerName.classList.add('playerNameNoHealth');
|
|
||||||
}
|
|
||||||
|
|
||||||
return this._container;
|
|
||||||
|
|
||||||
// var div = (oldIcon && oldIcon.tagName === 'DIV') ? oldIcon : document.createElement('div'),
|
|
||||||
// options = this.options;
|
|
||||||
//
|
|
||||||
// if (options.html instanceof Element) {
|
|
||||||
// empty(div);
|
|
||||||
// div.appendChild(options.html);
|
|
||||||
// } else {
|
|
||||||
// div.innerHTML = options.html !== false ? options.html : '';
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// if (options.bgPos) {
|
|
||||||
// var bgPos = toPoint(options.bgPos);
|
|
||||||
// div.style.backgroundPosition = (-bgPos.x) + 'px ' + (-bgPos.y) + 'px';
|
|
||||||
// }
|
|
||||||
// this._setIconStyles(div, 'icon');
|
|
||||||
//
|
|
||||||
// return div;
|
|
||||||
},
|
|
||||||
|
|
||||||
update() {
|
|
||||||
this._playerName.innerText = this.player.name;
|
|
||||||
|
|
||||||
if (this.options.player.health !== undefined && this.options.player.armor !== undefined) {
|
|
||||||
this.options.player.healthContainer.hidden = false;
|
|
||||||
this._this.options.playerHealthBar.style.width = Math.ceil(this.options.player.health * 2.5) + 'px';
|
|
||||||
this._this.options.playerArmourBar.style.width = Math.ceil(this.options.player.armor * 2.5) + 'px';
|
|
||||||
} else {
|
|
||||||
this.options.player.healthContainer.hidden = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
export default PlayerMarker;
|
|
29
src/leaflet/marker/PlayerMarker.ts
Normal file
29
src/leaflet/marker/PlayerMarker.ts
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
import L, {LatLng, MarkerOptions} from 'leaflet';
|
||||||
|
import {DynmapPlayer} from "@/dynmap";
|
||||||
|
import {PlayerIcon} from "@/leaflet/icon/PlayerIcon";
|
||||||
|
|
||||||
|
export interface PlayerMarkerOptions extends MarkerOptions {
|
||||||
|
smallFace: boolean,
|
||||||
|
showSkinFace: boolean,
|
||||||
|
showBody: boolean,
|
||||||
|
showHealth: boolean,
|
||||||
|
}
|
||||||
|
|
||||||
|
export class PlayerMarker extends L.Marker {
|
||||||
|
private _player: DynmapPlayer;
|
||||||
|
|
||||||
|
constructor(player: DynmapPlayer, options: PlayerMarkerOptions) {
|
||||||
|
super(new LatLng(0,0), options);
|
||||||
|
this._player = player;
|
||||||
|
options.draggable = false;
|
||||||
|
options.icon = new PlayerIcon(player, {
|
||||||
|
smallFace: options.smallFace,
|
||||||
|
showSkinFace: options.showSkinFace,
|
||||||
|
showBody: options.showBody,
|
||||||
|
showHealth: options.showHealth,
|
||||||
|
});
|
||||||
|
|
||||||
|
L.Util.setOptions(this, options);
|
||||||
|
//this._latlng = toLatLng(latlng); //TODO
|
||||||
|
}
|
||||||
|
}
|
@ -1,15 +0,0 @@
|
|||||||
import L from 'leaflet';
|
|
||||||
|
|
||||||
const DynmapProjection = L.Class.extend({
|
|
||||||
initialize: function (options) {
|
|
||||||
L.Util.setOptions(this, options);
|
|
||||||
},
|
|
||||||
fromLocationToLatLng: function () {
|
|
||||||
throw "fromLocationToLatLng not implemented";
|
|
||||||
},
|
|
||||||
fromLatLngToLocation: function () {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
export default DynmapProjection;
|
|
25
src/leaflet/projection/DynmapProjection.ts
Normal file
25
src/leaflet/projection/DynmapProjection.ts
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
import L from 'leaflet';
|
||||||
|
import {Coordinate} from "@/dynmap";
|
||||||
|
|
||||||
|
export interface DynmapProjectionOptions {}
|
||||||
|
|
||||||
|
export interface DynmapProjection {
|
||||||
|
locationToLatLng(location: Coordinate): L.LatLng;
|
||||||
|
latLngToLocation(latLng: L.LatLng, y: number): Coordinate;
|
||||||
|
}
|
||||||
|
|
||||||
|
export class DynmapProjection extends L.Class {
|
||||||
|
|
||||||
|
constructor(options: DynmapProjectionOptions) {
|
||||||
|
super();
|
||||||
|
L.Util.setOptions(this, options);
|
||||||
|
}
|
||||||
|
|
||||||
|
locationToLatLng(location: Coordinate): L.LatLng {
|
||||||
|
throw new Error("fromLocationToLatLng not implemented");
|
||||||
|
}
|
||||||
|
|
||||||
|
latLngToLocation(latLng: L.LatLng, y: number): Coordinate {
|
||||||
|
throw new Error("fromLatLngToLocation not implemented");
|
||||||
|
}
|
||||||
|
}
|
@ -1,25 +0,0 @@
|
|||||||
import DynmapProjection from "@/leaflet/projection/DynmapProjection";
|
|
||||||
import L from 'leaflet';
|
|
||||||
|
|
||||||
const HDProjection = DynmapProjection.extend({
|
|
||||||
fromLocationToLatLng: function (location) {
|
|
||||||
var wtp = this.options.worldtomap;
|
|
||||||
var lat = wtp[3] * location.x + wtp[4] * location.y + wtp[5] * location.z;
|
|
||||||
var lng = wtp[0] * location.x + wtp[1] * location.y + wtp[2] * location.z;
|
|
||||||
|
|
||||||
return new L.LatLng(
|
|
||||||
-((128 - lat) / (1 << this.options.mapzoomout)),
|
|
||||||
lng / (1 << this.options.mapzoomout),
|
|
||||||
true);
|
|
||||||
},
|
|
||||||
fromLatLngToLocation: function (latlon, y) {
|
|
||||||
var ptw = this.options.maptoworld;
|
|
||||||
var lat = latlon.lng * (1 << this.options.mapzoomout);
|
|
||||||
var lon = 128 + latlon.lat * (1 << this.options.mapzoomout);
|
|
||||||
var x = ptw[0] * lat + ptw[1] * lon + ptw[2] * y;
|
|
||||||
var z = ptw[6] * lat + ptw[7] * lon + ptw[8] * y;
|
|
||||||
return {x: x, y: y, z: z};
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
export default HDProjection;
|
|
42
src/leaflet/projection/HDProjection.ts
Normal file
42
src/leaflet/projection/HDProjection.ts
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
import {DynmapProjection} from "@/leaflet/projection/DynmapProjection";
|
||||||
|
import L from 'leaflet';
|
||||||
|
import {Coordinate} from "@/dynmap";
|
||||||
|
|
||||||
|
export interface HDProjectionOptions {
|
||||||
|
mapToWorld: [number, number, number, number, number, number, number, number, number],
|
||||||
|
worldToMap: [number, number, number, number, number, number, number, number, number],
|
||||||
|
nativeZoomLevels: number
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface HDProjection extends DynmapProjection {
|
||||||
|
options: HDProjectionOptions
|
||||||
|
}
|
||||||
|
|
||||||
|
export class HDProjection extends DynmapProjection {
|
||||||
|
constructor(options: HDProjectionOptions) {
|
||||||
|
super(options);
|
||||||
|
L.Util.setOptions(this, options);
|
||||||
|
}
|
||||||
|
|
||||||
|
locationToLatLng(location: Coordinate): L.LatLng {
|
||||||
|
const wtp = this.options.worldToMap,
|
||||||
|
lat = wtp[3] * location.x + wtp[4] * location.y + wtp[5] * location.z,
|
||||||
|
lng = wtp[0] * location.x + wtp[1] * location.y + wtp[2] * location.z;
|
||||||
|
|
||||||
|
return new L.LatLng(
|
||||||
|
-((128 - lat) / (1 << this.options.nativeZoomLevels)),
|
||||||
|
lng / (1 << this.options.nativeZoomLevels));
|
||||||
|
}
|
||||||
|
|
||||||
|
latLngToLocation(latLng: L.LatLng, y: number): Coordinate {
|
||||||
|
const ptw = this.options.mapToWorld,
|
||||||
|
lat = latLng.lng * (1 << this.options.nativeZoomLevels),
|
||||||
|
lon = 128 + latLng.lat * (1 << this.options.nativeZoomLevels),
|
||||||
|
x = ptw[0] * lat + ptw[1] * lon + ptw[2] * y,
|
||||||
|
z = ptw[6] * lat + ptw[7] * lon + ptw[8] * y;
|
||||||
|
|
||||||
|
return {x: x, y: y, z: z};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export default HDProjection;
|
@ -1,128 +0,0 @@
|
|||||||
import L from 'leaflet';
|
|
||||||
|
|
||||||
const DynmapTileLayer = L.TileLayer.extend({
|
|
||||||
options: {
|
|
||||||
worldName: '',
|
|
||||||
prefix: '',
|
|
||||||
},
|
|
||||||
|
|
||||||
_cachedTileUrls: null,
|
|
||||||
_namedTiles: null,
|
|
||||||
|
|
||||||
initialize(options) {
|
|
||||||
L.TileLayer.prototype.initialize.call(this, options);
|
|
||||||
this._cachedTileUrls = {};
|
|
||||||
this._namedTiles = {};
|
|
||||||
L.Util.setOptions(this, options);
|
|
||||||
},
|
|
||||||
|
|
||||||
getProjection: function () {
|
|
||||||
return this.projection;
|
|
||||||
},
|
|
||||||
|
|
||||||
getTileName: function() {
|
|
||||||
throw "getTileName not implemented";
|
|
||||||
},
|
|
||||||
|
|
||||||
getTileUrl: function (coords) {
|
|
||||||
var tileName = this.getTileName(coords, coords.z),
|
|
||||||
url = this._cachedTileUrls[tileName];
|
|
||||||
|
|
||||||
if (!url) {
|
|
||||||
let path = escape(`${this.options.worldName}/${tileName}`);
|
|
||||||
url = `${window.config.url.tiles}${path}`;
|
|
||||||
this._cachedTileUrls[tileName] = url;
|
|
||||||
}
|
|
||||||
|
|
||||||
return url;
|
|
||||||
},
|
|
||||||
|
|
||||||
updateNamedTile: function (name) {
|
|
||||||
var tile = this._namedTiles[name];
|
|
||||||
delete this._cachedTileUrls[name];
|
|
||||||
|
|
||||||
if (tile) {
|
|
||||||
tile.src = this._cachedTileUrls[name] = this.options.dynmap.getTileUrl(name);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
createTile(coords, done) {
|
|
||||||
var tile = L.TileLayer.prototype.createTile.call(this, coords, done),
|
|
||||||
name = this.getTileName(coords);
|
|
||||||
|
|
||||||
tile.tileName = name;
|
|
||||||
|
|
||||||
// console.log("Adding " + tile.tileName);
|
|
||||||
this._namedTiles[name] = tile;
|
|
||||||
|
|
||||||
return tile;
|
|
||||||
},
|
|
||||||
|
|
||||||
// stops loading all tiles in the background layer
|
|
||||||
_abortLoading: function () {
|
|
||||||
var i, tile;
|
|
||||||
for (i in this._tiles) {
|
|
||||||
if (!Object.prototype.hasOwnProperty.call(this._tiles, i)) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
tile = this._tiles[i]
|
|
||||||
|
|
||||||
if (tile.coords.z !== this._tileZoom) {
|
|
||||||
if (!tile.complete && tile.el && tile.el.tileName) {
|
|
||||||
// console.log("Aborting " + tile.el.tileName);
|
|
||||||
delete this._namedTiles[tile.el.tileName];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
L.TileLayer.prototype._abortLoading.call(this);
|
|
||||||
},
|
|
||||||
|
|
||||||
_removeTile: function (key) {
|
|
||||||
var tile = this._tiles[key];
|
|
||||||
|
|
||||||
if (!tile) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
var tileName = tile.el.tileName;
|
|
||||||
|
|
||||||
if (tileName) {
|
|
||||||
// console.log("Removing " + tileName);
|
|
||||||
delete this._namedTiles[tileName];
|
|
||||||
delete this._cachedTileUrls[tileName];
|
|
||||||
}
|
|
||||||
|
|
||||||
L.TileLayer.prototype._removeTile.call(this, key);
|
|
||||||
},
|
|
||||||
|
|
||||||
// Some helper functions.
|
|
||||||
zoomprefix: function (amount) {
|
|
||||||
return 'zzzzzzzzzzzzzzzzzzzzzz'.substr(0, amount);
|
|
||||||
},
|
|
||||||
|
|
||||||
getTileInfo: function (coords) {
|
|
||||||
// zoom: max zoomed in = this.options.maxZoom, max zoomed out = 0
|
|
||||||
// izoom: max zoomed in = 0, max zoomed out = this.options.maxZoom
|
|
||||||
// zoomoutlevel: izoom < mapzoomin -> 0, else -> izoom - mapzoomin (which ranges from 0 till mapzoomout)
|
|
||||||
var izoom = this._getZoomForUrl();
|
|
||||||
var zoomoutlevel = Math.max(0, izoom - (this.options.maxZoom - this.options.maxNativeZoom));
|
|
||||||
var scale = 1 << zoomoutlevel;
|
|
||||||
var x = scale * coords.x;
|
|
||||||
var y = scale * coords.y;
|
|
||||||
return {
|
|
||||||
prefix: this.options.prefix,
|
|
||||||
nightday: (this.options.nightandday && this.options.dynmap.serverday) ? '_day' : '',
|
|
||||||
scaledx: x >> 5,
|
|
||||||
scaledy: y >> 5,
|
|
||||||
zoom: this.zoomprefix(zoomoutlevel),
|
|
||||||
zoomprefix: (zoomoutlevel == 0) ? "" : (this.zoomprefix(zoomoutlevel) + "_"),
|
|
||||||
x: x,
|
|
||||||
y: y,
|
|
||||||
fmt: this.options['image-format'] || 'png'
|
|
||||||
};
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
export default DynmapTileLayer;
|
|
162
src/leaflet/tileLayer/DynmapTileLayer.ts
Normal file
162
src/leaflet/tileLayer/DynmapTileLayer.ts
Normal file
@ -0,0 +1,162 @@
|
|||||||
|
import L, {Coords, DoneCallback, TileLayerOptions} from 'leaflet';
|
||||||
|
import {DynmapProjection} from "@/leaflet/projection/DynmapProjection";
|
||||||
|
import {Coordinate, DynmapMap} from "@/dynmap";
|
||||||
|
|
||||||
|
export interface DynmapTileLayerOptions extends TileLayerOptions {
|
||||||
|
mapSettings: DynmapMap;
|
||||||
|
errorTileUrl: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface DynmapTileLayer extends L.TileLayer {
|
||||||
|
options: DynmapTileLayerOptions;
|
||||||
|
_projection: any;
|
||||||
|
_mapSettings: any;
|
||||||
|
_cachedTileUrls: any;
|
||||||
|
_namedTiles: any;
|
||||||
|
|
||||||
|
locationToLatLng(location: Coordinate): L.LatLng;
|
||||||
|
|
||||||
|
latLngToLocation(latLng: L.LatLng): Coordinate;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface DynmapTile extends HTMLImageElement {
|
||||||
|
tileName: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface TileInfo {
|
||||||
|
prefix: string;
|
||||||
|
nightday: string;
|
||||||
|
scaledx: number;
|
||||||
|
scaledy: number;
|
||||||
|
zoom: string;
|
||||||
|
zoomprefix: string;
|
||||||
|
x: number;
|
||||||
|
y: number;
|
||||||
|
fmt: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export class DynmapTileLayer extends L.TileLayer {
|
||||||
|
constructor(options: DynmapTileLayerOptions) {
|
||||||
|
super('', options);
|
||||||
|
|
||||||
|
if (options.mapSettings === null) {
|
||||||
|
throw new TypeError("mapSettings missing");
|
||||||
|
}
|
||||||
|
|
||||||
|
this._projection = new DynmapProjection({});
|
||||||
|
this._mapSettings = options.mapSettings;
|
||||||
|
this._cachedTileUrls = {};
|
||||||
|
this._namedTiles = {};
|
||||||
|
L.Util.setOptions(this, options);
|
||||||
|
}
|
||||||
|
|
||||||
|
getTileName(coords: Coordinate): string {
|
||||||
|
throw "getTileName not implemented";
|
||||||
|
}
|
||||||
|
|
||||||
|
getTileUrl(coords: Coordinate) {
|
||||||
|
const tileName = this.getTileName(coords);
|
||||||
|
let url = this._cachedTileUrls[tileName];
|
||||||
|
|
||||||
|
if (!url) {
|
||||||
|
const path = escape(`${this._mapSettings.world.name}/${tileName}`);
|
||||||
|
url = `${window.config.url.tiles}${path}`;
|
||||||
|
this._cachedTileUrls[tileName] = url;
|
||||||
|
}
|
||||||
|
|
||||||
|
return url;
|
||||||
|
}
|
||||||
|
|
||||||
|
updateNamedTile(name: string) {
|
||||||
|
const tile = this._namedTiles[name];
|
||||||
|
delete this._cachedTileUrls[name];
|
||||||
|
|
||||||
|
if (tile) {
|
||||||
|
//tile.src = this._cachedTileUrls[name] = this.getTileUrl(name);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
createTile(coords: Coords, done: DoneCallback) {
|
||||||
|
const tile = super.createTile.call(this, coords, done) as DynmapTile,
|
||||||
|
name = this.getTileName(coords);
|
||||||
|
|
||||||
|
tile.tileName = name;
|
||||||
|
|
||||||
|
// console.log("Adding " + tile.tileName);
|
||||||
|
this._namedTiles[name] = tile;
|
||||||
|
|
||||||
|
return tile;
|
||||||
|
}
|
||||||
|
|
||||||
|
// stops loading all tiles in the background layer
|
||||||
|
_abortLoading() {
|
||||||
|
let tile;
|
||||||
|
for (const i in this._tiles) {
|
||||||
|
if (!Object.prototype.hasOwnProperty.call(this._tiles, i)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
tile = this._tiles[i];
|
||||||
|
|
||||||
|
if (tile.coords.z !== this._tileZoom) {
|
||||||
|
if (tile.loaded && tile.el && (tile.el as DynmapTile).tileName) {
|
||||||
|
// console.log("Aborting " + (tile.el as DynmapTile).tileName);
|
||||||
|
delete this._namedTiles[(tile.el as DynmapTile).tileName];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
super._abortLoading.call(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
_removeTile(key: string) {
|
||||||
|
const tile = this._tiles[key];
|
||||||
|
|
||||||
|
if (!tile) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const tileName = (tile.el as DynmapTile).tileName;
|
||||||
|
|
||||||
|
if (tileName) {
|
||||||
|
// console.log("Removing " + tileName);
|
||||||
|
delete this._namedTiles[tileName];
|
||||||
|
delete this._cachedTileUrls[tileName];
|
||||||
|
}
|
||||||
|
|
||||||
|
// @ts-ignore
|
||||||
|
super._removeTile.call(this, key);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Some helper functions.
|
||||||
|
zoomprefix(amount: number) {
|
||||||
|
return 'z'.repeat(amount);
|
||||||
|
}
|
||||||
|
|
||||||
|
getTileInfo(coords: Coordinate): TileInfo {
|
||||||
|
// zoom: max zoomed in = this.options.maxZoom, max zoomed out = 0
|
||||||
|
// izoom: max zoomed in = 0, max zoomed out = this.options.maxZoom
|
||||||
|
// zoomoutlevel: izoom < mapzoomin -> 0, else -> izoom - mapzoomin (which ranges from 0 till mapzoomout)
|
||||||
|
const izoom = this._getZoomForUrl(),
|
||||||
|
zoomoutlevel = Math.max(0, izoom - this._mapSettings.extraZoomLevels),
|
||||||
|
scale = 1 << zoomoutlevel,
|
||||||
|
x = scale * coords.x,
|
||||||
|
y = scale * coords.y;
|
||||||
|
|
||||||
|
return {
|
||||||
|
prefix: this._mapSettings.prefix,
|
||||||
|
nightday: /*(this._mapSettings.nightAndDay && this.options.dynmap.serverday) ? '_day' :*/ '',
|
||||||
|
scaledx: x >> 5,
|
||||||
|
scaledy: y >> 5,
|
||||||
|
zoom: this.zoomprefix(zoomoutlevel),
|
||||||
|
zoomprefix: (zoomoutlevel == 0) ? "" : (this.zoomprefix(zoomoutlevel) + "_"),
|
||||||
|
x: x,
|
||||||
|
y: y,
|
||||||
|
fmt: this._mapSettings.imageFormat || 'png'
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
getProjection(): DynmapProjection {
|
||||||
|
return this._projection;
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user