SIN@SAPPOROWORKSの覚書

C#を中心に、夜な夜な試行錯誤したコードの記録です。

Xamarin.Formsでプラットフォームごとの微調整を行うには?

【 Xamarin 記事一覧 】

BuildInsiderで連載されている「Xamarin逆引きTips」に寄稿させて頂きました。

Xamarin.Formsでプラットフォームごとの微調整を行うには? - Build Insider

使用したコードは、下記にあります。


github.com


【 Xamarin 記事一覧 】

Xamarin.Forms PCLでのファイルIO ( PCL Storageを使用する )

【 Xamarin 記事一覧 】

1. PCL Storage

Xamarin.FormsのPCLでファイルのIOを書こうとしたとき、System.IOに File や Directory が無くて固まった経験はないでしょうか?
もともと、ファイルの扱いはプラットフォーム固有なので、当然といえば当然なのですが・・・

しかし、Xamarin.iOSやXamarni.Androidでは、ちゃんと、System.IO.FileやSystem.IO.Directoryが使えるので、それをラッパーすればいいだけです。
フォルダのパスがプラットフォーム固有になるので、そこだけ気を付ければいいって事でしょうか。


と言いながら、いろいろ検索していると、コンポーネントストアに「PCL Storage」なるものを見つけました。
f:id:furuya02:20150506131241p:plain:w350:left
f:id:furuya02:20150506131254p:plain:w350:left


2. インストール

同プログラムは、CodePlexGithubでコードも公開されています。
また、NuGetでのインストールも可能です。

f:id:furuya02:20150506131307p:plain:w350
コンソールでも可能ですが、今回は、「NnuGetパッケージの管理」から行いました。
※実は、ComponentsというフォルダがiOSAndroidのプロジェクトにしかなく、PCLプロジェクトが無かったので、右クリックでの導入要領が分かりませんでした・・・

f:id:furuya02:20150506131324p:plain
全プロジェクトにインストールされます。
f:id:furuya02:20150506131331p:plain

3. 動作確認

次のようなサンプルを書いて、動作確認してみました。
EntryコントロールとButtonコントロールを配置し、ボタンを押すと、Entryコントロールの内容をファイルに書き込むものです。

//App.cs
using PCLStorage;
using Xamarin.Forms;
namespace PCLStorageSample {
    public class App : Application {
        public App() {
            MainPage = new MyPage();
        }
    }

    internal class MyPage : ContentPage {
        public MyPage() {
            var entry = new Entry();
            var button = new Button() {
                Text = "OK",
                Command = new Command(async () => {
                    // ルートフォルダの取得
                    var folder = FileSystem.Current.LocalStorage;

                    // フォルダの作成
                    var subFolder = await folder.CreateFolderAsync("SubFolder", CreationCollisionOption.OpenIfExists);

                    // フォルダの作成
                    var file = await subFolder.CreateFileAsync("Text.txt", CreationCollisionOption.ReplaceExisting);

                    // Entryコントロール尾内容をの書き込む
                    await file.WriteAllTextAsync(entry.Text);
                    
                    // ファイルの内容を読み込む
                    var str = await file.ReadAllTextAsync();
                    str = "";
                })
            };
            Content = new StackLayout{
                Padding = new Thickness(0,Device.OnPlatform(20,0,0),0,0),
                Children = {
                    entry,button
                }
            };
        }
    }
}

(1) iOS

上記のコードを実行すると、下記のような画面になります。
f:id:furuya02:20150506131342p:plain:w200
Entryコントロールに「test-message」と入力して、OKボタンを押し、ファイルのIOを行ったところでブレークポイントで止めて、内容を確認してみました。
f:id:furuya02:20150506131351p:plain
ファイルから読み込んだ内容が、書き込んだものと同じになっているのが、確認できます。
また、この時の、各オブジェクトの状況は次のようになっています。
f:id:furuya02:20150506131356p:plain
PCLStorage.IFolder folder のパスは、「/User/username/Library/developer/CoreSimulator/Data/Application/A3297...C370/Document/..Library」となっており、そのサブフォルダ「SubFolder」とその中の
ファイル「Text.txt」が見て取れます。

※これは、シュミレータでの動作ですが、実機では「/var/mobile/Containers/Data/Application/53B38A17-AC94-49C9-A3E7-21A2B08F5706/Documents/../Library」のようになっています。

(2) Android

Androidでは、次のようになります。
f:id:furuya02:20150506131402p:plain:w200
Entryコントロールに「test-android」と入力して、iOSと同じ要領で確認してみました。
f:id:furuya02:20150506131410p:plain

今度は、PCLStorage.IFolder folder のパスが「/data/data/PCLStorageSample.Droid/files」となっているのが確認できます。

(3) WindowsPhone

最後に、WindowsPhoneです。
f:id:furuya02:20150506131435p:plain:w200
こちらの、PCLStorage.IFolder folder は、「/data/data/PCLStorageSample.Droid/files」です。
f:id:furuya02:20150506131420p:plain

4. ルートフォルダ

念のため、各プラットフォームごとのルートフォルダの取得について、Githubからコードを確認しておきます。
https://github.com/dsplaisted/PCLStorage/blob/master/src/PCLStorage.FileSystem.Desktop/DesktopFileSystem.cs

public IFolder LocalStorage{
            get{
                //  SpecialFolder.LocalApplicationData is not app-specific, so use the Windows Forms API to get the app data path
                //var localAppData = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData);
#if ANDROID
                var localAppData = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments);
#elif IOS
                var documents = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments);
                var localAppData = Path.Combine(documents, "..", "Library");
#else
                var localAppData = System.Windows.Forms.Application.LocalUserAppDataPath;
#endif
                return new FileSystemFolder(localAppData);
            }
        }

コードを確認すると、AndroidiOS、WindowsPhoneについては、ルートフォルダの取得以外やパスの扱いいがは、ほとんど共通のようです。
しかし、何と言っても、パッケージインストールだけで簡単に使えてしまう魅力は捨てがたいです。




【 Xamarin 記事一覧 】

BlackJumboDogの設定画面などは、メモ帳で変更できるようになりました

大阪弁バージョン

最新バージョンのBlackJumboDogでは、設定画面などに表示される文字を、メモ帳で変更できるようになりました。blackjumbodog.codeplex.com

本来の目的は、多言語対応なのですが、文字定義を外部(テキスト)ファイルにしたことで、大阪弁バージョンなども簡単に作れてしまいます。

f:id:furuya02:20150505055302p:plain

言語設定ファイル

BlackJumboDogがインストールされたフォルダにある、「BJD.Lang.txt」を修正します。

f:id:furuya02:20150505055558p:plain

テキストファイルの形式は、「識別タグ」タブ「日本語用」タブ「英語用」です。

f:id:furuya02:20150505055603p:plain


例外

修正を誤ると、起動時に「例外」が発生します。

f:id:furuya02:20150505055809p:plain
上記の例外は、カテゴリ「OptionFtp」の識別タブ「bannerMessage」の行に誤りがあることがわかります。

#Page1(基本設定)
OptionFtp_bannerMessage	「いらっしゃい」のメッセージ	Banner message

上記の行を確認してみてください。


修正する場合は、念のため最初の状態の「BJD.Lang.txt」を残しておいてください。
上書きしてBlackJumboDogを再起動するれば、元に戻ります。

自由なバージョンのXamarin.iOSを Visual Studio と ビルドホスト(Mac)にセットアップする

【 Xamarin 記事一覧 】

1. 色々嵌るBuild Hostとの連携

Visual Studio でXamarinを使用していると、ビルド・ホスト(Mac)との連携で、いろいろ手間取ることがあります。そして、その原因の一つとして、Xamarin.iOSのバージョンの不整合があります。

Xamarin.VisualStudioのバージョンアップなどを行うと、Xamarin.iOSとXamarni.Androidの(その時点での)最新版のが一緒にインストールされます。

しかし、ビルドホスト(Mac)側のバージョンアップが同期しているわけではないので、この問題が発生するのです。

[バージョンが不整合などでビルドホストと連携できていないときのエラー]

警告	1	Connection to Xamarin.iOS Build Host failed. Double click here to attempt to reconnect/select a server.		0	0	

今回は、Windows側のXamarin.iOSMac側のXamarin.iOSのバージョンを正確に一致させる手順をまとめてみました。
なお、この方法を使用すれば、過去のバージョンに戻すことも可能ですので、いざという時の回避に応用可能だと思います。


2. バージョンの確認

最初に、現在のバージョンを確認する方法です。

(1) Macs

Mac側で動作しているXamarin.iOSのバージョンは、XamarinStudioで確認できます。
メニューから「Xamarin Studio About」を選択して表示されたダイアログで「Show Detail」(詳細を表示)ボタンを押します。
f:id:furuya02:20150504123021p:plain:w300:leftf:id:furuya02:20150504123026p:plain:w300:left

(2) Windows

Windowsでは、Visual Studioで確認します。
メニューから「ヘルプ」-「Microsoft Visual Studioのバージョン情報」と辿って表示されたダイアログの「インストールされている製品」の中で、ちょっと下のほうにスクロールすると確認できます。
f:id:furuya02:20150504124928p:plain


3. 任意のバージョンのダウンロード

過去のバージョンは、下記のページでダウンロードが可能です。(最近の数件のみ)
https://store.xamarin.com/account/my/subscription/downloads
ページ内で、青い大きいボタンの下の「View All Versions」を選択すると、下に選択ボタンが増えます。
f:id:furuya02:20150504123033p:plain
Mac用のXamarin.iOSが必要な時は、青線で示したボタンを選択し、Windows用のものが必要な時は、赤線で示したところを選択します。
Mac用は、Xamarin.iOS単体ですが、Windows用は、Xamarin.VisualStudioに含まれるものなので、Androidのところを選択しても同じです。
f:id:furuya02:20150504123114p:plain

(1) OS X

OS X 用の方をプルダウンした様子です。
f:id:furuya02:20150504123045p:plain
ダウンロードした後は、実行「インストール」するだけです。
f:id:furuya02:20150504123059p:plain

インストール後、Mac本体の再起動が必要です。

(2) Windows

Windows用の方をプルダウンした様子です。
f:id:furuya02:20150504123054p:plain
こちらも、ダウンロード後はダブルクリックでインストールします。
f:id:furuya02:20150504123131p:plain

インストール後、VisualStudioの再起動が必要です。

Windows用の選択で表示されているバージョン番号は、Xamarin.iOSのものではなくXamarin.VisualStudioのバージョンなので、日付あたりでOS X のものと比較するしかないでしょう。
f:id:furuya02:20150504123108p:plain
Xamarin.iOSについては、赤枠、青枠がそれぞれ、同じバージョンだと思います。

4. シンクロ

念のため、Visual Studio とビルドホスト(Mac)の間でシンクロするために介在しているプログラムを列挙しておきます。

(1) Bonjour Service

Windows側では、サービスでBonjour Serviceが起動しています。
タスクマネージャの「サービス」タブで確認できます。
f:id:furuya02:20150504123141p:plain

(2) Xamarin.iOS Build Host

Mac側で起動されているのは、Xamarin.iOS Build Hostです。
f:id:furuya02:20150504123149p:plain
「Unpair」-「Pair」でPINコードを更新すると、VisualStudio側でも変更が必要になります。
※PINは、コネクト開始時だけ必要なようなので、次にプロジェクトを開きなおしたりするときに、PIN入力の催促が表示されます)
f:id:furuya02:20150504123157p:plain

どうしても、うまく連携できないときは、これらのサービスを再起動してみるのも、ありかも知れません。


【 Xamarin 記事一覧 】

Visual Studio 2015 対応の特別バージョンのインストーラーが無い(T^T)

【 Xamarin 記事一覧 】

この記事は、2015年5月2日に書かれたものです。インストーラーの問題は、近いうちに修正されるでしょう。

1. Visual Studio 2015 RC へのインストール失敗

Build 2015 でアナウンスされた、Windows10の最新ビルド(Insider Preview 10074)とVisual Studio 2015 RC をインストールしてみました。

しかし、Xamarinのセットアップが、ちょっとうまく行かなかったので、記録しておきます。

初めてiOSAndroidのプロジェクトを作成しようとすると、Xamarinのインストーラのダウンロードへ誘導され、それを実行するとXamarinのインストールが完了する・・・というのが、本来の手順のはずですが・・・

f:id:furuya02:20150502003431p:plain:w350:left
f:id:furuya02:20150502003437p:plain:w350:left

この手順では、Visual Studio 2015 では、利用できるようになりませんでした。
よくみると、ダウンロードされているのは、普通のXamarinインストーラーであり、以前の落ちてきていた特別バージョン( XamarinInstaller-VS2015.exe)ではありませんでした。
f:id:furuya02:20150502003501p:plain


2. 修復

この問題は、以下の手順で修復できます。

「プログラムと機能」で「Xamarin」を選択して「変更」を押します。
f:id:furuya02:20150502003509p:plain
表示されたダイアログで「Change」を選択します。
f:id:furuya02:20150502003514p:plain
表示された「CustomSetup」で「Xamarin for Visual Studi 2015」が×になっているので
f:id:furuya02:20150502003519p:plain
「Will be installed on local hard drive」に変更して「Next」を押します。
f:id:furuya02:20150502003523p:plain
これで、2015へのセットアップは完了です。
f:id:furuya02:20150502003527p:plain
プロジェクトのテンプレートにも「Mobile Apps」が追加されています。
f:id:furuya02:20150502003532p:plain


【 Xamarin 記事一覧 】

Xamarin.Forms Mobile AppでToDoアプリを作成する(その1)

【 Xamarin 記事一覧 】

1. モバイルサービスからMobile Appsへ

f:id:furuya02:20150425084643p:plain:w200:leftf:id:furuya02:20150425084642p:plain:w200:leftMicrosoft Azureの新ポータル(2015年4月28日時点でPREVIEW版)では、従来の「モバイルサービス」が「Mobile Apps」となっています。

今回は、ちょっと気が早い?かも知れませんが・・・
新ポータルの綺麗な画面に誘われて、Xamarin.Formsで使ってみました。

現(PREVIEW)時点で・・・
・「モバイルサービス」で作成したものは、Mobile Appsから見えません・・・
・「モバイルサービス」では、サーバ側の処理をnodejsと.NETの2種類から選択できましたが、「Mobile Apps」では、.NETのみです。
・一応、モバイルサービスも残るみたいです。
「Mobile Services continue to be available as a standalone service and remain fully supported.」
http://azure.microsoft.com/en-us/documentation/articles/app-service-changes-existing-services/


2. Mobile Appの作成

以下、Mobile Appを作成する手順です。
(1)新ポータルでは、すべてのサービスは左下の(+新規)から行います。
f:id:furuya02:20150425084702p:plain:w450
(2)展開したウインドウから「Web + Mobile」>「Mobile App」と選択し「Name」の所にサービス名(ここでは「AzureToDoSample」とした)を入力します。
f:id:furuya02:20150425084716p:plain:w450
(3)続いてデータベースの設定を行います。
「PACKAGE SETTING」>「USERDATABASE」>「新しいデータベースの作成」を選択します。
ここで、「新しいデータベースの作成」ではなく「既存のデータベースの使用」を選択した場合、この先のDB関連の指定は必要なくなります。
f:id:furuya02:20150425084752p:plain:w450
(4)「名前」の所にデータベースの名前を入力し、「サーバー名」「サーバ管理者ログイン」「パスワード」を入力して「OK」「OK」で閉じていきます。
f:id:furuya02:20150425084802p:plain:w450
(5)設定が終わったら「作成」ボタンを押します。
f:id:furuya02:20150425084814p:plain:w450
(6)作成中の表示が出ますので、しばらく待ちます。(1分ぐらい?)
f:id:furuya02:20150425084822p:plain:w450
(7)出来上がると、作成したサービスを設定する画面になります。
ここで、「Add Client」を選択します。
f:id:furuya02:20150425084831p:plain:w450
(8)「Xamarin.Android」を選択し、「CREATE A NEW APP」で「DOWNLOAD」を押してひな形となるテンプレートをダウンロードします。
実は、Xamarin.Formsでプログラムを書く場合、テンプレートから使用するのは、サーバ側のMVCプロジェクトだけなので、「Windows(C#)」でも「Xamarin.iOS」でも、何をダウンロードしても関係ありませんw
f:id:furuya02:20150425084842p:plain:w450
(9)ダウンロードした、テンプレートは次のようになっています。
f:id:furuya02:20150425084853p:plain

3. Xamarin.Formsプロジェクトの作成

(1)VisualStudioで開いてみると、Xamarin.Android用のプロジェクト「AzureToDoSample」と、サーバ側のMVCプロジェクト「AzureToDoSampleService」の2つが含まれているのを確認することができます。
f:id:furuya02:20150425084908p:plain
(2)Xamarin.Android用のプロジェクトは要らないので、ばっさり削除します。
※実はXamarin.Android用のコードは、Xamarin.Formsでも利用可能なものが多いので、適当にフォルダ名を変えて置いておくと、色々吉です。
f:id:furuya02:20150425084913p:plain:w450
(3)続いて、このソリューションにXamarinFormsのプロジェクトを追加します。
ここでは、プロジェクト名を「AzureToDoSample」としました。
f:id:furuya02:20150425084924p:plain:w450
(4)プロジェクトの追加後、ソリューションに5つのプロジェクトが確認できます。(追加されたのは4つ)
AzureToDoSample(移植可能) : クラアントPCLプロジェクト
AzureToDoSample.Droid :Androidクラアントプロジェクト
AzureToDoSample.iOS :iOSクラアントプロジェクト
AzureToDoSample.WinPhone :WindowsPhone クラアントプロジェクト
AzureToDoSampleService :サーバ用MVCプロジェクト(これは、削除しないで残ったテンプレートのプロジェクト)
f:id:furuya02:20150425084932p:plain:w450

4. サーバ側MVCプロジェクトのコンパイルと登録

当初、サーバ側の構築を行います。
(1)コンパイルの後、ソリューションエクスプローラMVCプロジェクト「AzureToDoSampleService」を右クリックして「登録」を選択します。
f:id:furuya02:20150425085002p:plain:w450
(2)「Microsoft Azure Websites」を選択します。
f:id:furuya02:20150425085012p:plain:w450
(3)「既存のWebサイト」で、作成したサービスが選択できます。
サーバから検索するためには、Microsoftアカウントにサイインしている必要があります。
f:id:furuya02:20150425085020p:plain:w450
(4)「サーバー」「ユーザ名」「パスワード」など、全てがインポートされるので「発行」ボタンを押すだけです。
f:id:furuya02:20150425085027p:plain:w450


すいません、まだXamarin.Forms書いてませんが・・・
つづく・・・

5. 参考にさせて頂いたページ

Azure Mobile Apps と Mobile Services の違いについて - nnasakiのブログ
Azure App Service | ブチザッキ



【 Xamarin 記事一覧 】