Как вы копируете произвольные данные в буфер обмена в виде файла? - PullRequest
10 голосов
/ 16 апреля 2009

Разрабатываем приложение базы данных. Пользователь запрашивает новую функцию: скопируйте капли в буфер обмена так, чтобы проводник Windows мог вставить их как новые файлы. Одним из решений является сохранение больших двоичных объектов во временную папку и добавление этих временных файлов в буфер обмена.

Но я ищу лучшее решение. Можно ли подключить действие вставки в проводнике Windows и сохранить капли в путь назначения самостоятельно?

Ответы [ 4 ]

13 голосов
/ 16 апреля 2009

Я никогда не пробовал, но думаю, что это действительно возможно. Пожалуйста, ознакомьтесь с документацией MSDN для форматов буфера обмена Shell . CFSTR_FILECONTENTS и CFSTR_FILEDESCRIPTOR - форматы, которые вы, вероятно, должны обрабатывать.

Кроме того, я нашел статью в Code Project, в которой представлена ​​демонстрационная программа: Как перетащить виртуальный файл из приложения в проводник Windows .

Обновление: Пример, написанный на .NET:

7 голосов
/ 16 апреля 2009

Из статьи MSDN Обработка сценариев передачи данных в оболочке

  • Существующие файлы должны предлагаться в формате CF_HDROP.
  • Предложение файловоподобных данных с CFSTR_FILECONTENTS / CFSTR_FILEDESCRIPTOR форматы. Такой подход позволяет цель создать файл из данных объект без необходимости знать что-нибудь о базовых данных место хранения. Вы должны нормально представить данные как интерфейс IStream. это механизм передачи данных больше гибкий, чем глобальный объект памяти и использует намного меньше памяти.

Две другие хорошие статьи для чтения из MSDN:

Когда я впервые начал работать с буфером обмена для передачи файлов, я распечатал все три статьи и прочитал их несколько раз.

Работа с интерфейсами может быть довольно сложной. Я нашел две хорошие библиотеки, чтобы помочь с этим.

Набор компонентов Drag and Drop для Delphi . Если вы прокрутите вниз на главной странице, вы увидите, что некоторые часто задаваемые вопросы хорошо читаются. Есть также много примеров приложений с загрузкой. Я думаю, что демонстрации AsyncSource должны быть полезны для того, что вы ищете. Пакет бесплатен с источником. Код, кажется, хорошо прокомментирован.

В настоящее время я использую компонент Transfer @ Once из Quasidata. Это не бесплатно, но очень недорого. Первоначально я использовал Transfer @ Once, потому что в то время он лучше поддерживался, чем набор компонентов Drag and Drop. Однако эта ситуация изменилась. Transfer @ Once еще не поддерживает Delphi 2009. Когда я перейду к перемещению своего приложения, я, вероятно, переключу компоненты. Код Transfer @ Once включен в стоимость покупки. Лично я обнаружил, что код перетаскивания гораздо легче читать и следовать.

5 голосов
/ 16 апреля 2009

Я бы сказал, что проводник сам выполняет копирование в файлы назначения, поэтому нет возможности напрямую записать файлы назначения. Это имеет смысл, поскольку имена исходных файлов могут поступать только из приложения, которое скопировало данные в буфер обмена, который не обязательно должен быть проводником. OTOH имена файлов назначения могут фактически отличаться, потому что файлы с тем же именем могут уже существовать в папке назначения, и только проводник может создавать измененные имена для файлов назначения (например, добавляя «Копия» или добавляя « 2) "к основному имени файла).

Вам нужно будет предоставить формат буфера обмена для проводника Windows, чтобы он мог вставлять файлы. Документация стандартных форматов буфера обмена предполагает, что CF_HDROP является правильным. В этом формате буфера обмена вы предоставляете список имен исходных файлов, но файлы, конечно, должны существовать, поэтому вам потребуется , чтобы сохранить их на диск.

Вы можете попытаться сделать процесс как можно более легким. Обычно, когда пользователь копирует данные в буфер обмена, они немедленно помещаются туда, независимо от того, будут ли они использоваться для операции вставки. Для вашего приложения это будет означать, что вам нужно будет каждый раз создавать файлы и помещать список имен файлов в буфер обмена. Однако Windows поддерживает режим с именем Delayed Rendering , который используется именно для таких случаев. По сути, вы помещаете в буфер обмена только пустую заглушку данных, и только когда другое приложение пытается получить доступ к данным, оно будет запрошено вашим приложением. Таким образом, вы можете реализовать это так, что только когда пользователь попытается вставить файлы в проводник, вы сохраните их на диск и вернете список имен файлов.

1 голос
/ 16 апреля 2009

Прошло много времени с тех пор, как я поиграл с копированием / вставкой, но я почти уверен, что вы можете делать то, что предлагаете (вставить каплю как новый файл в буфер обмена).

Кажется, я помню, что в зависимости от того, как вы добавляете в буфер обмена, вы можете указать, какой тип данных вы копируете. Я думаю, что если вы правильно выберете этот тип данных, вы сможете вставить его так, как если бы вы копировали его из проводника Windows.

Я постараюсь выкопать еще кое-что сегодня вечером, если у меня будет возможность (у меня здесь нет всех моих закладок на работе) ...

[Редактировать] Посмотрите документацию wxWidgets по перетаскиванию . Это было то, с чем я работал, и это дает некоторые подсказки о типах данных.

Что ты пишешь? Delphi?

[Edit2] Я думаю, что это может быть ограничением Windows (?). Это может быть просто документация по wxWidgets, но есть предложение, что вы копируете только имена файлов, а не сами файлы . Если это так, то сначала вам нужно будет исходное предложение создать временный файл: - (

...