web-dev-qa-db-ja.com

コンソール出力を直接メモ帳にパイプするにはどうすればよいですか?

コマンドプロンプトまたは Git シェルでアプリケーションを実行していますが、後で簡単に確認および編集できるように、出力をメモ帳に取得したいと考えています。

次のことを試しましたが、常にメモ帳の空のインスタンスが表示されます。

diff file1.txt file2.txt | notepad

出力を別のファイルにリダイレクトし、そのファイルをメモ帳で開くことができることを知っています。 Windows以外のシステムでは Vim 以下へのパイプ処理に慣れているだけなので、追加の手順は避けたいです。

48
Der Hochstapler

私が言うことができることから、直接メモ帳にパイプする方法はありません。

ただし、次のように、メモ帳でclipにパイプしてからpasteにパイプできます。

 diff file1.txt file2.txt | clip && notepad

次に押すだけ Ctrl+V メモ帳で。

64
Der Hochstapler

Vim の使用を検討してください。グラフィカル環境が必要な場合は、gVimを使用してください。

次に、単一のハイフンを引数としてパイプを使用して、Vim/gVimに標準入力から読み取るように指示できます。

diff file1.txt file2.txt | gvim -
32

ここ はそれを正しく行う(クリップボードを壊さない)短いWindowsプログラムです。それはPowerShellに適応できるはずです。時間があれば、この答えを更新するかもしれませんが、そのプログラムを直接使用することもできます。

さて、PowerShellはどうですか?別のアプリケーションをインストールする必要はありません。残念ながら、あなたPATH...のどこかにスクリプトファイルを作成する必要があります.

使用できるショートバージョン

次の内容のバッチファイル(例:ShowInNotepad.bat)を作成し、それをPATHのどこかに配置すると、

@echo off
clip
powershell -Command $process = Start-Process -PassThru notepad;$SW_SHOW = 5;$sig = '[DllImport("""user32.dll""")] public static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);';Add-Type -MemberDefinition $sig -name NativeMethods -namespace Win32;[Win32.NativeMethods]::ShowWindow($process.Id, $SW_SHOW) ^| Out-Null;Add-Type -AssemblyName System.Windows.Forms;[System.Windows.Forms.SendKeys]::SendWait('^^V');

その後、どこからでもecho blah | ShowInNotepadを呼び出すことができます。

これはが実行することに注意してくださいWindowsの最近のバージョン(Vista +)を使用していて、PowerShellを無効にしていないか、.NET Frameworkをアンインストールしていないことを前提としています。つまり、デフォルトのWindowsインストールが機能します。


長い説明と代替案

私が考えることができる最も簡単な方法は、貼り付けを自動化することです(Ctrl+V)アクション。少なくとももう1つの回答が既に行われていますが、AHKを使用しています。ロックダウンされた企業環境でPowerShellを機能させることができれば幸いです。

ええと、スクリプトを続けましょう。

#start notepad, get process object (to get pid later)
$process = Start-Process -PassThru notepad;

# activate Notepad window
# based on http://stackoverflow.com/a/4994020/1030702
# SW_SHOW activates and shows a window http://msdn.Microsoft.com/en-us/library/windows/desktop/ms633548%28v=vs.85%29.aspx
$SW_SHOW = 5;
$sig = '[DllImport("user32.dll")] public static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);';
Add-Type -MemberDefinition $sig -name NativeMethods -namespace Win32;
[Win32.NativeMethods]::ShowWindow($process.Id, $SW_SHOW) | Out-Null;

# send a "Ctrl+V" keystroke to the active window
# from http://stackoverflow.com/a/17851491/1030702
Add-Type -AssemblyName System.Windows.Forms;
[System.Windows.Forms.SendKeys]::SendWait('^V');

これは非常に簡単なので、コメントの説明以上にスクリプトを説明する必要はありません。

使用法

これを使用するには、スクリプトを.ps1ファイル(例:ShowInNotepad.ps1)に配置し、PATHのどこかに配置して、表示するテキストを配置した後でpowershell ShowInNotepad.ps1を呼び出すだけです。クリップボードに。

例:

echo blah | clip && powershell ShowInNotepad.ps1

残念ながら、PowerShellスクリプトの実行はときどき難しい場合があります(実行ポリシーなど)。したがって、このスクリプトを、コマンドプロンプトから直接呼び出すことができるワンライナーに圧縮したか、バッチファイルに配置することもできます。

powershell -Command $process = Start-Process -PassThru notepad;$SW_SHOW = 5;$sig = '[DllImport("""user32.dll""")] public static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);';Add-Type -MemberDefinition $sig -name NativeMethods -namespace Win32;[Win32.NativeMethods]::ShowWindow($process.Id, $SW_SHOW) ^| Out-Null;Add-Type -AssemblyName System.Windows.Forms;[System.Windows.Forms.SendKeys]::SendWait('^^V');

次の内容のバッチファイル(例:ShowInNotepad.bat)を作成し、それをPATHのどこかに配置すると、

@echo off
clip
powershell -Command $process = Start-Process -PassThru notepad;$SW_SHOW = 5;$sig = '[DllImport("""user32.dll""")] public static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);';Add-Type -MemberDefinition $sig -name NativeMethods -namespace Win32;[Win32.NativeMethods]::ShowWindow($process.Id, $SW_SHOW) ^| Out-Null;Add-Type -AssemblyName System.Windows.Forms;[System.Windows.Forms.SendKeys]::SendWait('^^V');

その後、どこからでもecho blah | ShowInNotepadを呼び出すことができます。

8
Bob

AutoHotkey を使用するのはどうですか?

以下をstdin.ahkとして保存し、AutoHotkeyディレクトリに配置します。

StdIn(max_chars=0xfff)
{
    static hStdIn=-1
    ; The following is for Vanilla compatibility
    ptrtype := (A_PtrSize = 8) ? "ptr" : "uint"

    if (hStdIn = -1)
    {
        hStdIn := DllCall("GetStdHandle", "UInt", -10,  ptrtype) ; -10=STD_INPUT_HANDLE
        if ErrorLevel
            return 0
    }

    max_chars := VarSetCapacity(text, max_chars*(!!A_IsUnicode+1), 0)

    ret := DllCall("ReadFile"
        ,  ptrtype, hStdIn        ; hFile
        ,  "Str", text          ; lpBuffer
        , "UInt", max_chars*(!!A_IsUnicode+1)     ; nNumberOfBytesToRead
        , "UInt*", bytesRead    ; lpNumberOfBytesRead
        ,  ptrtype, 0)            ; lpOverlapped

    return text
}

loop 
{
    sleep 100 ;wait for data
    Buffer:=StdIn()
    PipeText:=PipeText . Buffer
    IfWinActive Untitled - Notepad
        {
        SendInput {Raw}%PipeText%
        PipeText = 
        }
}

次に、コマンドライン:

ping -t www.google.com | AutoHotkeyA32.exe stdin.ahk

ウィンドウが開いていてUntitled - Notepadというタイトルが付けられている限り、コマンドの出力をメモ帳にパイプします。ウィンドウがアクティブでない場合、ウィンドウがアクティブになるまでバックグラウンドでバッファリングされます。別のプログラムに移動することもでき、バッファリングが再度実行されます。

私たちの標準入力に出力するプログラムが死ぬと、これは死ぬようです...

(詳細については、stdin()コードは here から恥ずかしがらずに半分インチ調整されました)

5
Mokubai

これは完全に可能です。試してみたところです。メモ帳がデフォルトでtxtファイルを開くように設定されていると想定しています。

diff file1.txt file2.txt > output.txt && start output.txt && timeout /T 3 && del output.txt

はい、技術的にファイルを作成していますが、保存されません。

さらに配管することもオプションです。

4
Casey

これは醜いですが、これを達成する効果的な方法です:

$OutputString = 'Hello World'
$WScript = New-Object -ComObject 'wscript.Shell'
$WScript.Run('notepad.exe') | Out-Null
do 
    {
    Start-Sleep -Milliseconds 100
    }
until ($WScript.AppActivate('notepad'))
$WScript.SendKeys($OutputString)

テキスト出力のみを送信するようにしてください。その他のデータは制御文字(CTRL、ALT、DELなど)として解釈される可能性があります。

1
Sean

考慮すべきさらに別の解決策! VSコードは、メモ帳の代わりにこれを使用すると、パイプ入力も受信できます。 V1.41でこれに気づきましたが、いつ実装されたかわかりません。

この例では:

diff file1.txt file2.txt | code -

コードのパラメータとしてのダッシュに注意してください。

1
rwg

動作する可能性のあるVBScriptベースのソリューションをいくつか示します(ただし、時間どおりに開くアプリに少し依存しています)。

pipe2key.vbs-最初の引数として指定されたアプリケーションを開き、StdInをキーストロークとしてそれに送信します。 wscriptはStdInアクセスを提供しないため、cscript.exeと一緒に使用する必要があります。おそらく、長いドキュメントの場合はかなり遅くなりますが、クリップボードを壊すことはありません

Set inPipe=wScript.StdIn
Set wShell=wScript.CreateObject("wscript.Shell")
wShell.Run wScript.Arguments(0), 5 ' Execute specified app, foreground it's window
wScript.Sleep 500 ' Wait for app to load
KeysToEscape="{}[]()^+%"
KeysToDrop=vbLf
While Not inPipe.AtEndOfStream
    keyChar=inPipe.Read(1)
    If InStr(KeysToDrop, keyChar) = 0 Then
        If InStr(KeysToEscape, keyChar) > 0 Then
            wShell.SendKeys "{" & keyChar & "}"
        Else
            wShell.SendKeys keyChar
        End If
    End If
Wend

使用例:diff file1.txt file2.txt | cscript pipe2key.vbs notepad.exe

または、pasteinto.vbs。アプリの起動後にCTRL-V操作を自動化します(したがって、以前の回答で述べたように「clip」コマンドを使用します)。 pipe2key.vbsよりもかなり高速でクリーン(私の意見では)ですが、プロセスはクリップボードを上書きします

Set wShell=wScript.CreateObject("wscript.Shell")
wShell.Run wScript.Arguments(0), 5 ' Execute specified app, foreground it's window
wScript.Sleep 500 ' Wait for app to load
wShell.SendKeys "^v"

使用例:diff file1.txt file2.txt | clip && pasteinto notepad.exe

0
Jason Musgrove