0

スクリプトと同じフォルダーからいくつかの画像を使用する必要があるスクリプトを準備しています。画像は WinForms GUI に表示されます。

$imgred = [System.Drawing.Image]::FromFile("red.png")

クリックするだけでフォルダーから ps1 スクリプトを手動で実行すると、画像が読み込まれて表示されます。残念ながら、これをどのようにセットアップしたか正確には覚えていませんが、できる限り、ps1 ファイルに使用するデフォルトのプログラムにすぎませんでした。cmd ファイルからスクリプトを実行すると (cmd ウィンドウを非表示にするため)、スクリプトも読み込まれます。

しかし、Powershell IDE で開いて実行すると、エラーが発生し、GUI にアイコンが表示されません。Powershell で開くと、読み込みにも失敗します。

私が見つけることができるこれらの実行モードの唯一の違いは次のとおりです。

$scriptPath = split-path -parent $MyInvocation.MyCommand.Definition
$scriptPath             #always same, the location of script
(Get-Location).Path     #scriptlocation when icons loaded, system32 folder when unsuccessful load

cd $scriptPath を実行するときと同じ動作であるため、現在のフォルダーが問題のあるフォルダーではない可能性が高くなります。

各ファイル読み取り行 (FromFile) に $scriptPath/red.png を記述できることはわかっていますが、それを 1 回 (FromFile のデフォルトの場所) 定義してから、実行方法に関係なく単純なファイル名を機能させることが必要です。 .

デフォルトのファイル読み取りパスがスクリプトの場所と同じになるようにするには、何を変更すればよいですか?

4

1 に答える 1

2

PowerShell ( $PWD) で既定の場所のスタックを変更しても、ホスト アプリケーションの作業ディレクトリには影響しません。

これを実際に見るには:

PS C:\Users\Mathias> $PWD.Path
C:\Users\Mathias
PS C:\Users\Mathias> [System.IO.Directory]::GetCurrentDirectory()
C:\Users\Mathias

今すぐ場所を変更してください:

PS C:\Users\Mathias> cd C:\
PS C:\> $PWD.Path
C:\
PS C:\> [System.IO.Directory]::GetCurrentDirectory()
C:\Users\Mathias

のように、ファイル パス引数を取る .NET メソッドを呼び出すとImage.FromFile()、パスは ではなく後者を基準にして解決され$PWDます。

に相対するファイル パスを渡したい場合は、次の$PWDようにします。

$pngPath = Join-Path $PWD "red.png"
[System.Drawing.Image]::FromFile($pngPath)

また

[System.Drawing.Image]::FromFile("$PWD\red.png")

実行中のスクリプトへの相対パスが必要な場合、PowerShell 3.0 以降では$PSScriptRoot自動変数を使用できます。

$pngPath = Join-Path $PSScriptRoot "red.png"    

v2.0 もサポートする必要がある場合は、スクリプトの先頭に次のようなものを追加できます。

if(-not(Get-Variable -Name PSScriptRoot)){
  $PSScriptRoot = Split-Path $MyInvocation.MyCommand.Definition -Parent 
}

インタラクティブ モードで PowerShell を使用する場合、次のように "フォローする" ように関数を構成できます。prompt.NET

$function:prompt = {
    if($ExecutionContext.SessionState.Drive.Current.Provider.Name -eq "FileSystem"){
        [System.IO.Directory]::SetCurrentDirectory($PWD.Path)
    }
    "PS $($executionContext.SessionState.Path.CurrentLocation)$('>' * ($nestedPromptLevel + 1)) ";
}

代わりに、完全修飾パスを提供する習慣を身につけることをお勧めします。

于 2017-01-04T08:09:23.767 に答える