UNPKG

6.34 kBJavaScriptView Raw
1/**
2 * @file source-updater.js
3 */
4'use strict';
5
6Object.defineProperty(exports, '__esModule', {
7 value: true
8});
9
10var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();
11
12function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { 'default': obj }; }
13
14function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }
15
16var _videoJs = require('video.js');
17
18var _videoJs2 = _interopRequireDefault(_videoJs);
19
20var noop = function noop() {};
21
22/**
23 * A queue of callbacks to be serialized and applied when a
24 * MediaSource and its associated SourceBuffers are not in the
25 * updating state. It is used by the segment loader to update the
26 * underlying SourceBuffers when new data is loaded, for instance.
27 *
28 * @class SourceUpdater
29 * @param {MediaSource} mediaSource the MediaSource to create the
30 * SourceBuffer from
31 * @param {String} mimeType the desired MIME type of the underlying
32 * SourceBuffer
33 */
34
35var SourceUpdater = (function () {
36 function SourceUpdater(mediaSource, mimeType) {
37 var _this = this;
38
39 _classCallCheck(this, SourceUpdater);
40
41 var createSourceBuffer = function createSourceBuffer() {
42 _this.sourceBuffer_ = mediaSource.addSourceBuffer(mimeType);
43
44 // run completion handlers and process callbacks as updateend
45 // events fire
46 _this.onUpdateendCallback_ = function () {
47 var pendingCallback = _this.pendingCallback_;
48
49 _this.pendingCallback_ = null;
50
51 if (pendingCallback) {
52 pendingCallback();
53 }
54
55 _this.runCallback_();
56 };
57
58 _this.sourceBuffer_.addEventListener('updateend', _this.onUpdateendCallback_);
59
60 _this.runCallback_();
61 };
62
63 this.callbacks_ = [];
64 this.pendingCallback_ = null;
65 this.timestampOffset_ = 0;
66 this.mediaSource = mediaSource;
67 this.processedAppend_ = false;
68
69 if (mediaSource.readyState === 'closed') {
70 mediaSource.addEventListener('sourceopen', createSourceBuffer);
71 } else {
72 createSourceBuffer();
73 }
74 }
75
76 /**
77 * Aborts the current segment and resets the segment parser.
78 *
79 * @param {Function} done function to call when done
80 * @see http://w3c.github.io/media-source/#widl-SourceBuffer-abort-void
81 */
82
83 _createClass(SourceUpdater, [{
84 key: 'abort',
85 value: function abort(done) {
86 var _this2 = this;
87
88 if (this.processedAppend_) {
89 this.queueCallback_(function () {
90 _this2.sourceBuffer_.abort();
91 }, done);
92 }
93 }
94
95 /**
96 * Queue an update to append an ArrayBuffer.
97 *
98 * @param {ArrayBuffer} bytes
99 * @param {Function} done the function to call when done
100 * @see http://www.w3.org/TR/media-source/#widl-SourceBuffer-appendBuffer-void-ArrayBuffer-data
101 */
102 }, {
103 key: 'appendBuffer',
104 value: function appendBuffer(bytes, done) {
105 var _this3 = this;
106
107 this.processedAppend_ = true;
108 this.queueCallback_(function () {
109 _this3.sourceBuffer_.appendBuffer(bytes);
110 }, done);
111 }
112
113 /**
114 * Indicates what TimeRanges are buffered in the managed SourceBuffer.
115 *
116 * @see http://www.w3.org/TR/media-source/#widl-SourceBuffer-buffered
117 */
118 }, {
119 key: 'buffered',
120 value: function buffered() {
121 if (!this.sourceBuffer_) {
122 return _videoJs2['default'].createTimeRanges();
123 }
124 return this.sourceBuffer_.buffered;
125 }
126
127 /**
128 * Queue an update to remove a time range from the buffer.
129 *
130 * @param {Number} start where to start the removal
131 * @param {Number} end where to end the removal
132 * @see http://www.w3.org/TR/media-source/#widl-SourceBuffer-remove-void-double-start-unrestricted-double-end
133 */
134 }, {
135 key: 'remove',
136 value: function remove(start, end) {
137 var _this4 = this;
138
139 if (this.processedAppend_) {
140 this.queueCallback_(function () {
141 _this4.sourceBuffer_.remove(start, end);
142 }, noop);
143 }
144 }
145
146 /**
147 * Whether the underlying sourceBuffer is updating or not
148 *
149 * @return {Boolean} the updating status of the SourceBuffer
150 */
151 }, {
152 key: 'updating',
153 value: function updating() {
154 return !this.sourceBuffer_ || this.sourceBuffer_.updating || this.pendingCallback_;
155 }
156
157 /**
158 * Set/get the timestampoffset on the SourceBuffer
159 *
160 * @return {Number} the timestamp offset
161 */
162 }, {
163 key: 'timestampOffset',
164 value: function timestampOffset(offset) {
165 var _this5 = this;
166
167 if (typeof offset !== 'undefined') {
168 this.queueCallback_(function () {
169 _this5.sourceBuffer_.timestampOffset = offset;
170 });
171 this.timestampOffset_ = offset;
172 }
173 return this.timestampOffset_;
174 }
175
176 /**
177 * Queue a callback to run
178 */
179 }, {
180 key: 'queueCallback_',
181 value: function queueCallback_(callback, done) {
182 this.callbacks_.push([callback.bind(this), done]);
183 this.runCallback_();
184 }
185
186 /**
187 * Run a queued callback
188 */
189 }, {
190 key: 'runCallback_',
191 value: function runCallback_() {
192 var callbacks = undefined;
193
194 if (!this.updating() && this.callbacks_.length) {
195 callbacks = this.callbacks_.shift();
196 this.pendingCallback_ = callbacks[1];
197 callbacks[0]();
198 }
199 }
200
201 /**
202 * dispose of the source updater and the underlying sourceBuffer
203 */
204 }, {
205 key: 'dispose',
206 value: function dispose() {
207 this.sourceBuffer_.removeEventListener('updateend', this.onUpdateendCallback_);
208 if (this.sourceBuffer_ && this.mediaSource.readyState === 'open') {
209 this.sourceBuffer_.abort();
210 }
211 }
212 }]);
213
214 return SourceUpdater;
215})();
216
217exports['default'] = SourceUpdater;
218module.exports = exports['default'];
\No newline at end of file