Leaflet Map manipulation

  • 1
  • 1
  • Question
  • Updated 2 weeks ago
  • In Progress
I am wondering if it is possible to interact with the Leaflet map before it is initialized and apply a filter to a layer on the map?

My first problem is being able to consistently load the Leaflet package. This goes hand in hand with being able to load any additional package in QuickBase using the IOL method, what is the best practice for this?

I attempted using JQuery's getScript function, but Leaflet (L) was not consistently defined, sometimes it loaded successfully, sometimes it did not.

The times that L was successfully defined, I was able to use the  L.Map.addInitHook function to get a list of Leaflet map objects. The next goal would be to bind an event handler to the load event of the map, and then iterate through the layer list. However, when I did this the layers were empty, so maybe the "load" event is not correct. 

If I call map.eachLayer(); in the console after all loading is complete, I am able to get a list of layers with marker objects representing my data. This is what I want to filter but I am not sure how to bind my filter function to the appropriate event so that it is called at the proper time.

Any insight would be greatly appreciated!
Photo of Nick Wade

Nick Wade

  • 122 Points 100 badge 2x thumb
  • confused

Posted 2 weeks ago

  • 1
  • 1
Photo of Ⲇanom the ultimate (Dan Diebolt)

Ⲇanom the ultimate (Dan Diebolt), Champion

  • 28,304 Points 20k badge 2x thumb

Leaflet - like many JavaScript libraries today - has detection logic in it that dynamically determines the environment the script is in and loads the guts of library code (1) as a global variable, (2) as an AMD module, (3) as a CommonJS module or (4) as a ES6 module.  You have to unminify the Leaflet library to see this code and since it is machine generated as part of the build process it can be very difficult to read and understand:
! function(t, i) {
  "object" == typeof exports && "undefined" != typeof module ? i(exports) : "function" == typeof define && define.amd ? define(["exports"], i) : i(t.L = {})
}(this, function(t) {
  // .... lots of code ...
});
Since QuickBase uses requirejs to load AMD modules onto its pages, Leaflet will detect this condition and load as an AMD module if properly configured.
require.config({
  paths: {
    "leaflet": "https://cdnjs.cloudflare.com/ajax/libs/leaflet/1.3.4/leaflet";
  }
});
require(['leaflet'], function(L) {
  console.dir(L);
});
(Edited)
Photo of Nick Wade

Nick Wade

  • 122 Points 100 badge 2x thumb
Thanks, I am somewhat familiar with module loading in JS. I think my initial issue is stemming from Leaflet not being loaded when my IOL injected script is running. Because of this, I have to attach an event handler to an event that occurs after Leaflet is loaded by QuickBase.

Is there a way to postpone my IOL script from running until after all modules have successfully loaded?
Photo of Ⲇanom the ultimate (Dan Diebolt)

Ⲇanom the ultimate (Dan Diebolt), Champion

  • 28,304 Points 20k badge 2x thumb
I would have to see the code but the IOL is the bootstrapper for loading everything else so its code must and will run first. Within module.js you place the following code and requirejs will insure all the required modules under its management will load at the point of console.dir() statement:
require.config({
  paths: {
    "leaflet": "https://cdnjs.cloudflare.com/ajax/libs/leaflet/1.3.4/leaflet";
  }
});

require(['leaflet'], function(L) {
  console.dir(L);
  /your code here
});
(Edited)
Photo of Nick Wade

Nick Wade

  • 122 Points 100 badge 2x thumb
Alright, this is making more sense to me now. I wasn't aware that requirejs was available to me in the IOL loaded modules. That helps a ton. 
Photo of Ⲇanom the ultimate (Dan Diebolt)

Ⲇanom the ultimate (Dan Diebolt), Champion

  • 28,304 Points 20k badge 2x thumb
>. I wasn't aware that requirejs was available to me in the IOL loaded modules.

You are injecting module.js into a QuickBase authored page so everything on the QuickBase page is available within module.js.
We use a closure within module.js so our code does not bleed into QuickBase authored page and interfere with its operation: 

Leave No Trace