2017-03-21 1 views
0

J'ai une section de code censée interroger la bibliothèque musicale sur un appareil iOS et renvoyer un sous-ensemble de son contenu. Lorsque ce code est déclenché pour une playlist, je crée un MPMediaQuery, puis j'applique une série de filtres en utilisant MPMediaPropertyPredicate. Premièrement, je filtre pour le type de contenu que je veux (musique), puis j'enlève tout le contenu du nuage, et enfin, lorsque je navigue sur une playlist, je filtre les éléments appartenant à cette playlist. Tout cela fonctionne bien - sauf sur les listes de lecture intelligentes (et même alors, il fonctionne sur certains appareils). Ci-dessous le code - je peux voir qu'après les deux premiers filtres j'ai toujours une liste substantielle d'éléments (10107), mais après que le filtre final est appliqué, ma requête est réduite à 0 éléments quand il s'agit d'une playlist intelligente. Je pensais qu'il y avait une sorte de débordement d'entier, donc j'ai changé la "valeur" pour qu'elle soit un NSDecimalNumber au lieu de NSNumber, et je vois toujours l'ID de playlist complète comme un entier et jamais en notation scientifique, mais cela n'a pas corrigé problème. Une idée de ce qui se passe?MPMediaQuery addFilterPredicate supprimant tous les éléments de la requête de la liste de lecture intelligente

- (MPMediaQuery*) queryFromObjectId:(NSString*)objectId 
{ 

NSLog(@"INSIDE queryFromObjectId %@", objectId); 

NSString *s; 

MPMediaQuery* rv = [MPMediaQuery new]; 

NSURL* url = [NSURL URLWithString:objectId]; 
NSString* type = url.host; 

NSLog(@"URL: %@, type: %@", url, type); 

NSArray* rootItem = [self.rootDict objectForKey:type]; 
if (rootItem != nil) { 
    rv.groupingType = [rootItem[kRootIndexQuery] groupingType]; 
} 

NSDictionary *parameters = [url nvt_queryDictionary]; 

MPMediaPropertyPredicate* pred; 

// Filter proper media types 
if (parameters[MPMediaItemPropertyPodcastPersistentID] || rv.groupingType == MPMediaGroupingPodcastTitle) { 
    NSLog(@"Filtering for Podcast type"); 
    pred = [MPMediaPropertyPredicate predicateWithValue:[NSNumber numberWithInt:MPMediaTypePodcast] forProperty:MPMediaItemPropertyMediaType]; 
} else { 
    NSLog(@"Filtering for music/media type"); 
    pred = [MPMediaPropertyPredicate predicateWithValue:[NSNumber numberWithInt:MPMediaTypeMusic] forProperty:MPMediaItemPropertyMediaType]; 
} 
[rv addFilterPredicate:pred]; 

// Filter iCloud items 
if ([UIDevice currentDevice].systemVersion.floatValue >= 6) { 
    NSLog(@"Filtering iCloud items"); 
    pred = [MPMediaPropertyPredicate predicateWithValue:[NSNumber numberWithBool:NO] forProperty:MPMediaItemPropertyIsCloudItem]; 
    [rv addFilterPredicate:pred]; 
} 

int index = 0; 
for (NSString *key in parameters.allKeys) { 

    NSLog(@"Inside for loop, KEY: %@, index: %d", key, index); 
    MPMediaPropertyPredicate *pred; 

    if ([key isEqualToString:MPMediaPlaylistPropertyPersistentID] || [key isEqualToString:MPMediaItemPropertyPodcastPersistentID]) { 
     NSLog(@"IF inside FOR"); 
     NSNumberFormatter *formatter = [[NSNumberFormatter alloc] init]; 
     formatter.numberStyle = NSNumberFormatterDecimalStyle; 
//   NSNumber *value = [formatter numberFromString:parameters[key]]; 
     NSDecimalNumber *value = [NSDecimalNumber decimalNumberWithString:parameters[key]]; 
     pred = [MPMediaPropertyPredicate predicateWithValue:value forProperty:key]; 
    } 

    else { 
     NSLog(@"ELSE inside FOR"); 
     id value = parameters[key]; 
     pred = [MPMediaPropertyPredicate predicateWithValue:value forProperty:key]; 
    } 

    s = [NSString stringWithFormat:@"BEFORE FILTER items:%u", rv.items.count]; 
    NSLog(s); 

    s = [NSString stringWithFormat:@"Predicate: value: %@, key: %@", pred.value, pred.property]; 
    NSLog(s); 

    [rv addFilterPredicate:pred]; 

    s = [NSString stringWithFormat:@"AFTER FILTER items:%u", rv.items.count]; 
    NSLog(s); 

    index++; 
} 

return rv; 
} 

Dans les journaux que je vois:

2017-03-21 11:09:26.090316 T[1978:1214332] INSIDE queryFromObjectId //Tracks?playlistPersistentID=9690568479441451477 
2017-03-21 11:09:26.090549 T[1978:1214332] URL: //Tracks?playlistPersistentID=9690568479441451477, type: Tracks 
2017-03-21 11:09:26.090690 T[1978:1214332] Filtering for music/media type 
2017-03-21 11:09:26.090846 T[1978:1214332] Filtering iCloud items 
2017-03-21 11:09:26.090967 T[1978:1214332] Inside for loop, KEY: playlistPersistentID, index: 0 
2017-03-21 11:09:26.091017 T[1978:1214332] IF inside FOR 
2017-03-21 11:09:26.091200 T[1978:1214332] BEFORE FILTER items:10107 
2017-03-21 11:09:26.091298 T[1978:1214332] Predicate: value: 9690568479441451477, key: playlistPersistentID 
2017-03-21 11:09:26.091765 T[1978:1214332] AFTER FILTER items:0 

tout cela fonctionne parfaitement pour des listes de lecture non-smart. En outre, si je supprime la partie de filtrage iCloud - qui semble ne rien faire - toutes les listes de lecture intelligentes se chargent ... mais le même contenu est chargé: le contenu de la liste de lecture intelligente avec l'ID numéroté le plus bas. Voici les noms et les ID des listes de lecture que je teste avec:

Top500MostPlayed "9690568479441451477"

RecentlyPlayed "9690568479441451478"

RecentlyAdded "9690568479441451479"

5étoiles "9690568479441451476"

Lorsque le filtrage iCloud est supprimé, toutes les listes de lecture intelligentes chargent le contenu de la liste de lecture "5Stars".

Répondre

0

Compris!

L'ID devait être un unsigned long à tenir ce grand d'un nombre:

 unsigned long long valueLong = strtoull([parameters[key] UTF8String], NULL, 0); 
     NSNumber *value = [NSNumber numberWithUnsignedLongLong:valueLong]; 
     pred = [MPMediaPropertyPredicate predicateWithValue:value forProperty:key];