再问一次,关于拖放问题(两个问题,解决后再加300分!!)(200分)

  • 主题发起人 主题发起人 aricyoung
  • 开始时间 开始时间
A

aricyoung

Unregistered / Unconfirmed
GUEST, unregistred user!
两个问题,解决后再加300分!!
第一次提问的问题,解决一起给分:
http://www.delphibbs.com/delphibbs/dispq.asp?lid=3329064
另外再问:
从其他程序(如word等)中往自己的程序中拖放文字、图片等的时候,如何判断是拖动文字还是图片,然后根据判断的结果进行相应的操作?
试验了一下可以往richedit中拖放文字和图片,只是这样实现的是移动操作,不是复制,就是这样拖放后word中的原来的内容就不见了,怎样才能实现复制的操作?
望各位兄弟帮帮忙!
 
再加一点,就是如果判断出什么数据了,比如判断出拖放是图片,那么如何将拖放的图片处理出来,即比方我想把此图片插入到Richedit中应该怎么做?
 
哈巴狗站上可能有,而很详细
 
拖放控件下载地址:
ftp://code:code@www.cnzz.cn:21/code_200504/Delphi源代码/控件使用类/Drag and Drop Component Suite 3.7 (拖放).zip
 
你可以用IEnumFormatEtc接口来判断拖放类型,如:
var
Enum: IEnumFormatEtc;
Fe: TFormatEtc;
.....
DataObj.EnumFormatEtc(DATA_GET, Enum);
if Enum.Next(1, Fe, @Returned) = S_OK then
.....
或者 case Fe.cfFormat of ...
 
帮顶!

╭=========================================╮

80G海量源代码,控件,书籍全免费狂下不停!

http://www.source520.com

╰=========================================╯
 
我的问题怎么就没有一个可以在这得到正确答案的,都要自己解决,现在解决的差不多了,希望大家再给予帮助
 
或需你可以试试从文件的大小上下手
 
要想实现复制,你可以尝试着建个弹出菜单,默认左键移动,右件键弹出移动,复制的选项,然后利用剪贴板(TClipboard)进行数据交换,TClipboard类会根据你的拖动数据自动判断数据类型,你只要从其中的数据格式就可以读出类型.
[red]部分格式类型
CF_TEXT 文本。每行以CF_LF结束,nil标志文本结束
CF_BITMAP Windows位图
CF_METAFILE Windows元文件
CF_PICTURE TPicture类型的对象
CF_OBJECT 任何TPersistent类型的对象[/red]
如果你觉得想再提高层次的话,可以使用DDE来完成数据的动态操作.
 
哈吧狗站点有
 
<font color=#ff0000>.部分格式类型
CF_TEXT 文本。每行以CF_LF结束,nil标志文本结束
CF_BITMAP Windows位图
CF_METAFILE Windows元文件
CF_PICTURE TPicture类型的对象
CF_OBJECT 任何TPersistent类型的对象



这个方法好~~
 
//-----------------------------------------------------------------------------
// Drag & Drop Component
// Copyright (c) 2003 By Mental Studio -- http://mental.mentsu.com
// Author: Raptor.z<raptor@mentsu.com>
// Date: Dec.03-03, Dec.11-03
//-----------------------------------------------------------------------------

unit MOleDragDrop;

interface

uses
SysUtils, Classes, Types, Controls, Windows, ActiveX, ShellAPI, ShlObj, Graphics;

type
TOleDragEnterEvent = procedure (Sender: TObject; aDataObj : IDataObject;
grfKeyState : Integer; pt : TPoint; var dwEffect : Integer;
var feFormat : TFormatEtc ) of object;
TOleDragOverEvent = procedure (Sender: TObject;
grfKeyState : Integer; pt : TPoint; var dwEffect : Integer ) of object;
TOleDragLeaveEvent = TNotifyEvent;
TOleDragDropEvent = procedure (Sender: TObject; aDataObj : IDataObject;
grfKeyState : Integer; pt : TPoint; var dwEffect : Integer;
var feFormat : TFormatEtc ) of object;
TOleTextDropEvent = procedure (Sender: TObject; aText : String ) of object;
TOleFileDropEvent = procedure (Sender: TObject; aFiles : TStrings ) of object;
TOleBitmapDropEvent= procedure (Sender: TObject; aBitmap: TBitmap ) of object;

TMOleDragDrop = class;

TMOleDropTarget = class(TInterfacedObject, IDropTarget )
private
//FRefCount : Integer;

FOwner : TMOleDragDrop;
FCanDrop : HResult;
FDragResult : HResult;
FFormatEtc : TFormatEtc;

function DrawBitmap(aDest: TBitmap; aHandle, aPalette: Cardinal): Boolean;

protected
(*
{ Iunkown }
function _AddRef:integer;stdcall;
function _Release:integer;stdcall;
function QueryInterface(const IID:TGUID;out Obj):HResult;stdcall;
*)
{ IDropTarget }
Function DragEnter( const aDataObj : IDataObject; grfKeyState : Longint;
pt : TPoint; var dwEffect : Longint ) : HResult; stdcall;
Function DragOver( grfKeyState : Longint; pt : TPoint; var dwEffect : Longint ) : HResult; stdcall;
Function DragLeave : HResult; stdcall;
Function Drop( const aDataObj : IDataObject; grfKeyState : Longint; pt : TPoint;
var dwEffect : Longint ) : HResult; stdcall;

public
Constructor Create( aOwner : TMOleDragDrop );
Destructor Destroy; Override;
(*
procedure AfterConstruction; override;
procedure BeforeDestruction; override;
class function NewInstance: TObject; override;
*)
function GetDataText(aDataObj: IDataObject; aFmtEtc: TFormatEtc): String;
function GetDataFiles(aDataObj: IDataObject; aFmtEtc: TFormatEtc; aFiles: TStrings) : Integer;
function GetDataBitmap(aDataObj: IDataObject; aFmtEtc: TFormatEtc; aBitmap: TBitmap) : Boolean;

Property CanDrop : HResult Read FCanDrop;
Property DragResult : HResult Read FDragResult Write FDragResult;
end;

TMOleDragDrop = class(TComponent)
private
{ Private declarations }
FOleDrag : TMOleDropTarget;
FDropControl : TWinControl;
//FEnabledSource : Boolean;
FEnabledTarget : Boolean;

FOnDragEnter : TOleDragEnterEvent;
FOnDragOver : TOleDragOverEvent;
FOnDragLeave : TOleDragLeaveEvent;
FOnDragDrop : TOleDragDropEvent;
FOnTextDrop : TOleTextDropEvent;
FOnFileDrop : TOleFileDropEvent;
FOnURLDrop : TOleTextDropEvent;
FOnHTMLDrop : TOleTextDropEvent;
FOnBitmapDrop: TOleBitmapDropEvent;

Procedure SetDropControl( aValue : TWinControl );
Procedure SetEnabledTarget( aValue : Boolean );

protected
{ Protected declarations }
Procedure Loaded; override;
Procedure Notification( aComponent : TComponent; aOperation : TOperation ); Override;

public
{ Public declarations }
Property OleDrag : TMOleDropTarget Read FOleDrag;

Constructor Create( AComponent : TComponent ); Override;
Destructor Destroy( ); Override;

published
{ Published declarations }
Property DropControl : TWinControl Read FDropControl Write SetDropControl;
Property EnabledTarget : Boolean Read FEnabledTarget Write SetEnabledTarget Default true;

property OnDragEnter : TOleDragEnterEvent Read FOnDragEnter Write FOnDragEnter;
property OnDragOver : TOleDragOverEvent Read FOnDragOver Write FOnDragOver;
property OnDragLeave : TOleDragLeaveEvent Read FOnDragLeave Write FOnDragLeave;
property OnDragDrop : TOleDragDropEvent Read FOnDragDrop Write FOnDragDrop;
property OnTextDrop : TOleTextDropEvent Read FOnTextDrop Write FOnTextDrop;
property OnFileDrop : TOleFileDropEvent Read FOnFileDrop Write FOnFileDrop;
property OnURLDrop : TOleTextDropEvent Read FOnURLDrop Write FOnURLDrop;
property OnHTMLDrop : TOleTextDropEvent Read FOnHTMLDrop Write FOnHTMLDrop;
property OnBitmapDrop: TOleBitmapDropEvent Read FOnBitmapDrop Write FOnBitmapDrop;
end;

Var
CF_URL, CF_HTML : UINT;

procedure Register;

implementation

procedure Register;
begin
RegisterComponents('MentalCtrls', [TMOleDragDrop]);
end;

{ TMOleDropTarget }

constructor TMOleDropTarget.Create(aOwner: TMOleDragDrop);
begin
FOwner := aOwner;
OleInitialize( Nil );
With FFormatEtc Do
Begin
cfFormat := CF_TEXT;
ptd := Nil;
dwAspect := DVASPECT_CONTENT;
lIndex := -1;
tymed := TYMED_HGLOBAL;
End;
end;

destructor TMOleDropTarget.Destroy;
begin
FOwner.DropControl := Nil;
OleUninitialize;
inherited;
end;
(*
procedure TMOleDropTarget.AfterConstruction;
begin
// Release the constructor's implicit refcount
InterlockedDecrement(FRefCount);
end;

procedure TMOleDropTarget.BeforeDestruction;
begin
if FRefCount <> 0 then
Error(reInvalidPtr);
end;

// Set an implicit refcount so that refcounting
// during construction won't destroy the object.
class function TMOleDropTarget.NewInstance: TObject;
begin
Result := inherited NewInstance;
TInterfacedObject(Result).FRefCount := 1;
end;

{ IUnknown }
function TMOleDropTarget._AddRef: integer;
begin
Result := InterLockedIncrement( FRefCount );
end;

function TMOleDropTarget._Release: integer;
begin
Result := InterLockedDecrement( FRefCount );
If ( Result = 0 ) Then
Destroy;
end;

function TMOleDropTarget.QueryInterface(const IID: TGUID;
out Obj): HResult;
begin
If ( GetInterface( IID, Obj ) ) Then
Result := S_OK
Else
Result := E_NOINTERFACE;
end;
*)

{ IDropTarget }
function TMOleDropTarget.DragEnter(const aDataObj: IDataObject;
grfKeyState: Integer; pt: TPoint; var dwEffect: Integer): HResult;
Var
pEnumFE : IEnumFormatEtc;
fe : TFormatEtc;
nCount : Integer;
nSupports : Boolean;
begin
FDragResult := E_FAIL;
If ( FOwner.FEnabledTarget ) Then
Begin
dwEffect := DROPEFFECT_NONE;
If ( Assigned( FOwner.FOnDragEnter ) ) Then
Begin
FOwner.FOnDragEnter( Self, aDataObj, grfKeyState, pt, dwEffect, FFormatEtc );
fe := FFormatEtc;
End
Else
Begin
aDataObj.EnumFormatEtc( DATADIR_GET, pEnumFE );
nSupports := false;
While ( ( pEnumFE.Next( 1, fe, @nCount ) = S_OK ) AND ( nCount > 0 ) ) Do
Begin
If ( ( fe.ptd = Nil ) AND ( fe.dwAspect = DVASPECT_CONTENT )
AND ( fe.lindex = -1 )
AND ( ( fe.tymed = TYMED_HGLOBAL ) OR ( fe.tymed = TYMED_GDI ) )
AND ( ( ( ( fe.cfFormat = CF_TEXT ) OR ( fe.cfFormat = CF_UNICODETEXT ) )
AND ( Assigned( FOwner.FOnTextDrop ) ) )
OR ( ( fe.cfFormat = CF_HDROP ) AND ( Assigned( FOwner.FOnFileDrop ) ) )
OR ( ( fe.cfFormat = CF_URL ) AND ( Assigned( FOwner.FOnURLDrop ) ) )
OR ( ( fe.cfFormat = CF_HTML ) AND ( Assigned( FOwner.FOnHTMLDrop ) ) )
OR ( ( ( fe.cfFormat = CF_BITMAP ) OR ( fe.cfFormat = CF_DIB ) )
AND ( Assigned( FOwner.FOnBitmapDrop ) ) )
) ) Then
Begin
nSupports := true;
Break;
End;
End;
If ( nSupports ) Then
Begin
FDragResult := aDataObj.QueryGetData( fe );
If ( Not Failed( FDragResult ) ) Then
dwEffect := DROPEFFECT_COPY;
End;
End;
End;
FCanDrop := FDragResult;
Result := FDragResult;
end;

function TMOleDropTarget.DragLeave: HResult;
begin
FDragResult := S_OK;
If ( Assigned( FOwner.FOnDragLeave ) ) Then
FOwner.FOnDragLeave( Self );
Result := FDragResult;
end;

function TMOleDropTarget.DragOver(grfKeyState: Integer; pt: TPoint;
var dwEffect: Integer): HResult;
begin
FDragResult := S_OK;
If ( Assigned( FOwner.FOnDragOver ) ) Then
FOwner.FOnDragOver( Self, grfKeyState, pt, dwEffect );
Result := FDragResult;
end;

function TMOleDropTarget.Drop(const aDataObj: IDataObject;
grfKeyState: Integer; pt: TPoint; var dwEffect: Integer): HResult;
var
pEnumFE : IEnumFormatEtc;
fe : TFormatEtc;
nCount : Integer;
ss : TStrings;
bm : TBitmap;
begin
FDragResult := E_FAIL;
If ( Assigned( FOwner.FOnDragDrop ) ) Then
FOwner.FOnDragDrop( Self, aDataObj, grfKeyState, pt, dwEffect, FFormatEtc )
Else
Begin
aDataObj.EnumFormatEtc( DATADIR_GET, pEnumFE );
While ( ( pEnumFE.Next( 1, fe, @nCount ) = S_OK ) AND ( nCount > 0 ) ) Do
Begin
If ( ( ( fe.cfFormat = CF_TEXT ) (*OR ( fe.cfFormat = CF_UNICODETEXT )*) )
AND ( Assigned( FOwner.FOnTextDrop ) ) ) Then
FOwner.FOnTextDrop( Self, GetDataText( aDataObj, fe ) )
Else If ( ( fe.cfFormat = CF_URL ) AND ( Assigned( FOwner.FOnURLDrop ) ) ) Then
FOwner.FOnURLDrop( Self, GetDataText( aDataObj, fe ) )
Else If ( ( fe.cfFormat = CF_HTML ) AND ( Assigned( FOwner.FOnHTMLDrop ) ) ) Then
FOwner.FOnHTMLDrop( Self, GetDataText( aDataObj, fe ) )
Else If ( ( fe.cfFormat = CF_HDROP ) AND ( Assigned( FOwner.FOnFileDrop ) ) ) Then
Begin
ss := TStringList.Create;
Try
If ( GetDataFiles( aDataObj, fe, ss ) > 0 ) Then
FOwner.FOnFileDrop( Self, ss );
Finally
ss.Free;
End;
End
Else If ( ( ( fe.cfFormat = CF_DIB ) OR ( fe.cfFormat = CF_BITMAP ) )
AND ( Assigned( FOwner.FOnBitmapDrop ) ) ) Then
Begin
bm := TBitmap.Create;
Try
If ( GetDataBitmap( aDataObj, fe, bm ) ) Then
FOwner.FOnBitmapDrop( Self, bm );
Finally
bm.Free;
End;
End;
End;
End;
Result := FDragResult;
end;

function TMOleDropTarget.DrawBitmap(aDest: TBitmap; aHandle, aPalette: Cardinal): Boolean;

// -----------------------------------------------------------------------------
// Miscellaneous DIB Function
//
// From:
// Project: Drag and Drop Component Suite
// Component Names: TDropBMPSource
// Module: DropBMPSource
// Description: Implements Dragging & Dropping of Bitmaps
// FROM your application to another.
// Version: 3.7
// Date: 22-JUL-1999
// Target: Win32, Delphi 3 - Delphi 5, C++ Builder 3, C++ Builder 4
// Authors: Angus Johnson, ajohnson@rpi.net.au
// Anders Melander, anders@melander.dk
// http://www.melander.dk
// Copyright ?1997-99 Angus Johnson & Anders Melander
// -----------------------------------------------------------------------------

procedure CopyDIBToBitmap(Bitmap: TBitmap; BitmapInfo: PBitmapInfo; DIBSize: integer);
var
BitmapFileHeader : TBitmapFileHeader;
FileSize : integer;
InfoSize : integer;
Stream : TMemoryStream;
begin
// Write DIB to a stream in the BMP file format
Stream := TMemoryStream.Create;
try
FileSize := sizeof(TBitmapFileHeader) + DIBSize;
InfoSize := sizeof(TBitmapInfoHeader);
if (BitmapInfo^.bmiHeader.biBitCount > 8) then
begin
if ((BitmapInfo^.bmiHeader.biCompression and BI_BITFIELDS) <> 0) then
Inc(InfoSize, 12);
end else
Inc(InfoSize, sizeof(TRGBQuad) * (1 shl BitmapInfo^.bmiHeader.biBitCount));
Stream.SetSize(FileSize);
// Initialize file header
FillChar(BitmapFileHeader, sizeof(TBitmapFileHeader), 0);
with BitmapFileHeader do
begin
bfType := $4D42; // 'BM' = Windows BMP signature
bfSize := FileSize; // File size (not needed)
bfOffBits := sizeof(TBitmapFileHeader) + InfoSize; // Offset of pixel data
end;
// Save file header
Stream.Write(BitmapFileHeader, sizeof(TBitmapFileHeader));
// Save TBitmapInfo structure and pixel data
Stream.Write(BitmapInfo^, DIBSize);

// Rewind and load bitmap from stream
Stream.Position := 0;
Bitmap.LoadFromStream(Stream);
finally
Stream.Free;
end;
end;

begin
If ( aPalette <> 0 ) Then
aDest.LoadFromClipboardFormat( CF_BITMAP, aHandle, aPalette )
Else
Begin
Try
CopyDIBToBitmap( aDest, GlobalLock( aHandle ), GlobalSize( aHandle ) );
Finally
GlobalUnlock( aHandle );
End;
End;
Result := true;
end;

function TMOleDropTarget.GetDataText(aDataObj: IDataObject; aFmtEtc: TFormatEtc): String;
Var
medium : stgMedium;
begin
FDragResult := aDataObj.GetData( aFmtEtc, medium );
Result := String( PChar( GlobalLock( medium.hGlobal ) ) );
if ( ( aFmtEtc.cfFormat = CF_UNICODETEXT ) OR ( aFmtEtc.cfFormat = CF_URL )
OR ( aFmtEtc.cfFormat = CF_HTML ) )
Result = Utf8ToAnsi( Result );
GlobalUnlock( medium.hGlobal );
ReleaseStgMedium( medium );
end;

function TMOleDropTarget.GetDataFiles(aDataObj: IDataObject; aFmtEtc: TFormatEtc;
aFiles: TStrings) : Integer;
Var
medium : stgMedium;
i : Integer;
nCount : Integer;
sBuf : Array [0..MAX_PATH - 1] Of Char;
begin
FDragResult := aDataObj.GetData( aFmtEtc, medium );
Try
i := -1;
nCount := DragQueryFile( medium.hGlobal, i, sBuf, 0 ); // Get the Drag _Files Number.
If ( nCount > 0 ) Then
For i := 0 To nCount - 1 Do
If ( DragQueryFile( medium.hGlobal, i, sBuf, MAX_PATH ) > 0 ) Then
aFiles.Add( String( sBuf ) );
DragFinish( medium.hGlobal );
Finally
ReleaseStgMedium( medium );
End;
Result := aFiles.Count;
end;

function TMOleDropTarget.GetDataBitmap(aDataObj: IDataObject; aFmtEtc: TFormatEtc;
aBitmap: TBitmap) : Boolean;
Var
medium : stgMedium;
medium2 : stgMedium;
begin
Result := true;
FDragResult := aDataObj.GetData( aFmtEtc, medium );
If ( aFmtEtc.cfFormat = CF_BITMAP ) Then
Begin
aFmtEtc.cfFormat := CF_PALETTE;
aDataObj.GetData( aFmtEtc, medium2 );
End
Else
FillChar( medium2, SizeOf( medium2 ), 0 );
Try
DrawBitmap( aBitmap, medium.hBitmap, medium2.hBitmap );
Except
Result := false;
End;
If ( aFmtEtc.cfFormat = CF_PALETTE ) Then
ReleaseStgMedium( medium2 );
ReleaseStgMedium( medium );
end;

{ TMOleDragDrop }

constructor TMOleDragDrop.Create(AComponent: TComponent);
begin
Inherited;
FEnabledTarget := true;
FOleDrag := Nil;
If ( Not ( csDesigning In ComponentState ) ) Then
FOleDrag := TMOleDropTarget.Create( Self );
end;

destructor TMOleDragDrop.Destroy;
begin
DropControl := Nil;
inherited;
end;

procedure TMOleDragDrop.Loaded;
begin
inherited;
If ( Assigned( FOleDrag ) AND Assigned( FDropControl ) ) Then
RegisterDragDrop( FDropControl.Handle, FOleDrag );
end;

Procedure TMOleDragDrop.Notification( aComponent : TComponent;
aOperation : TOperation );
Begin
Inherited Notification( aComponent, aOperation );
If ( ( aComponent = FDropControl ) AND ( aOperation = opRemove ) ) Then
DropControl := Nil;
End;

procedure TMOleDragDrop.SetDropControl(aValue: TWinControl);
begin
If ( aValue <> FDropControl ) Then
Begin
If ( Assigned( FOleDrag ) AND Assigned( FDropControl ) ) Then
Begin
If ( ( aValue = Nil ) AND Assigned( FDropControl.Parent ) ) Then
RevokeDragDrop( FDropControl.Handle );
End;
FDropControl := aValue;
If ( Assigned( FOleDrag ) AND Assigned( FDropControl ) ) Then
RegisterDragDrop( FDropControl.Handle, FOleDrag );
End;
end;

procedure TMOleDragDrop.SetEnabledTarget(aValue: Boolean);
begin
If ( aValue <> FEnabledTarget ) Then
FEnabledTarget := aValue;
end;

Initialization
CF_URL := RegisterClipboardFormat( CFSTR_SHELLURL );
CF_HTML := RegisterClipboardFormat( 'HTML Format' );

end.
 
后退
顶部