View not updating fast enough with *ngIf binding

I’ve set up a google map which has markers on it :

      addMarkersToMap(markers) {
 for(let marker of markers) {
    this.geocoder = new google.maps.Geocoder();
    this.geocoder.geocode({
     'address': marker["address"]
    }, (results,status) => {  
              var position = new google.maps.LatLng(results[0].geometry.location.lat(),results[0].geometry.location.lng());
              this.personMarker = new google.maps.Marker({position: position, title: marker.name, markerInfo: marker, map : this.map , icon : marker.imageurl});
              google.maps.event.addListener(this.personMarker, 'click',  () => {
              this.showCard = true;
              this.org = marker.organization;
              this.gig = marker.gig;
              this.location = marker["address"];
              this.image = marker.imageurl;
              this.ngoData = marker;
              this.ownerusername = marker.ownerusername;
                      });
    });
 }
}

And I’ve set up an event handler for when a marker is clicked. As you can see, in the handler, this.showCard is set to true (initially set to false). A card in my view is supposed to bind to this variable through *ngIf :

 <ion-card *ngIf="showCard">
   {{showCard}}
   <ion-card-content>
     some message
  </ion-card-content>
 </ion-card>

But the issue is, clicking the marker does not make my ion-card appear immediately : It takes a while for it to show up. I added some log messages in my event handler and it shows that the value of this.showCard is indeed set to true as soon as I click the marker. But still, my card doesn’t show up and the {{showCard}} value in the template remains false (eventually becomes true after like 20 seconds, which is when the card becomes visible). I don’t understand what is causing the delay for the variable reference to get updated. What could be the cause of the problem here?

2 Likes

I have the same problem :frowning:

  1. Don’t put the ngIf in the card. Put it in a div that wraps the card.
  2. Did you post the html of your markers? If you can, make them all tappable.

Hey!

Wrapped it in a div :

         <div *ngIf="showCard">
           <ion-card>
           <ion-card-content>

           </ion-card-content>
          </ion-card>
        </div>

Still having the same issue :frowning:
Also, there is no explicit html for the markers, this is the line that adds the markers to the map :

  this.personMarker = new google.maps.Marker({position: position, title: marker.name, markerInfo: marker, map : this.map , icon : marker.imageurl});

and then this is the event handler for the marker :

       google.maps.event.addListener(this.personMarker, 'click',  () => {
          this.showCard = true;
          this.org = marker.organization;
          this.gig = marker.gig;
          this.location = marker["address"];
          this.image = marker.imageurl;
          this.ngoData = marker;
          this.ownerusername = marker.ownerusername;
                  });

There was another google maps thread where the problem was the newest version and the OP solved the problem by rolling back to a more stable version. You might want to search it, or if you’re using the newest version, try rolling back and seeing if things are faster. I don’t remember if it was the same issue though, sorry.

But I feel like the issue doesn’t have to do with Google Maps because the value of this.showCard does change to true when I click on a marker, it’s just that my view doesn’t seem to know that. It’s just really weird that the variable has different values when referred in the view and when logged in the controller. Could this be a bug with Angular?

I haven’t looked at your code properly, but if you are running code outside of Angular’s zone change detection will not be triggered, which results in your UI not updating.

To force code to run inside of Angular’s zone, you can import NgZone from @angular/core and inject it into your constructor as zone. Then you will be able to do this:

this.zone.run(() => {
  //run the code that should update the view
});
6 Likes

Hey guys, is there any update on what is causing this? I just started experiencing this problem on my ionic angular project and it wasn’t happening before. I am using the latest version of ionic (v6.16.3)

I was merely using ngIfs and ngFors and the Dom was updating as I was changing variables in my .ts files but now even when the variables change the html just won’t update unless I wrap the changes in the this.zone.run() block…

Generally speaking, “external sources of asynchronous events that aren’t Angular-aware”. Whenever you are considering adding a library dependency, especially one that deals with user interaction or events, always look for an Angular-friendly wrapper for it.