Skip to content

Commit

Permalink
Implement loadedmetadata, loadeddata, canplay and `canplaythrou…
Browse files Browse the repository at this point in the history
…gh` events
  • Loading branch information
ku1ik committed Nov 6, 2016
1 parent 286d91d commit ed1fd4e
Show file tree
Hide file tree
Showing 8 changed files with 74 additions and 19 deletions.
22 changes: 22 additions & 0 deletions README.md
Expand Up @@ -239,6 +239,28 @@ document.getElementById('player').currentTime = 33;

### Events

#### loadedmetadata, loadeddata, canplay, canplaythrough

The `loadedmetadata`, `loadeddata`, `canplay` and `canplaythrough` events are
fired (all of them, in this order) when the recording has been loaded and is
ready to play. The recordings are always fully fetched (you can't partially load
JSON) so there's no difference in the amount of metadata/data available between
these 4 events - when either event occurs the player already has all the
information for smooth playback. In other words, it's enough to listen to only
one of them, e.g. `canplaythrough` (all 4 are supported to make it more in line
with HTMLVideoElement).

```javascript
document.getElementById('player').addEventListener('canplaythrough, function(e) {
console.log("all ready to play");
}
```
NOTE: The player starts fetching the recording either when `preload` attribute
is set (in this case these events may not be immediately followed by `play`
event), or when user starts the playback (in this case these events are
immediately followed by `play` event).
#### play
The `play` event is fired when playback has begun.
Expand Down
16 changes: 16 additions & 0 deletions resources/public/element.html
Expand Up @@ -19,6 +19,22 @@
/* this.currentTime = 33;*/
})

player.addEventListener('loadedmetadata', function(e) {
console.log('got "loadedmetadata" event');
})

player.addEventListener('loadeddata', function(e) {
console.log('got "loadeddata" event');
})

player.addEventListener('canplay', function(e) {
console.log('got "canplay" event');
})

player.addEventListener('canplaythrough', function(e) {
console.log('got "canplaythrough" event');
})

player.addEventListener('play', function(e) {
console.log('got "play" event');
console.log("we're at", this.currentTime);
Expand Down
16 changes: 14 additions & 2 deletions resources/public/element.js
Expand Up @@ -45,8 +45,20 @@ function registerAsciinemaPlayerElement() {
this.opt('author-url', 'authorURL'),
this.opt('author-img-url', 'authorImgURL'),
{
onPlay: function() { self.dispatchEvent(new CustomEvent("play")); },
onPause: function() { self.dispatchEvent(new CustomEvent("pause")); }
onCanPlay: function() {
self.dispatchEvent(new CustomEvent("loadedmetadata"));
self.dispatchEvent(new CustomEvent("loadeddata"));
self.dispatchEvent(new CustomEvent("canplay"));
self.dispatchEvent(new CustomEvent("canplaythrough"));
},

onPlay: function() {
self.dispatchEvent(new CustomEvent("play"));
},

onPause: function() {
self.dispatchEvent(new CustomEvent("pause"));
}
}
);

Expand Down
3 changes: 2 additions & 1 deletion src/asciinema/player/core.cljs
Expand Up @@ -79,7 +79,8 @@
:font-size font-size
:theme theme
:show-hud false}
(select-keys options [:title :author :author-url :author-img-url :on-play :on-pause]))))
(select-keys options [:title :author :author-url :author-img-url
:on-can-play :on-play :on-pause]))))

(defn make-player-ratom
"Returns Reagent atom with initial player state."
Expand Down
1 change: 1 addition & 0 deletions src/asciinema/player/js.cljs
Expand Up @@ -15,6 +15,7 @@
:authorURL :author-url
:startAt :start-at
:authorImgURL :author-img-url
:onCanPlay :on-can-play
:onPlay :on-play
:onPause :on-pause}))
player (p/create-player dom-node url options)]
Expand Down
6 changes: 3 additions & 3 deletions src/asciinema/player/messages.cljs
Expand Up @@ -28,14 +28,14 @@

;;; Source originated messages

(defrecord Resize [width height])

(defrecord SetDuration [duration])
(defrecord SetMetadata [width height duration])

(defrecord SetLoading [loading])

(defrecord SetPlaying [playing])

(defrecord TriggerCanPlay [])

(defrecord UpdateScreen [screen])

(defrecord UpdateTime [time])
21 changes: 12 additions & 9 deletions src/asciinema/player/processing.cljs
Expand Up @@ -66,20 +66,23 @@
;;; Source originated messages

(extend-protocol m/Update
m/Resize
(update-player [this {player-width :width player-height :height :as player}]
(-> player
(assoc :width (or player-width (:width this)))
(assoc :height (or player-height (:height this)))))

m/SetDuration
(update-player [this player]
(assoc player :duration (:duration this)))
m/SetMetadata
(update-player [{:keys [width height duration]} {player-width :width player-height :height :as player}]
(assoc player
:width (or player-width width)
:height (or player-height height)
:duration duration))

m/SetLoading
(update-player [this player]
(assoc player :loading (:loading this)))

m/TriggerCanPlay
(update-player [this {:keys [on-can-play] :as player}]
(when on-can-play
(on-can-play))
player)

m/UpdateTime
(update-player [this player]
(assoc player :current-time (:time this))))
Expand Down
8 changes: 4 additions & 4 deletions src/asciinema/player/source.cljs
Expand Up @@ -87,14 +87,14 @@
:handler #(deliver (recording-fn %))
:error-handler #(println %)}))))

(defn report-duration-and-size
(defn report-metadata
"Waits for recording to load and then reports its size and duration to the
player."
[{:keys [recording-ch-fn]} msg-ch]
(go
(let [{:keys [duration width height]} (<! (@recording-ch-fn false))]
(>! msg-ch (m/->SetDuration duration))
(>! msg-ch (m/->Resize width height)))))
(>! msg-ch (m/->SetMetadata width height duration))
(>! msg-ch (m/->TriggerCanPlay)))))

(defn show-poster
"Forces loading of recording and sends 'poster' at a given time to the
Expand Down Expand Up @@ -226,7 +226,7 @@
(reset! command-ch (start-event-loop! this msg-ch))
(let [f (make-recording-ch-fn url recording-fn)]
(reset! recording-ch-fn f)
(report-duration-and-size this msg-ch))
(report-metadata this msg-ch))
(when preload?
(@recording-ch-fn true))
(if auto-play?
Expand Down

0 comments on commit ed1fd4e

Please sign in to comment.