1 introduction

With the rapid iteration of mobile technology and the rapid decline of data flow costs, video and live broadcast are becoming a media feast for the whole people, and our company will certainly not be missing this feast. What is described here is the effect of full-screen playback and sliding switching of imitation douaudiovideo through H5, which is used by our company for live broadcast identification and playback of video.

2 Effect

3 Design Scheme

  • Video playbackvideoThe label

The 'video' tag is a new HTML5 tag for video playback. MDN describes it as follows:Copy the code

The

Compatibility is as follows (from Can I Use) :Its good compatibility in mobile terminal, has become one of our first choice

  • Single video buffering

The preload property for the video tag: This property defines whether the video is preloaded. Property has three selectable values: None, metadata, and auto

- None: no preloading is performed. With this property value, it is possible that the page creator thinks the user does not expect the video, or that the HTTP request is reduced. - Metadata: partial preloading. With this property value, the page creator thinks the user does not expect the video, but provides the user with some metadata (including size, first frame, track list, duration, and so on). -auto: The user needs this video to be loaded first; In other words, a tip: you can download the entire video if you want, even if the user doesn't necessarily want to use it.Copy the code

But in real life, it’s only partially preloaded. It does not automatically download all the video content, such a strategy is actually beneficial to save users from unnecessary broadband requests.

If not set, the default value is browser-defined (that is, different browsers choose their own default value), even though the specification recommends metadata.

Due to different implementations of different browsers, some browsers are set to auto by default. In auto Settings, if there are multiple videos in the page, it will be buffered at the same time, resulting in waste of resources and white screen and crash on low-end Android machines.

Therefore, in order to ensure that the current video plays quickly and smoothly, try to ensure that only the current video is in the resource loading.

  • Infinite loading implementation

    • Simple solution: Use lists for infinite loading. Similar to the implementation of an infinite drop-down list, the implementation is simple, but there are bound to be page performance issues in the infinite loading case
    • Complex scheme: Refer to the cyclic loading scheme on the last page of the rotation diagram, use three large nodes, and implicitly switch after each animation. The schematic diagram is as follows:

4 implement

4.1 Code implementation at the template layer

Code implementation by vue, currently used three main nodes arranged up and down, up and down information, such as video cover is placed in the middle place the actual video information, and the node is mainly used for the user when sliding video preview video covers and other relevant information, through to monitor touch related events to switch on the mobile end implementation, the main code is as follows:

<div
  :class="[isMove && 'wrap-animation']"
  :style="{ transform: `translateY(${translateY}px)`}"
  @touchstart="onTouchStart"
  @touchmove.prevent="onTouchMove"
  @touchend="onTouchEnd"
>
  <div><! -- Some like information other than the video --></div>
  <div><! -- Video information --></div>
  <div><! -- Some like information other than the video --></div>
</div>
Copy the code

4.2 Automatic switching animation implementation

  • Js implementationPKCSS implementation

At the end of the user to touch, if switching conditions are met, then you need to switch to the next video, need to switch the animation, animation implementation are mainly requestAnimationFrame/setTimeout and other traditional methods, In this example, in order to achieve the smoothness of the low end Android machine, so the CSS transition is used to implement, through the isMove judgment to add the wrap-animation class, animation class implementation is as follows:

.wrap-animation {
  transition: transform .6s;
}
Copy the code
  • Determine whether to switch videos

It is determined by the user’s sliding distance and sliding speed. If one is satisfied, the main implementation is to record the sliding distance at the beginning and in the process of sliding by translateY parameter. Meanwhile, the page drag-and-follow effect is realized in the slide, and the time stamp at the beginning of the slide is used by startTime parameter. Judging at the end of the slide, if you need to move to the next video, the animation will be started with the isMove parameter, and then the switch will be made by modifying the translateY parameter.

onTouchEnd () {
  if (this.isMove || this.translateY == 0) return
  // Calculate the sliding speed
  const speed = Math.abs(this.translateY / (Date.now() - this.startTime));
  // Determine whether the moving distance and sliding speed reach the limit
  if (Math.abs(this.translateY) > this.maxY || speed > this.maxSpeed) {
    // Start the toggle animation
    this.isMove = true;
    this.translateY = this.translateY < 0 ? -this.clientHeight : this.clientHeight;
    // Animation end processing removes animation parameters and makes an implicit interface switch
    setTimeout(() = > {
      // Turn off toggle animation toggle data
      this.isMove = false
      this.videoIndex = this.translateY < 0 ? this.videoIndex + 1 : this.videoIndex - 1;
      this.translateY = 0;
      // Get the list of recommended videos
      // Switch videos and other operations
    }, 500)}else {
    // Restore the original position}}Copy the code

In the next frame after the end of the animation, remove the animation, and carry out implicit interface data switching, so repeated, to achieve the effect of infinite loading. In order to determine the end time of the animation, this example uses setTimeout implementation, this operation is not accurate, it is recommended to use the transitionend event to implement.

5 Various problems

In the implementation of the time of various problems, welcome to ridicule

5.1 Full-screen Video

According to MDN:

Use the provided API so that one element, along with its children, can take up the entire screen and, in the meantime, hide all the browser user interfaces and other applications from the screen.

In general, there are two ways to use full screen, one mock full screen and one Web native. The advantage of simulating full screen is that you can customize related controls to achieve the purpose of unified multi-end style, which is admittedly more complex; Native full screen is relatively convenient, processing will be relatively easy, the disadvantage is that after the full screen, almost can not do what intervention. Therefore, analog full screen is adopted

5.1.1 Preventing the default Full-screen Playback on iOS

Videos played on iOS will be played in full screen by default, and there is little intervention. Therefore, it is necessary to disable this capability and adopt simulated full screen playback. In iOS 10 and later, you can prevent default full screen playback on iOS by adding the Playsinline property to the video TAB. In iOS 9, you can add the Webkit-Playsinline property before it, and add both properties if you want compatibility.

5.2 Video Plays automatically

Automatically playing the video after entering the page can greatly improve the user experience. This function is mainly implemented by the video element autoplay attribute, which is prompted on the MDN as follows:

Note for use:

  • The autoPlay property takes precedence over Preload if the user wants toplay the video automatically, then the browser obviously needs to download the video. Setting autoPlay and Preload at the same time is allowed in the specification.
  • The specification does not force browsers to follow the value of this property; This is just a hint.

There is no need to force browsers to comply with this attribute, so some mobile browsers have autoplay and other muted Settings, such as IOS 10+ and Chrome, allow autoplay.

However, through practice, the android client can not realize autoplay most of the time. After multiple investigations, the web side can not deal with it. Finally, we turned to the client to modify related parameters of the webview container and add the autoplay attribute to realize autoplay.

webView.getSettings().setMediaPlaybackRequiresUserGesture(false);
Copy the code

5.3 Troubleshooting Play Method Errors

The play() method of the video tag returns a Promise object. If the play fails, an error message can be obtained by returning a Promise catch. This is very important for us, when there is a JS call playback failure, we can guide the user friendly, and report the relevant error information and model, especially in the strange Android model compatibility.

6 think

Continuous sliding smoothness Since this scheme requires an implicit data modification in the next frame after each switchover, it does not support continuous sliding. Is there a better scheme?

Let us know in the comments section!