на С++.
Когда об объектах говорят в рамках Windows, то имеют в виду
возможность встраивания в некоторый документ фрагмента, порожден-
ного другим приложением. Вот это "инородное тело" и называется
объектом.
В таком подходе нет ничего нового. Когда в текст, подготав-
ливаемый Write, вставляется рисунок из Paintbrush посредством
Clipboard или таблиц Exсel, в документ, подготавливаемый в Word,
то результатом действия будет как раз появления объекта.
Традиционные объекты всегда представляют собой копии. Рабо-
та с ними основывается на том, что все Windows приложения поддер-
живают не только свой собственный формат , но и некоторый обоб-
щенный, стандартный, играющий роль общеизвестного международного
языка. Если, например, в текстовый документ вставляется таблица
из табличного процессора, то буффер промежуточного обмена преоб-
разует ее в формат к стандартному, и тем самым обеспечивает
вставку. Такая копия в текстовом редакторе по виду не отличается
от оригиналу, но она недоступна для внесения изменений. Невозмож-
но, вставив таким способом копию из Paintbrush в Write документ,
изменить цвет, толщину линий или масштаб.
Новые объекты, доступные в рамках Windows 3.1 очень похожи
на традиционные, но они не являются копиями - это оригиналы. Они
имеются в единственном экземпляре и находятся непостредственно в
целевых документах. Там они существуют одновременно в двух форма-
тах - в стандартном и в формате приложения-источника.
Благодаря стандартному формату объект может идицироваться и
сохранять в рамках целевого документа. Имеется возможность обра-
ботки объекта также, как и любого файла оригинала. Ситуация выг-
лядит так, словно внутри объекта встроен другой. Это обеспечи-
вает доступ к средствам обработки нового объекта (приложению-ис-
точнику) посредством простого двойного щелчка на объекте.
Встроенные объекты
Информация, вставленныя в документ целевого приложения,
представляет собой объект. Такой объект встраивается в документ,
обрабатываемый ведущим приложением. Это значит, что он рассматри-
вается как составная часть данного документа, может распечаты-
ваться и сохраняться вместе с ним. Такие объекты могут содержать
информацию любого типа: текст, таблицы, графики и др.
Встроенные объекты существуют только в единственном экзем-
пляре и тлько там, где они встроены - в целевом документе. Обра-
батываются они своими "родительскими" программами, вызываемыми
весьма эффективным спосбом, в отличае от традиционного.
Связывание с родительским приложением
Следующей весьма удобной особенностью встроенных объектов
является то, что они остаются связанными с породившим их приложе-
ниями. Благодаря этому пользователь избавляется от необходимости
помнить имена и директории файлов-источников. Достаточно двойно-
го щелчка на объекте - и родительская программа запускается.
Важным достоинством подобного связывания встроенных объек-
тов является мобильность документов. Можно легко перенести такой
документ с одной машины на другую (необходимо только чтобы на них
обеих была установлена оболочка и были необходимые приложения или
динамические библиотеки от них). Для обработки встроенных объек-
тов достаточно будет щелкнуть по ней дважды и на другой машине
произойдет тоже самое, что и на вашей: вызовется соответсвующее
приложение. В этом случае необходимым условием переноса является
наличие на другой машине текстового редактора Write и графическо-
го редактора Paintbrush.
При работе в рамках DDE такой перенос не возможен, точнее он
будет включать в себя не только перенос самого файла-документа,
но и связанных с данным файлом файлов-источников и целевых фай-
лов - всей структуры.
Перспективы развития OLE
Технология OLE делает только первые шаги. Пока только неко-
торые Windows приложения являются OLE совместимыми. Среди утилит
группы Accessories версии 3.1 такими на сегоднешний день являют-
ся только Write, Paintbrush и Cardfile. Но даже они "в своем кру-
гу" не допускают вставки в произвольном направлении (т.е. из лю-
бой в любую другую). В настаящее время речь идет о поддержке наи-
более оправданного с практической точки зрения "напрвления
встраивания" - из Paintbrush в Write и Сardfile документа.
Чтобы определить какие из приложений поддерживаю OLE интер-
фейс, необходимо из OLE-совместимого приложения выполнить дирек-
тиву "ВСТАВИТЬ ОБЪЕКТ" в меню "Edit". В отрывшемся окне будет
продемонстрирован список доступных встраиваемых объектов.
В настоящий момент многие компиляторы уже ввели поодержку
OLE в свои библиотеки: Borland C++ ver4.5. Пример использования OLE
технологии приведен в приложении 1. Данная программа использует соз-
данный рисунок Paintbrush в виде файла или копирует его из Clipboard.
Заключение
В заключении хотелось бы отметить, что существующие способы
обмена информации возникали вместе с развитием Windows. Как сама
суть Windows, они являются продолжением заложенной в нее цель:
cпособность работать с файлами любых форматов, на любом оборудовании.
В отличие от стандартного решения, когда фирма-производитель обо-
лочки (типа Windows) пыталась сама написать различные драйверы
для поддержки устройств и различные библиотеки для поддержки
форматов многочисленных файлов других пакетов, фирма Microsoft
возложила эту обязанность на производителей оборудования и
программного обеспечения. Таким образом, последовательное разви-
тие Clipboard-->DDE-->OLE является продолжением воплощения
идеи "сам изобрел - сам внедряй". Естесственно, наибольшие на-
дежды сейчас возлагаются на OLE (ее новый стандарт OLE.2), так как
этот стандарт позволяет включать в себя очень мощные средства, такие
как Multimedia. В одном файле может находится не только текст,
рисунок, а и даже целый фильм, полностью озвученный и готовый
к показу.
СПИСОК ЛИТЕРАТУРЫ
1. Гладков С.А. Фролов Г.В. Программирование в Microsoft Windows:
В 2-х частях. М.:"ДИАЛОГ-МИФИ", 1992.
2. Фойц С. Windows 3.1 для пользователя. Пер. с немецкого
Киев:BHV, 1992.
3. Microsoft Windows Software Development Kit. Version 3.
Programmer's Reference, Programming Tools, Windows Extensions.
4. Charles Petzold. Programming Windows. Microsoft Press.
5. Библия Windows 3.X. М.: И.В.К. - Софт, 1992.
6. Borland C++. Usres manual.
Приложение 1. Пример использования OLE технологии
// ObjectWindows - (C) Copyright 1992 by Borland International
//
// oleclnt.cpp
// Пример Ole Client программы, испльзующей OWL. Она показывает
// пример использования Ole functions, и C++ классов .
// Основное окно позволяет пользователю создать paint brush
// object, или копировать его из clipboard.
#include <owl.h>
#include <listbox.h>
#include <string.h>
#include <edit.h>
#include <bwcc.h>
#include <filedial.h>
#include <ole.h>
#include <shellapi.h>
#pragma hdrstop
#include "oleclnte.h"
#include "oleclntr.h"
#include "oleclnt.h"
// статические данные класса
LPOLECLIENTVTBL TOwlClient::lpClientVtbl = NULL;
int TOleDocWindow::nNextObjectNum = 0;
void TOleApp::InitInstance()
{
TApplication::InitInstance();
vcfLink = RegisterClipboardFormat( "ObjectLink" );
vcfNative = RegisterClipboardFormat( "Native" );
vcfOwnerLink = RegisterClipboardFormat( "OwnerLink" );
// comments in owlole.h mention these ole clipboard formats
}
// описание функций OWL Object, которые
// позволяют хранить описание Ole Object
int FAR PASCAL _export StdCallBack(LPOLECLIENT lpClient,
OLE_NOTIFICATION notification,
LPOLEOBJECT lpObject )
{
return (( PTOwlClient )lpClient)->TOleDocWindowThis->
CallBack( lpClient ,
notification,
lpObject );
}
TOwlClient::TOwlClient( PTOleDocWindow owner , HINSTANCE hInst )
{
TOleDocWindowThis = owner;
if ( !lpClientVtbl )
{
lpClientVtbl = new OLECLIENTVTBL;
if ( hInst == 0 ) {
lpClientVtbl->CallBack = StdCallBack;
} else {
lpClientVtbl->CallBack = (TCallBack)
MakeProcInstance( (FARPROC)StdCallBack,
hInst );
}
}
lpvtbl = lpClientVtbl;
}
void TOleDocWindow::WMURedraw( RTMessage )
{
bObjectLoaded = TRUE;
InvalidateRect( HWindow, NULL, TRUE );
UpdateWindow( HWindow );
}
#pragma argsused
int TOleDocWindow::CallBack( LPOLECLIENT lpOleClient ,
OLE_NOTIFICATION oleNot,
LPOLEOBJECT lpOleObject )
{
switch ( oleNot ) {
case OLE_CHANGED:
case OLE_SAVED:
PostMessage( HWindow , WM_U_REDRAW, 0, 0L );
break;
case OLE_CLOSED:
break;
case OLE_QUERY_PAINT:
break;
case OLE_RELEASE:
break;
case OLE_RENAMED:
break;
default:
break;
}
return TRUE;
}
void TOleDocWindow::CMAbout( RTMessage )
{
MessageBox( HWindow , "OLE Client Program\n
Written using ObjectWindows\nCopyright (c) 1992 Borland",
GetApplication()->Name, MB_OK );
}
// создание новой paint brush
void TOleDocWindow::CMPBrush( RTMessage )
{
BackupObject();
bObjectLoaded = FALSE;
lstrcpy( lpszObjectName, GetNextObjectName() );
ret = OleCreate( "StdFileEditing",
(LPOLECLIENT)pOwlClient,
"PBRUSH",
lhClientDoc,
GetApplication()->Name,
&lpObject,
olerender_draw,
0 );
// Создание Ole Object - асинхронная операция.
// Необходимо ожидать его создание, иначе
// могут возникнуть ошибки при обработке
// сообщений этого объекта.
wait( ret , lpObject );
// OleSetHostNames устанавливает имя в сервере OLE.
ret = OleSetHostNames( lpObject, GetApplication()->Name,
lpszObjectName );
wait( ret , lpObject );
}
void TOleDocWindow::CMUndo( RTMessage msg)
{
if ( lpUndoObject )
if ( lpUndoObject != lpObject )
{
LPOLEOBJECT lpObjectToDelete = lpObject;
lpObject = lpUndoObject;
lpUndoObject = NULL;
ret = OleDelete( lpObjectToDelete );
wait( ret , lpObjectToDelete );
bObjectLoaded = bUndoObjectLoaded;
WMURedraw( msg );
}
}
void TOleDocWindow::CMCut( RTMessage msg)
{
CMCopy( msg );
CloseCurrentOle();
}
void TOleDocWindow::CMCopy( RTMessage )
{
if ( OpenClipboard( HWindow ) && EmptyClipboard() )
{
ret = OleCopyToClipboard( lpObject );
check( ret );
CloseClipboard();
}
}
void TOleDocWindow::BackupObject()
{
if ( lpObject )
{
ret = OleClone( lpObject, (LPOLECLIENT)pOwlClient,
lhClientDoc, GetApplication()->Name,
&lpUndoObject );
wait( ret, lpObject );
lstrcpy( lpszLastObjectName, lpszObjectName );
lstrcpy( lpszObjectName , GetNextObjectName() );
bUndoObjectLoaded = bObjectLoaded;
}
}
void TOleDocWindow::CMPaste( RTMessage )
{
if ( OpenClipboard( HWindow ) )
{
BackupObject();
lstrcpy( lpszObjectName, GetNextObjectName() );
ret = OleCreateFromClip( "StdFileEditing",
(LPOLECLIENT)pOwlClient,
lhClientDoc,
lpszObjectName,
&lpObject,
olerender_draw,
0 );
check( ret );
ret = OleSetHostNames( lpObject,
GetApplication()->Name, lpszObjectName );
wait( ret , lpObject );
bObjectLoaded = TRUE;
CloseClipboard();
PostMessage( HWindow , WM_U_REDRAW, 0, 0L );