Разработка приложений для iPhone и iPad с использованием MonoTouch

среда, 13 октября 2010, Александр Краковецкий

Для разработки программных продуктов для iPhone и iPad необходимо погружаться в изучение Objective-C и Xcode IDE. Для многих разработчиков это является стоп-фактором. Особенно это касается .NET разработчиков, которые редко “волнуются” по поводу управления памятью, указателей и других "сишных" вещей. В этой статье рассказано, как разрабатывать приложения для iPhone и iPad с помощью MonoDevelop на привычном для .NET программистов языке высокого уровня C#.

Содержание
  • Установка необходимых компонентов.
  • Начинаем работу с MonoTouch.
  • Ограничения MonoTouch.
  • Hello, World!.
  • Interface Builder.
  • Ссылки.
  • Assemblies.

Установка необходимых компонентов

Для разработки приложений с использованием MonoTouch нам понадобятся следующие инструменты:

  1. Apple Macintosh с установленной OS X 10.5.7 (также можно обойтись и Mac Mini).
  2. iPhone SDK, который можно получить на сайте http://developer.apple.com/, предварительно зарегистрировавшись.  iPhone SDK содержит эмулятор устройств, с помощью которых можно тестировать приложения без наличия реальных устройств[Концевая сноска].
  3. Mono Framework – независимый проект компании Novell с открытым исходным кодом, который можно скачать с сайта  http://mono-project.com/
  4. MonoTouch Framework - .NET-прослойка над iPhone SDK, разрабатываемая компанией Novell. Платформа доступна по адресу http://monotouch.net/. В данный момент это коммерческая разработка, стоимость лицензии начинается от $399. Более подробно о способах лицензирования можно почитать по ссылке: http://monotouch.net/Store#Buy.
  5. MonoDevelop – бесплатная IDE для разработки приложений на Mono и MonoTouch (аналог Visual Studio для Windows). Можно загрузить версии MonoDevelop для Windows, Linux и Mac OSX с официального сайта http://monodevelop.com/.
  6. Xcode – IDE от Apple для разработки iPhone и iPad приложений. В данной статье Xcode использоваться не будет, но при желании можно использовать некоторые компоненты Xcode вместе с MonoDevelop для отладки и тестирования iPhone приложений.

После установки всех вышеперечисленных компонентов можно приступать непосредственно к разработке приложений.

Начинаем работу с MonoTouch

Когда вы разрабатываете MonoTouch приложения, вы можете использовать большинство из технологий Microsoft стека .NET 3.5 (за исключением UI вещей). Это стек технологий включает в себя Windows Communication Framework (WCF), Workflow Foundation (WF) и др. Также присутствует Base Class Library (BCL), которая включает Garbage Collection, Threading, Math, System.Net, Cryptography. Список стандартных библиотек, доступных в MonoTouch, можно посмотреть по ссылке http://monotouch.net/Documentation/Assemblies. Это означает, что вы можете использовать .NET библиотеки в MonoTouch приложениях. MonoTouch также включает обвертки на iPhone API - расположение (GPS), акселерометр, адресную книгу и т.д.

Для разработки MonoTouch UI необходимо использовать встроенный Interface Builder (IB) от Apple, который поставляется вместе с iPhone SDK. Interface Builder использует родные для iPhone объекты Cocoa Touch (UI Framework для iPhone). Это означает, что вы можете использовать стандартные для iPhone элементы управления, такие как Pickers, Sliders, Buttons и др. В данный момент вы не можете такие технологии, как Silverlight, WPF, WinForms для разработки пользовательского интерфейса.

MonoTouch состоит из четырех основных компонентов:

  • MonoTouch.dll – это C# библиотека, которая предоставляет программный интерфейс взаимодействия с iPhone API. Поддерживаются Quartz, Core Animation и другие API для iPhone.
  • SDK в виде командной строки для компиляции C# CIL (Common Intermediate Language) кода в родной для iPhone код, который будет исполняться в эмуляторе или реальном устройстве.
  • Надстройка над MonoDevelop, которая позволяет создавать проекты для iPhone и предоставляет взаимодействие с Interface Builder.
  • Коммерческая лицензия на среду выполнения Mono, которая позволяет статическое линкование среды и разработанного кода.

MonoTouch состоит из таких пространств имен:

  • MonoTouch.ObjCRuntime предоставляет “мост” между .NET / C# и Objective-C.
  • MonoTouch.Foundation – tbd
  • MonoTouch.UIKit – tbd
  • OpenTK

Кроме того, MonoTouch содержит ряд дополнительных пространств имен, назначение которых понятно из названий:

  • MonoTouch.AddressBook
  • MonoTouch.CoreGraphics
  • MonoTouch.AddressBookUI
  • MonoTouch.MapKit
  • MonoTouch.AudioToolbox
  • MonoTouch.MediaPlayer
  • MonoTouch.AVFoundation
  • MonoTouch.MediaPlayer
  • MonoTouch.CoreAnimation
  • MonoTouch.SystemConfiguration

Ограничения MonoTouch

Согласно правил Apple, приложения не должны включать код, который требует Just-in-Time (JIT) компиляцию. Поэтому MonoTouch компилирует приложения в родной для iPhone код, минуя это ограничение.

Единственным языком, который поддерживается, является C#, но в планах есть Visual Basic.NET.

Другие ограничения:

  • Generics – генерики создаются с помощью JIT компилятора в рантайме, но Mono имеет Ahead of Time (AOT) компиляцию, которая генерирует все методы и свойства для объектов типа List. Другие использования Generics, такие как Generic Virtual Methods, P/Invokes в Generic Types, и Value Types в Dictionary, не поддерживаются;
  • Нет поддержки P/Invokes для генериков;
  • Dynamic Code Generation – генерация динамического кода зависит от JIT компилятора, поэтому MonoTouch не поддерживает динамическую компиляцию динамических языков. Это включает System.Reflection.Emit, Remoting и Dynamic Language Runtime;
  • Нет .NET Remoting;
  • Некоторые возможности исполняемой среды, такие как Profiler, Reflection.Emit, функциональность Reflection.Emit.Save, COM, проверка метаданных не поддерживаются;
  • Функциональность тестировалась на платформах, начиная с iPhoneOS 3.0. Корректность работы приложений, написанных для более ранних версий, не гарантируется;
  • .NET API реализовано не полностью (детальнее можно почитать по ссылке  http://monotouch.net/FAQ#What_.NET_features_does_MonoTouch_support.3f) .

Список всех ограничений доступен по адресу  http://monotouch.net/Documentation/Limitations.

Hello, World!

Открываем MonoDevelop и видим следующее окно:

http://www.infoq.com/resource/articles/monotouch-introduction/en/resources/image1.png

MonoDevelop выглядит как и стандартные IDE, такие как Visual Studio, SharpDevelop, Visual C# Express и т.д.

Создаем новое приложение (solution), которые совместимые с solutions в Visual Studioю Пос сути,  вы можете открывать проекты, написанные в Visual Studio, в MonoDevelop. Единственным отличием является тот факт, что вы можете открыть несколько solutions в одной версии MonoDevelop:

В OS X вы не можете открывать несколько версий MonoDevelop (и других приложений).

Создаем новое приложение - File : New : Solution:

Выбираем “iPhone MonoTouch Project” (как показано на рисунку) и назовем его Example_HelloWorld_1.

Нажимаем Forward и на следующем этапе нажимаем OK, так как нам не нужны дополнительные возможности:

Теперь вы должны получить solution на подобии этого:

Итак:

  • References – эта папка содержит базовые ссылки которые нужны для запуска простейшего MonoTouch приложения. Библиотека MonoTouch включает все, что специфично для iPhone, включая обвертки над элементами управления Cocoa Touch и такие фичи, как Location, Data и др. Также присутствуют библиотеки из пространства System[.x] из .NET Base Class Library.
  • Main.cs – основной файл (как это сделано в консольных приложениях). Здесь есть метод static void main(), который является точкой входа в приложение.
  • MainWindow.xib & MainWindow.xib.designer.cs – аналоги Winforms Window или WPF Window. Файл с расширением xib можен быть отредактирован в Interface Builder.

Посмотрим на код в файле Main.cs:

using System;
using System.Collections.Generic;
using System.Linq;
using MonoTouch.Foundation;
using MonoTouch.UIKit;

namespace Example_HelloWorld_1
{
  public class Application
  {
    static void Main (string[] args)
    {
      UIApplication.Main (args);
    }
  }

  // The name AppDelegate is referenced in the MainWindow.xib file.
  public partial class AppDelegate : UIApplicationDelegate
  {
    // This method is invoked when the application has loaded its UI and its ready to run
    public override bool FinishedLaunching (UIApplication app, NSDictionary options)
    {
      // If you have defined a view, add it here:
      // window.AddSubview (navigationController.View);
      window.MakeKeyAndVisible ();
      return true;
    }

    // This method is required in iPhoneOS 3.0
    public override void OnActivated (UIApplication application)
    {
    }
  }
}

Здесь мы имеем классы Application и AppDelegate. Этот подход немного отличается от привычного .NET GUI.

Мы имеем класс приложения (унаследованный от UIApplication) содержит все окна (Windows), виды (Views), элементы управления (Controls), ресурсы (Resources) и т.д. и класс делегата (унаследованный от UIApplicationDelegate), который обрабатывает события iPhone OS (такие как запуск программы или ее закрытие) и события рантайма (например предупреждения о недостаточном количестве памяти).

Обрабатывая события, вы можете на них реагировать. Например, когда ваше приложение выключается, то будет вызван метод WillTerminate() вашего класса-делегата и вы можете сохранить данные, состояние иили выполнить другие действия.

В нашем Application классе есть метод Main(). Вызывая UIApplication.Main, рантайм Objective-C найдет файл MainWindow.xib file (который содержит название нашего UIApplicationDelegate класса), создаст класс Application class (в виде Singleton) и потом вызовет события из жизненного цикла класса AppDelegate.

Interface Builder

Следующим шагом является разработка дизайна приложения. Для этого мы будем использовать Interface Builder. С его помощью можно редактировать .xib файлы, которые отвечают за пользовательский интерфейс. Файлы Nib содержат XML представление вашего интерфейса (похоже на XAML в WPF/Silverlight).

Независимо от того, что вы используете (Objective-C в XCode или C# в MonoDevelop), вы все равно используете Interface Builder.

Вы можете создавать GUI программно без использования Interface Builder и часто некоторые разработчики выбирают этот вариант. Есть много вещей, которые Interface Builder не может сделать, поэтому часто приходится дописывать GUI программно. Но для начала работы использование Interface Builder оправдано.

Поэтому открываем файл MainWindow.xib:

http://www.infoq.com/resource/articles/monotouch-introduction/en/resources/image7.png

Давайте рассмотрим все окна по порядку. Слева направо - Document Window, Design Surface Window, Library Window и Inspector Window.

Давайте посмотрим сначала на Document Window:

Это окно отображает все объекты, которые находятся в .xib файле. Это окно показывается по умолчанию, и здесь вы можете найти иерархию объектов. Когда мы добавим элементы управления в наше окно, они не будут здесь показаны. Поэтому изменим способ отображения на list view путем нажатия на центральной иконке в View Mode. В результате мы должны увидеть следующее:

С помощью элементов Cocoa Touch мы можем создавать дизайн. Для этого есть окно UIWindow:

Библиотека (Library) содержит все элементы управления, доступные в Cocoa Touch (описание всех элементов управления приведен в приложении 1). Внешний вид библиотеки показан на рисунке ниже.

Последним в обзоре является окно испектирования (Inspector Window). Это окно содержит 4 таба: инспектор атрибутов (Attribute Inspector), инспектор связей (Connections Inspector), инспектор размера (Size Inspector) и инспектор идентичности (Identity Inspector). Инспектор является аналогом Property Explorer в Visual Studio, и показывает все свойства выбранного Cocoa Touch объекта. С помощью инспектора можно создавать аутлеты (Outlets) и события (Actions), а также настраивать другие свойства объектов.

Внешний вид Inspector Window показан на рисунке ниже:

http://www.infoq.com/resource/articles/monotouch-introduction/en/resources/image11.png

После того, как мы рассмотрели все основные элементы Interface Builder, приступим к дизайну нашего приложения. Перетащим в наше окне “Round Rect Button” (UIButton), по двойному клику установим текст кнопки. Дальше добавим элемент управления “Label” (UILabel), установим ее длину на всю ширину окна и удалим текст по умолчанию, чтобы текст label был пустым.

Если вы все сделали правильно, то ваш Document Window должен приянть такой вид:

На этом процесс создания интерфейса будем считать законченным. В отличие от разработке интерфейса в .NET, на данном этапе мы не можем программно доступиться к созданным элементам управления. В данный момент в файле MainWindow.designer.cs вы кроме свойства window ничего не увидите.

Для того, чтобы иметь возможность программно работать с созданными элементами управления, необходимо создать аутлеты. Это можно сделать в окне Library. Для этого необходимо в закладке «Classes» выбрать “Other Classes”, нажать на AppDelegate и дважды нажать на кнопку «+» (для каждого элемента необходимо создать свой аутлет).

Каждый аутлет имеет имя и тип. Имя соответствует ID в ASP.NET и Windows Forms или Name в WPF. Соответственно, тип аутлета должен соответствовать типу элемента управления. В нашем случае аутлеты с именами btnClickMe и lblResult.

Примечание. Мы можем и не менять тип аутлетов, который по умолчанию устанавливается как id. Этот тип является аналогом object в .NET (или dynamic, начиная с.NET 4.0) и обозначает динамический тип. В качестве иллюстрации отличия в поведении, обозначим btnClickMe как UIButton, а тип lblResult оставим как id.

На данном этапе окно должно иметь следующий вид:

Примечание. Если по каким то причинам в списке аулетов у вас нет window, это означает, что вы создали ваши аулеты не внутри App Delegate. В таком случае необходимо удалить созданные аутлеты и пересоздать их внутри App Delegate.

После того, как аутлеты созданы, их необходимо ассоциировать с контролами в окне. Для этого необходимо перейти в вкладку «Connections Inspector», где в секции Outlets с помощью drag & drop связать элементы таким образом:

http://www.infoq.com/resource/articles/monotouch-introduction/en/resources/image20.png

Так как мы задали тип кнопки как UIButton, то дизайнер позволит ассоциировать аутлет лишь с элементами типа UIButton, в то время когда lblResults может быть ассоциирован с любым элементом управления окна. Поэтому аутлеты лучше строго типизировать, чтобы в дальнейшем не возникало проблем с типизацией.

Теперь все дизайнерский приготовления закончены, можно возвращаться назад к программированию.

Теперь, если вы откроете MainWindow.designer.cs, то увидите два дополнительных свойства:

С помощью этих свойств мы можем работать с нашими элементами управления программно. Несмотря на то, что мы указали id в качестве типа для lblResult, MonoTouch установила  тип свойства как UILabel.

MonoTouch.Foundation.Connect("btnClickMe")]
private MonoTouch.UIKit.UIButton btnClickMe {
  get {
    return ((MonoTouch.UIKit.UIButton)(this.GetNativeField("btnClickMe")));
  }
  set {
    this.SetNativeField("btnClickMe", value);
  }
}

MonoTouch.Foundation.Connect("lblResult")]
private MonoTouch.UIKit.UILabel lblResult {
  get {
    return ((MonoTouch.UIKit.UILabel)(this.GetNativeField("lblResult")));
  }
  set {
    this.SetNativeField("lblResult", value);
  }
}

В файле Main.cs посмотрим на метод FinishedLaunching:

// This method is invoked when the application has loaded its UI and its ready to run
public override bool FinishedLaunching (UIApplication app, NSDictionary options)
{
  // If you have defined a view, add it here:
  // window.AddSubview (navigationController.View);

  window.MakeKeyAndVisible ();
  return true;
}

Это метод вызывается, когда приложение инициируется и готово к запуску. Строчка window.AddSubview в данном примере закоментирована, так как наше приложение не использует UINavigationController для перемещения между окнами.

Следующая строчка window.MakeKeyAndVisible указывает на то, что MainWindow будет основным окном и делает его видимым. В целом, iPhone приложение может иметь только одно окно, а если есть необходимость в нескольких экранах, то необходимо добавить несколько UIView и использовать UINavigationController для управления их видимостью и переходами между ними. Но, если вы уберете эту строчку, то iPhone OS не будет посылать события и вы не сможете полноценно работать с вашим приложением.

В отличие от классического программирования в .NET, обработчики событий находятся не в файле основного окна, а в файле делегата (AppDelegate). Поэтому изменим его таким образом, добавив обработчик события на нажатие кнопки и переменну, в которой будем записывать количество нажатий:

// The name AppDelegate is referenced in the MainWindow.xib file.
public partial class AppDelegate : UIApplicationDelegate
{
  //---- number of times we've clicked
  protected int _numberOfClicks;

  // This method is invoked when the application has loaded its UI and its ready to run
  public override bool FinishedLaunching (UIApplication app, NSDictionary options)
  {
    // If you have defined a view, add it here:
    // window.AddSubview (navigationController.View);
  
    window.MakeKeyAndVisible ();
  
    //---- wire up our event handler
    this.btnClickMe.TouchDown += BtnClickMeTouchDown;

    return true;
  }

  protected void BtnClickMeTouchDown (object sender, EventArgs e)
  {
    //---- increment our counter
    this._numberOfClicks++;

    //---- update our label
    this.lblResult.Text = "Hello World, [" + this._numberOfClicks.ToString () + "] times";

  }

  // This method is required in iPhoneOS 3.0
  public override void OnActivated (UIApplication application)
  {
  }
}

В обработчике событий мы будем менять текст label и выводить количество нажатий.

Теперь скомпилируем приложение (вверху выбираем debug|iPhoneSimulator) и запускаем приложение (Run : Run).

В триальной версии MonoTouch вы можете запускать приложения лишь на симуляторе. Для того, чтобы иметь возможность тестровать на реальных устройствах, необходимо купить полную версию.

Если все было сделано правильно, то вы должны увидеть такой экран:

Нажатие на кнопку будет изменять текст label:

Поздравляю! Вы написали и запустили первое приложение на iPhone с помощью MonoTouch.

Assemblies

Сборки, которые поставляются вместе с MonoTouch:

Assembly Added API Compatibility
Mono.CompilerServices.SymbolWriter.dll

1.0

For compiler writers.
Mono.Data.Sqlite.dll

1.2

ADO.NET provider for SQLite; see limitations.
Mono.Data.Tds.dll

1.2

TDS Protocol support; used for System.Data.SqlClient support within System.Data.
Mono.Security.dll

1.0

Cryptographic APIs.
monotouch.dll

1.0

This assembly contains the C# binding to the CocoaTouch API.  
mscorlib.dll

1.0

Silverlight 
OpenTK.dll

1.0

The OpenGL/OpenAL object oriented APIs, extended to provide iPhone device support.
System.dll

1.0

Silverlight, plus types from the following namespaces: 
  • System.Collections.Specialized
  • System.ComponentModel
  • System.ComponentModel.Design
  • System.Diagnostics
  • System.IO.Compression
  • System.Net
  • System.Net.Cache
  • System.Net.Mail
  • System.Net.Mime
  • System.Net.NetworkInformation
  • System.Net.Security
  • System.Net.Sockets
  • System.Security.Authentication
  • System.Security.Cryptography
  • System.Timers
System.Core.dll

1.0

Silverlight 
System.Data.dll

1.2

.NET 3.5 , with some functionality removed.
System.Json.dll

1.1

Silverlight 
System.Runtime.Serialization.dll

?

Silverlight
System.ServiceModel.dll

1.1

WCF stack as present in Silverlight
System.ServiceModel.Web.dll

?

Silverlight, plus types from the following namespaces:   
  • System
  • System.ServiceModel.Channels
  • System.ServiceModel.Description
  • System.ServiceModel.Web
System.Transactions.dll

1.2

.NET 3.5; part of System.Data support.
System.Web.Services

1.1

Basic Web services from the .NET 3.5 profile, with the server features removed.
System.Xml.dll

1.0

.NET 3.5 
System.Xml.Linq.dll

1.0

.NET 3.5 

Ссылки

PDF версию статьи в виде брошюры можно скачать внизу статьи.

Компании из статьи


Microsoft Украина


Сайт:
http://www.microsoft.com/ukr/ua/

Microsoft Украина Украинское подразделение компании Microsoft.

Ищите нас в интернетах!

Комментарии

Свежие вакансии