Browse Source

Added dispose method

Ievgen Naida 5 năm trước cách đây
mục cha
commit
7966294ee0

+ 13 - 0
README.md

@@ -58,6 +58,19 @@ import {
 timeline.initialize({ id: 'timeline' });
 timeline.initialize({ id: 'timeline' });
 ```
 ```
 
 
+### Build 
+
+run once to install development references:
+```bash
+  npm install
+```
+
+to pack JavaScript as a bundle:
+
+```bash
+  npm run build
+```
+
 ### Draw the outline tree
 ### Draw the outline tree
 
 
 Scroll events can be synchronized with the outline at the left side of the control.
 Scroll events can be synchronized with the outline at the left side of the control.

+ 1 - 12
demo/index.html

@@ -67,18 +67,7 @@
       {
       {
         //keyframesShape: "rect",
         //keyframesShape: "rect",
         drawKeyframes: true,
         drawKeyframes: true,
-        // Custom keyframes renderer:
-        renderKeyframes: function (ctx, pos, bounds, keyframe, lane) {
-          if (!bounds) {
-            return;
-          }
 
 
-          ctx.fillStyle = 'gray';
-          let size = 15;
-          ctx.beginPath();
-          ctx.rect(pos.x, pos.y - size / 2, 5, size);
-          ctx.fill();
-        },
         selected: false,
         selected: false,
         hidden: false,
         hidden: false,
         keyframes: [
         keyframes: [
@@ -143,7 +132,7 @@
       },
       },
     ];
     ];
 
 
-    let timeline = new timelineModule.Timeline({id:'timeline'})
+    let timeline = new timelineModule.Timeline({ id: 'timeline' })
 
 
     timeline.setModel({ rows: rows });
     timeline.setModel({ rows: rows });
 
 

+ 66 - 20
lib/animation-timeline.js

@@ -207,7 +207,7 @@ var TimelineEventsEmitter = /*#__PURE__*/function () {
   function TimelineEventsEmitter() {
   function TimelineEventsEmitter() {
     _classCallCheck(this, TimelineEventsEmitter);
     _classCallCheck(this, TimelineEventsEmitter);
 
 
-    _defineProperty(this, "subscriptions", []);
+    _defineProperty(this, "_subscriptions", []);
   }
   }
 
 
   _createClass(TimelineEventsEmitter, [{
   _createClass(TimelineEventsEmitter, [{
@@ -218,7 +218,7 @@ var TimelineEventsEmitter = /*#__PURE__*/function () {
         return;
         return;
       }
       }
 
 
-      this.subscriptions.push({
+      this._subscriptions.push({
         topic: topic,
         topic: topic,
         callback: callback
         callback: callback
       });
       });
@@ -230,7 +230,7 @@ var TimelineEventsEmitter = /*#__PURE__*/function () {
   }, {
   }, {
     key: "off",
     key: "off",
     value: function off(topic, callback) {
     value: function off(topic, callback) {
-      this.subscriptions = this.subscriptions.filter(function (event) {
+      this._subscriptions = this._subscriptions.filter(function (event) {
         return event && event.callback != callback && event.topic != topic;
         return event && event.callback != callback && event.topic != topic;
       });
       });
     }
     }
@@ -241,14 +241,14 @@ var TimelineEventsEmitter = /*#__PURE__*/function () {
   }, {
   }, {
     key: "offAll",
     key: "offAll",
     value: function offAll() {
     value: function offAll() {
-      this.subscriptions.length = 0;
+      this._subscriptions.length = 0;
     } // emit event.
     } // emit event.
     // eslint-disable-next-line @typescript-eslint/no-explicit-any
     // eslint-disable-next-line @typescript-eslint/no-explicit-any
 
 
   }, {
   }, {
     key: "emit",
     key: "emit",
     value: function emit(topic, args) {
     value: function emit(topic, args) {
-      this.subscriptions.forEach(function (event) {
+      this._subscriptions.forEach(function (event) {
         if (event && event.topic == topic && event.callback) {
         if (event && event.topic == topic && event.callback) {
           event.callback(args);
           event.callback(args);
         }
         }
@@ -906,10 +906,7 @@ var timeline_Timeline = /*#__PURE__*/function (_TimelineEventsEmitte) {
     });
     });
 
 
     timeline_defineProperty(_assertThisInitialized(_this), "handleScrollEvent", function (args) {
     timeline_defineProperty(_assertThisInitialized(_this), "handleScrollEvent", function (args) {
-      if (_this.scrollFinishedTimerRef) {
-        clearTimeout(_this.scrollFinishedTimerRef);
-        _this.scrollFinishedTimerRef = null;
-      } // Set a timeout to run event 'scrolling end'.
+      _this.clearScrollFinishedTimer(); // Set a timeout to run event 'scrolling end'.
 
 
 
 
       _this.scrollFinishedTimerRef = setTimeout(function () {
       _this.scrollFinishedTimerRef = setTimeout(function () {
@@ -1274,6 +1271,42 @@ var timeline_Timeline = /*#__PURE__*/function (_TimelineEventsEmitte) {
       window.addEventListener('mouseup', this.handleMouseUpEvent, false);
       window.addEventListener('mouseup', this.handleMouseUpEvent, false);
       window.addEventListener('touchend', this.handleMouseUpEvent, false);
       window.addEventListener('touchend', this.handleMouseUpEvent, false);
     }
     }
+  }, {
+    key: "dispose",
+    value: function dispose() {
+      this._subscriptions = null;
+      this.container = null;
+      this.canvas = null;
+      this.scrollContainer = null;
+      this.scrollContent = null;
+      this.ctx = null;
+      this.cleanUpSelection();
+      this.container.removeEventListener('wheel', this.handleWheelEvent);
+
+      if (this.scrollContainer) {
+        this.scrollContainer.removeEventListener('scroll', this.handleScrollEvent);
+      }
+
+      window.removeEventListener('blur', this.handleBlurEvent);
+      window.removeEventListener('resize', this.handleWindowResizeEvent);
+      document.removeEventListener('keydown', this.handleDocumentKeydownEvent);
+      this.canvas.removeEventListener('touchstart', this.handleMouseDownEvent);
+      this.canvas.removeEventListener('mousedown', this.handleMouseDownEvent);
+      window.removeEventListener('mousemove', this.handleMouseMoveEvent);
+      window.removeEventListener('touchmove', this.handleMouseMoveEvent);
+      window.removeEventListener('mouseup', this.handleMouseUpEvent);
+      window.removeEventListener('touchend', this.handleMouseUpEvent);
+      this.stopAutoPan();
+      this.clearScrollFinishedTimer();
+    }
+  }, {
+    key: "clearScrollFinishedTimer",
+    value: function clearScrollFinishedTimer() {
+      if (this.scrollFinishedTimerRef) {
+        clearTimeout(this.scrollFinishedTimerRef);
+        this.scrollFinishedTimerRef = null;
+      }
+    }
   }, {
   }, {
     key: "performClick",
     key: "performClick",
     value: function performClick(pos, args, drag) {
     value: function performClick(pos, args, drag) {
@@ -1925,7 +1958,7 @@ var timeline_Timeline = /*#__PURE__*/function (_TimelineEventsEmitte) {
 
 
         if (!includeStipesBounds && (!row.keyframes || !row.keyframes.forEach || row.keyframes.length <= 0)) {
         if (!includeStipesBounds && (!row.keyframes || !row.keyframes.forEach || row.keyframes.length <= 0)) {
           return;
           return;
-        } // Get min and max ms to draw keyframe lane:
+        } // Get min and max ms to draw keyframe rows:
 
 
 
 
         if (row && row.keyframes) {
         if (row && row.keyframes) {
@@ -2057,25 +2090,25 @@ var timeline_Timeline = /*#__PURE__*/function (_TimelineEventsEmitte) {
   }, {
   }, {
     key: "getKeyframesStripeSize",
     key: "getKeyframesStripeSize",
     value: function getKeyframesStripeSize(row, rowY, minValue, maxValue) {
     value: function getKeyframesStripeSize(row, rowY, minValue, maxValue) {
-      var keyframeLaneHeight = TimelineStyleUtils.rowStripeHeight(row, this.options.rowsStyle);
+      var stripeHeight = TimelineStyleUtils.rowStripeHeight(row, this.options.rowsStyle);
       var height = TimelineStyleUtils.getRowHeight(row, this.options.rowsStyle);
       var height = TimelineStyleUtils.getRowHeight(row, this.options.rowsStyle);
 
 
-      if (!keyframeLaneHeight && keyframeLaneHeight !== 0 || isNaN(keyframeLaneHeight) || keyframeLaneHeight == 'auto') {
-        keyframeLaneHeight = Math.floor(height * 0.8);
+      if (!stripeHeight && stripeHeight !== 0 || isNaN(stripeHeight) || stripeHeight == 'auto') {
+        stripeHeight = Math.floor(height * 0.8);
       }
       }
 
 
-      if (keyframeLaneHeight > height) {
-        keyframeLaneHeight = height;
+      if (stripeHeight > height) {
+        stripeHeight = height;
       }
       }
 
 
-      var margin = height - keyframeLaneHeight; // draw keyframes lane.
+      var margin = height - stripeHeight; // draw keyframes rows.
 
 
       var xMin = this.valToPx(minValue);
       var xMin = this.valToPx(minValue);
       var xMax = this.valToPx(maxValue);
       var xMax = this.valToPx(maxValue);
       return {
       return {
         x: xMin,
         x: xMin,
         y: rowY + Math.floor(margin / 2),
         y: rowY + Math.floor(margin / 2),
-        height: keyframeLaneHeight,
+        height: stripeHeight,
         width: TimelineUtils.getDistance(xMin, xMax)
         width: TimelineUtils.getDistance(xMin, xMax)
       };
       };
     }
     }
@@ -2516,21 +2549,34 @@ var timeline_Timeline = /*#__PURE__*/function (_TimelineEventsEmitte) {
         radius: radius
         radius: radius
       };
       };
     }
     }
+    /**
+     * Apply container div size to the container.
+     */
+
   }, {
   }, {
-    key: "rescale",
-    value: function rescale(newWidth, newHeight, scrollMode) {
+    key: "rescaleCanvas",
+    value: function rescaleCanvas() {
+      var changed = false;
       var width = this.scrollContainer.clientWidth * this.pixelRatio;
       var width = this.scrollContainer.clientWidth * this.pixelRatio;
       var height = this.scrollContainer.clientHeight * this.pixelRatio;
       var height = this.scrollContainer.clientHeight * this.pixelRatio;
 
 
       if (Math.floor(width) != Math.floor(this.ctx.canvas.width)) {
       if (Math.floor(width) != Math.floor(this.ctx.canvas.width)) {
         this.ctx.canvas.width = width;
         this.ctx.canvas.width = width;
+        changed = true;
       }
       }
 
 
       if (Math.floor(height) != Math.floor(this.ctx.canvas.height)) {
       if (Math.floor(height) != Math.floor(this.ctx.canvas.height)) {
         this.ctx.canvas.height = height;
         this.ctx.canvas.height = height;
+        changed = true;
       }
       }
 
 
       this.ctx.setTransform(this.pixelRatio, 0, 0, this.pixelRatio, 0, 0);
       this.ctx.setTransform(this.pixelRatio, 0, 0, this.pixelRatio, 0, 0);
+      return changed;
+    }
+  }, {
+    key: "rescale",
+    value: function rescale(newWidth, newHeight, scrollMode) {
+      this.rescaleCanvas();
       var data = this.calculateRowsBounds();
       var data = this.calculateRowsBounds();
 
 
       if (data && data.area) {
       if (data && data.area) {
@@ -2567,7 +2613,7 @@ var timeline_Timeline = /*#__PURE__*/function (_TimelineEventsEmitte) {
       }
       }
     }
     }
     /**
     /**
-     * Find clickable elements under the current position.
+     * Find clickable elements under the mouse position.
      */
      */
 
 
   }, {
   }, {

Những thai đổi đã bị hủy bỏ vì nó quá lớn
+ 0 - 0
lib/animation-timeline.min.js


+ 1 - 1
package.json

@@ -1,6 +1,6 @@
 {
 {
   "name": "animation-timeline-js",
   "name": "animation-timeline-js",
-  "version": "2.0.0",
+  "version": "2.0.1",
   "description": "animation timeline control based on the canvas.",
   "description": "animation timeline control based on the canvas.",
   "main": "lib/animation-timeline.min.js",
   "main": "lib/animation-timeline.min.js",
   "types": "src/index.ts",
   "types": "src/index.ts",

+ 48 - 4
src/timeline.ts

@@ -189,6 +189,36 @@ export class Timeline extends TimelineEventsEmitter {
     window.addEventListener('mouseup', this.handleMouseUpEvent, false);
     window.addEventListener('mouseup', this.handleMouseUpEvent, false);
     window.addEventListener('touchend', this.handleMouseUpEvent, false);
     window.addEventListener('touchend', this.handleMouseUpEvent, false);
   }
   }
+
+  public dispose(): void {
+    // Unsubscribe all events
+    this.offAll();
+    this.container = null;
+    this.canvas = null;
+    this.scrollContainer = null;
+    this.scrollContent = null;
+    this.ctx = null;
+    this.cleanUpSelection();
+
+    this.container.removeEventListener('wheel', this.handleWheelEvent);
+
+    if (this.scrollContainer) {
+      this.scrollContainer.removeEventListener('scroll', this.handleScrollEvent);
+    }
+
+    window.removeEventListener('blur', this.handleBlurEvent);
+    window.removeEventListener('resize', this.handleWindowResizeEvent);
+    document.removeEventListener('keydown', this.handleDocumentKeydownEvent);
+    this.canvas.removeEventListener('touchstart', this.handleMouseDownEvent);
+    this.canvas.removeEventListener('mousedown', this.handleMouseDownEvent);
+    window.removeEventListener('mousemove', this.handleMouseMoveEvent);
+    window.removeEventListener('touchmove', this.handleMouseMoveEvent);
+    window.removeEventListener('mouseup', this.handleMouseUpEvent);
+    window.removeEventListener('touchend', this.handleMouseUpEvent);
+    // Stop times
+    this.stopAutoPan();
+    this.clearScrollFinishedTimer();
+  }
   private handleBlurEvent = (): void => {
   private handleBlurEvent = (): void => {
     this.cleanUpSelection();
     this.cleanUpSelection();
   };
   };
@@ -206,12 +236,14 @@ export class Timeline extends TimelineEventsEmitter {
     }
     }
   };
   };
 
 
-  private handleScrollEvent = (args: MouseEvent): void => {
+  private clearScrollFinishedTimer(): void {
     if (this.scrollFinishedTimerRef) {
     if (this.scrollFinishedTimerRef) {
       clearTimeout(this.scrollFinishedTimerRef);
       clearTimeout(this.scrollFinishedTimerRef);
       this.scrollFinishedTimerRef = null;
       this.scrollFinishedTimerRef = null;
     }
     }
-
+  }
+  private handleScrollEvent = (args: MouseEvent): void => {
+    this.clearScrollFinishedTimer();
     // Set a timeout to run event 'scrolling end'.
     // Set a timeout to run event 'scrolling end'.
     this.scrollFinishedTimerRef = setTimeout(() => {
     this.scrollFinishedTimerRef = setTimeout(() => {
       if (!this.isPanStarted) {
       if (!this.isPanStarted) {
@@ -1540,18 +1572,30 @@ export class Timeline extends TimelineEventsEmitter {
     } as MousePoint;
     } as MousePoint;
   }
   }
 
 
-  private rescale(newWidth?: number, newHeight?: number, scrollMode?: string): void {
+  /**
+   * Apply container div size to the container.
+   */
+  private rescaleCanvas(): boolean {
+    let changed = false;
     const width = this.scrollContainer.clientWidth * this.pixelRatio;
     const width = this.scrollContainer.clientWidth * this.pixelRatio;
     const height = this.scrollContainer.clientHeight * this.pixelRatio;
     const height = this.scrollContainer.clientHeight * this.pixelRatio;
     if (Math.floor(width) != Math.floor(this.ctx.canvas.width)) {
     if (Math.floor(width) != Math.floor(this.ctx.canvas.width)) {
       this.ctx.canvas.width = width;
       this.ctx.canvas.width = width;
+      changed = true;
     }
     }
 
 
     if (Math.floor(height) != Math.floor(this.ctx.canvas.height)) {
     if (Math.floor(height) != Math.floor(this.ctx.canvas.height)) {
       this.ctx.canvas.height = height;
       this.ctx.canvas.height = height;
+      changed = true;
     }
     }
 
 
     this.ctx.setTransform(this.pixelRatio, 0, 0, this.pixelRatio, 0, 0);
     this.ctx.setTransform(this.pixelRatio, 0, 0, this.pixelRatio, 0, 0);
+
+    return changed;
+  }
+
+  private rescale(newWidth?: number, newHeight?: number, scrollMode?: string): void {
+    this.rescaleCanvas();
     const data = this.calculateRowsBounds();
     const data = this.calculateRowsBounds();
     if (data && data.area) {
     if (data && data.area) {
       const additionalOffset = this.options.stepPx;
       const additionalOffset = this.options.stepPx;
@@ -1592,7 +1636,7 @@ export class Timeline extends TimelineEventsEmitter {
   }
   }
 
 
   /**
   /**
-   * Find clickable elements under the current position.
+   * Find clickable elements under the mouse position.
    */
    */
   private getDraggable(pos: MousePoint): TimelineDraggableData {
   private getDraggable(pos: MousePoint): TimelineDraggableData {
     // few extra pixels to select items:
     // few extra pixels to select items:

+ 5 - 5
src/timelineEventsEmitter.ts

@@ -4,7 +4,7 @@ interface Event {
 }
 }
 
 
 export class TimelineEventsEmitter {
 export class TimelineEventsEmitter {
-  private subscriptions: Array<Event> = [];
+  protected _subscriptions: Array<Event> = [];
 
 
   // on event.
   // on event.
   on(topic: string, callback: Function): void {
   on(topic: string, callback: Function): void {
@@ -12,7 +12,7 @@ export class TimelineEventsEmitter {
       return;
       return;
     }
     }
 
 
-    this.subscriptions.push({
+    this._subscriptions.push({
       topic: topic,
       topic: topic,
       callback: callback,
       callback: callback,
     });
     });
@@ -21,7 +21,7 @@ export class TimelineEventsEmitter {
    * Remove an event from the subscriptions list.
    * Remove an event from the subscriptions list.
    */
    */
   off(topic: string, callback: Function): void {
   off(topic: string, callback: Function): void {
-    this.subscriptions = this.subscriptions.filter((event) => {
+    this._subscriptions = this._subscriptions.filter((event) => {
       return event && event.callback != callback && event.topic != topic;
       return event && event.callback != callback && event.topic != topic;
     });
     });
   }
   }
@@ -30,13 +30,13 @@ export class TimelineEventsEmitter {
    * Unsubscribe all
    * Unsubscribe all
    */
    */
   offAll(): void {
   offAll(): void {
-    this.subscriptions.length = 0;
+    this._subscriptions.length = 0;
   }
   }
 
 
   // emit event.
   // emit event.
   // eslint-disable-next-line @typescript-eslint/no-explicit-any
   // eslint-disable-next-line @typescript-eslint/no-explicit-any
   emit(topic: string, args: any): void {
   emit(topic: string, args: any): void {
-    this.subscriptions.forEach((event) => {
+    this._subscriptions.forEach((event) => {
       if (event && event.topic == topic && event.callback) {
       if (event && event.topic == topic && event.callback) {
         event.callback(args);
         event.callback(args);
       }
       }

+ 2 - 5
tsconfig.json

@@ -10,8 +10,5 @@
     "strict": false,
     "strict": false,
     "declaration": true
     "declaration": true
   },
   },
-  "exclude": [
-    "node_modules",
-    "dist"
-  ]
-}
+  "exclude": ["node_modules", "dist"]
+}

+ 1 - 1
webpack.config.js

@@ -24,5 +24,5 @@ module.exports = {
     // eslint-disable-next-line no-undef
     // eslint-disable-next-line no-undef
     path: path.resolve(__dirname, 'lib'),
     path: path.resolve(__dirname, 'lib'),
   },
   },
-  plugins:[new UnminifiedWebpackPlugin()]
+  plugins: [new UnminifiedWebpackPlugin()],
 };
 };

Một số tệp đã không được hiển thị bởi vì quá nhiều tập tin thay đổi trong này khác