📚

C#/Unityでファイルパスを取得する方法とその使い分け

2024/06/25に公開

概要

  • Unity/C#の拡張機能を使っていて、外部Shellファイルと連携するようなケースが考えられる
  • Unity内のAssets相対パスから拡張機能で関係ないパス等それぞれの使い分けを記載しておく

ファイルパスの取得方法とその特徴

CallerFilePathAttributeを使った方法

CallerFilePathAttribute を利用してコンパイル時に解釈される情報からファイルパスを得る。
ファイルパスだけではくファイル行番号やメソッド名も取得できる。

https://learn.microsoft.com/ja-jp/dotnet/api/system.runtime.compilerservices.callerfilepathattribute?view=netframework-4.8

// 自分自身のファイルパス
private static string GetSourceFilePath([CallerFilePath]string sourceFilePath = "") {
  return souceFilePath
}

利用ケースとしてはエディタ拡張としての外部ライブラリ連携がありそう。Unityとは関係ないライブラリやバイナリをUnity外から連携するケースを考える。その場合はプロジェクトごとに構成が変わってしまうので、ファイル間の相対パスでリソース間を参照するケースがありそう。

UnityのAssetDatabaseを使った方法

UnityのAssets以下にあるファイル(インポートされたファイル)であればUnityのAssetDatabaseに登録済みであるはず。Selectedでもいいですし参照でもいいのでUnityの仕組みを使って参照後にパスに変換ができる。

https://docs.unity3d.com/ja/2022.3/ScriptReference/AssetDatabase.html

private static string GetAssetPath()
{
    UnityEngine.Object selectedObject = Selection.activeObject;
    if (selectedObject != null)
    {
        var assetPath = AssetDatabase.GetAssetPath(selectedObject);
        var fullPath = System.IO.Path.GetFullPath(assetPath);
        return fullPath;
    }
    else
    {
        Debug.Log("No asset selected.");
    }
}

利用ケースとしてはUnity内に組み込んでいる機能や拡張機能であればこれで十分なケースが多いと思う。

アセンブリからパスを参照する

Unityでアセンブリ定義でアセンブリを分割できる。そこでアセンブリを指定してそこからパスを辿る方法がある。
https://docs.unity3d.com/ja/2022.3/Manual/ScriptCompilationAssemblyDefinitionFiles.html

public class AssemblyPathExample : MonoBehaviour
{
    void Start()
    {
        // 実行中のアセンブリを取得
        Assembly assembly = Assembly.GetExecutingAssembly();

        // アセンブリのファイルパスを取得
        string assemblyPath = assembly.Location;
    }
}

利用ケースとしてはあまり思いつかない。

Discussion