Xamarin.Mac/システム環境設定を開く

提供: MonoBook
ナビゲーションに移動 検索に移動

Xamarin.Macで作ったアプリから設定変更を促すためにMac OS Xシステム環境設定Windowsでいうコントロールパネル)を開きたい。

実装:Scripting Bridgeを利用する[編集 | ソースを編集]

以下のObjective-Cでの実装を見ながら試してみた。

システム環境設定を開くだけであれば簡単にできた。

using System;
using System.Drawing;
using MonoMac.Foundation;
using MonoMac.AppKit;
using MonoMac.ObjCRuntime;
using MonoMac.ScriptingBridge;

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

            var systemPrefs = SBApplication.FromBundleIdentifier(@"com.apple.systempreferences");
            systemPrefs.Activate();
        }
    }
}

さらに内側の値はValueForKeyメソッドを使えばNSObjectとして抜ける。 非常に煩雑だがこれを繰り返せば各種設定画面を開いたり設定値を抜いたりもできる。 マッピング用のクラスを作ればもっと楽になると思われる。

            var panes = systemPrefs.ValueForKey(new NSString("panes")) as SBElementArray;
            for (int i = 0; i < panes.Count; i++)
            {
                var pane = panes.GetItem<NSObject>(i);
                var id = pane.ValueForKey(new NSString("id")) as NSString;
                Console.WriteLine(id);
           }

動的なメソッド呼び出しはPerformSelectorメソッドで行える。Xamarin公式のScripting BridgeでFinderを制御しているサンプルを参考に実装したのでこれで正しいのかは知らん。[1]

        static void Main(string[] args)
        {
            NSApplication.Init();
            //NSApplication.Main(args);

            // システム環境設定
            var systemPrefs = SBApplication.FromBundleIdentifier(@"com.apple.systempreferences");
            //systemPrefs.Activate();

            var panes = systemPrefs.ValueForKey(new NSString("panes")) as SBElementArray;
            for (int i = 0; i < panes.Count; i++)
            {
                var pane = panes.GetItem<NSObject>(i);
                var id = pane.ValueForKey(new NSString("id")) as NSString;
                Console.WriteLine(id);

                // セキュリティとプライバシー
                if (id == "com.apple.preference.security")
                {
                    var anchors = pane.ValueForKey(new NSString("anchors")) as SBElementArray;
                    for (int j = 0; j < anchors.Count; j++)
                    {
                        var anchor = anchors.GetItem<NSObject>(j);
                        var name = anchor.ValueForKey(new NSString("name")) as NSString;
                        Console.WriteLine(name);

                        // アクセシビリティ
                        if (name == "Privacy_Accessibility")
                        {
                            anchor.PerformSelector(new Selector("reveal"));

                            // 表示
                            systemPrefs.Activate();
                        }
                    }
                }
            }
        }

実装:パネル直叩き[編集 | ソースを編集]

システム環境設定の各種設定画面(パネル)は「/System/Library/PreferencePanes/」以下に独立したアプリ(拡張子はappではなくprefPane)として存在しているので直叩きしてやる。 この方法は手軽だが、タブを切り替えたり、設定値を取れないなどの問題点も多々ある。 なおシステム環境設定の各種設定値はdefaultsコマンドで読み書きできるのが普通なのでそちらと組み合わせれば何とかなるかもしれない。

どちらにしろ非公式の値を決め打ち実装するのは危険なので非推奨である。

            NSWorkspace.SharedWorkspace.OpenUrl(NSUrl.FromFilename(@"/System/Library/PreferencePanes/Security.prefPane"));

関連項目[編集 | ソースを編集]

参考文献[編集 | ソースを編集]