Question

I am building a little HTA for personal use, and would like to be able to drag and drop a file to the interface. Once the file is dropped, I would either automatically run it (assuming it fits some parameters I set, like file extension), or at least fill in the input box on the HTA interface.

I've searched extensively, but can't find a solution. Thoughts?

Was it helpful?

Solution

An HTA obviously cannot be target of a shell drop operation – at least on my system, dropping something on an HTA is impossible.

This would imply you cannot directly do what you intend.

A .vbs can however be a drop target. Full paths of the dropped files are available via the WScript.Arguments.Unnamed collection.

HTA has access to it's command line arguments via the commandLine Property. This would mean you could build a small helper VBScript that translates the dropped files into a command line and calls the HTA for you.

Note that you cannot drop endless amounts of files on a .vbs, and command lines are not unlimited either. There will be a length limit in the area of a few kB (I have not tried to find where exactly the limit is, just be prepared to face a limit.)

OTHER TIPS

Tomalak, is incorrect in his statement...there is way to do what you want except that you have to add the DropHandler in the registry for HTA files it's really easy to do and once done you will be able to do exactly what your trying to do. I couldn't find much documentation on it, but here is a link to an HTA that was written a long time ago by a guy named Michel Gallant, that shows you how to it: http://www.jensign.com/JavaScience/www/wsh/imager/index.html

When the HTA is launched it looks to see if you have the DropHandler already configured. If you don't it gives you the option for it to configure it for you. Once configure all you have to do is close and reopen the HTA and wallah, there you go Drag and Drop support in HTA files.

If you don't want to enable the drop handler, I could imagine a way that this might be possible. It's a bit of a comedy chain, but I could see myself implementing this if I was backed into a corner and needed that functionality.

You can create an IFRAME which has its src as a temp folder somewhere. This folder will be displayed as an Explorer view. You can then drag files into that. Set up a polling routine against that folder to see if there are any new files. And voila, you have a lame way to support drag and drop operations with a given file.

Go and try google gears which supplies drag and drop.

You can even use mysql in hta.

Google Gears is not available in hta, however, you can create the activexobject in a html file, then include it using an iframe(<iframe application="true" src=".."></iframe>)

After that, you can use the activexobject through the iframe.

Regarding …

would like to be able to drag and drop a file to the [HTA] interface

… which I interpret as a desire to drop files to the HTA’ running window, rather than dropping files on the HTA file itself or a shortcut to it.

With HTML5 the dropping itself is easy. Use e.g. a <div> element as a drop area. For this element handle the events dragenter, dragover and drop. E.g. the drop handler can look like this:

function on_drop( e )
{
    e.preventDefault();  // stops the browser from redirecting off to the file
    var dt = e.dataTransfer

    var is_file_transfer = false;
    for( var i = 0; i < dt.types.length; ++i )
    {
        if( dt.types[i].toLowerCase() == 'files' )
        {
            is_file_transfer = true;
        }
    }
    if( !is_file_transfer )
    {
        return false;
    }
    on_files_dropped( dt.files );
    return true;
}

… where on_files_dropped is a function defined by you that handles a files drop.

Adding the event handlers dynamically in the document loaded event, can look like this:

var dropbox = document.getElementById( 'blah' );
dropbox.addEventListener( 'dragenter', on_dragenter, false );
dropbox.addEventListener( 'dragover', on_dragover, false );
dropbox.addEventListener( 'drop', on_drop, false );

So far so good.

However, security intervenes with a restriction: you do not get direct knowledge of the original file paths, only the file names and the file sizes. For this functionality is designed for the web, not for local trusted HTML applications. So it may or may not necessarily be a problem.

  • For the purpose of using a dropped file as a source for an HTML element, and generally for reading a dropped file, HTML5 provides a FileReader (there are a number of tutorials available, which link further to technical documentation).

  • Where a local path is needed, e.g. for playing a file in Windows Mediaplayer, you can assume that the drag operation originated with Windows Explorer, now also called File Explorer, and then just check which Explorer window, if any, contains a file with that name and size.

Hopefully not more than one such originating window will be found.

var shell   = new ActiveXObject( "Shell.Application" );
var fso     = new ActiveXObject( "Scripting.FileSystemObject" );

function possible_paths_for( filename )
{
    var windows     = shell.windows();      // Windows Explorer windows.
    var n_windows   = windows.Count;

    var lowercase_filename = filename.toLowerCase();
    var paths = Array();
    for( var i = 0; i < n_windows; ++i )
    {
        var url     = windows.Item(i).LocationURL;
        var path    = decodeURI( url.substr( 8 ) ).replace( /\//g, '\\' );
        // The path can be the path of this HTML application (.hta file), so:
        if( fso.FolderExists( path ) )
        {
            var folder  = fso.GetFolder( path );
            for( var it = new Enumerator( folder.Files ); !it.atEnd(); it.moveNext() )
            {
                var file = it.item();
                if( file.Name.toLowerCase() == lowercase_filename )
                {
                    paths.push( file.Path.toLowerCase() );
                }
            }
        }
    }
    return paths;
}

Essentially that’s it. Except, maybe, since HTAs default to IE7, how does one get HTML5 functionality. Well may through doctype declaration, but so far in my little experimentation I just use the following:

<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
        <!-- A windows web control defaults to quirky IE7 semantics. Request for better: -->
        <meta http-equiv="X-UA-Compatible" content="IE=edge">
        <meta http-equiv="MSThemeCompatible" content="yes">

This gives you latest Internet Explorer engine, but at the cost of no HTA element, and hence no direct access to the command line. I found that the command line can be retrieved by running Windows’ wmic program, but that’s an awful hack. This whole problem area, with most apparently open roads turning out to be closed, appears to be a consequence of Microsoft now considering HTAs a legacy technology, to be quietly phased out in favor of fullscreen ad-ridden Windows 8 AppStore apps.

Anyway, good luck!

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top