View / add a 'smoothResolutionConstraint' options

When enabled (true by default), the resolution min/max values will be applied with
a smoothing effect for a better user experience.
This commit is contained in:
Olivier Guyot
2019-01-20 20:45:49 +01:00
parent e023c144bb
commit ef6d17d817
6 changed files with 187 additions and 65 deletions

View File

@@ -102,13 +102,13 @@ class ZoomSlider extends Control {
* @type {number|undefined}
* @private
*/
this.previousX_;
this.startX_;
/**
* @type {number|undefined}
* @private
*/
this.previousY_;
this.startY_;
/**
* The calculated thumb size (border box plus margins). Set when initSlider_
@@ -234,9 +234,10 @@ class ZoomSlider extends Control {
*/
handleDraggerStart_(event) {
if (!this.dragging_ && event.originalEvent.target === this.element.firstElementChild) {
const element = /** @type {HTMLElement} */ (this.element.firstElementChild);
this.getMap().getView().beginInteraction();
this.previousX_ = event.clientX;
this.previousY_ = event.clientY;
this.startX_ = event.clientX - parseFloat(element.style.left);
this.startY_ = event.clientY - parseFloat(element.style.top);
this.dragging_ = true;
if (this.dragListenerKeys_.length === 0) {
@@ -260,15 +261,11 @@ class ZoomSlider extends Control {
*/
handleDraggerDrag_(event) {
if (this.dragging_) {
const element = /** @type {HTMLElement} */ (this.element.firstElementChild);
const deltaX = event.clientX - this.previousX_ + parseFloat(element.style.left);
const deltaY = event.clientY - this.previousY_ + parseFloat(element.style.top);
const deltaX = event.clientX - this.startX_;
const deltaY = event.clientY - this.startY_;
const relativePosition = this.getRelativePosition_(deltaX, deltaY);
this.currentResolution_ = this.getResolutionForPosition_(relativePosition);
this.getMap().getView().setResolution(this.currentResolution_);
this.setThumbPosition_(this.currentResolution_);
this.previousX_ = event.clientX;
this.previousY_ = event.clientY;
}
}
@@ -282,18 +279,9 @@ class ZoomSlider extends Control {
const view = this.getMap().getView();
view.endInteraction();
const zoom = view.getValidZoomLevel(
view.getZoomForResolution(this.currentResolution_));
view.animate({
zoom: zoom,
duration: this.duration_,
easing: easeOut
});
this.dragging_ = false;
this.previousX_ = undefined;
this.previousY_ = undefined;
this.startX_ = undefined;
this.startY_ = undefined;
this.dragListenerKeys_.forEach(unlistenByKey);
this.dragListenerKeys_.length = 0;
}
@@ -360,7 +348,7 @@ class ZoomSlider extends Control {
*/
getPositionForResolution_(res) {
const fn = this.getMap().getView().getValueForResolutionFunction();
return 1 - fn(res);
return clamp(1 - fn(res), 0, 1);
}
}
@@ -379,10 +367,8 @@ export function render(mapEvent) {
this.initSlider_();
}
const res = mapEvent.frameState.viewState.resolution;
if (res !== this.currentResolution_) {
this.currentResolution_ = res;
this.setThumbPosition_(res);
}
this.currentResolution_ = res;
this.setThumbPosition_(res);
}