Kontakty a contactsUI v Xamarin.iOS
Tento článek popisuje práci s novými architekturami uživatelského rozhraní Kontakty a Kontakty v aplikaci Xamarin.iOS. Tyto architektury nahrazují stávající uživatelské rozhraní adresáře a adresáře použité v předchozích verzích iOS.
S zavedením iOS 9 společnost Apple vydala dvě nové architektury a Contacts
ContactsUI
, které nahrazují stávající architektury adresáře a uživatelského rozhraní adresáře používané iOS 8 a starší.
Dvě nové architektury obsahují následující funkce:
Kontakty – Poskytuje přístup k datům seznamu kontaktů uživatele. Vzhledem k tomu, že většina aplikací vyžaduje přístup jen pro čtení, je tato architektura optimalizovaná pro přístup jen pro přístup jen pro čtení.
ContactsUI – Poskytuje prvky uživatelského rozhraní Xamarin.iOS pro zobrazení, úpravy, výběr a vytváření kontaktů na zařízeních s iOSem.
Důležité
Stávající AddressBook
a AddressBookUI
architektury používané iOSem 8 (a předchozím) jsou v iOSu 9 zastaralé a měly by být nahrazeny novými Contacts
a ContactsUI
architekturami co nejdříve pro všechny stávající aplikace Xamarin.iOS. Nové aplikace by měly být napsané proti novým architekturám.
V následujících částech se podíváme na tyto nové architektury a na to, jak je implementovat v aplikaci Xamarin.iOS.
Rozhraní Contacts Framework
Rozhraní Contacts Framework poskytuje přístup Xamarin.iOS k kontaktním informacím uživatele. Vzhledem k tomu, že většina aplikací vyžaduje přístup jen pro čtení, je tato architektura optimalizovaná pro přístup jen pro přístup jen pro čtení.
Objekty kontaktu
Třída CNContact
poskytuje bezpečný přístup z více vláken, přístup jen pro čtení k vlastnostem kontaktu, jako je jméno, adresa nebo Telefon čísla. CNContact
funkce jako a NSDictionary
obsahují více kolekcí vlastností jen pro čtení (například adresy nebo telefonní čísla):
Pro libovolnou vlastnost, která může mít více hodnot (například e-mailovou NSLabeledValue
adresu nebo telefonní čísla), budou reprezentovány jako pole objektů. NSLabeledValue
je řazená kolekce členů bezpečná pro vlákno, která se skládá ze sady popisků a hodnot jen pro čtení, kde popisek definuje hodnotu pro uživatele (například e-mail domů nebo do práce). Architektura Kontakty poskytuje výběr předdefinovaných popisků (prostřednictvím CNLabelKey
statických CNLabelPhoneNumberKey
tříd), které můžete použít ve své aplikaci nebo máte možnost definovat vlastní popisky pro vaše potřeby.
Pro libovolnou aplikaci Xamarin.iOS, která potřebuje upravit hodnoty existujícího kontaktu (nebo vytvořit nové), použijte NSMutableContact
verzi třídy a její podtřídy (například CNMutablePostalAddress
).
Následující kód například vytvoří nový kontakt a přidá ho do kolekce kontaktů uživatele:
// Create a new Mutable Contact (read/write)
var contact = new CNMutableContact();
// Set standard properties
contact.GivenName = "John";
contact.FamilyName = "Appleseed";
// Add email addresses
var homeEmail = new CNLabeledValue<NSString>(CNLabelKey.Home, new NSString("john.appleseed@mac.com"));
var workEmail = new CNLabeledValue<NSString>(CNLabelKey.Work, new NSString("john.appleseed@apple.com"));
contact.EmailAddresses = new CNLabeledValue<NSString>[] { homeEmail, workEmail };
// Add phone numbers
var cellPhone = new CNLabeledValue<CNPhoneNumber>(CNLabelPhoneNumberKey.iPhone, new CNPhoneNumber("713-555-1212"));
var workPhone = new CNLabeledValue<CNPhoneNumber>("Work", new CNPhoneNumber("408-555-1212"));
contact.PhoneNumbers = new CNLabeledValue<CNPhoneNumber>[] { cellPhone, workPhone };
// Add work address
var workAddress = new CNMutablePostalAddress()
{
Street = "1 Infinite Loop",
City = "Cupertino",
State = "CA",
PostalCode = "95014"
};
contact.PostalAddresses = new CNLabeledValue<CNPostalAddress>[] { new CNLabeledValue<CNPostalAddress>(CNLabelKey.Work, workAddress) };
// Add birthday
var birthday = new NSDateComponents()
{
Day = 1,
Month = 4,
Year = 1984
};
contact.Birthday = birthday;
// Save new contact
var store = new CNContactStore();
var saveRequest = new CNSaveRequest();
saveRequest.AddContact(contact, store.DefaultContainerIdentifier);
// Attempt to save changes
NSError error;
if (store.ExecuteSaveRequest(saveRequest, out error))
{
Console.WriteLine("New contact saved");
}
else
{
Console.WriteLine("Save error: {0}", error);
}
Pokud se tento kód spustí na zařízení s iOSem 9, přidá se do kolekce uživatele nový kontakt. Příklad:
Formátování a lokalizace kontaktů
Rozhraní Contacts obsahuje několik objektů a metod, které vám můžou pomoct formátovat a lokalizovat obsah pro zobrazení pro uživatele. Například následující kód by správně naformátoval jméno kontaktů a poštovní adresu pro zobrazení:
Console.WriteLine(CNContactFormatter.GetStringFrom(contact, CNContactFormatterStyle.FullName));
Console.WriteLine(CNPostalAddressFormatter.GetStringFrom(workAddress, CNPostalAddressFormatterStyle.MailingAddress));
U popisků vlastností, které budete zobrazovat v uživatelském rozhraní aplikace, má rozhraní Contact metody pro lokalizaci těchto řetězců. Opět je to založené na aktuálním národním prostředí zařízení s iOSem, na které aplikace běží. Příklad:
// Localized properties
Console.WriteLine(CNContact.LocalizeProperty(CNContactOptions.Nickname));
Console.WriteLine(CNLabeledValue<NSString>.LocalizeLabel(CNLabelKey.Home));
Načítání existujících kontaktů
Pomocí instance CNContactStore
třídy můžete načíst kontaktní informace z databáze kontaktů uživatele. Obsahuje CNContactStore
všechny metody potřebné k načtení nebo aktualizaci kontaktů a skupin z databáze. Vzhledem k tomu, že tyto metody jsou synchronní, doporučujeme je spustit ve vlákně na pozadí, aby se zabránilo blokování uživatelského rozhraní.
Pomocí predikátů (sestavených z CNContact
třídy) můžete filtrovat výsledky vrácené při načítání kontaktů z databáze. Chcete-li načíst pouze kontakty obsahující řetězec Appleseed
, použijte následující kód:
// Create predicate to locate requested contact
var predicate = CNContact.GetPredicateForContacts("Appleseed");
Důležité
Architektura Kontakty nepodporuje obecné a složené predikáty.
Pokud chcete například omezit načtení pouze na vlastnosti GivenName a FamilyName kontaktu, použijte následující kód:
// Define fields to be searched
var fetchKeys = new NSString[] {CNContactKey.GivenName, CNContactKey.FamilyName};
Nakonec vyhledejte databázi a vraťte výsledky pomocí následujícího kódu:
// Grab matching contacts
var store = new CNContactStore();
NSError error;
var contacts = store.GetUnifiedContacts(predicate, fetchKeys, out error);
Pokud se tento kód spustil po ukázce, kterou jsme vytvořili v oddílu Contacts Object výše, vrátí kontakt "John Appleseed", který jsme právě vytvořili.
Kontaktování ochrany osobních údajů v aplikaci Access
Vzhledem k tomu, že koncoví uživatelé můžou udělit nebo odepřít přístup ke svým kontaktním informacím na základě aplikace, zobrazí se při prvním volání CNContactStore
dialogové okno s žádostí o povolení přístupu k vaší aplikaci.
Žádost o oprávnění se zobrazí jenom jednou, při prvním spuštění aplikace a následné spuštění nebo volání této CNContactStore
aplikace použijí oprávnění, které uživatel vybral v daném okamžiku.
Aplikaci byste měli navrhnout tak, aby řádně zpracovala uživatele, který odepře přístup ke své kontaktní databázi.
Načítání částečných kontaktů
Částečný kontakt je kontakt, pro který byly z úložiště kontaktů načteny pouze některé z dostupných vlastností. Pokud se pokusíte získat přístup k vlastnosti, která nebyla dříve načtena, dojde k výjimce.
Pomocí metod CNContact
instance můžete snadno zjistit, jestli má daný kontakt požadovanou vlastnost.IsKeyAvailable
AreKeysAvailable
Příklad:
// Does the contact contain the requested key?
if (!contact.IsKeyAvailable(CNContactOption.PostalAddresses)) {
// No, re-request to pull required info
var fetchKeys = new NSString[] {CNContactKey.GivenName, CNContactKey.FamilyName, CNContactKey.PostalAddresses};
var store = new CNContactStore();
NSError error;
contact = store.GetUnifiedContact(contact.Identifier, fetchKeys, out error);
}
Důležité
GetUnifiedContacts
CNContactStore
Metody GetUnifiedContact
třídy vrací pouze částečný kontakt omezený na vlastnosti požadované ze zadaných klíčů pro načtení.
Sjednocené kontakty
Uživatel může mít různé zdroje kontaktních informací pro jednu osobu v jejich kontaktní databázi (například iCloud, Facebook nebo Google Mail). V aplikacích pro iOS a OS X se tyto kontaktní informace automaticky propojí a zobrazí se uživateli jako jediný sjednocený kontakt:
Tento jednotný kontakt je dočasný pohled na kontaktní informace v paměti, které budou mít svůj vlastní jedinečný identifikátor (který by se měl použít k opětovnému načtení kontaktu v případě potřeby). Ve výchozím nastavení vrátí architektura Kontakty jednotný kontakt, kdykoli je to možné.
Vytváření a aktualizace kontaktů
Jak jsme viděli v části Objekty kontaktu výše, použijete CNContactStore
instanci a instanci CNMutableContact
k vytvoření nových kontaktů, které se pak zapisují do databáze kontaktů uživatele pomocí CNSaveRequest
příkazu :
// Create a new Mutable Contact (read/write)
var contact = new CNMutableContact();
// Set standard properties
contact.GivenName = "John";
contact.FamilyName = "Appleseed";
// Save new contact
var store = new CNContactStore();
var saveRequest = new CNSaveRequest();
saveRequest.AddContact(contact, store.DefaultContainerIdentifier);
NSError error;
if (store.ExecuteSaveRequest(saveRequest, out error)) {
Console.WriteLine("New contact saved");
} else {
Console.WriteLine("Save error: {0}", error);
}
Lze CNSaveRequest
také použít k ukládání více změn kontaktů a skupin do mezipaměti do jedné operace a dávkování těchto úprav do CNContactStore
.
Chcete-li aktualizovat neměnitelný kontakt získaný z operace načítání, musíte nejprve požádat o proměnlivou kopii, kterou pak upravíte a uložíte zpět do úložiště kontaktů. Příklad:
// Get mutable copy of contact
var mutable = contact.MutableCopy() as CNMutableContact;
var newEmail = new CNLabeledValue<NSString>(CNLabelKey.Home, new NSString("john.appleseed@xamarin.com"));
// Append new email
var emails = new NSObject[mutable.EmailAddresses.Length+1];
mutable.EmailAddresses.CopyTo(emails,0);
emails[mutable.EmailAddresses.Length+1] = newEmail;
mutable.EmailAddresses = emails;
// Update contact
var store = new CNContactStore();
var saveRequest = new CNSaveRequest();
saveRequest.UpdateContact(mutable);
NSError error;
if (store.ExecuteSaveRequest(saveRequest, out error)) {
Console.WriteLine("Contact updated.");
} else {
Console.WriteLine("Update error: {0}", error);
}
Oznámení o změnách kontaktů
Pokaždé, když se kontakt změní, publikuje CNContactStoreDidChangeNotification
úložiště kontaktů do výchozího centra oznámení. Pokud jste uložili do mezipaměti nebo aktuálně zobrazují nějaké kontakty, budete muset tyto objekty aktualizovat z úložiště kontaktů (CNContactStore
).
Kontejnery a skupiny
Kontakty uživatele můžou existovat buď místně na zařízení uživatele, nebo jako kontakty synchronizované se zařízením z jednoho nebo více serverových účtů (jako je Facebook nebo Google). Každý fond kontaktů má svůj vlastní kontejner a daný kontakt může existovat pouze v jednom kontejneru.
Některé kontejnery umožňují uspořádání kontaktů do jedné nebo více skupin nebo dílčích skupin. Toto chování závisí na záložním úložišti pro daný kontejner. Například iCloud má pouze jeden kontejner, ale může mít mnoho skupin (ale žádné podskupy). Microsoft Exchange na druhé straně nepodporuje skupiny, ale může mít více kontejnerů (jeden pro každou složku Exchange).
Architektura ContactsUI
V situacích, kdy aplikace nepotřebuje prezentovat vlastní uživatelské rozhraní, můžete pomocí architektury ContactsUI prezentovat prvky uživatelského rozhraní k zobrazení, úpravě, výběru a vytváření kontaktů v aplikaci Xamarin.iOS.
Díky integrovaným ovládacím prvkům Společnosti Apple nejen snížíte množství kódu, který musíte vytvořit pro podporu kontaktů v aplikaci Xamarin.iOS, ale uživatelům aplikace prezentujete konzistentní rozhraní.
Kontroler zobrazení pro výběr kontaktu
Kontroler zobrazení pro výběr kontaktů (CNContactPickerViewController
) spravuje standardní zobrazení pro výběr kontaktů, které umožňuje uživateli vybrat vlastnost Kontakt nebo Kontakt z databáze kontaktů uživatele. Uživatel může vybrat jeden nebo více kontaktů (na základě jejího použití) a kontroler zobrazení pro výběr kontaktů před zobrazením výběru nezobrazí výzvu k zadání oprávnění.
Před voláním CNContactPickerViewController
třídy definujete, které vlastnosti může uživatel vybrat a definovat predikáty pro řízení zobrazení a výběru vlastností kontaktu.
Použijte instanci třídy, ze které dědí CNContactPickerDelegate
, aby reagovala na interakci uživatele s výběrem. Příklad:
using System;
using System.Linq;
using UIKit;
using Foundation;
using Contacts;
using ContactsUI;
namespace iOS9Contacts
{
public class ContactPickerDelegate: CNContactPickerDelegate
{
#region Constructors
public ContactPickerDelegate ()
{
}
public ContactPickerDelegate (IntPtr handle) : base (handle)
{
}
#endregion
#region Override Methods
public override void ContactPickerDidCancel (CNContactPickerViewController picker)
{
Console.WriteLine ("User canceled picker");
}
public override void DidSelectContact (CNContactPickerViewController picker, CNContact contact)
{
Console.WriteLine ("Selected: {0}", contact);
}
public override void DidSelectContactProperty (CNContactPickerViewController picker, CNContactProperty contactProperty)
{
Console.WriteLine ("Selected Property: {0}", contactProperty);
}
#endregion
}
}
Pokud chcete uživateli povolit výběr e-mailové adresy z kontaktů v databázi, můžete použít následující kód:
// Create a new picker
var picker = new CNContactPickerViewController();
// Select property to pick
picker.DisplayedPropertyKeys = new NSString[] {CNContactKey.EmailAddresses};
picker.PredicateForEnablingContact = NSPredicate.FromFormat("emailAddresses.@count > 0");
picker.PredicateForSelectionOfContact = NSPredicate.FromFormat("emailAddresses.@count == 1");
// Respond to selection
picker.Delegate = new ContactPickerDelegate();
// Display picker
PresentViewController(picker,true,null);
Kontroler zobrazení kontaktu
Třída Kontroler zobrazení kontaktu (CNContactViewController
) poskytuje kontroler pro prezentování standardního zobrazení kontaktu koncovému uživateli. Zobrazení Kontakt může zobrazit nové nové, neznámé nebo existující kontakty a typ musí být zadán před zobrazením zobrazení voláním správného statického konstruktoru (FromNewContact
, FromUnknownContact
, FromContact
). Příklad:
// Create a new contact view
var view = CNContactViewController.FromContact(contact);
// Display the view
PresentViewController(view, true, null);
Shrnutí
V tomto článku jsme se podrobně podívali na práci s architekturami uživatelského rozhraní contact a contact v aplikaci Xamarin.iOS. Nejprve se zabýval různými typy objektů, které architektura Contact poskytuje a jak je používáte k vytvoření nových nebo přístup k existujícím kontaktům. Prozkoumala také architekturu uživatelského rozhraní kontaktu a vybrala existující kontakty a zobrazila kontaktní informace.