4

我有一个 ListCtrl 包含一些代表(巨大和远程)文件的项目。我希望用户能够将项目拖到打开的目录窗口中,从而创建一个文件(真正启动下载)。我希望我的应用程序收到类似“用户将您的列表项拖到此路径”的消息,以便我可以继续并将文件数据写入该位置。

如果源文件在本地文件系统上可用,我知道如何做类似的事情,但是我的文件很大并且在远程系统上(想想 FTP 客户端),所以我不能推测性地将它们复制到磁盘以防用户想要拖动'n' 以后再放下它们。

如何使用 wxpython 完成此任务?甚至可能吗?

4

3 回答 3

4

我在网上搜索得很辛苦,但也找不到这样做的方法。甚至 Robin Dunn 也表示,当数据被放入文件系统时,drop source 应用程序对目标一无所知。但我想出了一个简单的方法来做到这一点,至少在 Windows 上是这样。我们只需将包含空 FileDataObject 的 DropSource 拖到资源管理器窗口中。由于没有数据,所有这一切都是将资源管理器窗口带到顶部,这使我们能够获取用户拖入的文件夹的路径。__init__首先,确保在 ListCtrl 的父级的 def 中将事件绑定到 ListCtrl up :

self.lc.Bind(wx.EVT_LIST_BEGIN_DRAG, self.onDrag)

然后在事件调用的方法中执行此操作:

def onDrag(self, event):
    data = wx.FileDataObject()
    obj = event.GetEventObject()
    dropSource = wx.DropSource(obj)

    dropSource.SetData(data)

    #next line will make the drop target window come to top, allowing us
    #to get the info we need to do the work, if it's Explorer
    result = dropSource.DoDragDrop(0)

    #get foreground window hwnd
    h = win32gui.GetForegroundWindow()

    #get explorer location
    s = win32com.client.Dispatch("Shell.Application")
    loc, outdir = None, None
    for w in s.Windows():
        if int(w.Hwnd) == h:
            loc = w.LocationURL
    if loc:
        outdir = loc.split('///')[1]
        outdir = urllib.unquote(outdir)

    #got what we need, now download to outfol
    if outdir and os.path.isdir(outdir):
        self.dloadItems(event, outdir)


    return

dloadItems 方法从 ListCtrl 获取所选项目,然后(在此应用程序中)将项目从 REST 服务器下载到 outdir。

当然,此解决方案需要 pywin32 扩展。

祝你好运,

麦克风

于 2012-12-14T15:11:18.027 回答
1

我不知道如何将它集成到 wxpython 中,但是shell 支持多种剪贴板格式来复制文件。如果文件在网络驱动器上(例如可通过 UNC 路径访问),那么您可以使用像 CF_DROP 格式这样简单的东西。如果没有那么简单,那么您将不得不使用 CFSTR_FILEDESCRIPTOR/CFSTR_FILECONTENTS 格式。这是在 C 或 C++ 中实现的真正苦差事,所以我想它在 python 中会加倍。不过,可能有人已经完成了繁重的工作;你应该看看是否有一个 python 库来处理 shell 剪贴板格式。

于 2012-10-29T20:18:22.310 回答
0

如果您可以在 ListCtrl 中显示数据,那么您可以将列表项绑定到路径。就个人而言,我会使用 ObjectListView ,因为这会使这类事情变得更容易。然后,当您进行拖放时,您可以取出放置的对象并提取路径/ URL。之后,您只需要使用适当的 Python 库,例如 ftplib 或 urllib 来下载文件。

既然您发现我的博客对您很有帮助,我将指出其他一些可能对您有所帮助的教程:

于 2012-10-29T20:57:36.330 回答