0

I am using apple's MapKit JS to embed a map into a webpage. I need to get access to marker annotations in the underlying HTML Shadow Dom, i want to add a classname to the elements. Using the browser developer tools I can "see" the shadow dom

Shadow Dom Structure

I use the following code to "traverse" the shadow dom:

  let annotationContainer = document.querySelector(".mk-annotation-container");

  let mapAnnotations = annotationContainer.shadowRoot.querySelector(".mk-annotations");

  console.log(mapAnnotations);

  if (!mapAnnotations.hasChildNodes()) {
    console.log("There are NO child nodes");
  }

  let firstAnnotation = mapAnnotations.firstElementChild;
  console.log("First Child: "+firstAnnotation);

  var annotationMarkers = mapAnnotations.children;
  console.log(annotationMarkers)

When this is run, the console logs shows the mapAnnotations does have a childElementCount of 2 and the nodes are shown in the childNodes and children attributes. However, when reading the children or childnodes it is displaying that there are no children and the resulting HTMLCollection in variable annotationMarkers has two elements but a length of 0.

Console Output showing parent node with children

Console Output shwoing logging messages

I have seen several similar questions where the answer seems to be that the DOM is not completely loaded, although when logging the parent node this does show child elements.

So my question is in 2 parts, does the parent element know it has 2 children but these elements arent actually loaded at that point and

secondly, is there a way to perform a similar $(document).ready function call on the shadowDom? Thus ensuring that all elements in the shadowDom (or all child elements of the parent mapAnnotations node) has been loaded?

I have tried a ready function on the shadowRoot element and had an eventListener attached listening for DomContentLeaded event but this doesnt fire at all.

Update 30/09/2020 @ 20:30

I have put a setTimeout in the JS, and the child node count is now showing as 2 after the timeout completes. I need to find a way to wait on the completion of the shadowDom and for elements to exist :/

davecymru
  • 11
  • 2
  • I suggest you to use jquery, it's much user friendly. Also add part of your html code. – ilyas Jumadurdyew Sep 30 '20 at 17:50
  • thaks ilyas. i hadnt thought of using jquery but yes would be more friendly ;) i'll convert it and try it again though i suspect the problem will still be there. There isnt any more relevant HTML , the section of DOM being read is in the image. I do have all the .js calls at the end of the main HTML (ie for jQuery and Apple Mapkit and also my own .js which is where I am reading the DOM). I have tried putting the code above in a script tag on $.ready but no difference. I suspect that it may be that the ready function is not detecting that the shadow DOM is not complete. :/ – davecymru Sep 30 '20 at 18:08
  • Try to use call_back function like: function some_action(call_back_function) {} – ilyas Jumadurdyew Sep 30 '20 at 22:15
  • jQuery doesn't know anything about Custom Elements, but feel free to add an extra 87KB download. The Custom Element API being *bare-bones* you have to develop this behaviour yourself; where Frameworks and Libraries have something like ``afterUpdate``. You have to wait in the ``connectedCallback`` till the EventLoop is ready with ``setTimeout( func , 0)`` or something similar. Be aware of FireFox differences: https://stackoverflow.com/questions/61971919/wait-for-element-upgrade-in-connectedcallback-firefox-and-chromium-differences – Danny '365CSI' Engelman Oct 01 '20 at 08:57

1 Answers1

-1

With Jquery library

var child_items = $('.your_parrent_class').find('li');

console.log(child_items.length);
ilyas Jumadurdyew
  • 883
  • 11
  • 24
  • tried this, same result. the parent class ".mk-annotations" has 2 child DIV elements but the child_items.length is still showing 0. I can only this that this is about timing on the elements actually existing in the Shadow Dom and when the .length is called the elements so not exist but in the console log as a "live" display. the elements are there. – davecymru Sep 30 '20 at 18:31
  • This is some kind of impossible, I've tried this and it's working. – ilyas Jumadurdyew Sep 30 '20 at 22:12