При открытом окне диалога Insert Control вы можете просто ввести букву O — начальную букву нашего элемента OpenGL. Теперь, используя клавиши навигации по списку (стрелки), вы быстро найдете в нем строку OpenGL Class. Выберите ее и нажмите OK. Вы должны увидеть окно внедренного элемента, которое выглядит так, как показано на рисунке.
Стартовая заготовка элемента ActiveX в окне тестового контейнера
Когда клиент COM-объекта пользуется услугами локального или удаленного сервера (то есть когда данные передаются через границы различных процессов или между узлами сети), требуется поддержка маршалинга (marshaling). Так называется процесс упаковки и посылки параметров, передавемых методам интерфейсов, через границы потоков или процессов, который мы слегка затронули ранее. Вы помните, что MIDL генерирует код на языке С для двух компонент: Proxy (представитель COM-объекта на стороне клиента) и Stub (заглушка на стороне COM-сервера).
Эти компоненты общаются между собой и решают проблемы Вавилонской башни, то есть преодолевают сложности обмена данными, возникающие из-за того, что клиент и сервер используют различные типы данных (разговаривают на разных языках). Поистине, чтобы увидеть проблему, надо ее создать.
Интересно то, что при объяснении необходимости этого чудовищного сооружения из:
¨ idl-файла,
¨ кода заглушек (proxy и stub) в вашем рабочем пространстве (см. файлы в папке ATLGLPS),
¨ структуры VARIANT, которую надо использовать (или просто иметь в виду), приводится соображение о том, что программы на разных языках программирования смогут общаться, то есть обмениваться данными. Как мы уже обсуждали, разработчики имеют в виду четыре COM-совместимых языка, два из которых реально используются (Visual C++ и Visual Basic), а два других (VBScrit и Visual J++) едва подают признаки жизни. Здесь надо учесть бурно развивающийся язык C#, который тоже поддерживает движение COM, но не рекомендует создавать новые компоненты в старом (тем, которым мы сейчас пользуемся) стиле.
Откройте и проанализируйте код файла ATLGL.idl. Постарайтесь вникнуть в смысл описаний. Прежде всего отметьте, что в библиотеке типов (library ATLGLLib), сопровождающей COM-объект, появилось описание COM-класса, который предоставляет своим пользователям два интерфейса.
coclass OpenGL
{
[default] interface IOpenGL;
[default, source] dispinterface _IOpenGLEvents;
};
Предшествующий классу блок описаний в квадратных скобках носит вспомогательный характер, поэтому я не привел его здесь. Элементы ActiveX используют события (events) для того, чтобы уведомить приложение-контейнер об изменениях в состоянии объекта в результате действий пользователя. Найдите описание одного из объявленных интерфейсов:
dispinterface _IOpenGLEvents
{
properties:
methods:
};
Пока пустые секции properties: и methods: намекают на то, что мы должны приложить усилия для того, чтобы ввести (с помощью инструментов студии) в разрабатываемый COM-объект способность общения с клиентом. Этот дуальный интерфейс появился потому, что мы (в момент создания COM-объекта) задали поддержку Connection Points.
Информация о втором интерфейсе расположена вне блока, описывающего библиотеку типов:
interface IOpenGL : IDispatch
{
[propput, id(DISPID_FILLCOLOR)]
HRESULT FillColor([in]OLE_COLOR clr);
[propget, id(DISPID_FILLCOLOR)]
HRESULT FillColor([out, retval]OLE_COLOR* pclr);
};
Интерфейс IOpenGL предоставляет своим пользователям двойной (dual) интерфейс. Эта штука опять понадобилось для того, чтобы VBScrit-сценарий мог использовать COM-объекты, созданные с помощью Visual C++. Клиенты, созданные на языке С++, могут (с помощью QueryInterface) получить адрес интерфейса и вызывать его методы, пользуясь таблицей виртуальных функций (vtable), например:
p->SomeMethod(i, d);
Уважаемый посетитель!
Чтобы распечатать файл, скачайте его (в формате Word).
Ссылка на скачивание - внизу страницы.