Associazioni Xamarin.Mac nelle app console

Esistono alcuni scenari in cui si vuole usare alcune API native di Apple in C# per creare un'applicazione headless, una che non ha un'interfaccia utente, usando C#.

I modelli di progetto per le applicazioni Mac includono una chiamata a NSApplication.Init() seguita da una chiamata a , in genere è simile al NSApplication.Main(args)seguente:

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

La chiamata per Init preparare il runtime Xamarin.Mac, la chiamata per Main(args) avviare il ciclo principale dell'applicazione Cocoa, che prepara l'applicazione a ricevere eventi di tastiera e mouse e visualizzare la finestra principale dell'applicazione. La chiamata a Main tenterà anche di individuare le risorse Cocoa, preparare una finestra di livello tople e prevede che il programma faccia parte di un bundle dell'applicazione (programmi distribuiti in una directory con l'estensione .app e un layout molto specifico).

Le applicazioni headless non necessitano di un'interfaccia utente e non devono essere eseguite come parte di un bundle di applicazioni.

Creazione dell'app console

È quindi preferibile iniziare con un normale tipo di progetto console .NET.

È necessario eseguire alcune operazioni:

  • Creare un progetto vuoto.
  • Fare riferimento alla libreria Xamarin.Mac.dll.
  • Portare la dipendenza non gestita nel progetto.

Questi passaggi sono illustrati in modo più dettagliato di seguito:

Creare un progetto console vuoto

Creare un nuovo progetto console .NET, assicurarsi che sia .NET e non .NET Core, perché Xamarin.Mac.dll non viene eseguito nel runtime di .NET Core, viene eseguito solo con il runtime mono.

Fare riferimento alla libreria Xamarin.Mac

Per compilare il codice, è necessario fare riferimento all'assembly Xamarin.Mac.dll da questa directory: /Library/Frameworks/Xamarin.Mac.framework/Versions/Current/lib/64bits/full

A tale scopo, passare ai riferimenti al progetto, selezionare la scheda Assembly .NET e fare clic sul pulsante Sfoglia per individuare il file nel file system. Passare al percorso precedente e quindi selezionare il Xamarin.Mac.dll da tale directory.

In questo modo sarà possibile accedere alle API Cocoa in fase di compilazione. A questo punto, è possibile aggiungere using AppKit all'inizio del file e chiamare il NSApplication.Init() metodo . Prima di poter eseguire l'applicazione, è necessario eseguire un solo passaggio.

Portare la libreria di supporto non gestita nel progetto

Prima dell'esecuzione dell'applicazione, è necessario inserire la Xamarin.Mac libreria di supporto nel progetto. A tale scopo, aggiungere un nuovo file al progetto (nelle opzioni del progetto selezionare Aggiungi e quindi Aggiungi file esistente) e passare a questa directory:

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

Selezionare il file libxammac.dylib. Verrà offerta una scelta di copia, collegamento o spostamento. Personalmente mi piace collegare, ma anche la copia funziona. È quindi necessario selezionare il file e nel riquadro delle proprietà (selezionare Visualizza proprietà riquadri>se il riquadro delle proprietà non è visibile), passare alla sezione Compilazione e impostare l'impostazione Copia nella directory di output su Copia se più recente.>

È ora possibile eseguire l'applicazione Xamarin.Mac.

Il risultato nella directory bin sarà simile al seguente:

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

Per eseguire questa app, saranno necessari tutti i file nella stessa directory.

Compilazione di un'applicazione autonoma per la distribuzione

È possibile distribuire un singolo eseguibile agli utenti. A tale scopo, è possibile usare lo mkbundle strumento per trasformare i vari file in un eseguibile autonomo.

Prima di tutto, assicurarsi che l'applicazione venga compilata ed eseguita. Dopo aver soddisfatto i risultati, è possibile eseguire il comando seguente dalla riga di comando:

$ 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]
$ _

Nella chiamata della riga di comando precedente, l'opzione -o viene usata per specificare l'output generato, in questo caso è stato passato /tmp/consoleapp. Questa è ora un'applicazione autonoma che è possibile distribuire e non ha dipendenze esterne da Mono o Xamarin.Mac, è un eseguibile completamente indipendente.

La riga di comando ha specificato manualmente il file machine.config da usare e un file di configurazione del mapping della libreria a livello di sistema. Non sono necessarie per tutte le applicazioni, ma è utile aggregarle, perché vengono usate quando si usano più funzionalità di .NET

Compilazioni senza progetto

Non è necessario un progetto completo per creare un'applicazione Xamarin.Mac autonoma, ma è anche possibile usare semplici makefile Unix per eseguire il processo. L'esempio seguente illustra come configurare un makefile per una semplice applicazione da riga di comando:

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

Il codice precedente Makefile fornisce tre destinazioni:

  • make compilerà il programma
  • make run compilerà ed eseguirà il programma nella directory corrente
  • make bundle creerà un eseguibile autonomo