📄 dragdrop2.c
字号:
#define STRICT
#include <windows.h>
#pragma hdrstop
#include <string.h>
#include <windowsx.h>
#include <stdio.h>
#include <shlobj.h>
#include <shellapi.h>
//#include "dragdrop.h"
//*
char *WhoAmI(struct FileList *ptr);
void WMDropFiles( WPARAM WParam, HWND hWnd);
struct FileList {
char *lpFileName; // Name of dragged file
int x, y; // Position in client area dropped
BOOL inClient; // Dropped in client Flag
struct FileList *Next; // Points to next file in group dragged
};
struct List {
struct List *Next; // Points to next node in List
struct FileList *FLptr; // Points to Filelist(s)
};
struct List *liAllFiles; // Pointer to main list of files
//*/
// Global variables
void AddFiles(HWND, struct List*);
void FileDrop( struct FileList* ptr, char *FileName , int px, int py,BOOL inClientarea );
void AddFiles( HWND hWnd, struct List *pliFiles );
void deleteFileList( struct FileList *pFList);
void deleteList( struct List *pliFiles);
BOOL InitApplication(HINSTANCE hInstance);
BOOL GetHelp;
HINSTANCE hInst; // current instance
/********************************************************************/
void FileDrop( struct FileList* ptr, char *FileName , int px, int py,
BOOL inClientarea )
{
ptr->lpFileName =(char*)malloc(strlen( FileName ) + 1 );
strcpy( ptr->lpFileName, FileName );
ptr->x = px;
ptr->y = py;
ptr->inClient = inClientarea;
ptr->Next=NULL;
}
char *WhoAmI(struct FileList *ptr)
{
static char buffer[ 512 ];
// wsprintf( buffer, "File: %s [ %d , %d ] inClient: %d",
// (LPSTR)ptr->lpFileName, ptr->x , ptr->y, ptr->inClient );
wsprintf( buffer, "%s\0",(LPSTR)ptr->lpFileName);
//WARNING!!: Serious problem recognized:
//In the small model, without the typecast,
//lpFileName was two bytes on the stack of which
//wsprintf took 4.
return buffer;
}
void WMDropFiles( WPARAM WParam, HWND hWnd)
/*********************************************************
Step 3:
Retrieve a handle to an internal data structure in
SHELL.DLL. Get the info of the files out of it.
**********************************************************/
{
struct FileList *FLptr, *FLCurrent=NULL, *FLHead=NULL;
struct List *liFiles;
int TotalNumberOfFiles;
int nFileLength;
char *pszFileName;
POINT pPoint;
BOOL inClientArea;
int i;
/********************************************************
Step 4:
Identify the handle
*********************************************************/
HANDLE Handle = (HANDLE)WParam;
//WParam contains the Handle to the
//internal data structure which has
//information about the dropped file(s)
/****************************************************************
Step 5:
Find out total number of files dropped, by passing -1 for
the index parameter to DragQueryFile
*****************************************************************/
TotalNumberOfFiles = DragQueryFile( Handle , -1, NULL, 0 );
GetHelp=FALSE;
liFiles =(struct List*)malloc(sizeof(struct List));
for ( i = 0; i < TotalNumberOfFiles ; i++ )
{
/************************************************************
Step 6:
Get the length of a filename by telling DragQueryFile
which file your querying about ( i ), and passing NULL
for the buffer parameter.
*************************************************************/
nFileLength = DragQueryFile( Handle , i , NULL, 0 );
pszFileName = (char*)malloc(nFileLength + 1);
/************************************************************
Step 7:
Copy a file name. Tell DragQueryFile the file
your interested in (i) and the length of your buffer.
NOTE: Make sure that the length is 1 more then the filename
to make room for the null charater!
*************************************************************/
DragQueryFile( Handle , i, pszFileName, nFileLength + 1 );
//copies over the filename
/**************************************************************
Step 8:
Getting the file dropped. The location is relative to your
client coordinates, and will have negative values if dropped
in the non client parts of the window.
DragQueryPoint copies that point where the file was dropped
and returns whether or not the point is in the client area.
Regardless of whether or not the file is dropped in the client
or non-client area of the window, you will still receive the
file name.
***************************************************************/
inClientArea = DragQueryPoint( Handle , &pPoint );
FLptr= (struct FileList*)malloc(sizeof(struct FileList));
if(FLHead == NULL)
FLHead = FLptr;
FileDrop(FLptr, pszFileName , pPoint.x, pPoint.y , inClientArea );
// Add new struct to FileList structure list
if(FLHead != FLptr)
{
FLCurrent->Next=FLptr;
FLCurrent=FLptr;
FLptr->Next=NULL;
}
else
{
FLHead->Next=NULL;
FLCurrent = FLHead;
}
}
liFiles->FLptr=FLHead; // Point to first FileList struct in list
AddFiles( hWnd, (struct List*)liFiles ); //Add this sublist of dropped files
//to the big list.
/************************************************************
Step 9:
Release the memory shell allocated for this handle
with DragFinish.
NOTE: This is an easy step to forget and could
explain memory leaks and incorrect program performance.
*************************************************************/
DragFinish( Handle );
free(pszFileName);
}
/************************************************************/
void AddFiles( HWND hWnd, struct List *pliFiles )
{
if(liAllFiles==NULL)
{
liAllFiles=pliFiles;
liAllFiles->Next=NULL;
}
else
{
pliFiles->Next=liAllFiles; // Put at front of list
liAllFiles=pliFiles;
}
InvalidateRect( hWnd, NULL, TRUE );
UpdateWindow( hWnd );
}
/************************************************************
Delete FileList structures on linked list
*************************************************************/
void deleteFileList( struct FileList *pFList)
{
if(pFList->Next != NULL)
deleteFileList(pFList->Next); // Recursion - delete next FileList struct
free(pFList->lpFileName); // free string allocation
free(pFList); // free structure FileList
}
/************************************************************
Delete List structures on linked list
*************************************************************/
void deleteList( struct List *pliFiles)
{
if(pliFiles != NULL)
{
if(pliFiles->Next != NULL)
deleteList(pliFiles->Next); // Recursion - delete next List struct
if(pliFiles->FLptr != NULL)
deleteFileList(pliFiles->FLptr);// Initial call to free FileList
free(pliFiles); // free List struct
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -