Запись и чтение данных из буфера обмена — КиберПедия 

Автоматическое растормаживание колес: Тормозные устройства колес предназначены для уменьше­ния длины пробега и улучшения маневрирования ВС при...

Таксономические единицы (категории) растений: Каждая система классификации состоит из определённых соподчиненных друг другу...

Запись и чтение данных из буфера обмена

2020-04-01 74
Запись и чтение данных из буфера обмена 0.00 из 5.00 0 оценок
Заказать работу

Буфер обмена (CLIPBOARD)

 

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

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

В некоторых случаях бывает удобно просмотреть данные, размещенные в буфере обмена – для этих целей Windows содержит специальную программу просмотра содержимого буфера обмена, (Clipboard Viewer). Не надо смешивать между собой сам буфер обмена и программу его просмотра. Буфер обмена реализован несколькими функциями Windows и специальными данными.

При рассмотрении буфера обмена нам надо будет рассмотреть три вопроса:

1) как можно самим класть или читать данные из буфера обмена

2) как можно использовать буфер обмена со стандартным окном–редактором

3) как написать собственную программу просмотра содержимого буфера обмена.

Предварительно мы разберемся с некоторыми основными понятиями, связанными с применением буфера обмена.

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

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

CF_TEXT                        соответствует ASCIIZ тексту

CF_BITMAP                    обычный битмап

CF_DIB                            битмап, независящий от устройства

CF_PALETTE                 палитра (обычно применяется вместе с CF_DIB)

CF_METAFILEPICT      метафайл

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

CF_OWNERDISPLAY             данные, отображаемые пользователем

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

Несколько дополнительных форматов, являясь обычными форматами данных, имеют отличные от них номера. В символических именах таких данных присутствует аббревиатура ‘DSP’

CF_DSPTEXT                 соответствует ASCIIZ тексту

CF_DSPBITMAP             обычный битмап

CF_DSPMETAFILEPICT метафайл

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

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

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

UINT    RegisterClipboardFormat(lpszFormatName);

для уже зарегистрированного формата Вы можете узнать его имя:

int         GetClipboardFormatName(nFormat, lpsBuffer, nMaxCount);

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

Атомы

 

Атомами в Windows называются нумерованные строки текста, хранимые в специальной таблице. Максимальный размер строки 255 символов. При помещении строки в таблицу ей присваивается уникальный номер, который собственно и используется вместо самой строки. Часто атомом называют именно эти номера, а строки — именами атомов. Обе платформы (Windows 3.x и Win32) используют для задания атомов 16-ти разрядные числа, называемые ATOM, что позволяет в одном двойном слове передавать до двух атомов.

Если добавлять две одинаковых строки в таблицу атомов, то они получат одинаковый номер. На этом основан один из способов сравнения строк — добавить обе строки в таблицу и сравнить атомы (не забудьте после этого удалить добавленный атом, даже если это было надо только для проверки).

Для каждого приложения доступны две таблицы атомов - локальная и глобальная. Так как DDE поддерживается между разными приложениями то, очевидно, должна применяться только глобальная таблица атомов.

Для работы с глобальными атомами предназначены следующие функции:

ATOM  GlobalAddAtom(lpszName); UINT    GlobalGetAtomName(aAtom, lpsBuffer, nMaxCount); ATOM  GlobalFindAtom(lpszName);     ATOM  GlobalDeleteAtom(aAtom);

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

Для работы с локальными атомами используются аналогичные функции, но не имеющие в начале слова “Global”. Помимо этого для работы с локальной таблицей атомов добавлена еще одна функция:

ATOM  AddAtom(lpszName);    UINT    GetAtomName(aAtom, lpsBuffer, nMaxCount); ATOM  FindAtom(lpszName);    ATOM    DeleteAtom(aAtom);

BOOL   InitAtomTable(UINT cTableEntries);

Которая позволяет указать максимальное число строк, помещаемых в локальную таблицу атомов. По умолчанию это число равно 37 (размер глобальной таблицы атомов изменить нельзя). При работе с локальной таблицей атомов удалять атомы в конце работы приложения необязательно — при завершении работы всего приложения таблица будет автоматически удалена.

При обмене данными посредством DDE происходит последовательная посылка сообщений от одного приложения к другому и наоборот. Одна DDE транзакция обычно состоит из двух — трех последовательных сообщений. В этих сообщениях часто передаются необходимые имена, представленные в виде глобальных атомов. При этом возникает необходимость так организовать обмен сообщениями, что бы обеспечить удаление всех вновь добавляемых атомов. Для этого принято такое решение: приложение, посылающее атомы вместе с сообщение должно эти атомы создать, а затем проверить код завершения функции PostMessage — если посылка прошла успешно, то атом должен быть освобожден принимающим приложением, а если при посылке возникла ошибка, то атом должно удалить посылющее приложение. В некоторых случаях атом, полученный приложением с сообщением, может быть послан вместе с ответным сообщением назад (кроме сообщения WM_DDE_INITIATE, о чем см. ниже). В этом случае не обязательно атом удалять а потом создавать снова, можно использовать полученный; однако необходимо убедиться, что он был послан с ответным сообщением и, если посылка не состоялась, его надо удалить.

Особенности задания параметра lParam сообщений DDE

 

Следует учесть некоторые различия в применении параметра lParam сообщений DDE на 16–ти и 32–х разрядных платформах (Windows 3.x и Win32). Дело в том, что первоначально этот параметр использовался для передачи двух значений, часто атома имени данных и хендла глобального блока. В случае 32–х разрядной платформы хендл блока сам занимает двойное слово и разместиться в lParam совместно с атомом имени данных не может.

Для решения этой проблемы были введены специальные функции, осуществляющие “упаковку” двух указанных значений (называемых младшим и старшим) в одно двойное слово. Фактически можно считать, что выделяется специальная структура, содержащая пару полей, идентификатор которой используется в качестве lParam.

Так как разные сообщения DDE используют lParam различным образом, то и упаковка данных осуществляется не для каждого сообщения, так что для каждого сообщения надо проверять необходимость использования этого механизма, а для сообщения WM_DDE_ACK надо еще проверить, в ответ на какое сообщение он послан. Для работы с “упакованными” данными необходимо применять специальные функции:

LONG  PackDDElParam(UINT uMsg, UINT uLow, UINT uHigh);     LONG  UnpackDDElParam(UINT uMsg, LONG lParam, PUINT puLow, PUINT puHigh);    LONG  FreeDDElParam(UINT uMsg, LONG lParam);     LONG  ReuseDDElParam(          LONG lParam, UINT uMsgIn, UINT uMsgOut, UINT uLow, UINT uHigh);

Функция PackDDElParam упаковывает указанные данные в промежуточную структуру, хендл которой возвращается в виде LONG; возвращаемое значение может быть использовано только для передачи данных с помощью функции PostMessage и только для некоторых сообщений DDE. Функция UnpackDDElParam выполняет обратную операцию, но промежуточная структура данных при этом сохраняется. Для того, что бы ее удалить необходимо использовать FreeDDElParam. Последняя функция ReuseDDElParam может применяться для использования одной структуры при повторной передаче данных или ответе на принятое сообщение. В качестве параметра lParam функции PostMessage необходимо указывать возвращаемое, а не первоначальное значение.

В описании параметров сообщений мы сохраняем прежний синтаксис, причем lParam может по–прежнему задаваться в виде двух компонент старший & младший. Единственное отличие, что под старшим и младшим компонентом не надо подразумевать слова, а для получения этих компонентом может потребоваться функция UnpackDDElParam, о чем в описании сообщения будет сделана специальная оговорка. В редких случаях могут даваться два описания параметров, для Windows 3.x и для Win32. Для различия этих вариантов в описании параметров сообщения могут быть добавлены специальные пояснения

(Packed Win32) — если параметр упаковывается в случае платформы Win32

(Windows 3.x) — если описание применяется только в случае Windows 3.x

(Win32) — если описание применяется только в случае Win32

Выполнение команд DDE

 

Помимо механизма обмена данными между клиентом и сервером DDE предусматривает еще один способ взаимодействия приложений — выполнение сервером команд клиента. Для того, что бы указать серверу на необходимость выполнения команды, клиент должен послать специальное сообщение WM_DDE_EXECUTE, в ответ на которое сервер пытается выполнить команду и сообщает клиенту о результате ее выполнения, посылая в ответ сообщение WM_DDE_ACK (положительное или отрицательное).

 

 

WM_DDE_EXECUTE                       hWnd hCmd & 0 (Windows 3.x)

WM_DDE_EXECUTE                       hWnd       hCmd (Win32)

Параметр lParam описывает команду, передаваемую серверу. Для этого строка, содержащая команду, помещается в блок данных, выделяемый с помощью функции GlobalAlloc с флагом GMEM_DDESHARE. В случае платформы Windows 3.x старшее слово параметра lParam содержит хендл этого блока, а младшее — просто 0; А в случае платформы Win32 параметр lParam непосредственно содержит этот хендл. Освобождение ресурсов: блок данных, содержащий команду, должен быть освобожден клиентом при получении подтверждения от сервера. Вместе с этим подтверждением возвращается хендл этого блока, так что клиент свободно может его освободить.

В случае платформы Win32 строка, содержащая команду может быть представлена UNICODE–строкой, но только в том случае, если оба участвующие в DDE–разговоре окна поддерживают UNICODE, то есть оба возвращают TRUE при вызове функции IsWindowUnicode(hWnd).

В ответ на сообщение WM_DDE_EXECUTE сервер посылает сообщение WM_DDE_ACK, информирующее о выполнении команды (положительное) или о неудаче (отрицательное). В этом сообщении возвращается хендл блока, содержащего команду, так что сервер может этот блок удалить, а также в параметре wStatus — в младшем байте — может быть возвращен дополнительный код, уточняющий результат или причину ошибки (см. описание структуры DDEACK, представляющей параметр wStatus в разделе, посвященном холодной связи).

WM_DDE_ACK hWnd                   hCmd & wStatus (Packed Win32)

Младший компонент lParam содержит информацию о посылаемом подтверждении. Младший байт этого слова содержит код, возвращаемый приложением, старший байт содержит два значащих бита 0x80 и 0x40. Часто этот параметр представляется в виде структуры DDEACK. Старший компонент lParam представляет собой хендл блока, содержащего команду. Согласно документации этот блок обязательно должен быть освобожден при обработке этого сообщения. В случае платформы Win32 параметр lParam используется для передачи хендла “упакованных” данных.

При разработке собственных DDE–серверов, исполняющих какие–либо команды, надо обратить внимание на формат записи этих команд. Разработчики Microsoft предполагают совершенно определенный формат записи команд, который, к сожалению, часто не поддерживается сторонними разработчиками. Конечно, с точки зрения совместимости, желательно придерживаться этого формата.

В соответствии с документацией Microsoft команда должна представлять собой строку, оканчивающуюся нулевым символом и содержащую одну или несколько команд. Каждая команда должна быть заключена в квадратные скобки […]. Каждая команда состоит из двух частей — имени команды и, возможно, списка параметров. При этом список параметров заключается в круглые скобки, а параметры в списке разделяются запятыми. Имя команды не может содержать пробелов, скобок, запятых и кавычек; параметры могут содержать эти символы, но в таком случае такой параметр должен быть заключен в кавычки, а символ кавычек в тексте параметра представляется как повторяющаяся кавычка. В прежних версиях DDE — для Windows 3.x — требовалось, что бы символы () [ ], встречаемые в тексте параметра (в кавычках) дублировались; в то время как в Win32 это уже не требуется. Проблема, однако, существует — в среде Win32 могут быть запущены как 16–ти разрядные приложения, так и 32–х разрядные, при этом возможно взаимодействие таких приложений посредством DDE. В такой ситуации серверы должны распознавать оба варианта представления скобок — как повторяющиеся, так и не повторящиеся.

Примеры для Win32:

[команда] [команда1][команда2][команда_с_параметрами(параметр1,параметр2)][командаN]     [команда(параметр1,”параметр2 с пробелами, скобками []() и “” кавычками”)]

В случае Windows 3.x последний пример будет выглядеть так:

[команда(параметр1,”параметр2 с пробелами, скобками [[]](()) и “” кавычками”)]

Если строка содержит несколько заключенных в квадратные скобки команд, то сервер должен разобрать эту строку по командам и обработать их последовательно. Вариант с передачей нескольких команд в одной строке имеет одно неудобство — возвращается результат выполнения всей последовательности команд, причем понять где возникла ошибка (скажем, синтаксис команды или недостаток свободных ресурсов) будет практически невозможно.


Тема DDE–разговора “System”

 

Согласно документации Microsoft всем вновь разрабатываемым DDE–серверам рекомендуется поддерживать в каждом сервисе специальную служебную тему DDE–разговора “System”. Эта тема предназначена для получения основной информации о сервере. В пределах этой темы определено несколько стандартных имен данных, к которым можно обратиться для получения требуемой информации.

К сожалению сами разработчики Microsoft не очень строго соблюдают это правило. Так, например, Microsoft Word и Microsoft Excel поддерживают эту тему, а Program Manager, Explorer, Internet Explorer — не поддерживают. Однако документация остается документацией, поэтому при разработке собственных DDE–серверов стоит придерживаться предлагаемых правил.

При обмене данными с серверами, поддерживающими тему “System” надо придерживаться следующих правил:

· для получения данных используется холодная связь

· данные предоставляются только в формате CF_TEXT

· по многим запрашиваемым данным возвращается список значений. Этот список представлен в виде строки, оканчивающейся нулевым символом, отдельные пункты которой отделяются символом табуляции (код — 9).

· При использовании DDEML имя темы “System” определено в файле DDEML.H как SZDDESYS_TOPIC.

Помимо темы “System” предусмотрен специальное название данных, которые должны поддерживаться во всех остальных темах, с помощью которого можно получить информацию о всех поддерживаемых именах данных в данной теме.

При разработке собственного сервера не обязательно поддерживать все приведенные данные, равно как не обязательно вообще поддерживать тему “System” (хотя это желательно). Если Вы поддерживаете только некоторые данные этой темы, обратите внимание на данные “SysItems”, которые позволяют клиенту узнать, какие именно данные можно запрашивать.

 

Название темы для DDE Название темы для DDEML Описание
Formats SZDDESYS_ITEM_FORMATS Возвращает список поддерживаемых сервером форматов данных. Обычно названия совпадают с названиями форматов буфера обмена, но первые три символа “CF_” опущены. То есть формат CF_BITMAP будет представлен как BITMAP. Рекомендуется так упорядочивать названия форматов в списке, что бы форматы передающие больше информации были первыми. То есть, например, формат DIB должен быть расположен до формата BITMAP.
Help SZDDESYS_ITEM_HELP Пояснения к использованию данного DDE сервера. Достаточно произвольный текст, желательно поясняющий, какие данные могут быть получены, какие команды могут быть выполнены какие данные могут быть переданы серверу и т.д.
ReturnMessage SZDDESYS_ITEM_RTNMSG Информация о последнем отправленом подтверждении WM_DDE_ACK. С помощью этого типа данных можно передавать дополнительные данные, уточняющие результат выполнения последней транзакции.
Status SZDDESYS_ITEM_STATUS В ответ на этот запрос сервер должен отправить строку “Busy” или “Ready”, информирующую о состоянии сервера. Заметьте, что эту строку сервер должен посылать, даже если он занят и не может обрабатывать иные запросы.
SysItems SZDDESYS_ITEM_SYSITEMS Возвращает список имен данных, которые представлены в теме “System”. Этот список может использоваться клиентом, что бы узнать, какие данные он может запрашивать в рамках темы “System”.
Topics SZDDESYS_ITEM_TOPICS Возвращает список тем, поддерживаемых сервером в данный момент времени. В процессе работы сервера этот список может изменяться, так, например, Microsoft Word открывает отдельную тему для работы с каждым загруженным документом.
TopicItemList SZDDE_ITEM_ITEMLIST Аналогично SysItems, возвращает список данных, поддерживаемых для данной темы. Этот запрос может применяться к темам, не являющимися темой “System”. Этот список может изменяться в процессе работы сервера.

Буфер обмена (CLIPBOARD)

 

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

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

В некоторых случаях бывает удобно просмотреть данные, размещенные в буфере обмена – для этих целей Windows содержит специальную программу просмотра содержимого буфера обмена, (Clipboard Viewer). Не надо смешивать между собой сам буфер обмена и программу его просмотра. Буфер обмена реализован несколькими функциями Windows и специальными данными.

При рассмотрении буфера обмена нам надо будет рассмотреть три вопроса:

1) как можно самим класть или читать данные из буфера обмена

2) как можно использовать буфер обмена со стандартным окном–редактором

3) как написать собственную программу просмотра содержимого буфера обмена.

Предварительно мы разберемся с некоторыми основными понятиями, связанными с применением буфера обмена.

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

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

CF_TEXT                        соответствует ASCIIZ тексту

CF_BITMAP                    обычный битмап

CF_DIB                            битмап, независящий от устройства

CF_PALETTE                 палитра (обычно применяется вместе с CF_DIB)

CF_METAFILEPICT      метафайл

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

CF_OWNERDISPLAY             данные, отображаемые пользователем

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

Несколько дополнительных форматов, являясь обычными форматами данных, имеют отличные от них номера. В символических именах таких данных присутствует аббревиатура ‘DSP’

CF_DSPTEXT                 соответствует ASCIIZ тексту

CF_DSPBITMAP             обычный битмап

CF_DSPMETAFILEPICT метафайл

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

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

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

UINT    RegisterClipboardFormat(lpszFormatName);

для уже зарегистрированного формата Вы можете узнать его имя:

int         GetClipboardFormatName(nFormat, lpsBuffer, nMaxCount);

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

Запись и чтение данных из буфера обмена

 

Общие правила работы с буфером обмена сводятся к следующему:

1) Вся работа с буфером обмена должна проводиться за время обработки одного сообщения. Во время работы с буфером Вы не должны вызывать никаких функций, которые могут передать управление другому приложению. То есть Вы не должны использовать функций типа: DialogBox, MessageBox, GetMessage, PeekMessage.

Данные должны размещаться только в перемещаемом блоке глобальной памяти.

Когда буфер обмена получает данные, он объявляет себя владельцем этих данных, так что приложение больше не должно использовать переданные данные. Более того, эти данные нельзя удалять при завершении работы Вашего приложения - когда будет надо, буфер обмена сам удалит их.

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

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

2) Перед началом обмена данными с буфером обмена Вы должны его открыть. Делается это с помощью функции

BOOL   OpenClipboard(hWnd);

если Вы положите какие-либо данные в буфер, то окно, указанное Вами, будет считаться владельцем всех данных буфера обмена.

3) Затем Вы можете осуществить необходимые операции обмена данными. Если Вы собираетесь положить данные в буфер обмена, то Вы должны предварительно удалить все уже находящиеся в нем данные:

BOOL   EmptyClipboard(void);

и только затем положить нужные данные, воспользовавшись функцией:

HGLOBAL    SetClipboardData(nFormat, hGlobal);

параметр nFormat задает имя формата данных, а hGlobal является хендлом глобального блока данных. Функция возвращает Вам новый хендл этого блока данных, с помощью которого Вы можете обращаться к этим данным до закрытия буфера обмена.

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

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

WM_RENDERFORMAT                  nFormat                       0L

сообщение требует данные для буфера обмена. При этом буфер уже открыт другим приложением, поэтому Вам открывать или закрывать его не надо. Вам надо просто вызвать функцию

SetClipboardData(nFormat, hGlobal);

передав ей хендл реального блока данных.

WM_RENDERALLFORMATS, 0, 0L

сообщение посылается Вашему окну когда оно уничтожается, а буфер обмена содержит задержанные данные Вашего окна. Вы должны обычным образом (то есть открыть–очистить–положить–закрыть) передать все данные в буфер обмена.

WM_DESTROYCLIPBOARD, 0, 0L

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

Если Вы собираетесь только читать данные из буфера обмена, то очищать его не надо, а получить данные нужного формата можно с помощью функции

HGLOBAL    GetClipboardData(nFormat);

Функция возвращает хендл глобального блока памяти, который Вы должны скопировать к себе.

4) После завершения обмена с буфером обмена Вы должны закрыть его с помощью функции

BOOL   CloseClipboard(void);

На этом заканчиваются операции обмена данными с буфером обмена.

Кроме рассмотренных, Вы можете применять еще несколько функций, облегчающих работу с буфером обмена:

BOOL   IsClipboardFormatAvailable(nFormat);

Эта функция сообщает, присутствуют–ли данные нужного формата в буфере обмена. Проверку на наличие тех или иных форматов данных можно выполнить и иным способом, с помощью функции

UINT    EnumClipboardFormats(nFormat);

Эта функция перебирает присутствующие форматы данных в буфере обмена и возвращает номер следующего в списке или 0. Пример применения:

UINT nFormat= 0;

while ((nFormat= EnumClipboardFormats(nFormat))!= 0) { // перебор форматов }

Можно узнать количество присутствующих в буфере обмена форматов данных с помощью функции

UINT    CountClipboardFormats(void);

5) Сейчас мы рассмотрим правила применения форматов данных CF_DSP... Эти данные предназначены для использования только Вашим приложениями.

Основная идея заключается в том, что приложения, читающие, скажем, формат CF_TEXT, его и будут запрашивать у буфера обмена. При этом, даже если буфер обмена содержит данные в формате CF_DSPTEXT, он их не передаст – номера форматов разные, поэтому считается, что Вы можете передавать данные в формате CF_DSP... только для своего приложения, “спрятав” его от остальных.

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

HWND GetClipboardOwner(void);

которая вернет хендл окна, положившего данные. Если вы затрудняетесь по хендлу определить принадлежность окна к нужному приложению, то Вы почти наверняка знаете, к какому классу оно должно принадлежать (так как и данные, и приложение, и класс окон разработаны Вами). Поэтому Вы можете узнать еще и имя класса окна:

int         GetClassName(hWnd, lpsBuffer, nMaxCount);


Поделиться с друзьями:

История развития хранилищ для нефти: Первые склады нефти появились в XVII веке. Они представляли собой землянные ямы-амбара глубиной 4…5 м...

Особенности сооружения опор в сложных условиях: Сооружение ВЛ в районах с суровыми климатическими и тяжелыми геологическими условиями...

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

Биохимия спиртового брожения: Основу технологии получения пива составляет спиртовое брожение, - при котором сахар превращается...



© cyberpedia.su 2017-2024 - Не является автором материалов. Исключительное право сохранено за автором текста.
Если вы не хотите, чтобы данный материал был у нас на сайте, перейдите по ссылке: Нарушение авторских прав. Мы поможем в написании вашей работы!

0.131 с.