XAML in Xamarin.Forms 基礎篇 電子書

XAML in Xamarin.Forms 基礎篇 電子書
XAML in Xamarin.Forms 基礎篇 電子書

Xamarin.Forms 快速入門 電子書

Xamarin.Forms 快速入門 電子書
Xamarin.Forms 快速入門 電子書

2016/07/14

Xamarin.Forms 與裝置硬體互動

與裝置硬體互動

在進行 Xamarin.Forms 跨平台應用程式開發的時候,您需要取得特定平台硬體內的許多資訊,例如:您需要取得裝置硬體的唯一識別碼、GPS定位最新資訊、電池狀態、網路連線狀況等等。
在這個章節內,開發者可以在核心PCL專案內,
  • 得知裝置的電池電力、充電狀態等等 (使用 Battery Plugin)
  • 檢查網路連線狀態、連線類型、可用頻寬等資訊 (使用 Connectivity Plugin)
  • 取出裝置的相關資訊,如型號、作業系統等等 (使用 Device Info Plugin)`
  • 取得 GPS 當時定位資訊,必且開啟手機內建的地圖應用程式來顯示 (使用 Geolocator / External Maps Plugin)
  • 讓裝置硬體震動 (使用 Vibrate Plugin)`

建立標籤式的樣板式頁面方案

  1. 首先,開啟您的 Visual Studio 2015
  2. 接著透過 Visual Studio 2015 功能表,選擇這些項目 檔案 > 新增 > 專案 準備新增一個專案。
  3. 接著,Visual Studio 2015 會顯示 新增專案 對話窗,請在這個對話窗上,進行選擇 Visual C# >Cross-Platform > Blank Xaml App (Xamarin.Forms Portable)
  4. 接著,在最下方的 名稱 文字輸入盒處,輸入 XFDevInfo 這個名稱,最後使用滑鼠右擊右下方的 確定 按鈕。
  5. 當專案建立到一半,若您的開發環境還沒有建置與設定完成 Mac 電腦與 Xamarin Studio for Mac 系統,此時會看到 Xamarin Mac Agent Instructions 對話窗出現,這個對話窗是要提醒您進行與 Mac 電腦連線設定,這是因為,您無法在 Windows 作業系統進行 iOS 相關應用程式的建立與設計工作,而是需要透過 Mac 電腦安裝的 XCode 來協助您完成這些 iOS 應用程式的建立工作。不過,這不影響您繼續開發 Xamarin.Forms 的應用程式,只不過此時,您無法編譯與執行 iOS 的應用程式。
  6. 接著會看到 新的通用Windows專案 對話視窗,此時,您只需要按下 確定 按鈕即可,此時,專案精靈會繼續完成相關平台的專案建立工作。
  7. 最後,整個新的 Xamarin.Forms 專案就建立完成了。

準備安裝套件

Battery Plugin

  • 滑鼠右擊方案節點 XFDevInfo,接著選擇 管理方案的 NuGet 套件
  • 在 NuGet - 解決方案 子標籤頁次出現後,點選 瀏覽
  • 請在搜尋文字輸入盒內,輸入 Xam.Plugin.Battery,接著點選 Xam.Plugin.Battery 項目;在右方點選要安裝到全部的專案內,最後,點選 安裝 按鈕
    在方案內加入NuGet套件

Connectivity Plugin

  • 滑鼠右擊方案節點 XFDevInfo,接著選擇 管理方案的 NuGet 套件
  • 在 NuGet - 解決方案 子標籤頁次出現後,點選 瀏覽
  • 請在搜尋文字輸入盒內,輸入 Xam.Plugin.Connectivity,接著點選 Xam.Plugin.Connectivity 項目;在右方點選要安裝到全部的專案內,最後,點選 安裝 按鈕

Device Info Plugin

  • 滑鼠右擊方案節點 XFDevInfo,接著選擇 管理方案的 NuGet 套件
  • 在 NuGet - 解決方案 子標籤頁次出現後,點選 瀏覽
  • 請在搜尋文字輸入盒內,輸入 Xam.Plugin.DeviceInfo,接著點選 Xam.Plugin.DeviceInfo 項目;在右方點選要安裝到全部的專案內,最後,點選 安裝 按鈕

Geolocator

  • 滑鼠右擊方案節點 XFDevInfo,接著選擇 管理方案的 NuGet 套件
  • 在 NuGet - 解決方案 子標籤頁次出現後,點選 瀏覽
  • 請在搜尋文字輸入盒內,輸入 Xam.Plugin.Geolocator,接著點選 Xam.Plugin.Geolocator 項目;在右方點選要安裝到全部的專案內,最後,點選 安裝 按鈕

External Maps

  • 滑鼠右擊方案節點 XFDevInfo,接著選擇 管理方案的 NuGet 套件
  • 在 NuGet - 解決方案 子標籤頁次出現後,點選 瀏覽
  • 請在搜尋文字輸入盒內,輸入 Xam.Plugin.ExternalMaps,接著點選 Xam.Plugin.ExternalMaps 項目;在右方點選要安裝到全部的專案內,最後,點選 安裝 按鈕

Vibrate

  • 滑鼠右擊方案節點 XFDevInfo,接著選擇 管理方案的 NuGet 套件
  • 在 NuGet - 解決方案 子標籤頁次出現後,點選 瀏覽
  • 請在搜尋文字輸入盒內,輸入 Xam.Plugins.Vibrate,接著點選 Xam.Plugins.Vibrate 項目;在右方點選要安裝到全部的專案內,最後,點選 安裝 按鈕

MainPage

  • 在安裝好所有的擴充插件(Plugins),打開核心PCL 的 MainPage.xaml 檔案,將底下的 XAML 宣告定義複製到這個檔案內。
  • 首先為了避免在 iOS 平台執行時候,最上方的狀態烈被遮蔽掉的問題,因此,透過ContentPage.Padding 來定義整個頁面皆內縮 20dp。
  • 這個頁面的控制項,使用了 ScrollView 版面配置來進行所有控制項的定位,因此,當螢幕無法顯示所有控制項的時候,使用者可以透過手勢滑動螢幕的操作方式,看到其他內容。
  • 在這個 XAML 中,使用到的 ContentPage.Resources 功能,在這裡所宣告的內容,都可以直接在這個頁面內來引用;其中,<x:Double x:Key="TopicLabelFontSize">30</x:Double> 這個是宣告了一個Double 型別的物件,他的值為 30,在其他控制項若要參考這個物件,可以使用 StaticResource 這個延伸標記功能取得這個物件值。
  • 在這個頁面內,定義了大量的 Label 控制項,並且都有定義 x:Name 延伸標記,而這個延伸標記是用於讓 code-behind 的C#程式碼,可以存取到這個控制項。因此,實際的處理邏輯,都存在 code-behind 程式碼內。

MainPage.xaml

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:local="clr-namespace:XFDevInfo"
             x:Class="XFDevInfo.MainPage">

  <ContentPage.Padding>20</ContentPage.Padding>
  <ContentPage.Resources>
    <ResourceDictionary>
      <x:Double x:Key="TopicLabelFontSize">30</x:Double>
      <x:Double x:Key="DetailLabelFontSize">18</x:Double>
    </ResourceDictionary>
  </ContentPage.Resources>

  <ScrollView
    Orientation="Vertical"
    >
    <StackLayout
      Orientation="Vertical"
      >

    <StackLayout
      Orientation="Vertical"
      HorizontalOptions="Start" VerticalOptions="Start"
      >
      <Label Text="電池狀態" FontSize="{StaticResource TopicLabelFontSize}" />

      <Label x:Name="label電池狀態1" FontSize="{StaticResource DetailLabelFontSize}" />
      <Label x:Name="label電池狀態2" FontSize="{StaticResource DetailLabelFontSize}" />
      <Label x:Name="label電池狀態3" FontSize="{StaticResource DetailLabelFontSize}" />

    </StackLayout>

    <StackLayout
      Orientation="Vertical"
      HorizontalOptions="Start" VerticalOptions="Start"
      >
      <Label Text="網路狀態" FontSize="{StaticResource TopicLabelFontSize}" />

      <Label x:Name="label網路狀態1" FontSize="{StaticResource DetailLabelFontSize}" />
      <Label x:Name="label網路狀態2" FontSize="{StaticResource DetailLabelFontSize}" />
      <Label x:Name="label網路狀態3" FontSize="{StaticResource DetailLabelFontSize}" />
      <Label x:Name="label網路狀態4" FontSize="{StaticResource DetailLabelFontSize}" />
    </StackLayout>

    <StackLayout
     Orientation="Vertical"
     HorizontalOptions="Start" VerticalOptions="Start"
      >
      <Label Text="裝置資訊" FontSize="{StaticResource TopicLabelFontSize}" />

      <Label x:Name="label裝置資訊1" FontSize="{StaticResource DetailLabelFontSize}" />
      <Label x:Name="label裝置資訊2" FontSize="{StaticResource DetailLabelFontSize}" />
      <Label x:Name="label裝置資訊3" FontSize="{StaticResource DetailLabelFontSize}" />
      <Label x:Name="label裝置資訊4" FontSize="{StaticResource DetailLabelFontSize}" />
      <Label x:Name="label裝置資訊5" FontSize="{StaticResource DetailLabelFontSize}" />
      <Label x:Name="label裝置資訊6" FontSize="{StaticResource DetailLabelFontSize}" />
    </StackLayout>

    <StackLayout
      Orientation="Vertical"
      HorizontalOptions="Start" VerticalOptions="Start"
      >
      <Label Text="位置定位" FontSize="{StaticResource TopicLabelFontSize}" />

      <Label x:Name="label位置定位1" FontSize="{StaticResource DetailLabelFontSize}" />

      <Button x:Name="button位置定位" Text="位置定位" Clicked="Onbutton位置定位" />
      <Button x:Name="button開啟地圖" Text="開啟地圖" Clicked="Onbutton開啟地圖" />
    </StackLayout>

    <StackLayout
      Orientation="Vertical"
      HorizontalOptions="Start" VerticalOptions="Start"
      >
      <Label Text="觸發震動" FontSize="{StaticResource TopicLabelFontSize}" />

      <Button x:Name="button觸發震動" Text="觸發震動" Clicked="Onbutton觸發震動" />
    </StackLayout>

    </StackLayout>

  </ScrollView>

</ContentPage>
  • 請將下列 C# 程式碼複製到 MainPage.xaml.cs內。
  • Init() 方法會由建構式來呼叫,其適用於透過剛剛安裝的各個插件(Plugins),進行存取,取得相關內容,並且設定到 XAML 控制項內。
  • 各個插件(Plugins)使用方式其實相當簡單,首先,取得現在插件物件,這裡以電池資訊插件為例。
    var CrossBattery = Plugin.Battery.CrossBattery.Current;
    接著就可以透過 CrossBattery 物件變數,來取得更詳盡的電池資訊,底下為取得電池電力上下多少?
    CrossBattery.RemainingChargePercent
  • 想要透過插件取得當時手機位置定位,可以透過 CrossGeolocator 取得當時的物件
    var fooCrossGeolocator = CrossGeolocator.Current;
    設定 DesiredAccuracy 屬性,設定定位精準度,單位是公尺
    最後,透過非同步方法 GetPositionAsync,取得現在所在位置座標資訊`,方法內所傳遞過去的參數為逾時時間,單位是毫秒(1毫秒 = 1/1000 秒)
    position = await fooCrossGeolocator.GetPositionAsync(timeoutMilliseconds: 10000);

MainPage.xaml.cs

using Plugin.Battery;
using Plugin.Connectivity;
using Plugin.DeviceInfo;
using Plugin.ExternalMaps;
using Plugin.Geolocator;
using Plugin.Geolocator.Abstractions;
using Plugin.Vibrate;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Xamarin.Forms;
using Xamarin.Forms.Xaml;

[assembly: XamlCompilation(XamlCompilationOptions.Compile)]
namespace XFDevInfo
{
    public partial class MainPage : ContentPage
    {
        public MainPage()
        {
            InitializeComponent();

            Init();
        }

        public async void Init()
        {
            #region 電池資訊
            var CrossBattery = Plugin.Battery.CrossBattery.Current;

            label電池狀態1.Text = $"電源來源 : {CrossBattery.PowerSource}";
            label電池狀態2.Text = $"充電狀態 : {CrossBattery.Status}";
            label電池狀態3.Text = $"可用電力 : {CrossBattery.RemainingChargePercent}";
            #endregion

            #region 網路狀態
            var fooCrossConnectivity = CrossConnectivity.Current;

            label網路狀態1.Text = $"是否連上Internet : {fooCrossConnectivity.IsConnected}";
            var fooBandwidths = fooCrossConnectivity.Bandwidths;
            string fooBandwidthsString = "";
            foreach (var item in fooBandwidths)
            {
                fooBandwidthsString += item + " ";
            }
            label網路狀態2.Text = $"可用頻寬 : {fooBandwidthsString}";
            var fooConnectionTypes = fooCrossConnectivity.ConnectionTypes;
            string fooConnectionTypesString = "";
            foreach (var item in fooConnectionTypes)
            {
                fooConnectionTypesString += item + " ";
            }
            label網路狀態3.Text = $"連線類型 : {fooConnectionTypesString}";
            var fooIsReachable = await fooCrossConnectivity.IsRemoteReachable("www.xamarin.com", 80, 2000);
            label網路狀態4.Text = $"可否連上 Xamarin : {fooIsReachable}";
            #endregion

            #region 裝置資訊
            var fooCrossDeviceInfo = CrossDeviceInfo.Current;

            label裝置資訊1.Text = $"此裝置的ID : {fooCrossDeviceInfo.Id}";
            var fooGenerateAppId = fooCrossDeviceInfo.GenerateAppId();
            label裝置資訊6.Text = $"此應用程式的ID : {fooGenerateAppId}";
            label裝置資訊2.Text = $"裝置的型號 : {fooCrossDeviceInfo.Model}";
            label裝置資訊3.Text = $"裝置平台 : {fooCrossDeviceInfo.Platform}";
            label裝置資訊4.Text = $"作業系統版本 : {fooCrossDeviceInfo.Version}";
            label裝置資訊5.Text = $"作業系統版本編號 : {fooCrossDeviceInfo.VersionNumber}";
            #endregion

            #region 位置定位

            #endregion

            #region 觸發震動

            #endregion
        }

        #region 位置定位
        Position position;
        async void Onbutton位置定位(object sender, EventArgs e)
        {
            var fooCrossGeolocator = CrossGeolocator.Current;
            fooCrossGeolocator.DesiredAccuracy = 50;

            position = await fooCrossGeolocator.GetPositionAsync(timeoutMilliseconds: 10000);

            label位置定位1.Text = $"Lat={position.Latitude}, Lon={position.Longitude}";
        }

        void Onbutton開啟地圖(object sender, EventArgs e)
        {
            if (position != null)
            {
                CrossExternalMaps.Current.NavigateTo("現在位置", position.Latitude, position.Longitude);
            }
        }
        #endregion

        #region 觸發震動
        void Onbutton觸發震動(object sender, EventArgs e)
        {
            var fooCrossVibrate = CrossVibrate.Current;
            fooCrossVibrate.Vibration(1000);
        }
        #endregion
    }
}

實際執行畫面

Android 執行結果

請在方案總管內,滑鼠右擊 XFDevInfo.Droid 專案,選擇 設定為起始專案,接著按下 F5 開始執行。
Android_執行結果1
若是要在 Visual Studio Emulator for Android 模擬器下測試 GPS 定位功能,可以點選該模擬器右邊的工具列最下方的往右雙箭頭,如下圖所示。
模擬器設定標籤
此時模擬器的其他工具對話窗就會顯示出來,請點選 位置 標籤頁,將地圖縮放與移動到您想要的位置,接著點選上方的 開啟與關閉定位模式,在進入到定位模式後,點選地圖上的任一個地方,左下方就是出現一個座標點,若此時應用程式要取得當時GPS定位位置,就會取得這個位置。
模擬器位置設定
Android_執行結果2
Android_執行結果3

佈署注意事項

iOS 執行結果

請在方案總管內,滑鼠右擊 XFDevInfo.iOS 專案,選擇 設定為起始專案,接著按下 F5 開始執行。
iOS_執行結果1
iOS_執行結果2

佈署注意事項

參考

沒有留言:

張貼留言