1

Context:

With the help of http://melander.dk/delphi/dragdrop/ i've created a little prototype to Save attachments in a AdsTable (the prototype is build so that the way the Stream is saved can be decided by the user).

Everything works fine so far with the exception of .ZIP files.

The TDropEmptyTarget.OnDrop event doesn't get the information... to be more precise not even the TDropEmptyTarget.OnEnter event triggers

I've found out that the problem lies within the different tagFORMATETC of the .ZIP file. Compared to an .EXE file they have the same formats except for one

.EXE = (49441, nil, 1, -1, 4) // ClipboardFormatname = 'FileContents'
.ZIP = (49159, nil, 1, -1, 1) // ClipboardFormatname = 'FileNameW'

I've managed that the components will accept the Format and i can Drop it... but it won't read the Data correctly.

Simply changing the extention from .ZIP to whatever allows me to drop the file in my control... save it and drag it out... changing it back to .ZIP and everything works fine... but that's the last thing i want.

[EDIT1]

Code To Enable the .ZIP drop (only allows the zip file to be dropped but Data can not be read

  // ClipboardFormat for Zip
TFileContentsOnDemandZipFormat = class(TAnsiFileGroupDescriptorClipboardFormat)
public
  function GetClipboardFormat: TClipFormat; override;
end;

function TFileContentsOnDemandZipFormat.GetClipboardFormat: TClipFormat;
begin
  Result := RegisterClipboardFormat('DragContext'); // also tried 'FileNameW'
end;

...

// Enables to drop Zip-Format
aClipboardZipFormat := TFileContentsOnDemandZipFormat.CreateFormat(1 or 4);
// VirtualTargetFiles = TVirtualFileStreamDataFormat(fTargetData.DataFormat)
aIndex := VirtualTargetFiles.CompatibleFormats.Add(aClipboardZipFormat);
// fDropTarget = TDropEmptyTarget
fDropTarget.DataFormats.Formats[0].AcceptFormat(VirtualTargetFiles.CompatibleFormats[aIndex].FormatEtc);

All formats for an .EXE file EXE-File:

(49438, nil, 1, -1, 1)
(50098, nil, 1, -1, 1)
(50099, nil, 1, -1, 1)
(49454, nil, 1, -1, 4)
(50100, nil, 1, -1, 1)
(49453, nil, 1, -1, 1)
(15, nil, 1, -1, 1)
(49158, nil, 1, -1, 1)
(49441, nil, 1, -1, 4) = 'FileContents' // Used by the component 

ZIP-File:

(49438, nil, 1, -1, 1)
(50098, nil, 1, -1, 1)
(50099, nil, 1, -1, 1)
(49454, nil, 1, -1, 4)
(50100, nil, 1, -1, 1)
(49453, nil, 1, -1, 1)
(15, nil, 1, -1, 1)
(49158, nil, 1, -1, 1)
(49159, nil, 1, -1, 1) = 'FileNameW'

Formats accepted by the component

(49441, nil, 1, -1, x)
(49442, nil, 1, -1, x)
(49443, nil, 1, -1, x)

[\EDIT1]

[EDIT2]

After enabeling the .ZIP file to onto the control, the component still can't read the data (apparently) and i've managed to follow the Code to the Funktion: (Well it looks like it can read the data but doesn't know the right thing to do with it)

 Unit DragDropFormats
 TCustomSimpleClipboardFormat.DoGetDataSized()

Which seems to be the important part... but at this depth it get's to complicated for me.

[\EDIT2]

Repeatable:

You can download the component here: http://melander.dk/delphi/dragdrop/

and run the demo VirtualFileStream this demo also doesn't allow the .ZIP file for all the same reasons.

You might want to remove the file cap in DropEmptyTarget1Drop by removing

if (BufferSize > MaxBufferSize) then
   BufferSize := MaxBufferSize;

Question:

Has anyone a simple solution for this problem?

MBe
  • 35
  • 2
  • 1
    What is the actual problem? That you cannot drag/drop a .ZIP file onto your app? Or that you cannot drag/drop something from your app onto a .ZIP file? Or what? FWIW, `FileNameW` is a valid drag/drop format, are YOU not handling that format in your code, or is Melanders components not handling that format internally, or what? It is very unclear what you are actually having a problem with. Please clarify. Maybe the problem stems from the fact that Windows has built-in support for treating .ZIP files as virtual folders, so it is representing a .ZIP file differently to the drag/drop system. – Remy Lebeau Sep 18 '15 at 15:53
  • 3
    And please don't ask people to download and run an external project to understand the problem. Please post the relevant code here and explain the behavior you are seeing in it. – Remy Lebeau Sep 18 '15 at 15:53
  • Yes as stated above the problem is that i can't drop .ZIP files on my control. It is not very clear but you can also read that the problem comes from the component (Melanders), since the events it provides doesn't even trigger. what does FWIW mean? Yes the problem is that windows is treating the .ZIP file differently. Thanks for the quick responds. – MBe Sep 21 '15 at 02:42
  • I'd like to post only the relevant code but i think this isn't quite possible with this example. – MBe Sep 21 '15 at 02:48
  • 2
    Melander's site says `TDropEmptyTarget` is "A basic drop target component that does not support any data formats on its own. Can be extended with support for any data format through the use of a `TDataFormatAdapter` component.". In the VirtualFileStream demo, the drop target's `OnEnter` event will "Reject the drop unless the source supports *both* the FileContents and FileGroupDescriptor formats in the storage medium we require (IStream)." When dropping a .zip file, the `FileNameW`/`HGLOBAL` format is being reported, so the drop would be rejected anyway, even if the event were being triggered. – Remy Lebeau Sep 21 '15 at 17:05
  • As for why the `TDropEmptyTarget.OnEnter` event is not being triggered, I don't see anything in the demo that is configuring the drop target's `TDataFormatAdapter` component with any data format(s) that it can accept, so `TDropEmptyTarget` would reject the drop before its `OnEnter` event can be triggered. – Remy Lebeau Sep 21 '15 at 17:10
  • In any case, the VirtualFileStream demo is designed to transfer only *virtual* files (hence its name), but a .zip file is a *physical* file, so the demo ignores it because only a physical filename is being provided. Why an .exe file is providing `FileContent`/`FileGroupDescriptor` formats like a virtual file does, I do not know. That is up to the drag source to decide. It is the responsibility of a drag source to provide as many formats as it feasibly can, and the responsibility of a drop target to decide if it can handle any of the formats it is given. – Remy Lebeau Sep 21 '15 at 17:17
  • What you are seeing is just a limitation of the VirtualFileStream demo, not a limitation of Melander's components in general. Other configurations would allow for accepting drops by filename. – Remy Lebeau Sep 21 '15 at 17:20
  • The drops with any other files are just woring fine. _virtual_ and _physical_ even in the demo. but as you have stated above it does not accept the .ZIP file because the Windows is not sending the .zip file with the same format as any other file.. you can enable the drop on the control for zip with the following code: – MBe Sep 22 '15 at 13:11
  • Sorry i'm new so i didn't know the limitations of the comment section and just found out that i can change the post above (which i will do) – MBe Sep 22 '15 at 13:17
  • You can also delete your comments. :) – GabrielF Sep 22 '15 at 14:38
  • Clipboard formats in the $C000 - $FFFF range (49152 - 65535) **cannot** be hard-coded like you have done. You **must** use the [`RegisterClipboardFormat()`](https://msdn.microsoft.com/en-us/library/windows/desktop/ms649049.aspx) function, as the values of registered clipboard formats change dynamically on each system reboot. For instance, you need to change `49159` to `RegisterClipboardFormat('FileNameW')`. – Remy Lebeau Sep 22 '15 at 16:45
  • I tried it and it didn't work either... it enabled the DragEnter justl ike the hard-copy but the drop didn't got any Data (i also tried 'DragContext' (49454) because 'FileContents' used the same tymed). – MBe Oct 07 '15 at 10:21

0 Answers0