35
ProgramClip
Objective
- Responder
- View
- Clip
- ProgramClip
- Clip
- View
Move the pointer of the mouse over the clip. Click in the clip or press the space bar to start playing it. Click or press again the space bar to pause it, continue to play it. Use the right and left arrows to move forward or backward by one second, press the Shift key or the Ctrl key at the same time to move forward or backward by ten seconds or a hundred milliseconds. Press the 0 key to come back to the beginning. Press the plus key to play the clip faster, the minus key to play it slower, the asterisk key to play it at the normal speed.
- function ProgramClip() {
- Clip.call(this);
- this._interval = 200;
- this._timer = null;
- }
- ProgramClip.prototype = Object.create(Clip.prototype);
- Object.defineProperty(ProgramClip.prototype, 'constructor', { value: ProgramClip, enumerable: false, writable: true });
- Object.defineProperty(ProgramClip.prototype, 'playbackRate', {
- get: function() {
- return this._playbackRate;
- },
- set: function(r) {
- if (typeof r !== 'number')
- throw new TypeError();
- if (r < Clip.minPlaybackRate || r > Clip.maxPlaybackRate)
- throw new RangeError();
- this._playbackRate = r;
- if (this._timer)
- this._startTimer();
- }
- });
- ProgramClip.prototype.drawWidget = function() {
- return this;
- };
- ProgramClip.prototype.setInterval = function(ms) {
- if (!Number.isInteger(ms))
- throw new TypeError();
- if (ms <= 0)
- throw new RangeError();
- if (this._interval == ms)
- return this;
- this._interval = ms;
- if (this._timer)
- this._startTimer();
- return this;
- };
- ProgramClip.prototype.seek = function(ms) {
- if (!Number.isInteger(ms))
- throw new TypeError();
- if (ms < 0)
- throw new RangeError();
- let duration = this.duration;
- if (duration && ms > duration)
- ms = duration;
- this._currentTime = ms;
- this._ended = false;
- this.drawWidget();
- this.notify('clipSeeked', this);
- return this;
- };
- ProgramClip.prototype.play = function() {
- if (this._timer)
- return this;
- if (this._ended || this._currentTime == 0)
- this.seek(0);
- this._ended = this._paused = false;
- this._startTimer();
- return this;
- };
- ProgramClip.prototype.pause = function() {
- if (!this._timer)
- return this;
- this._paused = true;
- this._stopTimer();
- return this;
- };
- ProgramClip.prototype._startTimer = function() {
- if (this._timer)
- window.clearInterval(this._timer);
- const duration = this.duration;
- this._timer = window.setInterval(() => {
- this._currentTime += this._interval;
- if (duration && this._currentTime > duration)
- this._currentTime = duration;
- this.drawWidget();
- if (duration && this._currentTime == duration) {
- window.clearInterval(this._timer);
- this._timer = null;
- this._ended = this._paused = true;
- this.notify('clipEnded', this);
- }
- }, Math.floor(this._interval / this._playbackRate));
- return this;
- };
- ProgramClip.prototype._stopTimer = function() {
- if (this._timer) {
- window.clearInterval(this._timer);
- this._timer = null;
- }
- return this;
- };
Test
- <?php $id=uniqid('id'); ?>
- <div id="<?php echo $id; ?>" class="noprint">
- <div class="solarsystem"></div>
- </div>
- <?php head('javascript', '/objectivejs/Objective.js'); ?>
- <?php head('javascript', '/objectivejs/Responder.js'); ?>
- <?php head('javascript', '/objectivejs/View.js'); ?>
- <?php head('javascript', '/objectivejs/Clip.js'); ?>
- <?php head('javascript', '/objectivejs/ProgramClip.js'); ?>
- <?php head('javascript', '/objectivejs/tests/SolarSystemClip.js'); ?>
- const container = document.querySelector('#<?php echo $id; ?>');
- const display = container.querySelector('.solarsystem');
- const clip = new SolarSystemClip();
- clip.setWidget(display);
- clip.enablePlayer();
- window.onload = () => clip.drawWidget();
- function SolarSystemClip() {
- ProgramClip.call(this);
- this._width = this._height = 300;
- this._duration = 60*1000;
- this._interval = 40;
- this._sun = document.createElement('img');
- this._moon = document.createElement('img');
- this._earth = document.createElement('img');
- this._sun.src = '/objectivejs/tests/solarsystem_sun.png';
- this._moon.src = '/objectivejs/tests/solarsystem_moon.png';
- this._earth.src = '/objectivejs/tests/solarsystem_earth.png';
- this._ctx = null;
- }
- SolarSystemClip.prototype = Object.create(ProgramClip.prototype);
- Object.defineProperty(SolarSystemClip.prototype, 'constructor', { value: SolarSystemClip, enumerable: false, writable: true });
- SolarSystemClip.prototype.setWidget = function(w) {
- const canvas = document.createElement('canvas');
- canvas.width = this._width;
- canvas.height = this._height;
- const ctx = canvas.getContext('2d');
- ctx.fillStyle = 'black';
- ctx.fillRect(0, 0, this._width, this._height);
- this._ctx = ctx;
- w.appendChild(canvas);
- Clip.prototype.setWidget.call(this, canvas);
- return this;
- };
- SolarSystemClip.prototype.drawWidget = function() {
- const ms = this._currentTime;
- const ctx = this._ctx;
- ctx.globalCompositeOperation = 'destination-over';
- ctx.clearRect(0, 0, 300, 300);
- ctx.fillStyle = 'rgba(0, 0, 0, 0.4)';
- ctx.strokeStyle = 'rgba(0, 153, 255, 0.4)';
- ctx.save();
- ctx.translate(150, 150);
- // earth
- ctx.rotate(((2 * Math.PI) / 60000) * ms);
- ctx.translate(105, 0);
- ctx.fillRect(0, -12, 40, 24); // shadow
- ctx.drawImage(this._earth, -12, -12);
- // moon
- ctx.save();
- ctx.rotate(((2 * Math.PI) / 6000) * ms);
- ctx.translate(0, 28.5);
- ctx.drawImage(this._moon, -3.5, -3.5);
- ctx.restore();
- ctx.restore();
- ctx.beginPath();
- ctx.arc(150, 150, 105, 0, Math.PI * 2, false); // earth orbit
- ctx.stroke();
- ctx.drawImage(this._sun, 0, 0, 300, 300);
- return this;
- };
SEE ALSO
Clip, AnimateClip, VideoClip, Draggable, Editing a programmed clip
Comments