2022年5月
1 2 3 4 5 6 7
8 9 10 11 12 13 14
15 16 17 18 19 20 21
22 23 24 25 26 27 28
29 30 31        
無料ブログはココログ

« 2009年3月 | トップページ | 2009年5月 »

2009年4月30日 (木)

IE8 で「お気に入り」や「リンク」からのアプリ起動が再び可能になりました。

IE8 では「リンク」フォルダを「お気に入りバー」フォルダと呼ぶようです。紛らわしい。:-(

IE7 で「お気に入り」や「リンク」からのアプリ起動が制限されました。:-(
http://scripting.cocolog-nifty.com/blog/2008/05/ie7_shell_ie_d297.html
これが、IE8で、再び可能になりました。:-)

ただし、引数が渡りません。
A shortcut for Internet Explorer does not load the specified URL in Internet Explorer 8

なので、「IE7の「リンク」バーからアプリを起動する。」
http://scripting.cocolog-nifty.com/blog/2008/09/ie7-5a02.html
の回避策は不要になりました。:-)

と言うか、この回避策は、IE8では、危険です。
もし「フォルダショートカット」があると、IEがループします。:-(

2009年4月28日 (火)

XP SP3 + IE7 / IE8 で、エクスプローラの履歴バーがおかしい。(障害)

XP SP3 + IE7 / IE8 の環境で、エクスプローラの履歴バーが異常です。
履歴フォルダ(shell:history)も異常です。
IEの履歴バーは正常です。

例えば、デスクトップのファイルを選択すると、
---------------------------
file:///C:/Documents%2520and%2520Settings/user/デスクトップ/hoge.txt
指定されたパスは存在しません。
パスが正しいか確認してください。
---------------------------

半角空白を%20にエンコードして、更にもう一度、%をエンコードしてるようです。
それをエクスプローラは1回だけ、IEは2回デコードしてるようです。

IE7で履歴まわりを変更したのではないかと疑っています。

ところで、こういう一貫性のない振舞いは、セキュリティの脆弱性攻撃に使われそうな気がしません?

2009年4月26日 (日)

ファイルの関連付けで、長いファイル名を短いファイル名に変換する。(その2)

関連付けの書き方をちょっと変えるだけで、できちゃいます。

例えば、

"%systemroot%\system32\wscript.exe" "%1" %*

と書く代わりに、

%systemroot%\system 32\..\system32\wscript.exe %1 %*

ここで、

空白を含む長いファイル名を""で囲まないと、%1を短いファイル名に変換するのはShellの仕様です。
KB142275 Long File & Path Names Shorten When Launched Using Association

空白を含む長いファイル名を""で囲まなくても実行できるのは、Win32APIのCreateProcess()の仕様です。

空白を含まない場合は、OSのファイル名のコンベンションの\..\を利用して、架空のフォルダ名に空白を入れます。

2009年4月24日 (金)

ファイルの関連付けで、長いファイル名を短いファイル名に変換する。

コンソールアプリなら、cmd.exeを使って、例えば、

exe "%1" %*

の代わりに、

cmd.exe /q /c for %%I in ("%1") do for %%J in ("%~dpsI%~nxI") do exe %~sJ %*

ウィンドウアプリの場合は、cmdw.exeを使って、

cmdw.exe /c for %%I in ("%1") do for %%J in ("%~dpsI%~nxI") do start exe %~sJ %*

ここで、

cmd /c でのfor変数は%文字ですが、関連付けで%英数字は関連付け変数に解釈されるので、%%でエスケープします。

forを二段重ねているのは、%~sIの障害対策です。

2009年4月23日 (木)

cmd.exeをコンソールアプリの起動に使う。

コンソールアプリには、cmd.exeが、コンソールアプリのままで、いろいろ使えます。

「ファイル名を指定して実行」の「名前」のコマンドライン
「ショートカット」の「リンク先」のコマンドライン
「関連付け」の「command」キー値のコマンドライン
「タスクスケジューラ」の「実行するファイル名」のコマンドライン
などに使用すると、

作業フォルダを指定する。
cmd.exe /c cd /d "%1\.." & exe "%1" %*

長いファイルを短いファイル名に変える。
cmd.exe /q /c for %%I in ("%1") do for %%J in ("%~dpsI%~nxI") do exe %~sJ %*

環境変数を設定変更する。
cmd.exe /c set name=value & exe "%1" %*

などが可能になります。例は関連付け。

ただし、最小化、最大化を指定するのには、コンソールが開くので、使えません。

2009年4月22日 (水)

cmdw.exeで、バッチファイルを非表示にできるか?

バッチファイルを実行すれば、非表示にできるか? Yes and No。

バッチファイルが内部コマンドとウィンドウアプリだけなら、Yes。

もし、コンソールアプリを実行すると、コンソールが開くので、No。

2009年4月21日 (火)

ウィンドウアプリに化かしたcmd.exeを使う。

コンソールアプリのcmd.exeをウィンドウアプリのcmdw.exeに変えると、いろいろ使えます。

「ファイル名を指定して実行」の「名前」のコマンドライン
「ショートカット」の「リンク先」のコマンドライン
「関連付け」の「command」キー値のコマンドライン
「タスクスケジューラ」の「実行するファイル名」のコマンドライン
などに使用すると、

最小化、最大化を指定する。
cmdw.exe /c start /min exe "%1" %*

作業フォルダを指定する。
cmdw.exe /c start /d "%1\.." exe "%1" %*

長いファイルを短いファイル名に変える。
cmdw.exe /c for %%I in ("%1") do for %%J in ("%~dpsI%~nxI") do start exe %~sJ %*

環境変数を設定変更する。
cmdw.exe /c set name=value & start exe "%1" %*

などが可能になります。例は関連付け。

cmd.exeと異なって、コンソールが開かない。:-)

2009年4月20日 (月)

コンソールアプリをウィンドウアプリに化かす。

コンソールアプリ、例えば、cmd.exeをウィンドウアプリのcmdw.exeに変えるにはどうするか?

方法1

link.exeを持っていれば、
copy cmd.exe cmdw.exe
link /edit /subsystem:windows cmdw.exe

方法2

なければ、
copy cmd.exe cmdw.exe
c2w.vbs cmdw.exe

c2w.vbs

Option Explicit
Const adTypeBinary=1
Const adTypeText=2
Const adSaveCreateOverWrite=2
Dim Path
Dim Stream
Dim Buf
Dim Bytes

Path=WScript.Arguments.Item(0)
Set Stream=CreateObject("ADODB.Stream")
Stream.Open
Stream.Type=adTypeText
Stream.WriteText Chr(2)
Stream.Position=0
Stream.Type=adTypeBinary
Stream.Position=2
Bytes=Stream.Read(1)
Stream.Close
Stream.Open
Stream.Type=adTypeBinary
Stream.LoadFromFile Path
Buf=Stream.Read(512)
Stream.Position=AscB(MidB(Buf,1+&H3c,1))+AscB(MidB(Buf,2+&H3c,1))*256+AscB(MidB(Buf,3+&H3c,1))*256*256+AscB(MidB(Buf,4+&H3c,1))*256*256*256+(&H4+&H14+&H44)
Stream.Write Bytes
Stream.SaveToFile Path,adSaveCreateOverWrite
Stream.Close
Set Stream=Nothing

2009年4月14日 (火)

バッチファイルを Unicode や UTF-8 で書く。

ただし、拡張子は .cmdu と .cmd8 です。

バッチファイルは、シフトJIS、EUC、EBCDIC などで書けますが、Unicode や UTF-8 では書けません。:-(
しかし、Unicode や UTF-8 であっても、日本語文字だけなら、シフトJISにコード変換すれば、実行できます。
そこで、.cmdu と .cmd8 の拡張子を追加し、関連付けでコード変換します。

.cmdu

cmd.exe /c type "%1">"%1.cmd" & "%1.cmd" %* & del "%1.cmd"

.cmd8

cmd.exe /c start /min /wait cmd /c chcp.com 65001 ^& cmd /u /c type "%1"^>"%1.$$$" & type "%1.$$$" >"%1.cmd" & "%1.cmd" %* & del "%1.$$$" "%1.cmd"

レジストリ定義は、

[HKEY_CLASSES_ROOT\.cmdu\shell\open\command]
@="cmd.exe /c type \"%1\">\"%1.cmd\" & \"%1.cmd\" %* & del \"%1.cmd\""

[HKEY_CLASSES_ROOT\.cmdu\shell\edit\command]
@="notepad.exe %1"

[HKEY_CLASSES_ROOT\.cmd8\shell\open\command]
@="cmd.exe /c start /min /wait cmd /c chcp.com 65001 ^& cmd /u /c type \"%1\"^>\"%1.$$$\" & type \"%1.$$$\" >\"%1.cmd\" & \"%1.cmd\" %* & del \"%1.$$$\" \"%1.cmd\""

[HKEY_CLASSES_ROOT\.cmd8\shell\edit\command]
@="notepad.exe %1"

2009年4月12日 (日)

バッチファイルを暗号化する。

暗号化と言ってもEBCDICにするだけですが。。。

ただし、全角文字は使えません。半角カタカナはOK。

encrypt.cmd 元バッチファイル名 新バッチファイル名

echo chcp.com 20290 ^>nul ^& call :crypt %%* ^& chcp.com 932 ^>nul ^& goto :eof>%2
echo :crypt>>%2
( set /p x=""<nul & cmd /u /c type %1 ) >$$$
start /min /wait cmd /c chcp.com 20290 ^& cmd /c type $$$ ^>^>%2
del $$$

2009年4月 9日 (木)

IE8のHTAで、ローカルソースファイルを編集するコンテキストメニュー拡張

IE7までは、HTAのコンテキストメニューの「ソースの表示」でローカルソースファイルが編集できました。
しかし、IE8では、HTAのコンテキストメニューの「ソースの表示」で、キャッシュのソースファイルを開くようになりました。
そこで、コンテキストメニューに「ソースの編集」を追加します。

EditSource.htm

<script>
new ActiveXObject("Shell.Application").ShellExecute(external.menuArguments.top.document.URL,null,null,"edit");
</script>

EditSource.reg

Windows Registry Editor Version 5.00

[HKEY_CURRENT_USER\Software\Microsoft\Internet Explorer\MenuExt\ソースの編集]
@="C:\\どこか\\EditSource.htm"

2009年4月 7日 (火)

HTAで、シングルクリックとダブルクリックで排他的に分けて処理する。

シングルクリックとダブルクリックとで処理を分けようとしても、ダブルクリックすると、onclickとondblclickの両方がこの順序で発生するので、不可分です。

例えば、

<script language=vbscript>
sub document_onclick()
document.body.innerText=document.body.innerText & vbCrLf & window.event.type
end sub
sub document_ondblclick()
document.body.innerText=document.body.innerText & vbCrLf & window.event.type
end sub
</script>

では、シングルクリックでonclickだけが動き、ダブルクリックでonclickとondblclickの両方が動きます。

では、どうすれば、シングルクリックでonclickだけを動かし、ダブルクリックでondblclickだけを動かすことができるのでしょうか?

もし、ondblclick、onclickの順序で発生するのであれば、onclickでondblclickが先に発生しているか調べることができます。

<script language=vbscript>
dim type1
sub document_onclick()
type1=window.event.type
'settimeout "sub1",createobject("wscript.shell").regread("HKCU\Control Panel\Mouse\DoubleClickSpeed")
settimeout "sub1",createobject("shell.application").GetSystemInformation("DoubleClickTime")
end sub
sub document_ondblclick()
type1=window.event.type
end sub
sub sub1()
document.body.innerText=document.body.innerText & vbCrLf & type1
end sub
</script>

ダブルクリック時間は外部オブジェクトを使わないと取れない?
HTAなら使えますが、IEではセキュリティの制約で難しいかも。

2009年4月 5日 (日)

WSFファイルをCScript.exeで実行するための拡張子(.wsfc)を追加する。

VBSファイルやJSファイルは、//Eオプションを使って、拡張子の追加変更が可能ですが、WSFファイルの場合は.wsf固定です。

しかし、バッチファイルの場合と異なり、WSFファイルの場合は、短いファイル名の拡張子がWSFであればよいようです。

例えば、長いファイル名の hoge.wsfc の短いファイル名が HOGE~1.WSF なら、

cscript HOGE~1.WSF

で実行できます。

ならば、長いファイル名の拡張子(.wsfc)を作って、関連付けを、

cmd.exe /q /c for %%I in ("%1") do for %%J in ("%~dpsI%~nxI") do cscript.exe %~sJ %*

とすればよいのです。

[HKEY_CLASSES_ROOT\.wsfc\shell\open\command]
@="cmd.exe /q /c for %%I in (\"%1\") do for %%J in (\"%~dpsI%~nxI\") do cscript.exe %~sJ %*"

2009年4月 2日 (木)

常駐のWSHスクリプトを外部からの指示で終了する。(その3)

以下のスクリプトを実行して、出てきたIEのページで「終了」ボタンを押すと、スクリプトもIEも終了します。

Set ie=CreateObject("InternetExplorer.Application")
ie.Visible=True
ie.Navigate "about:blank"
Do While ie.Busy Or ie.ReadyState<>4
  WScript.Sleep 100
Loop
ie.document.body.innerHTML="<button id=button1>終了</button>"
Set ie.document.all.button1.onclick=GetRef("sub1")
MsgBox "waiting..."

Sub sub1()
ie.quit
WScript.Timeout=1
End Sub

2009年4月 1日 (水)

常駐のWSHスクリプトを外部からの指示で終了する。(その2)

htmlfileのwindow.setInterval()を利用して指示をポーリングする方法です。
ここではファイルを削除すると終了指示になります。

以下のスクリプトを実行して、作成されたスクリプトファイル名.Runというファイルを削除すると、スクリプトが終了します。

Set fso=CreateObject("Scripting.FileSystemObject")
fso.CreateTextFile(WScript.ScriptFullName & ".Run")
Set doc=CreateObject("htmlfile")
doc.parentWindow.setInterval GetRef("proc"),1000
MsgBox "waiting..."

Sub proc()
If Not fso.FileExists(WScript.ScriptFullName & ".Run") Then WScript.Timeout=1
End Sub

« 2009年3月 | トップページ | 2009年5月 »