Перенос из Windows 8 в Windows Phone 8. Общие сведения

Вначале давайте ознакомимся с приложением Contoso Cookbook.

Рис. 2. 
Приложение Contoso Cookbook для Windows 8: главная страница

Приложение состоит из трех страниц с рецептами, которыми пользователь может управлять. Рецепты собраны в группы и распределены по типам национальных кухонь. На главной странице (см. рисунок 2) представлены группы в несколькими рецептами национальных кухонь в каждой.

Рис. 3. 
Страница с группами рецептов

На странице с группами рецептов содержится информация о группе, показаны соответствующие рецепты, а также приведены подробные сведения о приготовлении каждого блюда.

Рис. 4. 
Страница с рецептами

На странице с рецептами представлена подробная информация о рецепте: список ингредиентов, инструкции по приготовлению и время приготовления.

Для переноса слоя представления Contoso Cookbook придется полностью переписать большую часть кода XAML. Ниже показаны примеры заданий этого упражнения.

  • Замените элементы верхнего уровня LayoutAwarePage (в приложении Windows Store) элементами PhoneApplicationPage (в приложении Windows Phone 8).
  • Установите портретную ориентацию страницы приложения для телефона.
  • Найдите замену для пользовательских элементов управления из приложения Windows Store (например, GridView и FlipView), отсутствующих в приложении Windows Phone.
  • Скорректируйте пространства имен XAML для Windows Phone. Например, в приложениях Windows Store элемент управления Grid расположен в пространстве имен Windows.UI.Xaml.Control, а в Windows Phone 8 — в пространстве имен System.Windows.Controls.

Мы начнем с главного экрана, а затем перейдем к другим страницам приложения.

Задание 1. Создание нового проекта Windows Phone, импорт общих файлов и файлов ресурсов

  1. Запустите Visual Studio Express 2012 для Windows Phone 8.
  2. В меню File (Файл) щелкните New (Создать) и выберите Project (Проект).
  3. На панели навигации слева разверните в дереве навигации узел Templates (Шаблоны), а затем — узел Visual C#, щелкните WindowsPhone.
  4. На панели справа щелкните Windows Phone Application (Приложение Windows Phone), введите его название ContosoCookbook и нажмите кнопку ОК.

    Рис. 5.
    Создание нового проекта Windows Phone


    Убедитесь, что в диалоговом окне выбора версии указана Windows Phone OS 8.0. Затем нажмите кнопку ОК.

    Рис. 6.
    Выбор нужной версии

  5. Перейдите в папку [Установочная папка практического занятия]/Assets/Code/Ex1, скопируйте три файла с изображениями и вставьте их в созданный проект Visual Studio. Эти файлы будут использоваться для брендирования нашего приложения Windows Phone.
  6. Перейдите к манифесту приложения (файл WMAppManifest.xml) в папке Properties (Свойства) в обозревателе решений и дважды щелкните его. Visual Studio откроет средство создания манифестов.
  7. Измените Display Name (Отображаемое имя) на Contoso Cookbook (см. рисунок 7).
  8. Нажмите кнопку «…», чтобы прикрепить значок приложения к файлу ApplicationIcon.png. Аналогично прикрепите мелкое и среднее изображения плиток к файлу Background.png.

    Рис. 7.
    Изменение манифеста приложения

  9. Создайте папку нового проекта: для этого щелкните правой кнопкой мыши имя проекта в обозревателе решений и последовательно выберите Add (Добавить)New Folder (Новая папка). Назовите новую папку Common.

    Рис. 8.
    Создание папки нового проекта

  10. Как упоминалось ранее, некоторые фрагменты кода приложения Windows Store практически несовместимы с таковыми в Windows Phone. Хороший примером этому — преобразователи значений (реализации IValueConverter). Эти две платформы различаются пространством имен (Windows.UI.Xaml.Data для приложений Windows Store и System.Windows.Data для приложений Windows Phone) и типом последнего параметра метода IValueConverter.Convert:

C# (приложения Windows Store)

C# (приложения Windows Phone)

  1. Примечание. Другой метод IValueConverter — ConvertBack — имеет те же различия.
                </div>
                <p>Чтобы облегчить создание приложения, мы предоставляем часть кода в качестве материалов к занятию. Добавьте файлы с кодом из папки <strong>/Assets/Code/Ex1/Common</strong>: щелкните правой кнопкой мыши папку <strong>Common</strong>, щелкните <strong>Add (Добавить)</strong> и выберите <strong>Existing Item (Существующий элемент)</strong>.</p>
                <p>
                  <img alt="" src="https://msdn.microsoft.com/ru-ru/jj917515.b5d5dcbd-3884-4dd1-be83-932164079caa(ru-ru,MSDN.10).png" title="" />
                </p>
                <p>
                  <strong>Рис. 9.</strong>
                  <br />
                  <em>Добавление в проект существующих элементов</em>
                </p>
              </li>
              <li>В диалоговом окне выбора файлов зайдите в папку <em>[Установочная папка практического занятия]/Assets/Code/Ex1/Common</em>, выделите все файлы и нажмите кнопку <strong>Add (Добавить)</strong>. <p><img alt="" src="https://msdn.microsoft.com/ru-ru/jj917515.f6145201-40f2-4784-ae3e-e3e4623bc7c5(ru-ru,MSDN.10).png" title="" /></p><p><strong>Рис. 10.</strong><br /><em>Добавление в проект готовых материалов</em></p></li>
              <li>Затем перенесите графические элементы из исходного приложения Windows Store. Следуя указаниям предыдущего шага, добавьте материалы из папки <em>[Установочная папка практического занятия]/Assets/Code/Ex1/Assets</em> в папку Assets приложения Windows Phone. Убедитесь, что сохранена структура папки (т. е. создана вложенная папка Icons и в нее добавлены соответствующие материалы). Структура папки должна совпадать с той, что показана на рисунке 10. <p><img alt="" src="https://msdn.microsoft.com/ru-ru/jj917515.aef999d0-5aee-41be-a37c-1ad97fb7f2bc(ru-ru,MSDN.10).png" title="" /></p><p><strong>Рис. 11.</strong><br /><em>Структура проекта с добавленными материалами</em></p></li>
              <li>Теперь мы внесем изменения в файл <strong>App.xaml</strong>, объявив некоторые из добавленных в предыдущем шаге материалов. Откройте файл <strong>App.xaml</strong>, найдите XML-элемент <strong>Application.Resources</strong> и измените его в соответствии с приведенным ниже кодом:</li>
            </ol>
          </div>
          <StoCodeHighlighter runat="server" ContainsMarkup="false" HideLineNumbers="False" Language="CSharp">&lt;ResourceDictionary&gt;
    

    <local:LocalizedStrings xmlns:local="clr-namespace:ContosoCookbook" x:Key="LocalizedStrings"/><sys:String x:Key="AppName">Contoso Cookbook</sys:String> <sys:Double x:Key="LogoImageWidth">150</sys:Double> <common:SizeToResolutionConverter x:Key="SizeToResolutionConverter"/> <common:StringImageSourceConverter x:Key="ToImageConverter"/> <common:ImageSourceToStringConverter x:Key="ToStringConverter"/> <common:BooleanToVisibilityConverter x:Key="VisibilityConverter"/> <common:BooleanNegationConverter x:Key="BooleanNegation"/> <common:UserImagesDisplayConverter x:Key="ImagesDisplayConverter"/>

            &lt;ResourceDictionary.MergedDictionaries&gt;
                &lt;ResourceDictionary Source="Common/CustomStyles.xaml"/&gt;
            &lt;/ResourceDictionary.MergedDictionaries&gt;
    

    </ResourceDictionary>

    Затем добавьте два пространства имен XML в элемент Application:

    xmlns:sys="clr-namespace:System;assembly=mscorlib" xmlns:common="clr-namespace:ContosoCookbook.Common"

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

    Задание 2. Перенос главной страницы

    Откройте главную страницу приложения Windows Store Contoso Cookbook (файл GroupedItemsPage.xaml). При переносе этой страницы обратите внимание на различия между платформами.

    • Корневые элементы XAML-кода двух страниц отличаются. Корневой элемент приложения Windows Store — это LayoutAwarePage (производный от класса Page), а корневой элемент приложения Windows Phone  — это PhoneApplicationPage.
    • XAML-код приложения Windows Store содержит двухстрочный элемент управления Grid, являющийся его корневым объектом: одна строка для заголовка и кнопки Back (Назад), другая — для содержимого страницы. Ниже представлена первая строка данной сетки:
    <Grid Style="{StaticResource LayoutRootStyle}"> <Grid.RowDefinitions> <RowDefinition Height="140"/> <RowDefinition Height="*"/> </Grid.RowDefinitions>

    &lt;!-- Back button and page title --&gt;
    &lt;Grid&gt;
        &lt;Grid.ColumnDefinitions&gt;
            &lt;ColumnDefinition Width="Auto"/&gt;
            &lt;ColumnDefinition Width="*"/&gt;
        &lt;/Grid.ColumnDefinitions&gt;
        &lt;Button x:Name="backButton" Click="GoBack" 
    

    IsEnabled="{Binding Frame.CanGoBack, ElementName=pageRoot}" Style="{StaticResource BackButtonStyle}"/>

        &lt;Image Source="/Images/theme/logo.png" Grid.Column="1" 
    

    HorizontalAlignment="Left" Margin="0,12,0,10" Width="280"/ > </Grid>

    При создании нового проекта Windows Phone в Visual Studio автоматически создается шаблон структуры MainPage.xaml, см. ниже:

    <Grid x:Name="LayoutRoot" Background="Transparent"> <Grid.RowDefinitions> <RowDefinition Height="Auto"/> <RowDefinition Height="*"/> </Grid.RowDefinitions>

    &lt;!--TitlePanel contains the name of the application and page title--&gt;
    &lt;StackPanel x:Name="TitlePanel" Grid.Row="0" Margin="12,17,0,28"&gt;
        &lt;TextBlock Text="MY APPLICATION"  
    

    Style="{StaticResource PhoneTextNormalStyle}" Margin="12,0"/> <TextBlock Text="page name" Margin="9,-7,0,0"
    Style="{StaticResource PhoneTextTitle1Style}"/> </StackPanel>

    &lt;!--ContentPanel - place additional content here--&gt;
    &lt;Grid x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0"&gt;
    

    </Grid>

    Шаблон по умолчанию состоит из двухстрочного элемента управления Grid. Первая строка предназначена для заголовка: названий приложения и страницы. На второй строке располагается второй элемент управления Grid для содержимого страницы.

    1. Сравним главные страницы приложения Windows Phone 8 и приложения Windows Store, а затем внесем в заголовок сетки два изменения:
      • Ориентация. Приложение Windows Phone обычно имеет книжную ориентацию, и в нем сложно отобразить несколько столбцов. Замените сетку из двух столбцов элементом StackPanel.
      • Кнопка Back (Назад). На телефоне имеется аппаратная кнопка Back, поэтому не нужно размещать аналогичную экранную кнопку Back в приложении Windows Phone.
    2. Руководствуясь вышесказанным, изменим XAML-код заголовка следующим образом:

    <StackPanel x:Name="TitlePanel" Grid.Row="0" Margin="12,17,0,15"> <Image x:Name="imgLogo" Source="Assets/Title.png" Stretch="Uniform" HorizontalAlignment="Left" Width="150"/> <TextBlock x:Name="PageTitle" Text="Contoso Recipes" Foreground="{StaticResource CustomGroupTitleBrush}" Style="{StaticResource PhoneTextTitle1Style}" Margin="9,-7,0,0"/> </StackPanel>

    Завершив работу над заголовком, перейдем к содержимому страницы. В приложении Windows Store используется новый элемент управления Semantic Zoom (Контекстное масштабирование), недоступный в приложениях Windows Phone.

    Примечание. Контекстное масштабирование — это сенсорная техника, используемая в приложениях Windows 8 для отображения больших наборов связанных данных или содержимого (фотоальбом, список приложений или адресная книга) в одном представлении, а также для навигации по этим данным или содержимому. Дополнительные сведения о контекстном масштабировании см. в документации Windows 8 на сайте:
    https://msdn.microsoft.com/en-us/library/windows/apps/hh465319.aspx

    В разделе содержимого приложения Windows Store имеется тег XAML-кода элемента управления SemanticZoom. Он определяет два разных представления, обеспечивающих, соответственно, увеличение и уменьшение. Windows Phone не поддерживает функцию контекстного масштабирования, то есть переносить состояние Zoomed In (Увеличено) в приложение Windows Phone придется вручную. Ниже представлено состояние Zoomed In для приложения Windows Store:

    <GridView x:Name="itemGridView" AutomationProperties.AutomationId="ItemGridView" AutomationProperties.Name="Grouped Items" Margin="0,-3,0,0" Padding="116,0,40,46" ItemsSource="{Binding Source={StaticResource groupedItemsViewSource}}" ItemTemplate="{StaticResource Standard250x250ItemTemplate}" SelectionMode="None" IsItemClickEnabled="True" ItemClick="ItemView_ItemClick">

    &lt;GridView.ItemsPanel&gt;
        &lt;ItemsPanelTemplate&gt;
            &lt;VirtualizingStackPanel Orientation="Horizontal"/&gt;
        &lt;/ItemsPanelTemplate&gt;
    &lt;/GridView.ItemsPanel&gt;
    &lt;GridView.GroupStyle&gt;
        &lt;GroupStyle&gt;
            &lt;GroupStyle.HeaderTemplate&gt;
                &lt;DataTemplate&gt;
                    &lt;Grid Margin="1,0,0,6"&gt;
                        &lt;Button
                    AutomationProperties.Name="Group Title"
                    Content="{Binding Title}"
                    Click="Header_Click"
                    Style="{StaticResource TextButtonStyle}"/&gt;
                    &lt;/Grid&gt;
                &lt;/DataTemplate&gt;
            &lt;/GroupStyle.HeaderTemplate&gt;
            &lt;GroupStyle.Panel&gt;
                &lt;ItemsPanelTemplate&gt;
                    &lt;VariableSizedWrapGrid Orientation="Vertical" Margin="0,0,80,0"/&gt;
                &lt;/ItemsPanelTemplate&gt;
            &lt;/GroupStyle.Panel&gt;
        &lt;/GroupStyle&gt;
    &lt;/GridView.GroupStyle&gt;
    

    </GridView>

    1. Представленный выше код XAML — это стандартный шаблон элемента управления GridView в приложении Windows Store со следующими модификациями.

      • Элемент ItemsPanel по умолчанию заменен элементом управления VirtualizingStackPanel.
      • Добавлен элемент GroupStyle с шаблонами HeaderTemplate и ItemsPanelTemplate.
    2. Элемент управления GridView подходит для экранов с альбомной ориентацией; мы заменим его в приложении Windows Phone элементом ListBox, который лучше работает с книжной ориентацией. Кроме того, мы заменим элемент ItemsPanel из элемента ListBox на элемент VirtualizingStackPanel: последний гораздо лучше подходит для работы с большим количеством объектов.

      Для начала создадим новый шаблон, чтобы отобразить в приложении Windows Phone группы рецептов. Добавьте следующий код в сетку ContentPanel:

    <ListBox x:Name="lstGroups" ItemsSource="{Binding}" SelectionChanged="lstGroups_SelectionChanged"> <!--This is the same ItemsPanel Template as in the Win8 app--> <ListBox.ItemsPanel> <ItemsPanelTemplate> <VirtualizingStackPanel Orientation="Vertical"/> </ItemsPanelTemplate> </ListBox.ItemsPanel> <ListBox.ItemTemplate> <!--A New DataTemplate suitable for the smaller Phone screen, similar to the GroupHeaderTemplate that we had for the GridView control in the Win8 app--> <DataTemplate> <Grid Margin="5" > <Grid.ColumnDefinitions> <ColumnDefinition Width="150"/> <ColumnDefinition Width="*"/> <ColumnDefinition Width="20"/> </Grid.ColumnDefinitions> <Grid.RowDefinitions> <RowDefinition/> <RowDefinition/> </Grid.RowDefinitions> <Image Source="{Binding BackgroundImage}" Width="150" Stretch="UniformToFill" Grid.RowSpan="2" /> <TextBlock Text="{Binding Title}" FontSize="48"
    Grid.Column="1" Grid.Row="0" Foreground="{StaticResource CustomApplicationTextBrush}"/> <Image Source="/Assets/lock.png" Visibility="{Binding LicensedRequired, Converter={StaticResource VisibilityConverter}}"
    Grid.Column="2" Grid.Row="0"HorizontalAlignment="Right" />

    <TextBlock Text="{Binding Description}" FontSize="24"
    Grid.Column="1" Grid.Row="1" Foreground="{StaticResource CustomApplicationTextBrush}"/> </Grid> </DataTemplate> </ListBox.ItemTemplate> </ListBox>

    Теперь внесем небольшие изменения в корневой элемент страницы приложения Windows Phone. Изменим свойство SystemTray.IsVisible элемента PhoneApplicationPage на False (значение по умолчанию — True):

    shell:SystemTray.IsVisible="False"
    1. Благодаря этому приложение будет выполняться в полноэкранном режиме, скрывая панель задач с текущим временем и индикатором заряда батареи.

    2. Теперь изменим фон сетки LayoutRoot, чтобы воспользоваться специальной кистью фона. Найдите элемент сетки LayoutRoot и измените его свойство Background следующим образом:
    Background="{StaticResource CustomApplicationBackgroundBrush}"

    Наконец, мы реализуем обработчик событий SelectionChanged в ListBox, как определено в коде XAML. Откройте файл MainPage.xaml.cs и добавьте в класс MainPage следующий код:

    private void lstGroups_SelectionChanged(object sender,
    SelectionChangedEventArgs e) {

    }

    На главную страницу приложения Windows Phone внесены все необходимые изменения XAML-кода.

    Примечание. Файл GroupedItemsPage.xaml содержит также вспомогательный код для прикрепленного представления Windows 8. Прикрепленное представление не поддерживается в Windows Phone, поэтому данную часть кода можно проигнорировать.

    Задание 3. Перенос страницы сведений о группе

    При переносе страницы GroupDetailPage.xaml могут возникнуть проблемы, с которыми мы еще не сталкивались при переносе главной страницы. На странице со сведениями о группе представлена информация о группе национальных кухонь и список рецептов группы.

    Рис.12. 
    Страница со сведениями о группе

    Для переноса этой страницы в Windows Phone потребуется поддерживаемый телефоном метод управления представлением, состоящим из двух столбцов (первый столбец — сведения о группе, второй — рецепты группы). Поскольку приложения Windows Phone имеют книжную ориентацию, воспользуемся элементом управления Pivot. Он служит для быстрой навигации по представлениям приложения. Его можно использовать в качестве интерфейса навигации для фильтрации больших наборов данных или переключения между представлениями и страницами. На первой странице Pivot отображаются сведения о группе, на другой — рецепты данной группы.

    1. Добавьте в приложение новую страницу с книжной ориентацией. В обозревателе решений Visual Studio щелкните правой кнопкой мыши название проекта, выберите Add (Добавить), а затем щелкните New Item (Новый элемент).

      Рис. 13.
      Добавление в проект нового элемента

    2. В открывшемся диалоговом окне выберите Windows Phone Portrait Page (Страница книжной ориентации Windows Phone), назовите ее GroupDetailPage.xaml и щелкните Add.

      Рис. 14.
      Добавление новой страницы книжной ориентации

    3. Теперь изменим страницу по умолчанию, чтобы разместить элемент управления Pivot с двумя страницами. Вначале добавим пространство имен в XML-элемент Page:
    xmlns:controls="clr-namespace:Microsoft.Phone. Controls;assembly=Microsoft.Phone"

    Кроме того, мы изменим значение свойства SystemTray.IsVisible на False:

    shell:SystemTray.IsVisible="False"

    Теперь найдите элемент Grid с именем LayoutRoot и измените его свойство Background:

    Background="{StaticResource CustomApplicationBackgroundBrush}"

    Замените содержимое элемента управления LayoutRootGrid новым элементом управления Pivot:

    <!--Pivot Control--> <controls:Pivot x:Name="pivot"> <controls:Pivot.Title> <Image x:Name="imgLogo" Source="Assets/Title.png" Stretch="Uniform" HorizontalAlignment="Left"
    Width="{StaticResource LogoImageWidth}"/> </controls:Pivot.Title>

    </controls:Pivot>

    Данный код объявляет логотип приложения в качестве названия элемента управления Pivot.

    7. Затем добавьте первый элемент PivotItem со сведениями о группе национальных кухонь. Добавьте в элемент Pivot следующий код, разместив его после объявления Pivot.Title:

    <!--Pivot item one--> <controls:PivotItem> <controls:PivotItem.Header> <Grid> <TextBlock Text="{Binding Title}"
    Foreground="{StaticResource CustomGroupTitleBrush}"/> </Grid> </controls:PivotItem.Header> <Grid> <Grid.RowDefinitions> <RowDefinition Height="250"/> <RowDefinition Height="*"/> </Grid.RowDefinitions> <Image Source="{Binding BackgroundImage}" Stretch="UniformToFill" x:Name="img"/> <Rectangle Fill="{StaticResource
    CustomListViewItemOverlayBackgroundBrush}"
    Width="{Binding ElementName=img, Path=ActualWidth}" Height="75" VerticalAlignment="Bottom"/> <StackPanel Orientation="Horizontal" Margin="5" HorizontalAlignment="Right" VerticalAlignment="Bottom" > <TextBlock Text="Total Recipes: "
    Foreground="{StaticResource CustomListViewItemOverlayTextBrush}"
    FontSize="48" /> <TextBlock Text="{Binding RecipesCount}"
    Foreground="{StaticResource CustomListViewItemOverlayTextBrush}"
    FontSize="48" /> </StackPanel> <ScrollViewer Grid.Row="1"> <TextBlock Text="{Binding Description}" TextWrapping="Wrap" Foreground="{StaticResource CustomApplicationTextBrush}" FontSize="24"/> </ScrollViewer> </Grid> </controls:PivotItem>

    8. Затем добавьте второй элемент PivotItem: он будет содержать ListBox с рецептами текущей группы национальных кухонь. Добавьте после первого объявления PivotItem следующий код:

    <!--Pivot item two--> <controls:PivotItem> <controls:PivotItem.Header> <StackPanel Orientation="Horizontal"> <TextBlock Text="Recipes"
    Foreground="{StaticResource CustomGroupTitleBrush}"/> </StackPanel> </controls:PivotItem.Header> <Grid> <ListBox x:Name="lstRecipes" ItemsSource="{Binding Items}" SelectionChanged="lstRecipes_SelectionChanged"> <ListBox.ItemsPanel> <ItemsPanelTemplate> <VirtualizingStackPanel Orientation="Vertical"/> </ItemsPanelTemplate> </ListBox.ItemsPanel> <ListBox.ItemTemplate> <DataTemplate> <Grid Margin="5"> <Grid.ColumnDefinitions> <ColumnDefinition Width="200"/> <ColumnDefinition Width="Auto"/> </Grid.ColumnDefinitions> <Grid.RowDefinitions> <RowDefinition/> <RowDefinition/> </Grid.RowDefinitions> <Image Source="{Binding BackgroundImage}" Width="150" Stretch="UniformToFill" Grid.RowSpan="2" /> <TextBlock Text="{Binding Title}" FontSize="48" Grid.Column="1" Grid.Row="0" Foreground="{StaticResource CustomApplicationTextBrush}"/> <StackPanel Grid.Column="1" Grid.Row="1" Orientation="Horizontal"> <TextBlock Text="Prep time: " FontSize="24" Foreground="{StaticResource CustomApplicationTextBrush}"/> <TextBlock Text="{Binding PrepTime}" FontSize="24"
    Foreground="{StaticResource CustomApplicationTextBrush}"/> </StackPanel> </Grid> </DataTemplate> </ListBox.ItemTemplate> </ListBox> </Grid> </controls:PivotItem>

    9. Наконец, добавьте в класс поддерживающего кода обработчик событий. Откройте файл GroupDetailPage.xaml.cs и добавьте следующий код:

    private void lstRecipes_SelectionChanged (object sender, SelectionChangedEventArgs e) {

    }

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

    10. Мы завершили перенос двух первых страниц; теперь можно переходить к последней странице.

    Задание 4. Перенос страницы сведений о рабочем элементе

    Напоследок мы перенесем страницу со сведениями о выбранном рецепте (ингредиенты, инструкции по приготовлению и т. д.).

    В приложении Windows Store корневым элементом управления страницы является FlipView, внутри FlipView расположен элемент управления Grid с горизонтальной прокруткой. FlipView позволяет переходить от одного рецепта к другому.

    Рис. 15. 
    Страница со сведениями о рецепте

    Windows Phone не имеет элемента управления FlipView, поэтому данную функциональность нужно заменить. Вместо исходной сетки с несколькими столбцами воспользуемся элементом управления Pivot. На исходной странице располагается сетка из трех столбцов, мы заменим их на три элемента PivotItem: сведения о рецепте (с изображением, описанием, инструкциями и временем приготовления), ингредиенты и изображения (предоставляются пользователем). Приложение Windows Phone также содержит панель приложения с несколькими кнопками, копирующими функции приложения Windows Store.

    Примечание. Мы не будем переносить элемент управления Тimer, показанный на снимке экрана выше

    1. Добавьте новую страницу с именем RecipeDetailPage. Внесите изменения, описанные в предыдущем задании: измените свойство SystemTray и фон LayoutRoot, удалите содержимое LayoutRoot.
    2. Добавьте в LayoutRoot Grid следующий код, реализующий элемент управления Pivot с тремя элементами PivotItem:
    <!--Pivot Control--> <controls:Pivot x:Name="pivot"> <controls:Pivot.Title> <Image x:Name="imgLogo" Source="Assets/Title.png" Stretch="Uniform" HorizontalAlignment="Left"
    Width="{StaticResource LogoImageWidth}"/> </controls:Pivot.Title>

    &lt;!--Pivot item one--&gt;
    &lt;controls:PivotItem&gt;
        &lt;controls:PivotItem.Header&gt;
            &lt;Grid&gt;
                &lt;TextBlock Text="{Binding Title}" 
    

    Foreground="{StaticResource CustomGroupTitleBrush}"/> </Grid> </controls:PivotItem.Header> <Grid> <Grid.RowDefinitions> <RowDefinition Height="250"/> <RowDefinition Height="*"/> <RowDefinition Height="Auto"/> </Grid.RowDefinitions> <Image Source="{Binding BackgroundImage}" Stretch="UniformToFill"/> <ScrollViewer Grid.Row="1"> <TextBlock Text="{Binding Directions}" TextWrapping="Wrap"
    Foreground="{StaticResource CustomApplicationTextBrush}"
    FontSize="24"/> </ScrollViewer> <StackPanel Grid.Row="2" Orientation="Horizontal" Margin="15"> <TextBlock Text="Prep time: " FontSize="24" Foreground="{StaticResource CustomApplicationTextBrush}"/> <TextBlock Text="{Binding PrepTime}" FontSize="24" Foreground="{StaticResource CustomApplicationTextBrush}"/> </StackPanel> </Grid> </controls:PivotItem>

    &lt;!--Pivot item two--&gt;
    &lt;controls:PivotItem&gt;
        &lt;controls:PivotItem.Header&gt;
            &lt;Grid&gt;
                &lt;TextBlock Text="Ingredients"
    

    Foreground="{StaticResource CustomGroupTitleBrush}"/> </Grid> </controls:PivotItem.Header> <ListBox x:Name="lstIngredieants"
    ItemsSource="{Binding Ingredients}"> <ListBox.ItemsPanel> <ItemsPanelTemplate> <VirtualizingStackPanel Orientation="Vertical"/> </ItemsPanelTemplate> </ListBox.ItemsPanel> <ListBox.ItemTemplate> <DataTemplate> <TextBlock Text="{Binding}" FontSize="24" Foreground="{StaticResource CustomApplicationTextBrush}" Margin="5"/> </DataTemplate> </ListBox.ItemTemplate> </ListBox> </controls:PivotItem>

    &lt;!--Pivot item three--&gt;
    &lt;controls:PivotItem x:Name="PicsPivot"&gt;
        &lt;controls:PivotItem.Header&gt;
            &lt;Grid&gt;
                &lt;TextBlock Text="My Pictures" 
    

    Foreground="{StaticResource CustomGroupTitleBrush}"/> </Grid> </controls:PivotItem.Header> <Grid> <TextBlock Text="No images found." Foreground="{StaticResource CustomGroupTitleBrush}"
    FontSize="24" HorizontalAlignment="Center" Visibility="{Binding UserImages, Converter={StaticResource ImagesDisplayConverter}}" VerticalAlignment="Center" /> <ListBox x:Name="listUserPictures"
    ItemsSource="{Binding UserImages}"> <ListBox.ItemsPanel> <ItemsPanelTemplate> <VirtualizingStackPanel Orientation="Vertical"/> </ItemsPanelTemplate> </ListBox.ItemsPanel> <ListBox.ItemTemplate> <DataTemplate> <Grid> <Image Source="{Binding Converter={StaticResource ToImageConverter}}"
    Margin="5"/> <Rectangle Fill="{StaticResource CustomListViewItemOverlayBackgroundBrush}" Height="50" VerticalAlignment="Bottom"/> <StackPanel Orientation="Horizontal" Margin="5" HorizontalAlignment="Left" VerticalAlignment="Bottom"> <TextBlock Text="{Binding Converter={StaticResource ToStringConverter}}" Margin="10,0,0,5" Foreground="{StaticResource CustomListViewItemOverlayTextBrush}" FontSize="22" /> </StackPanel> </Grid> </DataTemplate> </ListBox.ItemTemplate> </ListBox> </Grid> </controls:PivotItem> </controls:Pivot>

    3. Затем мы добавим элемент управления ApplicationBar с несколькими кнопками:

    <phone:PhoneApplicationPage.ApplicationBar> <shell:ApplicationBar IsVisible="True" IsMenuEnabled="True"
    Mode="Default" Opacity="1.0"> <shell:ApplicationBarIconButton x:Name="btnTakePicture" IconUri="/Assets/Icons/camera.png" Click="btnTakePicture_Click"
    Text="Take Picture"/> <shell:ApplicationBarIconButton x:Name="btnShareTask" IconUri="/Assets/Icons/share.png" Click="btnShareShareTask_Click" Text="Share Image"/> <shell:ApplicationBarIconButton x:Name="btnStartCooking" IconUri="/Assets/Icons/alarm.png" Click="btnStartCooking_Click" Text="Start Cooking"/> <shell:ApplicationBarIconButton x:Name="btnPinToStart" IconUri="/Assets/Icons/like.png" Click="btnPinToStart_Click" Text="Pin To Start"/> </shell:ApplicationBar> </phone:PhoneApplicationPage.ApplicationBar>

    4. Наконец, мы добавим в файл кода программной части (RecipeDetailPage.xaml.cs) следующие обработчики событий:

    private void btnTakePicture_Click(object sender, EventArgs e) {

    }

    private void btnShareShareTask_Click(object sender, EventArgs e) {

    }

    private void btnStartCooking_Click(object sender, EventArgs e) {

    }

    private void btnPinToStart_Click(object sender, EventArgs e) {

    }

    Итак, проанализируем внесенные изменения: нам пришлось переписать с нуля большинство страниц XAML-кода. Windows 8 и Windows Phone 8 — это разные операционные системы с разными API и методами разработки. Это делает практически невозможным полный перенос XAML-кода, созданного для 10-дюймовых (и больше) экранов, на экраны размером 5 дюймов. И тем не менее некоторые компоненты можно использовать повторно:

    • Стили. Перенос стилей, созданных в Windows 8, в Windows Phone, позволяет сохранить единообразие интерфейса. Возможно, потребуется незначительно скорректировать стили, но большинство из них работают на обеих платформах: сравните исходный файл CustomStyles.xaml и файл, добавленный в проект в задании 1.
    • Шаблоны данных. Все шаблоны данных, созданные в приложениях Windows Store, можно использовать повторно, практически без изменений. Мы хотим, чтобы большинство элементов выглядели одинаково, хотя для их удобного размещения на странице, возможно, потребуется изменить размер элементов и структуру страницы.

    Примечание. Зачастую в стилях и шаблонах данных используются ресурсы приложений Windows Store, например кисти. При переносе в Windows Phone 8 потребуется изменить эти элементы, то есть использовать их аналоги для этой ОС.

    При разработке приложения для развертывания сразу в двух системах (в Windows 8 и Windows Phone 8) продумайте, как устранить проблемы переноса, описанные в этом упражнении. Это поможет примерно оценить издержки, связанные с миграцией XAML-кода приложения. При проектировании и реализации стилей и шаблонов Windows 8 постарайтесь сделать так, чтобы их можно было легко перенести в Windows Phone 8.

    Предыдущая | Следующая