[particles] basic zoom/pan
Shift + left click to pan
mousewheel to zoom (centering on mouse coordinates)
Bug: skia:
Change-Id: I3bd0381734266e42e1ad5fe565890af3cf98f739
Reviewed-on: https://skia-review.googlesource.com/c/buildbot/+/201360
Commit-Queue: Kevin Lubick <kjlubick@google.com>
Reviewed-by: Mike Reed <reed@google.com>
Reviewed-by: Joe Gregorio <jcgregorio@google.com>
diff --git a/particles/modules/particles-player-sk/particles-player-sk.js b/particles/modules/particles-player-sk/particles-player-sk.js
index b04c334..af2f994 100644
--- a/particles/modules/particles-player-sk/particles-player-sk.js
+++ b/particles/modules/particles-player-sk/particles-player-sk.js
@@ -14,6 +14,9 @@
const CanvasKitInit = require('../../build/canvaskit/canvaskit.js');
+const ZOOM_IN_FACTOR = 1.1; // 10%
+const ZOOM_OUT_FACTOR = 1/ZOOM_IN_FACTOR;
+
// This element might be loaded from a different site, and that means we need
// to be careful about how we construct the URL back to the canvas.wasm file.
// Start by recording the script origin.
@@ -33,7 +36,10 @@
const runningTemplate = (ele) => html`
<div class=container>
+ <!-- It would be more mobile friendly to use pointermove, but Safari doesn't support it-->
<canvas id=player
+ @wheel=${ele._wheel}
+ @mousemove=${ele._drag}
width=${ele._config.width * window.devicePixelRatio}
height=${ele._config.height * window.devicePixelRatio}
style='width: ${ele._config.width}px; height: ${ele._config.height}px;'>
@@ -60,6 +66,9 @@
lastTs: 0, // last time stamp we had a frame
};
+
+ this._lastDrag = null;
+ this._zoomLevel = 1.0;
}
connectedCallback() {
@@ -72,6 +81,22 @@
this.render();
}
+ _drag(e) {
+ if (!e.buttons || !e.shiftKey) { // ignore movements unless shift is held
+ this._lastDrag = null;
+ return;
+ }
+ if (this._lastDrag) {
+ const dx = e.clientX - this._lastDrag[0];
+ const dy = e.clientY - this._lastDrag[1];
+
+ const canvas = this._engine.canvas.translate(dx / this._zoomLevel,
+ dy / this._zoomLevel);
+ }
+ this._lastDrag = [e.clientX, e.clientY];
+
+ }
+
_drawFrame() {
if (!this._engine.animation || !this._engine.canvas) {
return;
@@ -139,9 +164,9 @@
this._engine.canvas.clear(this._config.bgcolor);
// Center the animation
- this._engine.canvas.translate(this._config.width/2, this._config.height/2);
+ this.resetView();
- this.reset();
+ this.restartAnimation();
this._drawFrame();
}
@@ -170,8 +195,43 @@
this, {eventContext: this});
}
- reset() {
+ resetView() {
+ const ck = this._engine.kit;
+ const canvas = this._engine.canvas;
+ // Reset to identity
+ const tt = canvas.getTotalMatrix();
+ const itt = ck.SkMatrix.invert(tt);
+ canvas.concat(itt);
+ // Zoom to the middle of the animation
+ canvas.translate(this._config.width/2, this._config.height/2);
+ }
+
+ restartAnimation() {
this._state.time = 0;
this._state.lastTs = 0;
}
+
+ _wheel(e) {
+ e.preventDefault();
+ e.stopPropagation();
+
+ let zoom = 0;
+ if (e.deltaY < 0) {
+ zoom = ZOOM_IN_FACTOR;
+ } else {
+ zoom = ZOOM_OUT_FACTOR;
+ }
+ this._zoomLevel *= zoom;
+ const ck = this._engine.kit;
+ const canvas = this._engine.canvas;
+
+ const tt = canvas.getTotalMatrix();
+ const itt = ck.SkMatrix.invert(tt);
+ const pts = [e.clientX, e.clientY];
+ ck.SkMatrix.mapPoints(itt, pts); // Transform DOM pts into canvas space
+
+ let matr = ck.SkMatrix.scaled(zoom, zoom, pts[0], pts[1]);
+ canvas.concat(matr);
+
+ }
});
\ No newline at end of file
diff --git a/particles/modules/particles-sk/particles-sk.js b/particles/modules/particles-sk/particles-sk.js
index 53c10f2..c841b7b 100644
--- a/particles/modules/particles-sk/particles-sk.js
+++ b/particles/modules/particles-sk/particles-sk.js
@@ -39,6 +39,10 @@
<figcaption>
particles-wasm
+ <button @click=${ele._resetView}
+ title="Shift + Left click to pan, scroll wheel to zoom">
+ Reset Pan/Zoom
+ </button>
</figcaption>`;
const jsonEditor = (ele) => {
@@ -64,7 +68,7 @@
${ele._state.filename} ${ele._width}x${ele._height} ...
</button>
<div class=controls>
- <button @click=${ele._reset}>Reset</button>
+ <button @click=${ele._restartAnimation}>Restart</button>
<button id=playpause @click=${ele._playpause}>Pause</button>
<button ?hidden=${!ele._hasEdits} @click=${ele._applyEdits}>Apply Edits</button>
<div class=download>
@@ -344,8 +348,12 @@
this._editorLoaded = true;
}
- _reset() {
- this._particlesPlayer && this._particlesPlayer.reset();
+ _resetView() {
+ this._particlesPlayer && this._particlesPlayer.resetView();
+ }
+
+ _restartAnimation() {
+ this._particlesPlayer && this._particlesPlayer.restartAnimation();
}
_startEdit() {