leaflet.js 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160
  1. import { loadResource } from "../../static/utils/resources.js";
  2. import { cleanObject } from "../../static/utils/json.js";
  3. export default {
  4. template: "<div></div>",
  5. props: {
  6. center: Array,
  7. zoom: Number,
  8. options: Object,
  9. draw_control: Object,
  10. resource_path: String,
  11. hide_drawn_items: Boolean,
  12. additional_resources: Array,
  13. },
  14. async mounted() {
  15. await this.$nextTick(); // NOTE: wait for window.path_prefix to be set
  16. await Promise.all([
  17. loadResource(window.path_prefix + `${this.resource_path}/leaflet/leaflet.css`),
  18. loadResource(window.path_prefix + `${this.resource_path}/leaflet/leaflet.js`),
  19. ...this.additional_resources.map((resource) => loadResource(resource)),
  20. ]);
  21. if (this.draw_control) {
  22. await Promise.all([
  23. loadResource(window.path_prefix + `${this.resource_path}/leaflet-draw/leaflet.draw.css`),
  24. loadResource(window.path_prefix + `${this.resource_path}/leaflet-draw/leaflet.draw.js`),
  25. ]);
  26. }
  27. this.map = L.map(this.$el, {
  28. ...this.options,
  29. center: this.center,
  30. zoom: this.zoom,
  31. });
  32. for (const type of [
  33. "baselayerchange",
  34. "overlayadd",
  35. "overlayremove",
  36. "zoomlevelschange",
  37. "resize",
  38. "unload",
  39. "viewreset",
  40. "load",
  41. "zoomstart",
  42. "movestart",
  43. "zoom",
  44. "move",
  45. "zoomend",
  46. "moveend",
  47. "popupopen",
  48. "popupclose",
  49. "autopanstart",
  50. "tooltipopen",
  51. "tooltipclose",
  52. "locationerror",
  53. "locationfound",
  54. "click",
  55. "dblclick",
  56. "mousedown",
  57. "mouseup",
  58. "mouseover",
  59. "mouseout",
  60. "mousemove",
  61. "contextmenu",
  62. "keypress",
  63. "keydown",
  64. "keyup",
  65. "preclick",
  66. "zoomanim",
  67. ]) {
  68. this.map.on(type, (e) => {
  69. this.$emit(`map-${type}`, {
  70. ...e,
  71. originalEvent: undefined,
  72. target: undefined,
  73. sourceTarget: undefined,
  74. center: [e.target.getCenter().lat, e.target.getCenter().lng],
  75. zoom: e.target.getZoom(),
  76. });
  77. });
  78. }
  79. for (const type of ["layeradd", "layerremove"]) {
  80. this.map.on(type, (e) => {
  81. this.$emit(`map-${type}`, {
  82. id: e.layer.id,
  83. leaflet_id: e.layer._leaflet_id,
  84. });
  85. });
  86. }
  87. if (this.draw_control) {
  88. for (const key in L.Draw.Event) {
  89. const type = L.Draw.Event[key];
  90. this.map.on(type, async (e) => {
  91. await this.$nextTick(); // NOTE: allow drawn layers to be added
  92. const cleanedObject = cleanObject(e, [
  93. "_map",
  94. "_events",
  95. "_eventParents",
  96. "_handlers",
  97. "_mapToAdd",
  98. "_initHooksCalled",
  99. ]);
  100. this.$emit(type, {
  101. ...cleanedObject,
  102. target: undefined,
  103. sourceTarget: undefined,
  104. });
  105. });
  106. }
  107. const drawnItems = new L.FeatureGroup();
  108. this.map.addLayer(drawnItems);
  109. const drawControl = new L.Control.Draw({
  110. draw: this.draw_control.draw,
  111. edit: {
  112. ...this.draw_control.edit,
  113. featureGroup: drawnItems,
  114. },
  115. });
  116. this.map.addControl(drawControl);
  117. if (!this.hide_drawn_items) {
  118. this.map.on("draw:created", (e) => drawnItems.addLayer(e.layer));
  119. }
  120. }
  121. const connectInterval = setInterval(async () => {
  122. if (window.socket.id === undefined) return;
  123. this.$emit("init", { socket_id: window.socket.id });
  124. clearInterval(connectInterval);
  125. }, 100);
  126. },
  127. methods: {
  128. add_layer(layer, id) {
  129. const l = L[layer.type](...layer.args);
  130. l.id = id;
  131. l.addTo(this.map);
  132. },
  133. remove_layer(id) {
  134. this.map.eachLayer((layer) => layer.id === id && this.map.removeLayer(layer));
  135. },
  136. clear_layers() {
  137. this.map.eachLayer((layer) => this.map.removeLayer(layer));
  138. },
  139. run_map_method(name, ...args) {
  140. if (name.startsWith(":")) {
  141. name = name.slice(1);
  142. args = args.map((arg) => new Function(`return (${arg})`)());
  143. }
  144. return runMethod(this.map, name, args);
  145. },
  146. run_layer_method(id, name, ...args) {
  147. let result = null;
  148. this.map.eachLayer((layer) => {
  149. if (layer.id !== id) return;
  150. if (name.startsWith(":")) {
  151. name = name.slice(1);
  152. args = args.map((arg) => new Function(`return (${arg})`)());
  153. }
  154. result = runMethod(layer, name, args);
  155. });
  156. return result;
  157. },
  158. },
  159. };