getAssetUnsupportedReason(asset, needOffline) {
    if (needOffline &&
        (!shaka.offline.Storage.support() || !this.initialStoredList_)) {
      return 'Your browser does not support offline storage.';
    }

    if (asset.source == shakaAssets.Source.CUSTOM) {
      // We can't be sure if custom assets are supported or not. Just assume
      // they are.
      return null;
    }

    // Is the asset disabled?
    if (asset.disabled) {
      return 'This asset is disabled.';
    }

    if (needOffline && !asset.features.includes(shakaAssets.Feature.OFFLINE)) {
      return 'This asset cannot be downloaded.';
    }

    if (!asset.isClear() && !asset.isAes128()) {
      const hasSupportedDRM = asset.drm.some((drm) => {
        for (const identifier of shakaAssets.identifiersForKeySystem(drm)) {
          if (this.support_.drm[identifier]) {
            return true;
          }
        }
        return false;
      });
      if (!hasSupportedDRM) {
        return 'Your browser does not support the required key systems.';
      }
      if (needOffline) {
        const hasSupportedOfflineDRM = asset.drm.some((drm) => {
          for (const identifier of shakaAssets.identifiersForKeySystem(drm)) {
            // Special case when using clear keys.
            if (identifier == 'org.w3.clearkey') {
              const licenseServers = asset.getLicenseServers();
              if (!licenseServers.has(identifier)) {
                return this.support_.drm[identifier];
              }
            } else if (this.support_.drm[identifier]) {
              return this.support_.drm[identifier].persistentState;
            }
          }
          return false;
        });
        if (!hasSupportedOfflineDRM) {
          return 'Your browser does not support offline licenses for the ' +
              'required key systems.';
        }
      }
    }

    // Does the browser support the asset's manifest type?
    if (asset.features.includes(shakaAssets.Feature.DASH) &&
        !this.support_.manifest['application/dash+xml']) {
      return 'Your browser does not support MPEG-DASH manifests.';
    }
    if (asset.features.includes(shakaAssets.Feature.HLS) &&
        !this.support_.manifest['application/x-mpegurl']) {
      return 'Your browser does not support HLS manifests.';
    }
    if (asset.features.includes(shakaAssets.Feature.MSS) &&
        !this.support_.manifest['application/vnd.ms-sstr+xml']) {
      return 'Your browser does not support MSS manifests.';
    }

    // Does the asset contain a playable mime type?
    const mimeTypes = [];
    if (asset.features.includes(shakaAssets.Feature.WEBM)) {
      mimeTypes.push('video/webm');
    }
    if (asset.features.includes(shakaAssets.Feature.MP4)) {
      mimeTypes.push('video/mp4');
    }
    if (asset.features.includes(shakaAssets.Feature.MP2TS)) {
      mimeTypes.push('video/mp2t');
    }
    if (asset.features.includes(shakaAssets.Feature.CONTAINERLESS)) {
      mimeTypes.push('audio/aac');
    }
    if (asset.features.includes(shakaAssets.Feature.DOLBY_VISION_P8_1)) {
      mimeTypes.push('video/mp4; codecs="hvc1.2.4.L120.b0"');
      mimeTypes.push('video/mp4; codecs="dvh1.08.03"');
    }
    if (asset.features.includes(shakaAssets.Feature.DOLBY_VISION_P8_4)) {
      mimeTypes.push('video/mp4; codecs="hvc1.2.4.L123.b0"');
      mimeTypes.push('video/mp4; codecs="dvh1.08.03"');
    }
    if (asset.features.includes(shakaAssets.Feature.DOLBY_VISION_P5)) {
      mimeTypes.push('video/mp4; codecs="dvh1.05.01"');
    }
    if (asset.features.includes(shakaAssets.Feature.DOLBY_VISION_3D)) {
      mimeTypes.push('video/mp4; codecs="dvh1.20.01"');
    }
    if (asset.features.includes(shakaAssets.Feature.AV1)) {
      mimeTypes.push('video/mp4; codecs="av01.0.01M.08"');
    }
    if (asset.features.includes(shakaAssets.Feature.MV_HEVC)) {
      mimeTypes.push('video/mp4; codecs="hvc1.2.20000000.L153.B0"');
    }
    if (asset.features.includes(shakaAssets.Feature.APAC)) {
      mimeTypes.push('audio/mp4; codecs="apac.31.00"');
    }
    let hasSupportedMimeType = mimeTypes.some((type) => {
      return this.support_.media[type];
    });
    if (!hasSupportedMimeType &&
        !(window.ManagedMediaSource || window.MediaSource) &&
        !!navigator.vendor && navigator.vendor.includes('Apple')) {
      if (mimeTypes.includes('video/mp4')) {
        hasSupportedMimeType = true;
      }
      if (mimeTypes.includes('video/mp2t')) {
        hasSupportedMimeType = true;
      }
    }
    if (!hasSupportedMimeType) {
      return 'Your browser does not support the required video format.';
    }

    return null;
  }
Get why the asset is unplayable, if it is unplayable.

@param {!ShakaDemoAssetInfo} asset
@param {boolean} needOffline True if offline support is required.
@return {?string} unsupportedReason
  Null if asset is supported.