Partager via


Sélecteur de documents dans Xamarin.iOS

Le sélecteur de documents permet de partager des documents entre les applications. Ces documents peuvent être stockés dans iCloud ou dans le répertoire d’une autre application. Les documents sont partagés via l’ensemble d’extensions du fournisseur de documents que l’utilisateur a installés sur son appareil.

En raison de la difficulté de synchroniser les documents entre les applications et le cloud, ils introduisent une certaine complexité nécessaire.

Spécifications

Voici les étapes décrites dans cet article :

  • Xcode 7 et iOS 8 ou ultérieur : les API Xcode 7 et iOS 8 ou ultérieures d’Apple doivent être installées et configurées sur l’ordinateur du développeur.
  • Visual Studio ou Visual Studio pour Mac : la dernière version de Visual Studio pour Mac doit être installée.
  • Appareil iOS : appareil iOS exécutant iOS 8 ou version ultérieure.

Modifications apportées à iCloud

Pour implémenter les nouvelles fonctionnalités du sélecteur de documents, les modifications suivantes ont été apportées au service iCloud d’Apple :

  • Le démon iCloud a été entièrement réécrit à l’aide de CloudKit.
  • Les fonctionnalités iCloud existantes ont été renommées iCloud Drive.
  • La prise en charge du système d’exploitation Microsoft Windows a été ajoutée à iCloud.
  • Un dossier iCloud a été ajouté dans le Finder mac OS.
  • Les appareils iOS peuvent accéder au contenu du dossier iCloud mac OS.

Important

Apple fournit des outils pour aider les développeurs à gérer correctement le Règlement général sur la protection des données (RGPD) de l’Union européenne.

Qu’est-ce qu’un document ?

Lorsque vous faites référence à un document dans iCloud, il s’agit d’une entité autonome unique et doit être perçue comme telle par l’utilisateur. Un utilisateur peut souhaiter modifier le document ou le partager avec d’autres utilisateurs (à l’aide de l’e-mail, par exemple).

Il existe plusieurs types de fichiers que l’utilisateur reconnaîtra immédiatement en tant que documents, tels que les fichiers Pages, Keynote ou Numbers. Toutefois, iCloud n’est pas limité à ce concept. Par exemple, l’état d’un jeu (par exemple, une correspondance d’échecs) peut être traité comme un document et stocké dans iCloud. Ce fichier peut être passé entre les appareils d’un utilisateur et lui permettre de récupérer un jeu où il s’est arrêté sur un autre appareil.

Traitement des documents

Avant de vous plonger dans le code requis pour utiliser le sélecteur de documents avec Xamarin, cet article aborde les meilleures pratiques pour l’utilisation des documents iCloud et plusieurs des modifications apportées aux API existantes requises pour prendre en charge le sélecteur de documents.

Utilisation de la coordination des fichiers

Étant donné qu’un fichier peut être modifié à partir de plusieurs emplacements différents, la coordination doit être utilisée pour empêcher la perte de données.

Utilisation de la coordination des fichiers

Examinons l’illustration ci-dessus :

  1. Un appareil iOS utilisant la coordination des fichiers crée un document et l’enregistre dans le dossier iCloud.
  2. iCloud enregistre le fichier modifié dans le cloud pour la distribution sur chaque appareil.
  3. Un Mac attaché voit le fichier modifié dans le dossier iCloud et utilise La coordination des fichiers pour copier les modifications apportées au fichier.
  4. Un appareil qui n’utilise pas File Coordination apporte une modification au fichier et l’enregistre dans le dossier iCloud. Ces modifications sont répliquées instantanément sur les autres appareils.

Supposons que l’appareil iOS d’origine ou le Mac modifie le fichier, leurs modifications sont perdues et remplacées par la version du fichier à partir de l’appareil non coordonné. Pour éviter la perte de données, la coordination des fichiers est obligatoire lors de l’utilisation de documents basés sur le cloud.

Utilisation de UIDocument

UIDocument rend les choses simples (ou NSDocument sur macOS) en effectuant tout le travail lourd pour le développeur. Il fournit une coordination des fichiers intégrée avec des files d’attente en arrière-plan pour empêcher l’interface utilisateur de l’application.

UIDocument expose plusieurs API de haut niveau qui facilitent l’effort de développement d’une application Xamarin à tout usage requis par le développeur.

Le code suivant crée une sous-classe permettant d’implémenter UIDocument un document basé sur du texte générique qui peut être utilisé pour stocker et récupérer du texte à partir d’iCloud :

using System;
using Foundation;
using UIKit;

namespace DocPicker
{
    public class GenericTextDocument : UIDocument
    {
        #region Private Variable Storage
        private NSString _dataModel;
        #endregion

        #region Computed Properties
        public string Contents {
            get { return _dataModel.ToString (); }
            set { _dataModel = new NSString(value); }
        }
        #endregion

        #region Constructors
        public GenericTextDocument (NSUrl url) : base (url)
        {
            // Set the default document text
            this.Contents = "";
        }

        public GenericTextDocument (NSUrl url, string contents) : base (url)
        {
            // Set the default document text
            this.Contents = contents;
        }
        #endregion

        #region Override Methods
        public override bool LoadFromContents (NSObject contents, string typeName, out NSError outError)
        {
            // Clear the error state
            outError = null;

            // Were any contents passed to the document?
            if (contents != null) {
                _dataModel = NSString.FromData( (NSData)contents, NSStringEncoding.UTF8 );
            }

            // Inform caller that the document has been modified
            RaiseDocumentModified (this);

            // Return success
            return true;
        }

        public override NSObject ContentsForType (string typeName, out NSError outError)
        {
            // Clear the error state
            outError = null;

            // Convert the contents to a NSData object and return it
            NSData docData = _dataModel.Encode(NSStringEncoding.UTF8);
            return docData;
        }
        #endregion

        #region Events
        public delegate void DocumentModifiedDelegate(GenericTextDocument document);
        public event DocumentModifiedDelegate DocumentModified;

        internal void RaiseDocumentModified(GenericTextDocument document) {
            // Inform caller
            if (this.DocumentModified != null) {
                this.DocumentModified (document);
            }
        }
        #endregion
    }
}

La GenericTextDocument classe présentée ci-dessus sera utilisée dans cet article lors de l’utilisation du sélecteur de documents et des documents externes dans une application Xamarin.iOS 8.

Coordination des fichiers asynchrones

iOS 8 fournit plusieurs nouvelles fonctionnalités asynchrones de coordination des fichiers via les nouvelles API de coordination des fichiers. Avant iOS 8, toutes les API de coordination des fichiers existantes étaient totalement synchrones. Cela signifiait que le développeur était responsable de l’implémentation de sa propre file d’attente en arrière-plan pour empêcher la coordination des fichiers de bloquer l’interface utilisateur de l’application.

La nouvelle NSFileAccessIntent classe contient une URL pointant vers le fichier et plusieurs options pour contrôler le type de coordination requis. Le code suivant illustre le déplacement d’un fichier d’un emplacement vers un autre à l’aide d’intentions :

// Get source options
var srcURL = NSUrl.FromFilename ("FromFile.txt");
var srcIntent = NSFileAccessIntent.CreateReadingIntent (srcURL, NSFileCoordinatorReadingOptions.ForUploading);

// Get destination options
var dstURL = NSUrl.FromFilename ("ToFile.txt");
var dstIntent = NSFileAccessIntent.CreateReadingIntent (dstURL, NSFileCoordinatorReadingOptions.ForUploading);

// Create an array
var intents = new NSFileAccessIntent[] {
    srcIntent,
    dstIntent
};

// Initialize a file coordination with intents
var queue = new NSOperationQueue ();
var fileCoordinator = new NSFileCoordinator ();
fileCoordinator.CoordinateAccess (intents, queue, (err) => {
    // Was there an error?
    if (err!=null) {
        Console.WriteLine("Error: {0}",err.LocalizedDescription);
    }
});

Découverte et description de documents

La façon de découvrir et de répertorier les documents consiste à utiliser les API existantes NSMetadataQuery . Cette section traite des nouvelles fonctionnalités ajoutées pour NSMetadataQuery faciliter l’utilisation des documents.

Comportement existant

Avant iOS 8, NSMetadataQuery il était lent de prendre en charge les modifications de fichier local telles que : suppressions, créations et renommages.

Vue d’ensemble des modifications du fichier local NSMetadataQuery

Dans le diagramme ci-dessus :

  1. Pour les fichiers qui existent déjà dans le conteneur d’applications, NSMetadataQuery les enregistrements existants NSMetadata sont précréés et mis en pool afin qu’ils soient instantanément disponibles pour l’application.
  2. L’application crée un fichier dans le conteneur d’applications.
  3. Il existe un délai avant NSMetadataQuery de voir la modification apportée au conteneur d’applications et crée l’enregistrement requis NSMetadata .

En raison du délai de création de l’enregistrement NSMetadata , l’application doit avoir deux sources de données ouvertes : une pour les modifications de fichier local et une pour les modifications basées sur le cloud.

Couture

Dans iOS 8, NSMetadataQuery il est plus facile d’utiliser directement avec une nouvelle fonctionnalité appelée Stitching :

NSMetadataQuery avec une nouvelle fonctionnalité appelée Stitching

Utilisation de Stitching dans le diagramme ci-dessus :

  1. Comme précédemment, pour les fichiers qui existent déjà dans le conteneur d’applications, NSMetadataQuery les enregistrements existants NSMetadata sont précréés et mis en pool.
  2. L’application crée un fichier dans le conteneur d’applications à l’aide de la coordination des fichiers.
  3. Un hook dans le conteneur d’applications voit la modification et les appels NSMetadataQuery pour créer l’enregistrement requis NSMetadata .
  4. L’enregistrement NSMetadata est créé directement après le fichier et est mis à la disposition de l’application.

L’utilisation de Stitching de l’application n’a plus besoin d’ouvrir une source de données pour surveiller les modifications apportées aux fichiers locaux et cloud. À présent, l’application peut s’appuyer NSMetadataQuery directement.

Important

Le pointage fonctionne uniquement si l’application utilise la coordination des fichiers comme indiqué dans la section ci-dessus. Si la coordination des fichiers n’est pas utilisée, les API sont par défaut le comportement existant avant iOS 8.

Nouvelles fonctionnalités de métadonnées iOS 8

Les nouvelles fonctionnalités suivantes ont été ajoutées NSMetadataQuery dans iOS 8 :

  • NSMetatadataQuery peut maintenant répertorier les documents non locaux stockés dans le cloud.
  • De nouvelles API ont été ajoutées pour accéder aux informations de métadonnées sur les documents basés sur le cloud.
  • Il existe une nouvelle NSUrl_PromisedItems API qui permet d’accéder aux attributs de fichier des fichiers susceptibles ou non de disposer de leur contenu localement.
  • Utilisez la GetPromisedItemResourceValue méthode pour obtenir des informations sur un fichier donné ou utilisez la méthode pour obtenir des informations sur plusieurs fichiers à la GetPromisedItemResourceValues fois.

Deux nouveaux indicateurs de coordination de fichiers ont été ajoutés pour traiter les métadonnées :

  • NSFileCoordinatorReadImmediatelyAvailableMetadataOnly
  • NSFileCoordinatorWriteContentIndependentMetadataOnly

Avec les indicateurs ci-dessus, le contenu du fichier document n’a pas besoin d’être disponible localement pour qu’ils soient utilisés.

Le segment de code suivant montre comment utiliser NSMetadataQuery pour interroger l’existence d’un fichier spécifique et générer le fichier s’il n’existe pas :

using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using Foundation;
using UIKit;
using ObjCRuntime;
using System.IO;

#region Static Properties
public const string TestFilename = "test.txt";
#endregion

#region Computed Properties
public bool HasiCloud { get; set; }
public bool CheckingForiCloud { get; set; }
public NSUrl iCloudUrl { get; set; }

public GenericTextDocument Document { get; set; }
public NSMetadataQuery Query { get; set; }
#endregion

#region Private Methods
private void FindDocument () {
    Console.WriteLine ("Finding Document...");

    // Create a new query and set it's scope
    Query = new NSMetadataQuery();
    Query.SearchScopes = new NSObject [] {
                NSMetadataQuery.UbiquitousDocumentsScope,
                NSMetadataQuery.UbiquitousDataScope,
                NSMetadataQuery.AccessibleUbiquitousExternalDocumentsScope
            };

    // Build a predicate to locate the file by name and attach it to the query
    var pred = NSPredicate.FromFormat ("%K == %@"
        , new NSObject[] {
            NSMetadataQuery.ItemFSNameKey
            , new NSString(TestFilename)});
    Query.Predicate = pred;

    // Register a notification for when the query returns
    NSNotificationCenter.DefaultCenter.AddObserver (this,
            new Selector("queryDidFinishGathering:"),             NSMetadataQuery.DidFinishGatheringNotification,
            Query);

    // Start looking for the file
    Query.StartQuery ();
    Console.WriteLine ("Querying: {0}", Query.IsGathering);
}

[Export("queryDidFinishGathering:")]
public void DidFinishGathering (NSNotification notification) {
    Console.WriteLine ("Finish Gathering Documents.");

    // Access the query and stop it from running
    var query = (NSMetadataQuery)notification.Object;
    query.DisableUpdates();
    query.StopQuery();

    // Release the notification
    NSNotificationCenter.DefaultCenter.RemoveObserver (this
        , NSMetadataQuery.DidFinishGatheringNotification
        , query);

    // Load the document that the query returned
    LoadDocument(query);
}

private void LoadDocument (NSMetadataQuery query) {
    Console.WriteLine ("Loading Document...");    

    // Take action based on the returned record count
    switch (query.ResultCount) {
    case 0:
        // Create a new document
        CreateNewDocument ();
        break;
    case 1:
        // Gain access to the url and create a new document from
        // that instance
        NSMetadataItem item = (NSMetadataItem)query.ResultAtIndex (0);
        var url = (NSUrl)item.ValueForAttribute (NSMetadataQuery.ItemURLKey);

        // Load the document
        OpenDocument (url);
        break;
    default:
        // There has been an issue
        Console.WriteLine ("Issue: More than one document found...");
        break;
    }
}
#endregion

#region Public Methods
public void OpenDocument(NSUrl url) {

    Console.WriteLine ("Attempting to open: {0}", url);
    Document = new GenericTextDocument (url);

    // Open the document
    Document.Open ( (success) => {
        if (success) {
            Console.WriteLine ("Document Opened");
        } else
            Console.WriteLine ("Failed to Open Document");
    });

    // Inform caller
    RaiseDocumentLoaded (Document);
}

public void CreateNewDocument() {
    // Create path to new file
    // var docsFolder = Environment.GetFolderPath (Environment.SpecialFolder.Personal);
    var docsFolder = Path.Combine(iCloudUrl.Path, "Documents");
    var docPath = Path.Combine (docsFolder, TestFilename);
    var ubiq = new NSUrl (docPath, false);

    // Create new document at path
    Console.WriteLine ("Creating Document at:" + ubiq.AbsoluteString);
    Document = new GenericTextDocument (ubiq);

    // Set the default value
    Document.Contents = "(default value)";

    // Save document to path
    Document.Save (Document.FileUrl, UIDocumentSaveOperation.ForCreating, (saveSuccess) => {
        Console.WriteLine ("Save completion:" + saveSuccess);
        if (saveSuccess) {
            Console.WriteLine ("Document Saved");
        } else {
            Console.WriteLine ("Unable to Save Document");
        }
    });

    // Inform caller
    RaiseDocumentLoaded (Document);
}

public bool SaveDocument() {
    bool successful = false;

    // Save document to path
    Document.Save (Document.FileUrl, UIDocumentSaveOperation.ForOverwriting, (saveSuccess) => {
        Console.WriteLine ("Save completion: " + saveSuccess);
        if (saveSuccess) {
            Console.WriteLine ("Document Saved");
            successful = true;
        } else {
            Console.WriteLine ("Unable to Save Document");
            successful=false;
        }
    });

    // Return results
    return successful;
}
#endregion

#region Events
public delegate void DocumentLoadedDelegate(GenericTextDocument document);
public event DocumentLoadedDelegate DocumentLoaded;

internal void RaiseDocumentLoaded(GenericTextDocument document) {
    // Inform caller
    if (this.DocumentLoaded != null) {
        this.DocumentLoaded (document);
    }
}
#endregion

Miniatures de document

Apple estime que la meilleure expérience utilisateur lors de la liste des documents pour une application consiste à utiliser des préversions. Cela donne au contexte des utilisateurs finaux, afin qu’ils puissent rapidement identifier le document avec lequel ils souhaitent travailler.

Avant iOS 8, l’affichage des aperçus de document nécessite une implémentation personnalisée. Nouveautés d’iOS 8 sont des attributs de système de fichiers qui permettent au développeur de travailler rapidement avec les miniatures de document.

Récupération des miniatures de document

En appelant les méthodes, GetPromisedItemResourceValuesNSUrl_PromisedItems l’APIGetPromisedItemResourceValue, un NSUrlThumbnailDictionary, est retourné. La seule clé actuellement dans ce dictionnaire est la NSThumbnial1024X1024SizeKey et sa correspondance UIImage.

Enregistrement des miniatures de document

Le moyen le plus simple d’enregistrer une miniature consiste à utiliser UIDocument. En appelant la GetFileAttributesToWrite méthode de la UIDocument miniature et en définissant la miniature, elle est automatiquement enregistrée lorsque le fichier document est. Le démon iCloud verra cette modification et la propagera à iCloud. Sur Mac OS X, les miniatures sont générées automatiquement pour le développeur par le plug-in Quick Look.

Avec les principes de base de l’utilisation des documents basés sur iCloud, ainsi que les modifications apportées à l’API existante, nous sommes prêts à implémenter le contrôleur de vue sélecteur de documents dans une application mobile Xamarin iOS 8.

Activation d’iCloud dans Xamarin

Avant que le sélecteur de documents puisse être utilisé dans une application Xamarin.iOS, le support iCloud doit être activé à la fois dans votre application et via Apple.

Les étapes suivantes expliquent le processus d’approvisionnement pour iCloud.

  1. Créez un conteneur iCloud.
  2. Créez un ID d’application qui contient iCloud App Service.
  3. Créez un profil d’approvisionnement qui inclut cet ID d’application.

Le guide Utilisation des fonctionnalités décrit les deux premières étapes. Pour créer un profil d’approvisionnement, suivez les étapes décrites dans le guide du profil d’approvisionnement.

Les étapes suivantes expliquent le processus de configuration de votre application pour iCloud :

Effectuez les actions suivantes :

  1. Ouvrez le projet dans Visual Studio pour Mac ou Visual Studio.

  2. Dans le Explorateur de solutions, cliquez avec le bouton droit sur le projet, puis sélectionnez Options.

  3. Dans la boîte de dialogue Options, sélectionnez Application iOS, vérifiez que l’identificateurde bundle correspond à celui qui a été défini dans l’ID d’application créé ci-dessus pour l’application.

  4. Sélectionnez La signature de bundle iOS, sélectionnez l’identité du développeur et le profil d’approvisionnement créé ci-dessus.

  5. Cliquez sur le bouton OK pour enregistrer les modifications et fermer la boîte de dialogue.

  6. Cliquez avec le bouton droit sur Entitlements.plist le Explorateur de solutions pour l’ouvrir dans l’éditeur.

    Important

    Dans Visual Studio, vous devrez peut-être ouvrir l’éditeur de droits d’utilisation en cliquant dessus avec le bouton droit, en sélectionnant Ouvrir avec... et en sélectionnant Éditeur de liste de propriétés

  7. Activez iCloud , les documents iCloud, le stockage clé-valeur et CloudKit .

  8. Vérifiez que le conteneur existe pour l’application (comme créé ci-dessus). Exemple : iCloud.com.your-company.AppName

  9. Enregistrez les modifications du fichier.

Pour plus d’informations sur les droits d’utilisation, reportez-vous au guide sur les droits d’utilisation.

Avec la configuration ci-dessus en place, l’application peut désormais utiliser des documents basés sur le cloud et le nouveau contrôleur de vue sélecteur de documents.

Code d’installation commun

Avant de commencer avec le contrôleur de vue sélecteur de documents, il existe un code de configuration standard requis. Commencez par modifier le fichier de l’application AppDelegate.cs et faites-le ressembler à ce qui suit :

using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using Foundation;
using UIKit;
using ObjCRuntime;
using System.IO;

namespace DocPicker
{

    [Register ("AppDelegate")]
    public partial class AppDelegate : UIApplicationDelegate
    {
        #region Static Properties
        public const string TestFilename = "test.txt";
        #endregion

        #region Computed Properties
        public override UIWindow Window { get; set; }
        public bool HasiCloud { get; set; }
        public bool CheckingForiCloud { get; set; }
        public NSUrl iCloudUrl { get; set; }

        public GenericTextDocument Document { get; set; }
        public NSMetadataQuery Query { get; set; }
        public NSData Bookmark { get; set; }
        #endregion

        #region Private Methods
        private void FindDocument () {
            Console.WriteLine ("Finding Document...");

            // Create a new query and set it's scope
            Query = new NSMetadataQuery();
            Query.SearchScopes = new NSObject [] {
                NSMetadataQuery.UbiquitousDocumentsScope,
                NSMetadataQuery.UbiquitousDataScope,
                NSMetadataQuery.AccessibleUbiquitousExternalDocumentsScope
            };

            // Build a predicate to locate the file by name and attach it to the query
            var pred = NSPredicate.FromFormat ("%K == %@",
                 new NSObject[] {NSMetadataQuery.ItemFSNameKey
                , new NSString(TestFilename)});
            Query.Predicate = pred;

            // Register a notification for when the query returns
            NSNotificationCenter.DefaultCenter.AddObserver (this
                , new Selector("queryDidFinishGathering:")
                , NSMetadataQuery.DidFinishGatheringNotification
                , Query);

            // Start looking for the file
            Query.StartQuery ();
            Console.WriteLine ("Querying: {0}", Query.IsGathering);
        }

        [Export("queryDidFinishGathering:")]
        public void DidFinishGathering (NSNotification notification) {
            Console.WriteLine ("Finish Gathering Documents.");

            // Access the query and stop it from running
            var query = (NSMetadataQuery)notification.Object;
            query.DisableUpdates();
            query.StopQuery();

            // Release the notification
            NSNotificationCenter.DefaultCenter.RemoveObserver (this
                , NSMetadataQuery.DidFinishGatheringNotification
                , query);

            // Load the document that the query returned
            LoadDocument(query);
        }

        private void LoadDocument (NSMetadataQuery query) {
            Console.WriteLine ("Loading Document...");    

            // Take action based on the returned record count
            switch (query.ResultCount) {
            case 0:
                // Create a new document
                CreateNewDocument ();
                break;
            case 1:
                // Gain access to the url and create a new document from
                // that instance
                NSMetadataItem item = (NSMetadataItem)query.ResultAtIndex (0);
                var url = (NSUrl)item.ValueForAttribute (NSMetadataQuery.ItemURLKey);

                // Load the document
                OpenDocument (url);
                break;
            default:
                // There has been an issue
                Console.WriteLine ("Issue: More than one document found...");
                break;
            }
        }
        #endregion

        #region Public Methods

        public void OpenDocument(NSUrl url) {

            Console.WriteLine ("Attempting to open: {0}", url);
            Document = new GenericTextDocument (url);

            // Open the document
            Document.Open ( (success) => {
                if (success) {
                    Console.WriteLine ("Document Opened");
                } else
                    Console.WriteLine ("Failed to Open Document");
            });

            // Inform caller
            RaiseDocumentLoaded (Document);
        }

        public void CreateNewDocument() {
            // Create path to new file
            // var docsFolder = Environment.GetFolderPath (Environment.SpecialFolder.Personal);
            var docsFolder = Path.Combine(iCloudUrl.Path, "Documents");
            var docPath = Path.Combine (docsFolder, TestFilename);
            var ubiq = new NSUrl (docPath, false);

            // Create new document at path
            Console.WriteLine ("Creating Document at:" + ubiq.AbsoluteString);
            Document = new GenericTextDocument (ubiq);

            // Set the default value
            Document.Contents = "(default value)";

            // Save document to path
            Document.Save (Document.FileUrl, UIDocumentSaveOperation.ForCreating, (saveSuccess) => {
                Console.WriteLine ("Save completion:" + saveSuccess);
                if (saveSuccess) {
                    Console.WriteLine ("Document Saved");
                } else {
                    Console.WriteLine ("Unable to Save Document");
                }
            });

            // Inform caller
            RaiseDocumentLoaded (Document);
        }

        /// <summary>
        /// Saves the document.
        /// </summary>
        /// <returns><c>true</c>, if document was saved, <c>false</c> otherwise.</returns>
        public bool SaveDocument() {
            bool successful = false;

            // Save document to path
            Document.Save (Document.FileUrl, UIDocumentSaveOperation.ForOverwriting, (saveSuccess) => {
                Console.WriteLine ("Save completion: " + saveSuccess);
                if (saveSuccess) {
                    Console.WriteLine ("Document Saved");
                    successful = true;
                } else {
                    Console.WriteLine ("Unable to Save Document");
                    successful=false;
                }
            });

            // Return results
            return successful;
        }
        #endregion

        #region Override Methods
        public override void FinishedLaunching (UIApplication application)
        {

            // Start a new thread to check and see if the user has iCloud
            // enabled.
            new Thread(new ThreadStart(() => {
                // Inform caller that we are checking for iCloud
                CheckingForiCloud = true;

                // Checks to see if the user of this device has iCloud
                // enabled
                var uburl = NSFileManager.DefaultManager.GetUrlForUbiquityContainer(null);

                // Connected to iCloud?
                if (uburl == null)
                {
                    // No, inform caller
                    HasiCloud = false;
                    iCloudUrl =null;
                    Console.WriteLine("Unable to connect to iCloud");
                    InvokeOnMainThread(()=>{
                        var okAlertController = UIAlertController.Create ("iCloud Not Available", "Developer, please check your Entitlements.plist, Bundle ID and Provisioning Profiles.", UIAlertControllerStyle.Alert);
                        okAlertController.AddAction (UIAlertAction.Create ("Ok", UIAlertActionStyle.Default, null));
                        Window.RootViewController.PresentViewController (okAlertController, true, null);
                    });
                }
                else
                {    
                    // Yes, inform caller and save location the Application Container
                    HasiCloud = true;
                    iCloudUrl = uburl;
                    Console.WriteLine("Connected to iCloud");

                    // If we have made the connection with iCloud, start looking for documents
                    InvokeOnMainThread(()=>{
                        // Search for the default document
                        FindDocument ();
                    });
                }

                // Inform caller that we are no longer looking for iCloud
                CheckingForiCloud = false;

            })).Start();

        }

        // This method is invoked when the application is about to move from active to inactive state.
        // OpenGL applications should use this method to pause.
        public override void OnResignActivation (UIApplication application)
        {
        }

        // This method should be used to release shared resources and it should store the application state.
        // If your application supports background execution this method is called instead of WillTerminate
        // when the user quits.
        public override void DidEnterBackground (UIApplication application)
        {
            // Trap all errors
            try {
                // Values to include in the bookmark packet
                var resources = new string[] {
                    NSUrl.FileSecurityKey,
                    NSUrl.ContentModificationDateKey,
                    NSUrl.FileResourceIdentifierKey,
                    NSUrl.FileResourceTypeKey,
                    NSUrl.LocalizedNameKey
                };

                // Create the bookmark
                NSError err;
                Bookmark = Document.FileUrl.CreateBookmarkData (NSUrlBookmarkCreationOptions.WithSecurityScope, resources, iCloudUrl, out err);

                // Was there an error?
                if (err != null) {
                    // Yes, report it
                    Console.WriteLine ("Error Creating Bookmark: {0}", err.LocalizedDescription);
                }
            }
            catch (Exception e) {
                // Report error
                Console.WriteLine ("Error: {0}", e.Message);
            }
        }

        // This method is called as part of the transition from background to active state.
        public override void WillEnterForeground (UIApplication application)
        {
            // Is there any bookmark data?
            if (Bookmark != null) {
                // Trap all errors
                try {
                    // Yes, attempt to restore it
                    bool isBookmarkStale;
                    NSError err;
                    var srcUrl = new NSUrl (Bookmark, NSUrlBookmarkResolutionOptions.WithSecurityScope, iCloudUrl, out isBookmarkStale, out err);

                    // Was there an error?
                    if (err != null) {
                        // Yes, report it
                        Console.WriteLine ("Error Loading Bookmark: {0}", err.LocalizedDescription);
                    } else {
                        // Load document from bookmark
                        OpenDocument (srcUrl);
                    }
                }
                catch (Exception e) {
                    // Report error
                    Console.WriteLine ("Error: {0}", e.Message);
                }
            }

        }

        // This method is called when the application is about to terminate. Save data, if needed.
        public override void WillTerminate (UIApplication application)
        {
        }
        #endregion

        #region Events
        public delegate void DocumentLoadedDelegate(GenericTextDocument document);
        public event DocumentLoadedDelegate DocumentLoaded;

        internal void RaiseDocumentLoaded(GenericTextDocument document) {
            // Inform caller
            if (this.DocumentLoaded != null) {
                this.DocumentLoaded (document);
            }
        }
        #endregion
    }
}

Important

Le code ci-dessus inclut le code de la section Découverte et description des documents ci-dessus. Il est présenté ici dans son intégralité, comme il apparaît dans une application réelle. Par souci de simplicité, cet exemple fonctionne uniquement avec un seul fichier codé en dur (test.txt).

Le code ci-dessus expose plusieurs raccourcis iCloud Drive pour faciliter leur utilisation dans le reste de l’application.

Ensuite, ajoutez le code suivant à n’importe quel conteneur d’affichage ou d’affichage qui utilisera le sélecteur de documents ou travaillera avec des documents basés sur le cloud :

using CloudKit;
...

#region Computed Properties
/// <summary>
/// Returns the delegate of the current running application
/// </summary>
/// <value>The this app.</value>
public AppDelegate ThisApp {
    get { return (AppDelegate)UIApplication.SharedApplication.Delegate; }
}
#endregion

Cela ajoute un raccourci pour accéder aux AppDelegate raccourcis iCloud créés ci-dessus et y accéder.

Avec ce code en place, examinons l’implémentation du contrôleur de vue sélecteur de documents dans une application Xamarin iOS 8.

Utilisation du contrôleur de vue sélecteur de documents

Avant iOS 8, il était très difficile d’accéder aux documents d’une autre application, car il n’y avait aucun moyen de découvrir des documents en dehors de l’application à partir de l’application.

Comportement existant

Vue d’ensemble du comportement existant

Examinons l’accès à un document externe avant iOS 8 :

  1. Tout d’abord, l’utilisateur doit ouvrir l’application qui a créé le document à l’origine.
  2. Le document est sélectionné et il UIDocumentInteractionController est utilisé pour envoyer le document à la nouvelle application.
  3. Enfin, une copie du document d’origine est placée dans le conteneur de la nouvelle application.

À partir de là, le document est disponible pour la deuxième application à ouvrir et à modifier.

Découverte de documents en dehors du conteneur d’une application

Dans iOS 8, une application peut accéder facilement aux documents en dehors de son propre conteneur d’applications :

Découverte de documents en dehors du conteneur d’une application

À l’aide du nouveau sélecteur de documents iCloud (), UIDocumentPickerViewControllerune application iOS peut directement découvrir et accéder en dehors de son conteneur d’applications. Il UIDocumentPickerViewController fournit un mécanisme permettant à l’utilisateur d’accorder l’accès et de modifier ces documents découverts via des autorisations.

Une application doit choisir d’afficher ses documents dans le sélecteur de documents iCloud et être disponible pour que d’autres applications découvrent et fonctionnent avec elles. Pour qu’une application Xamarin iOS 8 partage son conteneur d’applications, modifiez-la Info.plist dans un éditeur de texte standard et ajoutez les deux lignes suivantes au bas du dictionnaire (entre les <dict>...</dict> balises) :

<key>NSUbiquitousContainerIsDocumentScopePublic</key>
<true/>

L’interface UIDocumentPickerViewController utilisateur fournit une nouvelle interface utilisateur qui permet à l’utilisateur de choisir des documents. Pour afficher le contrôleur de vue sélecteur de documents dans une application Xamarin iOS 8, procédez comme suit :

using MobileCoreServices;
...

// Allow the Document picker to select a range of document types
        var allowedUTIs = new string[] {
            UTType.UTF8PlainText,
            UTType.PlainText,
            UTType.RTF,
            UTType.PNG,
            UTType.Text,
            UTType.PDF,
            UTType.Image
        };

        // Display the picker
        //var picker = new UIDocumentPickerViewController (allowedUTIs, UIDocumentPickerMode.Open);
        var pickerMenu = new UIDocumentMenuViewController(allowedUTIs, UIDocumentPickerMode.Open);
        pickerMenu.DidPickDocumentPicker += (sender, args) => {

            // Wireup Document Picker
            args.DocumentPicker.DidPickDocument += (sndr, pArgs) => {

                // IMPORTANT! You must lock the security scope before you can
                // access this file
                var securityEnabled = pArgs.Url.StartAccessingSecurityScopedResource();

                // Open the document
                ThisApp.OpenDocument(pArgs.Url);

                // IMPORTANT! You must release the security lock established
                // above.
                pArgs.Url.StopAccessingSecurityScopedResource();
            };

            // Display the document picker
            PresentViewController(args.DocumentPicker,true,null);
        };

pickerMenu.ModalPresentationStyle = UIModalPresentationStyle.Popover;
PresentViewController(pickerMenu,true,null);
UIPopoverPresentationController presentationPopover = pickerMenu.PopoverPresentationController;
if (presentationPopover!=null) {
    presentationPopover.SourceView = this.View;
    presentationPopover.PermittedArrowDirections = UIPopoverArrowDirection.Down;
    presentationPopover.SourceRect = ((UIButton)s).Frame;
}

Important

Le développeur doit appeler la StartAccessingSecurityScopedResource méthode du NSUrl document externe avant qu’un document externe soit accessible. La StopAccessingSecurityScopedResource méthode doit être appelée pour libérer le verrou de sécurité dès que le document a été chargé.

Exemple de sortie

Voici un exemple de la façon dont le code ci-dessus affiche un sélecteur de documents lors de l’exécution sur un appareil i Téléphone :

  1. L’utilisateur démarre l’application et l’interface principale s’affiche :

    L’interface principale est affichée

  2. L’utilisateur appuie sur le bouton Action en haut de l’écran et est invité à sélectionner un fournisseur de documents dans la liste des fournisseurs disponibles :

    Sélectionnez un fournisseur de documents dans la liste des fournisseurs disponibles

  3. Le contrôleur de vue sélecteur de documents s’affiche pour le fournisseur de documents sélectionné :

    Le contrôleur de vue sélecteur de documents s’affiche

  4. L’utilisateur appuie sur un dossier de documents pour afficher son contenu :

    Contenu du dossier de documents

  5. L’utilisateur sélectionne un document et le sélecteur de documents est fermé.

  6. L’interface principale est réexéchée, le document est chargé à partir du conteneur externe et son contenu s’affiche.

L’affichage réel du contrôleur de vue sélecteur de documents dépend des fournisseurs de documents que l’utilisateur a installés sur l’appareil et le mode sélecteur de documents qui a été implémenté. L’exemple ci-dessus utilise le mode Open, les autres types de mode seront abordés en détail ci-dessous.

Gestion des documents externes

Comme indiqué ci-dessus, avant iOS 8, une application ne pouvait accéder qu’aux documents qui faisaient partie de son conteneur d’applications. Dans iOS 8, une application peut accéder aux documents à partir de sources externes :

Vue d’ensemble de la gestion des documents externes

Lorsque l’utilisateur sélectionne un document à partir d’une source externe, un document de référence est écrit dans le conteneur d’applications qui pointe vers le document d’origine.

Pour faciliter l’ajout de cette nouvelle capacité dans les applications existantes, plusieurs nouvelles fonctionnalités ont été ajoutées à l’API NSMetadataQuery . En règle générale, une application utilise l’étendue de document omniprésente pour répertorier les documents qui se trouvent dans son conteneur d’applications. À l’aide de cette étendue, seuls les documents du conteneur d’applications continueront d’être affichés.

L’utilisation de la nouvelle étendue de document externe Ubiquitous retourne des documents qui vivent en dehors du conteneur d’applications et retournent les métadonnées pour celles-ci. Le NSMetadataItemUrlKey pointez vers l’URL où se trouve réellement le document.

Parfois, une application ne souhaite pas utiliser les documents pointés par référence. Au lieu de cela, l’application souhaite utiliser directement le document de référence. Par exemple, l’application peut souhaiter afficher le document dans le dossier de l’application dans l’interface utilisateur ou permettre à l’utilisateur de déplacer les références à l’intérieur d’un dossier.

Dans iOS 8, un nouveau NSMetadataItemUrlInLocalContainerKey document a été fourni pour accéder directement au document de référence. Cette clé pointe vers la référence réelle au document externe dans un conteneur d’applications.

Il NSMetadataUbiquitousItemIsExternalDocumentKey est utilisé pour tester si un document est externe ou non au conteneur d’une application. Il NSMetadataUbiquitousItemContainerDisplayNameKey est utilisé pour accéder au nom du conteneur qui héberge la copie d’origine d’un document externe.

Pourquoi les références de document sont requises

La principale raison pour laquelle iOS 8 utilise des références pour accéder aux documents externes est la sécurité. Aucune application n’a accès au conteneur d’une autre application. Seul le sélecteur de documents peut le faire, car il est hors processus et dispose d’un accès à l’échelle du système.

La seule façon d’accéder à un document en dehors du conteneur d’applications consiste à utiliser le sélecteur de documents et si l’URL retournée par le sélecteur est étendue de sécurité. L’URL étendue de sécurité contient suffisamment d’informations pour sélectionner le document, ainsi que les droits d’étendue requis pour accorder à une application l’accès au document.

Il est important de noter que si l’URL étendue de la sécurité a été sérialisée dans une chaîne, puis désérialisée, les informations de sécurité sont perdues et le fichier est inaccessible à partir de l’URL. La fonctionnalité Référence de document fournit un mécanisme permettant de revenir aux fichiers signalés par ces URL.

Par conséquent, si l’application acquiert une NSUrl application à partir de l’un des documents de référence, elle a déjà l’étendue de sécurité attachée et peut être utilisée pour accéder au fichier. Pour cette raison, il est fortement suggéré que le développeur utilise UIDocument parce qu’il gère toutes ces informations et processus pour eux.

Utilisation de signets

Il n’est pas toujours possible d’énumérer les documents d’une application pour revenir à un document spécifique, par exemple lors de la restauration de l’état. iOS 8 fournit un mécanisme permettant de créer des signets qui ciblent directement un document donné.

Le code suivant crée un signet à partir d’une UIDocumentFileUrl propriété ' :

// Trap all errors
try {
    // Values to include in the bookmark packet
    var resources = new string[] {
        NSUrl.FileSecurityKey,
        NSUrl.ContentModificationDateKey,
        NSUrl.FileResourceIdentifierKey,
        NSUrl.FileResourceTypeKey,
        NSUrl.LocalizedNameKey
    };

    // Create the bookmark
    NSError err;
    Bookmark = Document.FileUrl.CreateBookmarkData (NSUrlBookmarkCreationOptions.WithSecurityScope, resources, iCloudUrl, out err);

    // Was there an error?
    if (err != null) {
        // Yes, report it
        Console.WriteLine ("Error Creating Bookmark: {0}", err.LocalizedDescription);
    }
}
catch (Exception e) {
    // Report error
    Console.WriteLine ("Error: {0}", e.Message);
}

L’API Bookmark existante permet de créer un signet sur un signet NSUrl pouvant être enregistré et chargé pour fournir un accès direct à un fichier externe. Le code suivant restaure un signet créé ci-dessus :

if (Bookmark != null) {
    // Trap all errors
    try {
        // Yes, attempt to restore it
        bool isBookmarkStale;
        NSError err;
        var srcUrl = new NSUrl (Bookmark, NSUrlBookmarkResolutionOptions.WithSecurityScope, iCloudUrl, out isBookmarkStale, out err);

        // Was there an error?
        if (err != null) {
            // Yes, report it
            Console.WriteLine ("Error Loading Bookmark: {0}", err.LocalizedDescription);
        } else {
            // Load document from bookmark
            OpenDocument (srcUrl);
        }
    }
    catch (Exception e) {
        // Report error
        Console.WriteLine ("Error: {0}", e.Message);
    }
}

Ouvrir le mode d’importation et le sélecteur de documents

Le contrôleur de vue sélecteur de documents propose deux modes d’opération différents :

  1. Mode Ouvert : dans ce mode, lorsque l’utilisateur sélectionne et externe Document, le sélecteur de documents crée un signet délimité par la sécurité dans le conteneur d’applications.

    Signet délimité par la sécurité dans le conteneur d’applications

  2. Mode d’importation : dans ce mode, lorsque l’utilisateur sélectionne et document externe, le sélecteur de documents ne crée pas de signet, mais copie le fichier dans un emplacement temporaire et fournit à l’application l’accès au document à cet emplacement :

    Le sélecteur de documents copie le fichier dans un emplacement temporaire et fournit à l’application l’accès au document à cet emplacement
    Une fois l’application terminée pour une raison quelconque, l’emplacement temporaire est vidé et le fichier a été supprimé. Si l’application doit conserver l’accès au fichier, elle doit effectuer une copie et la placer dans son conteneur d’application.

Le mode Ouvert est utile lorsque l’application souhaite collaborer avec une autre application et partager les modifications apportées au document avec cette application. Le mode d’importation est utilisé lorsque l’application ne souhaite pas partager ses modifications dans un document avec d’autres applications.

Création d’un document externe

Comme indiqué ci-dessus, une application iOS 8 n’a pas accès aux conteneurs en dehors de son propre conteneur d’applications. L’application peut écrire dans son propre conteneur localement ou dans un emplacement temporaire, puis utiliser un mode de document spécial pour déplacer le document résultant en dehors du conteneur d’applications vers un emplacement choisi par l’utilisateur.

Pour déplacer un document vers un emplacement externe, procédez comme suit :

  1. Commencez par créer un document dans un emplacement local ou temporaire.
  2. Créez un NSUrl point qui pointe vers le nouveau document.
  3. Ouvrez un nouveau contrôleur de vue sélecteur de documents et transmettez-le avec NSUrl le mode de MoveToService .
  4. Une fois que l’utilisateur choisit un nouvel emplacement, le document est déplacé de son emplacement actuel vers le nouvel emplacement.
  5. Un document de référence est écrit dans le conteneur d’applications de l’application afin que le fichier soit toujours accessible par l’application de création.

Le code suivant peut être utilisé pour déplacer un document vers un emplacement externe : var picker = new UIDocumentPickerViewController (srcURL, UIDocumentPickerMode.MoveToService);

Le document de référence retourné par le processus ci-dessus est exactement le même que celui créé par le mode Ouvert du sélecteur de documents. Toutefois, il est parfois possible que l’application souhaite déplacer un document sans conserver une référence à celui-ci.

Pour déplacer un document sans générer de référence, utilisez le ExportToService mode. Exemple : var picker = new UIDocumentPickerViewController (srcURL, UIDocumentPickerMode.ExportToService);

Lorsque vous utilisez le ExportToService mode, le document est copié dans le conteneur externe et la copie existante est laissée à son emplacement d’origine.

Extensions du fournisseur de documents

Avec iOS 8, Apple souhaite que l’utilisateur final puisse accéder à l’un de ses documents basés sur le cloud, quel que soit son emplacement. Pour atteindre cet objectif, iOS 8 fournit un nouveau mécanisme d’extension du fournisseur de documents.

Qu’est-ce qu’une extension fournisseur de documents ?

Il suffit d’indiquer qu’une extension fournisseur de documents est un moyen pour un développeur ou un tiers de fournir à une application un autre stockage de documents accessible de la même façon que l’emplacement de stockage iCloud existant.

L’utilisateur peut sélectionner l’un de ces emplacements de stockage alternatifs dans le sélecteur de documents et utiliser les mêmes modes d’accès (Ouvrir, Importer, Déplacer ou Exporter) pour travailler avec des fichiers dans cet emplacement.

Cette opération est implémentée à l’aide de deux extensions différentes :

  • Extension du sélecteur de documents : fournit une UIViewController sous-classe qui fournit une interface graphique à l’utilisateur pour choisir un document à partir d’un autre emplacement de stockage. Cette sous-classe s’affiche dans le cadre du contrôleur de vue sélecteur de documents.
  • Extension de fourniture de fichiers : il s’agit d’une extension non-interface utilisateur qui traite de fournir réellement le contenu des fichiers. Ces extensions sont fournies par le biais de la coordination des fichiers ( NSFileCoordinator ). Il s’agit d’un autre cas important où la coordination des fichiers est requise.

Le diagramme suivant illustre le flux de données classique lors de l’utilisation des extensions de fournisseur de documents :

Ce diagramme montre le flux de données classique lors de l’utilisation des extensions du fournisseur de documents

Le processus suivant se produit :

  1. L’application présente un contrôleur de sélecteur de documents pour permettre à l’utilisateur de sélectionner un fichier à utiliser.
  2. L’utilisateur sélectionne un autre emplacement de fichier et l’extension personnalisée UIViewController est appelée pour afficher l’interface utilisateur.
  3. L’utilisateur sélectionne un fichier à partir de cet emplacement et l’URL est renvoyée au sélecteur de documents.
  4. Le sélecteur de documents sélectionne l’URL du fichier et le retourne à l’application pour que l’utilisateur fonctionne.
  5. L’URL est transmise au coordinateur de fichiers pour renvoyer le contenu des fichiers à l’application.
  6. Le coordinateur de fichiers appelle l’extension de fournisseur de fichiers personnalisée pour récupérer le fichier.
  7. Le contenu du fichier est retourné au coordinateur de fichiers.
  8. Le contenu du fichier est retourné à l’application.

Sécurité et signets

Cette section examine rapidement la façon dont l’accès aux fichiers persistants et à la sécurité via les signets fonctionne avec les extensions du fournisseur de documents. Contrairement au fournisseur de documents iCloud, qui enregistre automatiquement la sécurité et les signets dans le conteneur d’applications, les extensions du fournisseur de documents ne font pas partie du système de référence de document.

Par exemple : dans un paramètre Entreprise qui fournit son propre magasin de données sécurisé à l’échelle de l’entreprise, les administrateurs ne veulent pas d’informations d’entreprise confidentielles accessibles ou traitées par les serveurs iCloud publics. Par conséquent, le système de référence de document intégré ne peut pas être utilisé.

Le système de signets peut toujours être utilisé et il incombe à l’extension du fournisseur de fichiers de traiter correctement une URL avec signet et de retourner le contenu du document pointé par celui-ci.

À des fins de sécurité, iOS 8 a une couche d’isolation qui conserve les informations sur l’application qui a accès à l’identificateur à l’intérieur duquel le fournisseur de fichiers est présent. Il convient de noter que l’accès à tous les fichiers est contrôlé par cette couche d’isolation.

Le diagramme suivant montre le flux de données lors de l’utilisation des signets et d’une extension fournisseur de documents :

Ce diagramme montre le flux de données lors de l’utilisation des signets et d’une extension fournisseur de documents

Le processus suivant se produit :

  1. L’application est sur le point d’entrer en arrière-plan et doit conserver son état. Il appelle NSUrl à créer un signet dans un fichier dans un autre stockage.
  2. NSUrl appelle l’extension du fournisseur de fichiers pour obtenir une URL persistante vers le document.
  3. L’extension du fournisseur de fichiers retourne l’URL sous forme de chaîne à l’objet NSUrl .
  4. Le NSUrl bundle de l’URL dans un signet et le retourne à l’application.
  5. Lorsque l’application se réveille d’être en arrière-plan et doit restaurer l’état, elle transmet le signet à NSUrl .
  6. NSUrl appelle l’extension du fournisseur de fichiers avec l’URL du fichier.
  7. Le fournisseur d’extensions de fichier accède au fichier et retourne l’emplacement du fichier à NSUrl .
  8. L’emplacement du fichier est groupé avec des informations de sécurité et retourné à l’application.

À partir de là, l’application peut accéder au fichier et l’utiliser normalement.

Écriture de fichiers

Cette section examine rapidement le fonctionnement de l’écriture de fichiers dans un autre emplacement avec une extension fournisseur de documents. L’application iOS utilise La coordination des fichiers pour enregistrer des informations sur le disque à l’intérieur du conteneur d’applications. Peu de temps après l’écriture du fichier, l’extension du fournisseur de fichiers sera avertie de la modification.

À ce stade, l’extension du fournisseur de fichiers peut commencer à charger le fichier à l’autre emplacement (ou marquer le fichier comme sale et exiger le chargement).

Création d’extensions de fournisseur de documents

La création de nouvelles extensions de fournisseur de documents est en dehors de l’étendue de cet article d’introduction. Ces informations sont fournies ici pour montrer que, en fonction des extensions qu’un utilisateur a chargées dans son appareil iOS, une application peut avoir accès aux emplacements de stockage document en dehors de l’emplacement iCloud fourni par Apple.

Le développeur doit connaître ce fait lors de l’utilisation du sélecteur de documents et de l’utilisation de documents externes. Ils ne doivent pas supposer que ces documents sont hébergés dans iCloud.

Pour plus d’informations sur la création d’une extension de fournisseur Stockage ou de sélecteur de documents, consultez le document Présentation des extensions d’application.

Migration vers iCloud Drive

Sur iOS 8, les utilisateurs peuvent choisir de continuer à utiliser le système de documents iCloud existant utilisé dans iOS 7 (et les systèmes antérieurs) ou ils peuvent choisir de migrer des documents existants vers le nouveau mécanisme iCloud Drive.

Sur Mac OS X Yosemite, Apple ne fournit pas la compatibilité descendante. Tous les documents doivent donc être migrés vers iCloud Drive ou ils ne seront plus mis à jour sur les appareils.

Une fois que le compte d’un utilisateur a été migré vers iCloud Drive, seuls les appareils utilisant iCloud Drive pourront propager les modifications apportées aux documents sur ces appareils.

Important

Les développeurs doivent savoir que les nouvelles fonctionnalités couvertes dans cet article ne sont disponibles que si le compte de l’utilisateur a été migré vers iCloud Drive.

Résumé

Cet article a abordé les modifications apportées aux API iCloud existantes requises pour prendre en charge iCloud Drive et le nouveau contrôleur de vue sélecteur de documents. Il a abordé la coordination des fichiers et pourquoi il est important lors de l’utilisation de documents basés sur le cloud. Il a abordé la configuration requise pour activer les documents basés sur le cloud dans une application Xamarin.iOS et a donné un aperçu de l’utilisation de documents en dehors du conteneur d’applications d’une application à l’aide du contrôleur de vue sélecteur de documents.

En outre, cet article a brièvement abordé les extensions du fournisseur de documents et pourquoi le développeur doit être informé de ces extensions lors de l’écriture d’applications capables de gérer des documents basés sur le cloud.