Drag and Drop for .BTM scripts

  • This site uses cookies. By continuing to use this site, you are agreeing to our use of cookies. Learn more.
#1
I was working on adding Drag and Drop support for .btm scripts.
This way it is possible to drag one or more files to your script to use the filenames of those as parameters:

2017-02-15 20_38_35-Drag.png


One little disadvantage: these filenames are returned as SFN's (short filenames; 8.3 names)
2017-02-15 20_43_35-C__Temp_TCMD20_TCC.exe.png


That might very well be caused by the way Take Command is installed on my computers:
It is in fact *not* installed and there is no (usual) association for .btm files.


Before reconfiguring my systems, a question:

Is there anyone courageous enough to report how this behaves on a more default system/ TC installation?


The script to install / remove drag and drop support is straightforward:

2017-02-15 20_51_54-Administrator_ TCC - AddRemoveDragDrop.btm.png

The script adds 1 registry key/value pair on install and removes that on uninstall. Should be pretty harmless.

How to?
  • Create some dummy files (if needed): do var = 1 to 5 (REM>"random filename %var.txt")
  • start AddRemoveDragDrop.btm as an admin
  • Choose 1
  • Drag one or more files to TestParms.btm
    TestParms only reports the parameters it was fed.
  • start AddRemoveDragDrop.btm as an admin
  • Choose 2
Except for the AddRemoveDragDrop.btm part, everything can be done as a regular user.
 

Attachments

Jul 29, 2016
36
1
#2
Even with TCMD/TCC installed like normal, drag and drop will only give you the SFN (unless SFN creation is disabled on the volume, then you will get the LFN).

You can always get the long name by using %@LFN[filename] in your batch file.
 
#3
Even with TCMD/TCC installed like normal, drag and drop will only give you the SFN (unless SFN creation is disabled on the volume, then you will get the LFN).
Is that because of TCC or Windows? If it's Windows, then I believe, where registry entries are involved, you can force a LFN with the use of "%L" instead of "%l" (or something like that).
 
#4
Is that because of TCC or Windows? If it's Windows, then I believe, where registry entries are involved, you can force a LFN with the use of "%L" instead of "%l" (or something like that).
Apparently not.

I've had the registry entry since 2013-11-02. And I don't think I have used it since that day. It has always been there for "batfile" (CMD.EXE) Tonight I tried it with this BTM and this BAT.
Code:
v:\> type btmargs.btm
echo %1
pause

v:\> type cmdbatargs.bat
@echo off
echo %1
pause
I have LFNs turned off. When I drag "a b c.txt" to the cmdbatargs.bat (CMD), I get
Code:
"V:\a b c.txt"
When I drag it to batargs.btm (TCC), I get
Code:
V:\a
b
c.txt
I don't understand. The argument handling is the same:
Code:
v:\> ftype batfile
batfile="%1" %*

v:\> ftype tcc.batch
tcc.batch="G:\tc19\tcc.exe" /c "%1" %*
Any idea why the name of the dragged file is quoted for the batfile and not quoted for the TCC.Batch file?
 
Jul 29, 2016
36
1
#5
Apparently not.

I've had the registry entry since 2013-11-02. And I don't think I have used it since that day. It has always been there for "batfile" (CMD.EXE) Tonight I tried it with this BTM and this BAT.
Code:
v:\> type btmargs.btm
echo %1
pause

v:\> type cmdbatargs.bat
@echo off
echo %1
pause
I have LFNs turned off. When I drag "a b c.txt" to the cmdbatargs.bat (CMD), I get
Code:
"V:\a b c.txt"
When I drag it to batargs.btm (TCC), I get
Code:
V:\a
b
c.txt
I don't understand. The argument handling is the same:
Code:
v:\> ftype batfile
batfile="%1" %*

v:\> ftype tcc.batch
tcc.batch="G:\tc19\tcc.exe" /c "%1" %*
Any idea why the name of the dragged file is quoted for the batfile and not quoted for the TCC.Batch file?
By saying that you have LFN's turned off, did you mean to say that you have SFN creation turned off for that volume (with FSUTIL program)?
When dragging file "a b c.txt" to the .BTM file, did you get a PAUSE prompt after each of the three lines displayed (V:\a <CR> b <CR> c.txt <CR>)? If so, it's like it ran the .BTM three times, once for each "separate" (unquoted) parameter. I didn't get that behavior, but noticed that the parameter displayed in the ECHO command of the .BAT file was quoted, but was not quoted in the .BTM file. For the record, within the "System" option in Control Panel, I set the "ComSpec" environment variable on the user level to point to TCC, and so even without having chosen the option to make TCC the default handler for .BAT/.CMD files (during installation), TCC is always called when running a .BAT/.CMD file anyway (unless I run it elevated), but even with TCC being called in both cases, the behavior is the same: the .BAT file will show the parameter having quotes, the .BTM file will show the parameter not having quotes.
 
Likes: MaartenG
Jul 29, 2016
36
1
#6
Apparently not.

I've had the registry entry since 2013-11-02. And I don't think I have used it since that day. It has always been there for "batfile" (CMD.EXE) Tonight I tried it with this BTM and this BAT.
Code:
v:\> type btmargs.btm
echo %1
pause

v:\> type cmdbatargs.bat
@echo off
echo %1
pause
I have LFNs turned off. When I drag "a b c.txt" to the cmdbatargs.bat (CMD), I get
Code:
"V:\a b c.txt"
When I drag it to batargs.btm (TCC), I get
Code:
V:\a
b
c.txt
I don't understand. The argument handling is the same:
Code:
v:\> ftype batfile
batfile="%1" %*

v:\> ftype tcc.batch
tcc.batch="G:\tc19\tcc.exe" /c "%1" %*
Any idea why the name of the dragged file is quoted for the batfile and not quoted for the TCC.Batch file?
Interesting discovery, I wasn't actually using your batch file; mine contained "echo %1 %2 %3 %4 %5" (w/o the quotes). This was both with the .BAT and the .BTM. When I edited them both to only contain "echo %1" and dragged the file "c:\Users\IEUser\Desktop\foo bar 2.txt" onto each, the .BAT showed the full path+name quoted, whereas the .BTM showed only "c:\Users\IEUser\Desktop\foo" (but w/o the quotes). Obviously the rest of the unquoted name in the original .BTM were showing up as parameters %2, %3, etc. But since TCC is running in both the .BAT and the .BTM case (because of my Windows "ComSpec" environment variable setting), this rules out TCC being the problem; it's something with Windows itself in what it chooses to pass in each of those cases.

I should also note, that was with "c:\users\IEUser\desktop\foo bar 2.txt" not having a short file name. With testing this with another file that had both an LFN and an SFN, the .BAT file echoed the LFN quoted as parameter %1, whereas the .BTM echoed the SFN (unquoted) instead as parameter %1.
 
Jul 29, 2016
36
1
#7
Apparently not.

I've had the registry entry since 2013-11-02. And I don't think I have used it since that day. It has always been there for "batfile" (CMD.EXE) Tonight I tried it with this BTM and this BAT.
Code:
v:\> type btmargs.btm
echo %1
pause

v:\> type cmdbatargs.bat
@echo off
echo %1
pause
I have LFNs turned off. When I drag "a b c.txt" to the cmdbatargs.bat (CMD), I get
Code:
"V:\a b c.txt"
When I drag it to batargs.btm (TCC), I get
Code:
V:\a
b
c.txt
I don't understand. The argument handling is the same:
Code:
v:\> ftype batfile
batfile="%1" %*

v:\> ftype tcc.batch
tcc.batch="G:\tc19\tcc.exe" /c "%1" %*
Any idea why the name of the dragged file is quoted for the batfile and not quoted for the TCC.Batch file?
This comment was found at the end of MaartenG's batch file:
Code:
::================================================
:: References:

%% parameters
http://superuser.com/questions/136838/which-special-variables-are-available-when-writing-a-shell-command-for-a-context

LFN Support
https://blogs.msdn.microsoft.com/oldnewthing/20041020-00/?p=37523
Maybe the "LFN Support" link will shed more light onto someone else than it did me?
 
#8
Even with TCMD/TCC installed like normal, drag and drop will only give you the SFN (unless SFN creation is disabled on the volume, then you will get the LFN).

You can always get the long name by using %@LFN[filename] in your batch file.
Thanks for testing!!!

The @LFN workaround is exactly the one I was using, but it is a workaround (I guess; I keep hoping for a Windows-native solution :-)

That's clever: Forcing Windows "in the corner" where the only way out is presenting the LFN. I like that! :-) (although maybe not the ultimate solution)
 
#9
I was a little mixed up. When I drag "a b c.txt" to
Code:
v:\> type batargs.btm
do i=1 to %#
        echo %[%i]
enddo
I get
Code:
V:\a
b
c.txt
When I use
Code:
v:\> type batargs2.btm
echo %1
pause
I get
Code:
V:\a
And when I use this one (CMD)
Code:
v:\> type cmdbatargs.bat
echo %1
pause
I get
Code:
"V:\a b c.txt"
My observation still seems to hold. The BTMs don't seem to get a quoted file name.

IIRC, I didn't use FSUTIL, but rather set
HKLM\SYSTEM\CurrentControlSet\Control\FileSystem\NtfsDisable8dot3NameCreation
manually. I think the registry entry goes back to Windows NT4 (maybe earlier).
 
#10
This comment was found at the end of MaartenG's batch file:
Code:
::================================================
:: References:

%% parameters
http://superuser.com/questions/136838/which-special-variables-are-available-when-writing-a-shell-command-for-a-context

LFN Support
https://blogs.msdn.microsoft.com/oldnewthing/20041020-00/?p=37523
Maybe the "LFN Support" link will shed more light onto someone else than it did me?
That's "false alarm". It's about the "%1" of the TCC.exe "%1" %*
Windows has it's own set of rules to decide if TCC.exe should be fed the SFN or the LFN.
TCC is one of the "good guys" that gets the LFN (which can be seen if you also do a echo %0 in the testscript.

The other (non-official) link is about how to pass through variations of the "%1". It has no effect on the %* part (which I was hoping for)




Apparently not.

I've had the registry entry since 2013-11-02. And I don't think I have used it since that day. It has always been there for "batfile" (CMD.EXE) Tonight I tried it with this BTM and this BAT.
Code:
v:\> type btmargs.btm
echo %1
pause

v:\> type cmdbatargs.bat
@echo off
echo %1
pause
I have LFNs turned off. When I drag "a b c.txt" to the cmdbatargs.bat (CMD), I get
Code:
"V:\a b c.txt"
When I drag it to batargs.btm (TCC), I get
Code:
V:\a
b
c.txt
I don't understand. The argument handling is the same:
Code:
v:\> ftype batfile
batfile="%1" %*

v:\> ftype tcc.batch
tcc.batch="G:\tc19\tcc.exe" /c "%1" %*
Any idea why the name of the dragged file is quoted for the batfile and not quoted for the TCC.Batch file?

(Oops, forgot to check the forum first. This has already be done.... )

With your "a b c.txt" and option //Win32SFNSearch=No (which is my default setting) I get the SFN (ABC~1.TXT)

After some searching on the internet, there are quite some references about the DropHandler just passing SFN's.
I tried other DropHandlers (those of .WSH, .LNK, .ZIP ; most of them against common sense, but hey, it's worth a try :-)
None of them worked.
Would be interesting to know what parameters a self created .EXE would get. SFN or LFN?

I think it's a "Windows-thing": .BAT and .CMD get LFN's, every other - non-native - registerd extension gets the SFN.

This is how I (finally!) got Windows fooled to pass LFN's to TCC.exe:

Code:
C:\Windows\system32>assoc .bat
.bat=batfile

C:\Windows\system32>ftype batfile
batfile="C:\Temp\TCMD20\tcc.exe" /c "%1" %*
Output:
Code:
TCC  20.00.25 x64   Windows 7 [Version 6.1.7601]
    parm 0 = [C:\Temp\TEST_TCMD\DragDrop\_TestParmsBTM.bat]
    parm 1 = ["C:\Temp\TEST_TCMD\DragDrop\dummy file name 1.txt"]
    parm 2 = ["C:\Temp\TEST_TCMD\DragDrop\dummy file name 2.txt"]
    parm 3 = ["C:\Temp\TEST_TCMD\DragDrop\dummy file name 3.txt"]
    parm 4 = ["C:\Temp\TEST_TCMD\DragDrop\dummy file name 4.txt"]
    parm 5 = ["C:\Temp\TEST_TCMD\DragDrop\dummy file name 5.txt"]
    parm 6 = []
    parm 7 = []
    parm 8 = []
    parm 9 = []
Press any key when ready...


Still a workaround, but it sheds some light on the innner working of the process:
The DropHandler (=Shell32.dll) just has special treatment for .BAT files!! (And I assume same goes for .CMD)

EDIT: Sorry @evensenm, that is basically what you said already. Completely missed that, coming from dark undocumented corners of the registry (analyzing Shell registry keys and following the trail of a Procmon trace).
I think I'll go the @LFN route (or start to learn programming and write my own Drophandler ;-)


That's it so far.

TL;DR: So far it seems that every non-native Windows program (like TCC) gets the short filenames instead of the long filenames.
 
Last edited: