정보
요청한 주제가 아래에 표시됩니다. 그러나 이 주제는 이 라이브러리에 포함되지 않습니다.

연습: Windows Phone 8의 연락처 및 일정 데이터 액세스

2014-06-18

적용 대상: Windows Phone 8 및 Windows Phone Silverlight 8.1 | Windows Phone OS 7.1

 

이 연습에서는 간단한 연락처와 일정 앱을 만듭니다. 이 연습에서 만들 앱에는 연락처, 약속, 그리고 데이터를 가져온 계정이 표시됩니다. 이 앱의 완료된 버전을 다운로드하려면 연락처 및 일정 샘플을 참조하세요.

이 항목에서는 사용자의 연락처 데이터에 대한 읽기 전용 액세스에 대해 설명합니다. 읽기 및 쓰기 권한을 제공하는 앱의 사용자 지정 연락처 저장소를 만드는 방법에 대한 자세한 내용은 Windows Phone 8의 사용자 지정 연락처 저장소를 참조하세요.

이 연습에서는 다음 작업을 수행합니다.

  • 연락처 및 일정 데이터 액세스

  • 연락처, 약속 및 계정을 사용자 인터페이스에 바인딩

  • 개별 연락처(사진 포함) 및 약속의 세부 정보 표시

  • 사용자 지정 데이터 변환기를 만들어 사용자 인터페이스에 연락처 사진 데이터 바인딩

완성된 앱은 다음과 같습니다.

The main page of the app

이 항목에는 다음 단원이 포함되어 있습니다.

 

이 연습을 완료하려면 Windows Phone SDK 를 설치해야 합니다. 자세한 내용은 Windows Phone 8 SDK 도구를 참조하세요.

먼저 이름이 ContactsAndCalendarTestApp인 새 Windows Phone 앱 프로젝트를 만듭니다. 이후 단계에서 앱 이름을 ContactsAndCalendarTestApp으로 가정하는 코드를 앱에 추가합니다. 앱에 다른 이름을 선택한 경우 코드에서 네임스페이스 참조를 변경해야 합니다.

앱 프로젝트를 만들려면

  1. Visual Studio의 파일 메뉴에서 새로 만들기를 가리킨 다음 프로젝트를 클릭합니다.

    새 프로젝트 대화 상자가 나타납니다.

  2. 왼쪽 창에서 설치된 템플릿을 클릭하고 Visual C# 또는 Visual Basic을 확장한 다음 Windows Phone을 클릭합니다.

  3. 프로젝트 형식 목록에서 Windows Phone 앱 을 클릭합니다.

  4. 이름 상자에 ContactsAndCalendarTestApp를 입력합니다.

  5. 확인을 클릭합니다.

    Windows Phone 플랫폼 선택 대화 상자가 나타납니다.

  6. 대상 Windows Phone 버전 드롭다운 목록에서 Windows Phone OS 7.1을 선택한 다음 확인을 클릭합니다.

    새 앱 프로젝트가 생성되고 Visual Studio에서 열립니다.

이 앱에는 연락처, 약속, 계정 각각에 대한 피벗 항목 세 개가 포함된 기본 페이지가 있습니다. 또한 연락처 및 약속 세부 정보용 추가 페이지도 두 개 있습니다.

앱 구조를 설정하려면

  1. 솔루션 탐색기에서 MainPage.xaml을 선택한 다음 Delete 키를 눌러 삭제합니다.

  2. 솔루션 탐색기에서 프로젝트를 마우스 오른쪽 버튼으로 클릭하고 추가를 가리킨 다음 새 항목을 클릭합니다.

    새 항목 추가 대화 상자가 나타납니다.

  3. Windows Phone 피벗 페이지를 선택하고 이름을 MainPage.xaml로 입력한 다음 추가를 클릭합니다.

    새 피벗 페이지가 디자이너에서 열립니다.

  4. XAML 코드에서 LayoutRoot라는 GRID 요소를 찾습니다. 해당 요소부터 파일 끝까지 포함된 모든 항목을 다음 코드로 바꿉니다. 이렇게 하면 피벗 항목이 세 개 만들어집니다. 나중에 이 항목에 내용을 입력합니다.

        <!--LayoutRoot is the root grid where all page content is placed-->
        <Grid x:Name="LayoutRoot" Background="Transparent">
    
            <!--Pivot Control-->
            <controls:Pivot Title="Contacts and Calendar Test App" >
    
                <!--Pivot item one-->
                <controls:PivotItem Header="contacts">
                </controls:PivotItem>
    
    
                <!--Pivot item two-->
                <controls:PivotItem Header="accounts">
                </controls:PivotItem>
    
    
                <!--Pivot item three-->
                <controls:PivotItem Header="appointments">
                </controls:PivotItem>
    
            </controls:Pivot>
        </Grid>
    </phone:PhoneApplicationPage>
    
  5. 솔루션 탐색기에서 프로젝트를 마우스 오른쪽 버튼으로 클릭하고 추가를 가리킨 다음 새 항목을 클릭합니다.

    새 항목 추가 대화 상자가 나타납니다.

  6. Windows Phone 세로 페이지를 선택하고 이름을 AppointmentDetails.xaml로 입력한 다음 추가를 클릭합니다.

    새 페이지가 디자이너에서 열립니다.

  7. 솔루션 탐색기에서 프로젝트를 마우스 오른쪽 버튼으로 클릭하고 추가를 가리킨 다음 새 항목을 클릭합니다.

    새 항목 추가 대화 상자가 나타납니다.

  8. Windows Phone 세로 페이지를 선택하고 이름을 ContactDetails.xaml로 입력한 다음 추가를 클릭합니다.

    새 페이지가 디자이너에서 열립니다.

  9. 솔루션 탐색기에서 App.xaml을 마우스 오른쪽 버튼으로 클릭한 다음 코드 보기를 클릭합니다.

    코드 숨김 파일이 코드 편집기에 열립니다.

  10. 클래스 맨 위에 다음 코드를 추가합니다. 이 코드는 기본 페이지와 세부 정보 페이지 간의 데이터를 전달하는 데 사용할 수 있는 전역 정적 변수 두 개를 만듭니다.

    public static Microsoft.Phone.UserData.Contact con;
    public static Microsoft.Phone.UserData.Appointment appt;
    
  11. 필요에 따라 다음 코드를 주석 처리하여 프레임 속도 카운터를 사용하지 않도록 설정합니다.

    Application.Current.Host.Settings.EnableFrameRateCounter = true;
    

이 절차에서는 진행 상태를 테스트할 앱을 실행합니다.

앱을 테스트하려면

  1. 파일 메뉴에서 모두 저장을 클릭합니다(Ctrl+Shift+S).

  2. 빌드(또는 디버그 메뉴)에서 솔루션 빌드를 클릭합니다(Ctrl+Shift+B).

  3. 표준 도구 모음에서 앱의 배포 대상을 Windows Phone 에뮬레이터 또는 Windows Phone 장치로 설정합니다.

    Target on Standard Toolbar selecting emulator 또는 Target on Standard Toolbar selecting device

  4. 디버그 메뉴에서 디버깅 시작을 클릭합니다(F5).

    앱이 시작되고 기본 페이지가 표시됩니다.

  5. 피벗 항목을 살짝 밉니다. 그러면 머리글이 각각 연락처, 계정, 약속인 세 피벗 항목이 모두 표시됩니다.

  6. 디버그 메뉴에서 디버깅 중지를 클릭합니다(F5).

연락처 데이터에 액세스하는 프로세스에서는 Contacts 개체에 대한 참조를 가져와 SearchAsync를 호출하여 해당 개체에 대한 비동기 검색을 수행한 다음, SearchCompleted 이벤트 처리기에서 Contact 개체의 컬렉션으로 결과를 캡처합니다.

연락처 피벗 항목 UI를 만들려면

  1. 솔루션 탐색기에서 MainPage.xaml을 두 번 클릭하여 디자이너에서 이 파일을 엽니다.

  2. 첫 번째 피벗 항목을 찾아 다음 코드로 바꿉니다. 이 코드는 연락처 검색에 사용되는 버튼, 라디오 버튼 및 텍스트 상자를 만듭니다. 또한 검색 결과가 포함되는 목록 상자도 만듭니다.

    <controls:PivotItem Header="contacts">
        <StackPanel Height="Auto" Width="Auto" HorizontalAlignment="Stretch" VerticalAlignment="Stretch" >
    
            <Grid>
                <Grid.ColumnDefinitions>
                    <ColumnDefinition Width="*"/>
                    <ColumnDefinition Width="*"/>
                </Grid.ColumnDefinitions>
                <Grid.RowDefinitions>
                    <RowDefinition Height="Auto" />
                    <RowDefinition Height="Auto" />
                    <RowDefinition Height="Auto" />
                </Grid.RowDefinitions>
    
                <TextBox Grid.Row="0" Grid.ColumnSpan="2" Name="contactFilterString" />
                <RadioButton Grid.Row="1" Grid.Column="0" Checked="FilterChange" Name="name" Content="name" />
                <RadioButton Grid.Row="1" Grid.Column="1" Checked="FilterChange" Name="phone" Content="phone"/>
                <RadioButton Grid.Row="2" Grid.Column="0" Checked="FilterChange" Name="email" Content="email"/>
                <Button Grid.Row="2" Grid.Column="1" Content="search" Click="SearchContacts_Click" />
            </Grid>
    
            <TextBlock Name="ContactResultsLabel" Text="Search for contacts" TextWrapping="Wrap" Margin="12,0,0,0" />
    
            <ListBox Name="ContactResultsData" ItemsSource="{Binding}" Tap="ContactResultsData_Tap" Height="300" Margin="24,0,0,0" >
                <ListBox.ItemTemplate>
                    <DataTemplate>
                        <TextBlock Name="ContactResults" Text="{Binding Path=DisplayName, Mode=OneWay}" FontSize="{StaticResource PhoneFontSizeExtraLarge}" Margin="18,8,0,0" />
                    </DataTemplate>
                </ListBox.ItemTemplate>
            </ListBox>
        </StackPanel>
    </controls:PivotItem>
    
    

연락처 데이터에 액세스하려면

  1. 솔루션 탐색기에서 MainPage.xaml을 마우스 오른쪽 버튼으로 클릭한 다음 코드 보기를 클릭합니다.

    코드 숨김 파일이 코드 편집기에 열립니다.

  2. 코드를 아래와 같이 바꿉니다. 이 코드는 기본 연락처 검색 필터를 None으로 설정하고 기본 연락처 검색 유형을 Name으로 설정합니다. 이 코드에는 라디오 버튼을 선택할 때 검색 필터를 변경하는 코드도 포함되어 있습니다. 자세한 내용은 Windows Phone 8의 연락처 필터링 및 일치를 참조하세요.

    using System;
    using System.Windows;
    using System.Windows.Controls;
    using System.Windows.Input;
    using Microsoft.Phone.Controls;
    using Microsoft.Phone.UserData;
    
    namespace ContactsAndCalendarTestApp
    {
        public partial class MainPage : PhoneApplicationPage
        {
            FilterKind contactFilterKind = FilterKind.None;
    
            // Constructor
            public MainPage()
            {
                InitializeComponent();
    
                name.IsChecked = true;
            }
    
    
            private void FilterChange(object sender, RoutedEventArgs e)
            {
                String option = ((RadioButton)sender).Name;
    
                InputScope scope = new InputScope();
                InputScopeName scopeName = new InputScopeName();
    
                switch (option)
                {
                    case "name":
                        contactFilterKind = FilterKind.DisplayName;
                        scopeName.NameValue = InputScopeNameValue.Text;
                        break;
    
                    case "phone":
                        contactFilterKind = FilterKind.PhoneNumber;
                        scopeName.NameValue = InputScopeNameValue.TelephoneNumber;
                        break;
    
                    case "email":
                        contactFilterKind = FilterKind.EmailAddress;
                        scopeName.NameValue = InputScopeNameValue.EmailSmtpAddress;
                        break;
    
                    default:
                        contactFilterKind = FilterKind.None;
                        break;
                }
    
                scope.Names.Add(scopeName);
                contactFilterString.InputScope = scope;
                contactFilterString.Focus();
            }
        }//End page class
    }//End namespace
    
  3. 생성자 뒤에 다음 코드를 추가합니다. 이 코드는 검색 버튼 클릭 이벤트를 포함하고 비동기 연락처 검색을 시작합니다.

    private void SearchContacts_Click(object sender, RoutedEventArgs e)
    {
        ContactResultsLabel.Text = "results are loading...";
        ContactResultsData.DataContext = null;
    
        Contacts cons = new Contacts();
    
        cons.SearchCompleted += new EventHandler<ContactsSearchEventArgs>(Contacts_SearchCompleted);
    
        cons.SearchAsync(contactFilterString.Text, contactFilterKind, "Contacts Test #1");
    }
    
  4. 클릭 이벤트 뒤에 다음 코드를 추가합니다. 이 코드에는 비동기 검색의 완료된 이벤트를 처리하기 위한 메서드가 포함되어 있습니다. 이 코드는 검색 결과와 같은 목록 상자의 데이터 컨텍스트를 설정하여 연락처 데이터를 사용자 인터페이스에 바인딩합니다. 여기에는 결과가 없는 경우의 오류 처리 방법도 포함됩니다. 또한 결과가 포함되어 있는지 여부에 따라 목록 상자 레이블의 텍스트를 변경합니다.

    void Contacts_SearchCompleted(object sender, ContactsSearchEventArgs e)
    {
        //MessageBox.Show(e.State.ToString());
    
        try
        {
            //Bind the results to the list box that displays them in the UI
            ContactResultsData.DataContext = e.Results;
        }
        catch (System.Exception)
        {
            //That's okay, no results
        }
    
        if (ContactResultsData.Items.Count > 0)
        {
            ContactResultsLabel.Text = "results (tap name for details...)";
        }
        else
        {
            ContactResultsLabel.Text = "no results";
        }
    }
    
  5. 검색 완료 이벤트 뒤에 다음 코드를 추가합니다. 결과 목록에서 연락처를 탭하면 이 코드가 해당 연락처를 전역 변수에 저장한 다음 연락처 세부 정보 페이지로 이동합니다.

    private void ContactResultsData_Tap(object sender, GestureEventArgs e)
    {
        App.con = ((sender as ListBox).SelectedValue as Contact);
    
        NavigationService.Navigate(new Uri("/ContactDetails.xaml", UriKind.Relative));
    }
    

기본 페이지의 결과 목록에서 연락처를 탭하면 연락처 세부 정보 페이지로 이동합니다.

연락처 세부 정보를 표시하려면

  1. 솔루션 탐색기에서 ContactDetails.xaml을 두 번 클릭하여 디자이너에서 이 파일을 엽니다.

  2. LayoutRoot라는 GRID 요소를 찾습니다. 해당 요소부터 파일 끝까지 포함된 모든 항목을 다음 코드로 바꿉니다. 이렇게 하면 연락처 이름용 텍스트 블록, 연락처 사진용 이미지 및 다른 연락처 데이터를 포함하기 위한 목록 상자가 만들어집니다.

        <!--LayoutRoot is the root grid where all page content is placed-->
        <Grid x:Name="LayoutRoot" Background="Transparent">
            <Grid.RowDefinitions>
                <RowDefinition Height="Auto"/>
                <RowDefinition Height="*"/>
            </Grid.RowDefinitions>
    
            <!--TitlePanel contains the name of the application and page title-->
            <StackPanel x:Name="TitlePanel" Grid.Row="0" Margin="12,17,0,0">
                <TextBlock x:Name="ApplicationTitle" Text="Contacts and Calendar Test App" Style="{StaticResource PhoneTextNormalStyle}"/>
                <TextBlock x:Name="PageTitle" Text="contact details" Margin="9,-7,0,0" Style="{StaticResource PhoneTextTitle1Style}"/>
            </StackPanel>
    
            <!--ContentPanel - place additional content here-->
            <StackPanel x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0">
    
                <TextBlock Text="{Binding Path=DisplayName, Mode=OneWay}" Foreground="{StaticResource PhoneAccentBrush}" FontSize="{StaticResource PhoneFontSizeExtraLarge}" />
    
                <Border BorderThickness="2" HorizontalAlignment="Left" BorderBrush="{StaticResource PhoneAccentBrush}" >
                    <Image Name="Picture" Height="85" Width="85" HorizontalAlignment="Left" />
                </Border>
    
                <TextBlock Text="phone numbers" Margin="12,12,0,0"/>
                <ListBox ItemsSource="{Binding Path=PhoneNumbers}" Height="60"  Margin="36,0,0,0">
                    <ListBox.ItemTemplate>
                        <DataTemplate>
                            <Grid>
                                <Grid.ColumnDefinitions>
                                    <ColumnDefinition Width="Auto"/>
                                    <ColumnDefinition Width="Auto"/>
                                    <ColumnDefinition Width="*"/>
                                </Grid.ColumnDefinitions>
                                <TextBlock Grid.Column="0" Text="{Binding Path=Kind, Mode=OneWay}" />
                                <TextBlock Grid.Column="1" Text=":  " />
                                <TextBlock Grid.Column="2" Text="{Binding Path=PhoneNumber, Mode=OneWay}" />
                            </Grid>
                        </DataTemplate>
                    </ListBox.ItemTemplate>
                </ListBox>
    
                <TextBlock Text="email addresses" Margin="12,12,0,0" />
                <ListBox ItemsSource="{Binding Path=EmailAddresses}" Height="60"  Margin="36,0,0,0">
                    <ListBox.ItemTemplate>
                        <DataTemplate>
                            <Grid>
                                <Grid.ColumnDefinitions>
                                    <ColumnDefinition Width="Auto"/>
                                    <ColumnDefinition Width="Auto"/>
                                    <ColumnDefinition Width="*"/>
                                </Grid.ColumnDefinitions>
                                <TextBlock Grid.Column="0" Text="{Binding Path=Kind, Mode=OneWay}" />
                                <TextBlock Grid.Column="1" Text=":  " />
                                <TextBlock Grid.Column="2" Text="{Binding Path=EmailAddress, Mode=OneWay}" />
                            </Grid>
                        </DataTemplate>
                    </ListBox.ItemTemplate>
                </ListBox>
    
                <TextBlock Text="web sites" Margin="12,12,0,0" />
                <ListBox ItemsSource="{Binding Path=Websites}" Height="60"  Margin="36,0,0,0" />
    
                <TextBlock Text="company information" Margin="12,12,0,0" />
                <ListBox ItemsSource="{Binding Path=Companies}" Height="60"  Margin="36,0,0,0">
                    <ListBox.ItemTemplate>
                        <DataTemplate>
                            <Grid>
                                <Grid.ColumnDefinitions>
                                    <ColumnDefinition Width="Auto"/>
                                    <ColumnDefinition Width="Auto"/>
                                    <ColumnDefinition Width="*"/>
                                </Grid.ColumnDefinitions>
                                <TextBlock Grid.Column="0" Text="{Binding Path=CompanyName, Mode=OneWay}" />
                                <TextBlock Grid.Column="1" Text=":  " />
                                <TextBlock Grid.Column="2" Text="{Binding Path=JobTitle, Mode=OneWay}" />
                            </Grid>
                        </DataTemplate>
                    </ListBox.ItemTemplate>
                </ListBox>
    
                <TextBlock Text="accounts" Margin="12,12,0,0" />
                <ListBox ItemsSource="{Binding Path=Accounts}" Height="60" Margin="36,0,0,0">
                    <ListBox.ItemTemplate>
                        <DataTemplate>
                            <Grid>
                                <Grid.ColumnDefinitions>
                                    <ColumnDefinition Width="Auto"/>
                                    <ColumnDefinition Width="Auto"/>
                                    <ColumnDefinition Width="*"/>
                                </Grid.ColumnDefinitions>
                                <TextBlock Grid.Column="0" Text="{Binding Path=Kind, Mode=OneWay}" />
                                <TextBlock Grid.Column="1" Text=":  " />
                                <TextBlock Grid.Column="2" Text="{Binding Path=Name, Mode=OneWay}" />
                            </Grid>
                        </DataTemplate>
                    </ListBox.ItemTemplate>
                </ListBox>
            </StackPanel>
        </Grid>
    </phone:PhoneApplicationPage>
    
    
  3. 솔루션 탐색기에서 ContactDetails.xaml을 마우스 오른쪽 버튼으로 클릭한 다음 코드 보기를 클릭합니다.

    코드 숨김 파일이 코드 편집기에 열립니다.

  4. 코드를 아래와 같이 바꿉니다. 이 코드는 페이지의 데이터 컨텍스트를 기본 페이지에서 선택한 연락처로 설정합니다. 또한 GetPicture 메서드를 호출하고 결과를 이미지 컨트롤에 표시합니다.

    using System;
    using Microsoft.Phone.Controls;
    using System.Windows.Media.Imaging;
    
    namespace ContactsAndCalendarTestApp
    {
        public partial class ContactDetails : PhoneApplicationPage
        {
            public ContactDetails()
            {
                InitializeComponent();
            }
    
            protected override void OnNavigatedTo(System.Windows.Navigation.NavigationEventArgs e)
            {
                base.OnNavigatedTo(e);
    
                //Set the data context for this page to the selected contact
                this.DataContext = App.con;
    
                try
                {
                    //Try to get a picture of the contact
                    BitmapImage img = new BitmapImage();
                    img.SetSource(App.con.GetPicture());
                    Picture.Source = img;
                }
                catch (Exception)
                {
                    //can't get a picture of the contact
                }
            }
        }
    }
    

이 절차에서는 진행 상태를 테스트할 앱을 실행합니다.

참고참고:

Windows Phone 에뮬레이터에는 샘플 연락처가 포함되어 있습니다. Windows Phone 에뮬레이터 또는 실제 장치를 사용해 이 절차를 테스트할 수 있습니다. 그러나 샘플 연락처에 사진은 없습니다.

앱을 테스트하려면

  1. 에뮬레이터 또는 장치에서 앱을 시작합니다. 필요한 경우 첫 번째 검사점의 지침을 사용합니다.

    앱이 시작되고 기본 페이지가 표시됩니다.

  2. 텍스트 상자에 A 문자를 입력한 다음 검색을 클릭합니다.

    결과가 목록에 채워집니다. Windows Phone 에뮬레이터에서 앱을 테스트하는 경우 다음이 표시됩니다.

    Andrew Hill

    Arturo Lopez

  3. 결과 목록에서 이름을 탭합니다.

    연락처 세부 정보 페이지가 열리고 연락처 세부 정보가 표시됩니다. 그러나 모든 연락처의 모든 정보가 제공되지는 않습니다.

  4. 디버그 메뉴에서 디버깅 중지를 클릭합니다(F5).

일정 데이터에 액세스하는 프로세스에서는 Appointments 개체에 대한 참조를 가져와 SearchAsync를 호출하여 해당 개체에 대한 비동기 검색을 수행한 다음, SearchCompleted 이벤트 처리기에서 Appointment 개체의 컬렉션으로 결과를 캡처합니다.

약속 피벗 항목 UI를 만들려면

  1. 솔루션 탐색기에서 MainPage.xaml을 두 번 클릭하여 디자이너에서 이 파일을 엽니다.

  2. 세 번째 피벗 항목을 찾아 다음 코드로 바꿉니다. 이 코드는 시작/종료 날짜의 레이블과 검색 버튼, 검색 결과를 포함하는 목록 상자를 만듭니다.

    <controls:PivotItem Header="appointments">
        <StackPanel Height="Auto" Width="Auto" HorizontalAlignment="Stretch" VerticalAlignment="Stretch" >
    
            <TextBlock Text="appointments between" Foreground="{StaticResource PhoneAccentBrush}" />
    
            <Grid>
                <Grid.ColumnDefinitions>
                    <ColumnDefinition Width="*"/>
                    <ColumnDefinition Width="*"/>
                </Grid.ColumnDefinitions>
                <Grid.RowDefinitions>
                    <RowDefinition Height="Auto" />
                    <RowDefinition Height="Auto" />
                    <RowDefinition Height="Auto" />
                </Grid.RowDefinitions>
    
                <TextBlock Grid.Row="0" Grid.Column="0" Text="start date" />
                <TextBlock Grid.Row="0" Grid.Column="1" Text="end date" />
                <TextBlock Grid.Row="1" Grid.Column="0" Text="placeholder" Name="StartDate" />
                <TextBlock Grid.Row="1" Grid.Column="1" Text="placeholder" Name="EndDate" />
                <Button Grid.Row="2" Grid.ColumnSpan="2" Content="search" Click="SearchAppointments_Click" HorizontalAlignment="Center" />
            </Grid>
    
            <TextBlock Name="AppointmentResultsLabel" Text="search for appointments" TextWrapping="Wrap" />
    
            <ListBox Name="AppointmentResultsData" ItemsSource="{Binding}" Tap="AppointmentResultsData_Tap" Height="400"  ScrollViewer.ManipulationMode="Control" Margin="24,0,0,0" >
                <ListBox.ItemTemplate>
                    <DataTemplate>
                        <TextBlock Text="{Binding Path=Subject, Mode=OneWay}"  FontSize="{StaticResource PhoneFontSizeExtraLarge}" />
                    </DataTemplate>
                </ListBox.ItemTemplate>
            </ListBox>
        </StackPanel>
    </controls:PivotItem>
    

약속 데이터에 액세스하려면

  1. 솔루션 탐색기에서 MainPage.xaml을 마우스 오른쪽 버튼으로 클릭한 다음 코드 보기를 클릭합니다.

    코드 숨김 파일이 코드 편집기에 열립니다.

  2. MainPage 클래스의 생성자 뒤에 다음 코드를 추가합니다. 이 코드는 검색 버튼 클릭 이벤트를 포함하고 비동기 약속 검색을 시작합니다. 또한 다음 주의 약속을 검색합니다.

    private void SearchAppointments_Click(object sender, RoutedEventArgs e)
    {
        AppointmentResultsLabel.Text = "results are loading...";
        AppointmentResultsData.DataContext = null;
        Appointments appts = new Appointments();
    
        appts.SearchCompleted += new EventHandler<AppointmentsSearchEventArgs>(Appointments_SearchCompleted);
    
        DateTime start = DateTime.Now;
        DateTime end = start.AddDays(7);
    
        appts.SearchAsync(start, end, 20, "Appointments Test #1");
    }
    
  3. 클릭 이벤트 뒤에 다음 코드를 추가합니다. 이 코드에는 비동기 검색의 완료된 이벤트를 처리하기 위한 메서드가 포함되어 있습니다. 이 코드는 목록 상자의 데이터 컨텍스트를 검색 결과와 동일하게 설정하여 약속 데이터를 사용자 인터페이스에 바인딩합니다. 여기에는 결과가 없는 경우의 오류 처리 방법도 포함됩니다. 또한 결과가 포함되어 있는지 여부에 따라 목록 상자 레이블의 텍스트를 변경합니다.

    void Appointments_SearchCompleted(object sender, AppointmentsSearchEventArgs e)
    {
        StartDate.Text = e.StartTimeInclusive.ToShortDateString();
        EndDate.Text = e.EndTimeInclusive.ToShortDateString();
    
        try
        {
            //Bind the results to the list box that displays them in the UI
            AppointmentResultsData.DataContext = e.Results;
        }
        catch (System.Exception)
        {
            //That's okay, no results
        }
    
        if (AppointmentResultsData.Items.Count > 0)
        {
            AppointmentResultsLabel.Text = "results (tap for details...)";
        }
        else
        {
            AppointmentResultsLabel.Text = "no results";
        }
    }
    
    
  4. 검색 완료 이벤트 뒤에 다음 코드를 추가합니다. 결과 목록에서 약속을 탭하면 이 코드가 해당 약속을 전역 변수에 저장한 다음 약속 세부 정보 페이지로 이동합니다.

    private void AppointmentResultsData_Tap(object sender, GestureEventArgs e)
    {
        App.appt = ((sender as ListBox).SelectedValue as Appointment);
    
        NavigationService.Navigate(new Uri("/AppointmentDetails.xaml", UriKind.Relative));
    }
    

기본 페이지의 결과 목록에서 약속을 탭하면 약속 세부 정보 페이지로 이동합니다.

약속 세부 정보를 표시하려면

  1. 솔루션 탐색기에서 AppointmentDetails.xaml을 두 번 클릭하여 디자이너에서 이 파일을 엽니다.

  2. LayoutRoot라는 GRID 요소를 찾습니다. 해당 요소부터 파일 끝까지 포함된 모든 항목을 다음 코드로 바꿉니다. 이렇게 하면 약속 제목용 텍스트 블록과 기타 약속 데이터를 포함할 스크롤 뷰어가 만들어집니다.

        <phone:PhoneApplicationPage.Resources>
    
            <DataTemplate x:Key="AttendeeTemplate">
                <Grid>
                    <Grid.ColumnDefinitions>
                        <ColumnDefinition Width="Auto"/>
                        <ColumnDefinition Width="Auto"/>
                        <ColumnDefinition Width="*"/>
                    </Grid.ColumnDefinitions>
                    <TextBlock Grid.Column="0" Text="{Binding Path=DisplayName, Mode=OneWay}" TextWrapping="Wrap" />
                    <TextBlock Grid.Column="1" Text=":  " />
                    <TextBlock Grid.Column="2" Text="{Binding Path=EmailAddress, Mode=OneWay}" TextWrapping="Wrap" />
                </Grid>
            </DataTemplate>
        </phone:PhoneApplicationPage.Resources>
    
    
        <!--LayoutRoot is the root grid where all page content is placed-->
        <Grid x:Name="LayoutRoot" Background="Transparent">
            <Grid.RowDefinitions>
                <RowDefinition Height="Auto"/>
                <RowDefinition Height="Auto"/>
                <RowDefinition Height="*"/>
            </Grid.RowDefinitions>
    
            <!--TitlePanel contains the name of the application and page title-->
            <StackPanel x:Name="TitlePanel" Grid.Row="0" Margin="12,17,0,6">
                <TextBlock x:Name="ApplicationTitle" Text="Contacts and Calendar Test App" Style="{StaticResource PhoneTextNormalStyle}"/>
                <TextBlock x:Name="PageTitle" Text="appt details" Margin="9,-7,0,0" Style="{StaticResource PhoneTextTitle1Style}"/>
            </StackPanel>
    
            <TextBlock Grid.Row="1" Text="{Binding Path=Subject, Mode=OneWay}" Foreground="{StaticResource PhoneAccentBrush}" FontSize="{StaticResource PhoneFontSizeExtraLarge}" TextWrapping="Wrap" />
    
            <!--ContentPanel - place additional content here-->
            <ScrollViewer x:Name="ContentPanel" Grid.Row="2" Margin="12,0,12,0">
                <StackPanel>
    
                    <TextBlock Text="{Binding Path=Details, Mode=OneWay}"  Margin="12,0,0,0" TextWrapping="Wrap" />
                    
                    <TextBlock Text="{Binding Path=StartTime, Mode=OneWay}"  Margin="12,12,0,0"/>
                    <TextBlock Text="{Binding Path=EndTime, Mode=OneWay}"  Margin="12,0,0,0"/>
    
                    <TextBlock Text="{Binding Path=Location, Mode=OneWay}"  Margin="12,12,0,0"/>
    
                    <TextBlock Text="{Binding Path=Status, Mode=OneWay}"  Margin="12,12,0,0"/>
    
                    <TextBlock Text="organizer" Margin="12,12,0,0" />
                    <ListBox ItemsSource="{Binding Path=Organizer}" ItemTemplate="{StaticResource AttendeeTemplate}" Margin="24,0,0,0" />
    
                    <TextBlock Text="attendees" Margin="12,12,0,0" />
                    <ListBox ItemsSource="{Binding Path=Attendees}" ItemTemplate="{StaticResource AttendeeTemplate}" Margin="24,0,0,0" />
    
                    <TextBlock Text="accounts" Margin="12,12,0,0" />
                    <ListBox ItemsSource="{Binding Path=Accounts}" Margin="24,0,0,0">
                        <ListBox.ItemTemplate>
                            <DataTemplate>
                                <Grid>
                                    <Grid.ColumnDefinitions>
                                        <ColumnDefinition Width="Auto"/>
                                        <ColumnDefinition Width="Auto"/>
                                        <ColumnDefinition Width="*"/>
                                    </Grid.ColumnDefinitions>
                                    <TextBlock Grid.Column="0" Text="{Binding Path=Kind, Mode=OneWay}" />
                                    <TextBlock Grid.Column="1" Text=":  " />
                                    <TextBlock Grid.Column="2" Text="{Binding Path=Name, Mode=OneWay}" />
                                </Grid>
                            </DataTemplate>
                        </ListBox.ItemTemplate>
                    </ListBox>
                </StackPanel>
            </ScrollViewer>
        </Grid>
    </phone:PhoneApplicationPage>
    
  3. 솔루션 탐색기에서 AppointmentDetails.xaml을 마우스 오른쪽 버튼으로 클릭한 다음 코드 보기를 클릭합니다.

    코드 숨김 파일이 코드 편집기에 열립니다.

  4. 코드를 아래와 같이 바꿉니다. 이 코드는 페이지의 데이터 컨텍스트를 기본 페이지에서 선택한 약속으로 설정합니다.

    using Microsoft.Phone.Controls;
    
    namespace ContactsAndCalendarTestApp
    {
        public partial class AppointmentDetails : PhoneApplicationPage
        {
            public AppointmentDetails()
            {
                InitializeComponent();
            }
    
            protected override void OnNavigatedTo(System.Windows.Navigation.NavigationEventArgs e)
            {
                base.OnNavigatedTo(e);
    
                //Set the data context for this page to the selected appointment
                this.DataContext = App.appt;
            }
        }
    }
    
    

이 절차에서는 진행 상태를 테스트할 앱을 실행합니다.

중요중요:

Windows Phone 에뮬레이터에는 샘플 약속이 포함되어 있지 않습니다. 따라서 Windows Phone 에뮬레이터를 사용해 이 절차를 테스트할 수는 있지만, 약속은 실제 장치에서만 볼 수 있습니다.

앱을 테스트하려면

  1. 에뮬레이터 또는 장치에서 앱을 시작합니다. 필요한 경우 첫 번째 검사점의 지침을 사용합니다.

    앱이 시작되고 기본 페이지가 표시됩니다.

  2. 화면을 살짝 밀어 약속 피벗 항목을 표시한 다음 검색 버튼을 클릭합니다.

    결과가 목록에 채워집니다.

  3. 목록에서 약속을 탭합니다.

    약속 세부 정보 페이지가 열리고 약속 세부 정보가 표시됩니다. 세부 정보가 길면 페이지를 스크롤하여 모든 세부 정보를 확인합니다.

  4. 디버그 메뉴에서 디버깅 중지를 클릭합니다(F5).

Windows Phone 에서는 사용자의 여러 계정에서 사용되는 연락처 데이터의 집계 보기를 제공합니다. 이러한 정보는 전화 자체에 입력된 데이터, 소셜 네트워크 사이트 및 기타 데이터 서비스 공급자로부터 가져올 수 있습니다. 이 절차에서는 연락처 및 일정 데이터를 가져오는 계정을 표시합니다.

계정 데이터에 액세스하려면

  1. 솔루션 탐색기에서 MainPage.xaml을 두 번 클릭하여 디자이너에서 이 파일을 엽니다.

  2. 두 번째 피벗 항목을 찾아 다음 코드로 바꿉니다. 이 코드는 연락처 계정과 약속 계정용으로 각각 하나씩, 두 개의 목록 상자를 만듭니다. 또한 다음 단계에서 추가할 항목 템플릿도 사용합니다.

    <controls:PivotItem Header="accounts">
        <Grid>
            <Grid.RowDefinitions>
                <RowDefinition Height="*" />
                <RowDefinition Height="*" />
            </Grid.RowDefinitions>
    
            <StackPanel Grid.Row="0" >
    
                <TextBlock Text="contact accounts" Foreground="{StaticResource PhoneAccentBrush}" Style="{StaticResource PhoneTextLargeStyle}" />
                <ListBox Name="ContactAccounts" ItemsSource="{Binding}" ItemTemplate="{StaticResource AccountTemplate}" Height="200" Margin="24,0,0,0" />
            </StackPanel>
    
            <StackPanel Grid.Row="1" >
    
                <TextBlock Text="appointment accounts" Foreground="{StaticResource PhoneAccentBrush}" Style="{StaticResource PhoneTextLargeStyle}" />
                <ListBox Name="CalendarAccounts" ItemsSource="{Binding}" ItemTemplate="{StaticResource AccountTemplate}" Height="200" Margin="24,0,0,0" />
            </StackPanel>
        </Grid>
    </controls:PivotItem>
    
  3. PHONE:PHONEAPPLICATIONPAGE 요소와 GRID 요소 사이에 다음 코드를 추가합니다. 이 템플릿은 목록의 모든 항목에 대한 계정 이름과 종류를 한 줄에 표시합니다.

    <phone:PhoneApplicationPage.Resources>
    
        <DataTemplate x:Key="AccountTemplate">
            <Grid>
                <Grid.ColumnDefinitions>
                    <ColumnDefinition Width="Auto"/>
                    <ColumnDefinition Width="Auto"/>
                    <ColumnDefinition Width="*"/>
                </Grid.ColumnDefinitions>
                <TextBlock Grid.Column="0" Text="{Binding Path=Name, Mode=OneWay}" />
                <TextBlock Grid.Column="1" Text=" account: " />
                <TextBlock Grid.Column="2" Text="{Binding Path=Kind, Mode=OneWay}" />
            </Grid>
        </DataTemplate>
    
    </phone:PhoneApplicationPage.Resources>
    
  4. 솔루션 탐색기에서 MainPage.xaml을 마우스 오른쪽 버튼으로 클릭한 다음 코드 보기를 클릭합니다.

    코드 숨김 파일이 코드 편집기에 열립니다.

  5. 생성자에서 기존 코드 뒤에 다음을 추가합니다. 이 코드는 연락처 목록 상자의 데이터 컨텍스트를 Accounts 속성으로 설정하고, 약속 목록 상자의 데이터 컨텍스트를 Accounts 속성으로 설정하여 사용자 인터페이스에 계정 데이터를 바인딩합니다.

    ContactAccounts.DataContext = (new Contacts()).Accounts;
    CalendarAccounts.DataContext = (new Appointments()).Accounts;
    

이 절차에서는 진행 상태를 테스트할 앱을 실행합니다.

앱을 테스트하려면

  1. 에뮬레이터 또는 장치에서 앱을 시작합니다. 필요한 경우 첫 번째 검사점의 지침을 사용합니다.

    앱이 시작되고 기본 페이지가 표시됩니다.

  2. 화면을 살짝 밀어 계정 피벗 항목을 표시합니다.

    결과가 목록에 채워집니다. Windows Phone 에뮬레이터에서 앱을 테스트하는 경우 두 목록에 다음이 표시됩니다.

    Phone account: Phone

  3. 디버그 메뉴에서 디버깅 중지를 클릭합니다(F5).

이전 절차에서는 단일 연락처의 사진을 연락처 세부 정보 페이지에 표시했습니다. 이 절차에서는 여러 연락처 사진을 기본 페이지의 결과 목록에 직접 데이터 바인딩합니다. 연락처 사진은 속성이 아니고 GetPicture 메서드를 호출하여 반환되므로, 사용자 지정 데이터 변환기를 만들어야 사진을 데이터 바인딩할 수 있습니다.

연락처 사진을 UI에 데이터 바인딩하려면

  1. 솔루션 탐색기에서 MainPage.xaml을 마우스 오른쪽 버튼으로 클릭한 다음 코드 보기를 클릭합니다.

    코드 숨김 파일이 코드 편집기에 열립니다.

  2. 다음 코드를 찾습니다. 다음 단계에서 이 줄 뒤에 새 코드를 추가합니다.

    }//End page class
    
  3. MainPage 클래스 코드 뒤에 다음과 같은 새 클래스를 추가합니다. 이 코드는 사용자 지정 데이터 변환기입니다.

    public class ContactPictureConverter : System.Windows.Data.IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            Contact c = value as Contact;
            if (c == null) return null;
    
            System.IO.Stream imageStream = c.GetPicture();
            if (null != imageStream)
            {
                return Microsoft.Phone.PictureDecoder.DecodeJpeg(imageStream);
            }
            return null;
        }
    
        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }//End converter class
    
  4. 솔루션 탐색기에서 MainPage.xaml을 두 번 클릭하여 디자이너에서 이 파일을 엽니다.

  5. <phone:PhoneApplicationPage> 태그에서 다른 네임스페이스 선언과 함께 다음 코드를 추가합니다. 이렇게 하면 사용자 지정 데이터 변환기에 액세스할 수 있습니다.

    xmlns:MyApp="clr-namespace:ContactsAndCalendarTestApp"
    
  6. 이전 절차에서 추가한 PHONE:PHONEAPPLICATION.RESOURCES 요소를 찾습니다. 데이터 템플릿 뒤, 종료 </phone:PhoneApplicationPage.Resources> 태그 앞에 다음을 추가합니다.

    <MyApp:ContactPictureConverter x:Key="ContactPictureConverter" />
    
  7. 첫 번째 피벗 항목의 연락처 결과에서 다음 데이터 템플릿을 찾습니다.

    <DataTemplate>
        <TextBlock Name="ContactResults" Text="{Binding Path=DisplayName, Mode=OneWay}" FontSize="{StaticResource PhoneFontSizeExtraLarge}" Margin="18,8,0,0" />
    </DataTemplate>
    
  8. 기존 데이터 템플릿을 다음으로 바꿉니다. 이렇게 하면 연락처 사진이 추가되고, 사용자 지정 데이터 변환기를 통해 데이터 바인딩됩니다.

    <DataTemplate>
        <StackPanel Orientation="Horizontal" >
            <Border BorderThickness="2" HorizontalAlignment="Left" VerticalAlignment="Center" BorderBrush="{StaticResource PhoneAccentBrush}" >
                <Image Source="{Binding Converter={StaticResource ContactPictureConverter}}" Width="48" Height="48" Stretch="Fill"  />
            </Border>
            <TextBlock Name="ContactResults" Text="{Binding Path=DisplayName, Mode=OneWay}" FontSize="{StaticResource PhoneFontSizeExtraLarge}" Margin="18,8,0,0" />
        </StackPanel>
    </DataTemplate>
    

이 절차에서는 진행 상태를 테스트할 앱을 실행합니다.

참고참고:

Windows Phone 에뮬레이터에는 샘플 연락처가 포함되어 있습니다. Windows Phone 에뮬레이터 또는 실제 장치를 사용해 이 절차를 테스트할 수 있습니다. 그러나 샘플 연락처에 사진은 없습니다.

앱을 테스트하려면

  1. 에뮬레이터 또는 장치에서 앱을 시작합니다. 필요한 경우 첫 번째 검사점의 지침을 사용합니다.

    앱이 시작되고 기본 페이지가 표시됩니다.

  2. 텍스트 상자에 A 문자를 입력한 다음 검색을 클릭합니다.

    결과가 목록에 채워집니다. 실제 장치에서 앱을 테스트하는 경우 일부 연락처에는 사진이 포함될 수 있습니다. 사진이 있는 연락처가 표시될 때까지 목록을 스크롤합니다.

  3. 디버그 메뉴에서 디버깅 중지를 클릭합니다(F5).

다음 방법으로 앱의 기능을 확장할 수 있습니다.

  • 사용자가 시작 날짜와 종료 날짜를 입력하도록 약속 검색을 변경합니다.

  • 약속 세부 정보 페이지와 비슷하게 스크롤 뷰어를 사용하도록 연락처 세부 정보 페이지를 변경합니다.

  • 사용자가 수행하는 검색 유형에 따라 연락처 이름, 이메일 또는 전화 번호를 표시하도록 연락처 검색 결과를 변경합니다.

  • 모든 연락처를 검색하는 기능을 추가하여 시작 화면에 고정합니다. 자세한 내용은 Windows Phone 8의 연락처 필터링 및 일치를 참조하세요.

표시: