2017-09-14 2 views
1

Je lis & en essayant l'exemple de code d'Apple sur le chargement des ressources vidéo.AVURLAsset loadValuesAsynchronously never fail

Mais je remarque que la fonction loadValuesAsynchronously sur AVURLAsset n'échoue jamais même si j'active le mode avion sur l'appareil ou désactiver le wifi sur mon mac. Quelqu'un sait dans quelle situation loadValuesAsynchronously ne parviendra pas à charger les clés?

Ceci est le parent sample code:

asset.loadValuesAsynchronously(forKeys: PlayerViewController.assetKeysRequiredToPlay) { 

    /* 
     The asset invokes its completion handler on an arbitrary queue. 
     To avoid multiple threads using our internal state at the same time 
     we'll elect to use the main thread at all times, let's dispatch 
     our handler to the main queue. 
    */ 
    DispatchQueue.main.async() { 
     /* 
      This method is called when the `AVAsset` for our URL has 
      completed the loading of the values of the specified array 
      of keys. 
     */ 

     /* 
      Test whether the values of each of the keys we need have been 
      successfully loaded. 
     */ 
     for key in PlayerViewController.assetKeysRequiredToPlay { 
      var error: NSError? 

      if asset.statusOfValue(forKey: key, error: &error) == .failed { 
       let stringFormat = NSLocalizedString("error.asset_%@_key_%@_failed.description", comment: "Can't use this AVAsset because one of it's keys failed to load") 

       let message = String.localizedStringWithFormat(stringFormat, title, key) 

       self.handleError(with: message, error: error) 

       return 
      } 
     } 

     // We can't play this asset. 
     if !asset.isPlayable || asset.hasProtectedContent { 
      let stringFormat = NSLocalizedString("error.asset_%@_not_playable.description", comment: "Can't use this AVAsset because it isn't playable or has protected content") 

      let message = String.localizedStringWithFormat(stringFormat, title) 

      self.handleError(with: message) 

      return 
     } 

     /* 
      We can play this asset. Create a new AVPlayerItem and make it 
      our player's current item. 
     */ 
     self.loadedAssets[title] = asset 

     let name = (thumbnailResourceName as NSString).deletingPathExtension 
     let type = (thumbnailResourceName as NSString).pathExtension 
     let path = Bundle.main.path(forResource: name, ofType: type)! 

     let thumbnail = UIImage(contentsOfFile: path)! 

     self.assetTitlesAndThumbnails[asset.url] = (title, thumbnail) 
    } 
} 

Répondre

1

Enfin compris cela, pour répondre à ma propre question: J'utilise des vidéos HLS et l'URL est du format https://www.foo.com/master.m3u8. loadValuesAsynchronously ne fera aucune opération réseau pour déterminer si l'URL contient des fichiers HLS valides. Voilà pourquoi la clé « jouable » est toujours valable:

static let assetKeysRequiredToPlay = [ 
    "playable", 
    "hasProtectedContent" 
] 

Cependant si, si j'ajoute également des informations de lecture telles que la « durée » et « pistes », il échouera s'il n'y a pas de connexion réseau . Plus de détails réfèrent à cette réponse: https://stackoverflow.com/a/31418812/1035008