ngx-openlayers icon indicating copy to clipboard operation
ngx-openlayers copied to clipboard

No way to detect zoom change

Open KthProg opened this issue 7 years ago • 14 comments

There's no way to tell when the user has zoomed in or out when using the default interaction tag.

KthProg avatar Mar 02 '18 20:03 KthProg

Not only that but it looks like the value of the zoom property does not change when you zoom using the default interaction tag plus a mouse scroll. So there appears to be no way to know that the zoom has changed and what it's changed to without some custom event detection.

KthProg avatar Mar 02 '18 20:03 KthProg

As a temporary workaround I added a wheel event handler to the map, and I update a backing variable that stores the actual zoom level. There really ought to be actual event handlers on either the map or the interaction directive though.

KthProg avatar Mar 02 '18 20:03 KthProg

I catch the changed zoom with a moveend listener on the wrapped OpenLayers type. For that I inject the map component object to my Typescript code ...

    ...
    @ViewChild('map1')
    map: MapComponent;
    ...

... and register after the view is initialized the event listener

   ngAfterViewInit(): void {
      this.map.instance.on('moveend', (e:MapEvent) => {
          console.log ('map-move-end: ' + e.map.getView().getZoom());
      });
  }

That approach works for me perfect

OkieOth avatar Mar 03 '18 21:03 OkieOth

That approach seems to work much better. Still think an event should be exposed directly on the directive but very nice workaround. The map re-rendering speed seems to be less than ideal so there's a bit of a lag though, but it works much better than what I was trying before.

KthProg avatar Mar 05 '18 14:03 KthProg

Actually this doesn't totally work. This only updates when the user moves the map, not when the zoom level is changed. And this event is already exposed to Angular on the map directive so there's no need to register a handler like that.

KthProg avatar Mar 05 '18 15:03 KthProg

I replaced the event listener with the tried and true interval method. Obviously this is not ideal and exposing an actual zoom change event would be better.

KthProg avatar Mar 05 '18 20:03 KthProg

Actually, maybe your method does work, this might be another bug. The circle I have drawn on the map is not refreshing until I move the map, even if I have a timeout constantly updating the circle radius value.

KthProg avatar Mar 05 '18 20:03 KthProg

I tested the version [email protected] in Chrome and Firefox (Ubuntu 17.10) and the 'moveend' event is raised also when I only changed the zoom w/o moving the map and got the event. It's not important how the zoom is done (mouse-wheel, double-click or zoom-control)

OkieOth avatar Mar 06 '18 07:03 OkieOth

So the issue appears to be that vectors are not always redrawn (or rather the radius of a circle vector is not redrawn after each moveend event). I can create a video of this issue if needed.

KthProg avatar Mar 09 '18 18:03 KthProg

I solved in my code by a custom style function. This function is called on every redraw and sets a scale related to current zoom.

OkieOth avatar Mar 10 '18 13:03 OkieOth

Can you show me how that was done?

KthProg avatar Mar 12 '18 13:03 KthProg

Hey. Can you give me more info? Thanks.

KthProg avatar May 11 '18 16:05 KthProg

Hi! You can use this.view.instance.on('change:zoom', evt => console.log(this.view.zoom)); where view is a viewChild : @ViewChild(ViewComponent) view: ViewComponent; to detect zoom changes. I'll create a PR to add the proper view outputs in the view.

aymeric-duchein avatar Sep 26 '18 09:09 aymeric-duchein