コンソール アプリでの Xamarin.Mac バインド

C# で Apple ネイティブ API の一部を使用して、ヘッドレス アプリケーション (ユーザー インターフェイスを持たないアプリケーション) を C# を使用するシナリオがいくつかあります。

Mac アプリケーション用のプロジェクト テンプレートには、 への呼び出しと、 へのNSApplication.Init()NSApplication.Main(args)呼び出しが含まれます。通常は次のようになります。

static class MainClass {
    static void Main (string [] args)
    {
        NSApplication.Init ();
        NSApplication.Main (args);
    }
}

Init呼び出すと Xamarin.Mac ランタイムが準備されます。呼び出しMain(args)によって Cocoa アプリケーション メイン ループが開始されます。これにより、アプリケーションがキーボードとマウスのイベントを受信し、アプリケーションのメイン ウィンドウが表示されます。 の Main 呼び出しでは、Cocoa リソースの検索、トップレベル ウィンドウの準備も試みられ、プログラムはアプリケーション バンドル (拡張機能と非常に具体的なレイアウトを持つ .app ディレクトリに分散されたプログラム) の一部であることが想定されます。

ヘッドレス アプリケーションはユーザー インターフェイスを必要とせず、アプリケーション バンドルの一部として実行する必要もありません。

コンソール アプリの作成

そのため、通常の .NET コンソール プロジェクトの種類から開始することをお勧めします。

いくつかの操作を行う必要があります。

  • 空のオブジェクトを作成します。
  • Xamarin.Mac.dll ライブラリを参照します。
  • アンマネージド依存関係をプロジェクトに持ち込みます。

これらの手順については、以下で詳しく説明します。

空のコンソール プロジェクトを作成する

新しい .NET コンソール プロジェクトを作成し、.NET Core ではなく .NET であることを確認します。Xamarin.Mac.dllは .NET Core ランタイムでは実行されず、Mono ランタイムでのみ実行されます。

Xamarin.Mac ライブラリを参照する

コードをコンパイルするには、次のディレクトリからアセンブリを Xamarin.Mac.dll 参照します。 /Library/Frameworks/Xamarin.Mac.framework/Versions/Current/lib/64bits/full

これを行うには、プロジェクト参照に移動し、[ .NET アセンブリ ] タブを選択し、[ 参照 ] ボタンをクリックしてファイル システム上のファイルを見つけます。 上記のパスに移動し、そのディレクトリから Xamarin.Mac.dll を選択します。

これにより、コンパイル時に Cocoa API にアクセスできるようになります。 この時点で、ファイルの先頭に を追加 using AppKit し、 メソッドを NSApplication.Init() 呼び出すことができます。 アプリケーションを実行するには、もう 1 つの手順しかありません。

アンマネージド サポート ライブラリをプロジェクトに取り込む

アプリケーションを実行する前に、サポート ライブラリを Xamarin.Mac プロジェクトに取り込む必要があります。 これを行うには、プロジェクトに新しいファイルを追加し (プロジェクト オプションで[ 追加]、[ 既存のファイルの追加] の順に選択)、次のディレクトリに移動します。

/Library/Frameworks/Xamarin.Mac.framework/Versions/Current/SDKs/Xamarin.macOS.sdk/lib

ここで、 libxammac.dylib ファイルを選択します。 コピー、リンク、または移動の選択肢が提供されます。 私は個人的にリンクするのが好きですが、コピーも同様に機能します。 次に、ファイルを選択し、プロパティ パッド (プロパティ パッドが表示されていない場合は [パッド>のプロパティの表示>] を選択) で[ビルド] セクションに移動し、[出力ディレクトリにコピー] 設定を [新しい場合はコピー] に設定します。

Xamarin.Mac アプリケーションを実行できるようになりました。

bin ディレクトリの結果は次のようになります。

Xamarin.Mac.dll
Xamarin.Mac.pdb
consoleapp.exe
consoleapp.pdb
libxammac.dylib

このアプリを実行するには、同じディレクトリ内のすべてのファイルが必要です。

配布用のスタンドアロン アプリケーションの構築

1 つの実行可能ファイルをユーザーに配布したい場合があります。 これを行うには、ツールを mkbundle 使用して、さまざまなファイルを自己完結型の実行可能ファイルに変換できます。

まず、アプリケーションがコンパイルされて実行されていることを確認します。 結果に問題がなければ、コマンド ラインから次のコマンドを実行できます。

$ mkbundle --simple -o /tmp/consoleapp consoleapp.exe --library libxammac.dylib --config /Library/Frameworks/Mono.framework/Versions/Current/etc/mono/config --machine-config /Library/Frameworks/Mono.framework/Versions/Current/etc/mono/4.5/machine.config
[Output from the bundling tool]
$ _

上記のコマンド ライン呼び出しでは、 オプション -o を使用して生成された出力を指定します。この場合は、 を渡しました /tmp/consoleapp。 これは現在、配布できるスタンドアロン アプリケーションであり、Mono または Xamarin.Mac に対する外部依存関係がなく、完全に自己完結型の実行可能ファイルです。

コマンド ラインは、使用する machine.config ファイルとシステム全体のライブラリ マッピング構成ファイルを手動で指定しました。 すべてのアプリケーションに必要なわけではありませんが、.NET のより多くの機能を使用する場合に使用されるため、バンドルすると便利です。

プロジェクトのないビルド

自己完結型の Xamarin.Mac アプリケーションを作成するために完全なプロジェクトは必要ありません。また、単純な Unix メイクファイルを使用してジョブを完了することもできます。 次の例は、単純なコマンド ライン アプリケーション用にメイクファイルを設定する方法を示しています。

XAMMAC_PATH=/Library/Frameworks/Xamarin.Mac.framework/Versions/Current/lib/x86_64/full/
DYLD=/Library/Frameworks/Xamarin.Mac.framework/Versions/Current/lib
MONODIR=/Library/Frameworks/Mono.framework/Versions/Current/etc/mono

all: consoleapp.exe

consoelapp.exe: consoleapp.cs Makefile
    mcs -g -r:$(XAMMAC_PATH)/Xamarin.Mac.dll consoleapp.cs
    
run: consoleapp.exe
    MONO_PATH=$(XAMMAC_PATH) DYLD_LIBRARY_PATH=$(DYLD) mono --debug consoleapp.exe $(COMMAND)

bundle: consoleapp.exe
    mkbundle --simple consoleapp.exe -o ncsharp -L $(XAMMAC_PATH) --library $(DYLD)/libxammac.dylib --config $(MONODIR)/config --machine-config $(MONODIR)/4.5/machine.config

上記 Makefile では、次の 3 つのターゲットが提供されます。

  • make はプログラムをビルドします
  • make run は、現在のディレクトリでプログラムをビルドして実行します
  • make bundle は自己完結型実行可能ファイルを作成します