.NET MAUIで人生初のMacデスクトップアプリを作ってみた

.NET MAUIの正式リリースから半年以上経った現時点での.NET MAUIの現在地の確認のために、一回最新の開発環境を整えて人生初のMac用のデスクトップアプリをC#でサクッと作ってみる

# 開発環境構築
まずマシンは最新のM2 MacBook Proなんて訳もなく、2019年製の余ってるMacBook Air 13inch
OSはBig Sur 11.2.1かあ、さすがは放置マシンですね
OSのバージョンアップ、Visual Studio for Mac 2022と順番に入れていきます
![ss1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/b4ca7c1a-1bc5-1349-694a-61c890371319.png)

Montereyはすっ飛ばして、Ventura(2022/10リリース)の最新版にあげます
![ss2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/b76d5b1d-c24e-fc01-4c76-5aa15bd221a4.png)

はい、入りました
ほんで、Visual Studio for Mac 2022を入れます、何は無くともMAUIは必須
![ss3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/4ea11679-2b00-8328-ac7e-fa80626653d8.png)

ほんで、Xcodeの更新も言われます、あるあるですね

![ss4.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/759df20e-2a24-34bd-cee0-3394574277b3.png)

でもXcodeのインストールって何処まで進んでるのかわからんし、時間滅茶苦茶かかります
なので、アクティビティモニタを横目で見つつのんびり待ちます、これリアルにMacの開発者の人ってどうしてんのやろ
どこまで進んでんのか不安のならんのかしらん？
![ss5.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/016b8b6d-9af0-f34a-bfbe-9e91126e5138.png)

# .NET MAUIでhello world
やっとここまで来た！
![ss6.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/a52aba71-27bd-8226-7536-f13d84adef51.png)

さて、MAUIでアプリ作っちゃうぞー
![ss7.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/cf3a277d-ce99-ed7e-e70e-e7b557e9d4af.png)
C#ってとこ気になるな

![ss8.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/3a0f5d10-931d-3765-3368-f9bcdfb532af.png)
C#しか選べやんのかー

![ss9.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/7a5f5e98-ab93-eeae-ca01-b56d97f4ff1d.png)

![ss10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/fac43b0d-1487-d51c-2e88-d0a270286e59.png)

おっと、テンプレート作っただけで何か怒られた、拒否する余地無いんでOKにする
![ss11.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/93d51933-aa90-fdfd-cb6a-a53eda40a5b9.png)

これをそのままビルドするだけでいとも容易く、Mac版、iOS版、Android版のHello worldが即座に動く
Xamarinの初期の不安定さとは全然違ってる、容易い！！！

macOS版
![ss12.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/eb9fb4c8-d2c1-7497-d2d8-34b0cd31c489.png)

Android版(エミュレータ)
![ss13.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/22b2ba4a-8e2c-f003-c0d0-8615d7c946c1.png)

iOS版(エミュレータ)
![ss14.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/1da1ba3c-fce3-d4b6-7b75-b2b5198e1aec.png)

# ここまでの感想
すごく簡単にマルチプラットフォームのアプリが作れるのは確認できた
LinuxのGUIアプリが正式に組み込まれるのかどうかはわからないけど、Linux版まで入ったらひとまず何でも作れる感じにはなるね

# MAUI の方言とか制限とか
Windowsで.NET Frameworkしか触ったことがない人がWindows8.0のWinRT APIに初めて触れたときの手探り感のような感覚は実際にあります
これはXamarinでスマホアプリを開発する時以上にデスクトップアプリを書きたい時に感じる不自由さです
すごく単純な例でいえば、ローカルファイルへのアクセスとか全然できないのでWindows Exploererみたいなファイラーを作るとかできません、個人的にはデスクトップアプリはツールとかばっかり作るのでMAUIでやる気にはならない感じ
私の主戦場はWindowsなので.NETでWPFって感じになります

# やれる範囲での実際の簡易アプリの実装例
突貫工事なので大したことやってません、ユーザーが画像ファイルを選ぶと画面に表示されるだけの超簡単なイメージビューワを作ってみました

```xml:MainPage.xaml
<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             x:Class="meetupapposaka7.MainPage">

    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="auto"/>
            <RowDefinition Height="*"/>

        </Grid.RowDefinitions>
        <Button
                x:Name="CounterBtn"
                Grid.Row="0"
                Text="ファイル選択"
                SemanticProperties.Hint="Counts the number of times you click"
                Clicked="OnCounterClicked"
                HorizontalOptions="Center" />
        <Image
            x:Name="image1"
                Grid.Row="1"
                HorizontalOptions="Center" />

    </Grid>
</ContentPage>
```

```csharp:MainPage.xaml.cs
namespace meetupapposaka7;

public partial class MainPage : ContentPage
{
	public MainPage()
	{
		InitializeComponent();
	}

	private async void OnCounterClicked(object sender, EventArgs e)
	{
        var imageFileTypes = new FilePickerFileType(new Dictionary<DevicePlatform, IEnumerable<string>>
                                                  {
                                                     { DevicePlatform.iOS, new[] { "jpg", "jpeg", "png" } },
                                                     { DevicePlatform.Android, new[] { "jpg", "jpeg", "png" } },
                                                     { DevicePlatform.WinUI, new[] { "jpg", "jpeg", "png" } },
                                                     { DevicePlatform.MacCatalyst, new[] { "jpg", "jpeg", "png" } },
                                                        });
        var options = new PickOptions
        {
            PickerTitle = "画像ファイルを選択してください",
            FileTypes = imageFileTypes,
        };


        var result = await FilePicker.Default.PickAsync(options);
        if (result != null)
        {
            image1.Source = ImageSource.FromFile(result.FullPath);
        }
    }
}
```

実行イメージはこんな感じ、こんなことやるだけでも変な挙動があって、実践投入するには慣れは必要って感じでした
![Videotogif (1).gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31737/7c391139-55f4-f18c-41ed-b3143a6d773a.gif)

以上です