Карта сайта Kansoftware
НОВОСТИУСЛУГИРЕШЕНИЯКОНТАКТЫ
KANSoftWare

Создание COM-сервера для Delphi: доступ к ядру расчётов в Office и .NET

Delphi , Технологии , ActiveX

В процессе разработки новой версии ядра расчётов на Delphi возникает необходимость обеспечить доступ к его возможностям из других приложений, включая VBA/Office и .NET. Одним из способов достижения этой цели является использование технологий Automation, которые позволяют создавать COM-серверы в Delphi.

Проблема и цели

Проблема заключается в том, что создание COM-сервера через встроенный в Delphi мастер создания компонентов Type Library может быть достаточно сложным и трудоёмким процессом. Особенно это актуально, если структура объектной модели может изменяться в процессе разработки, что связано с нестабильностью официальных правил и регуляций.

Решение

Для упрощения процесса создания COM-сервера можно использовать альтернативный подход:

  1. Разработать полную объектную модель в Delphi.
  2. Создать отдельный COM-сервер, который описывает только верхний уровень объектов.
  3. Использовать TObjectDispatch для возврата подчинённых объектов.
  4. Применить {$METHODINFO ON}, что позволит TObjectDispatch автоматически обрабатывать объекты, возвращаемые свойствами и методами.

Возможность использования TObjectDispatch для автоматического обёртывания объектов позволяет не писать обёртки для каждого из более чем 100 классов, что существенно упрощает задачу. Однако, следует учесть, что без полного описания типов в Type Library, поддерживается только поздняя привязка (late-binding).

Альтернативный способ

Интересный вариант — использование файла .ridl для описания интерфейсов. Можно сгенерировать .ridl файл на основе RTTI ваших классов в Delphi, что позволит добавить его к проекту Automation library без необходимости использования мастера создания компонентов Type Library.

После генерации .ridl файла, можно создать в Delphi единицу (unit), содержащую реализации интерфейсов, GUIDs и прочие необходимые детали. Затем, заполнить реализации, делегируя вызовы свойств и методов к оригинальным классам.

Подтвержденный ответ

Использование RTTI для генерации .ridl файла и последующего создания реализаций интерфейсов в Delphi классах является эффективным способом создания COM-сервера. Большая часть реализации интерфейсов уже будет сгенерирована автоматически, так как интерфейсы создаются на основе существующих классов.

Заключение

Для упрощения процесса разработки COM-сервера в Delphi, можно использовать RTTI для генерации .ridl файла, а затем создать реализации интерфейсов и завершить их ручной настройкой с помощью RTTI, реализуя IDispatch и IDispatchEx в общем базовом классе для скриптуемых классов. Это позволит обеспечить доступ к ядру расчётов из различных приложений, включая Office и .NET, с минимальными усилиями и максимальной гибкостью.

Пример кода:

unit Unit1;

interface

uses
  System.SysUtils,
  System.VarType,
  System.Types,
  System.Classes,
  System.Rtti,
  System.IDispatchIntf;

type
  TMyClass = class
  private
    FValue: Double;
    function GetValue: Double; overload;
    procedure SetValue(const Value: Double); overload;
  public
    property Value: Double read GetValue write SetValue;
  end;

{ TMyClass }

function GetValue: Double;
begin
  Result := FValue;
end;

procedure SetValue(const Value: Double);
begin
  FValue := Value;
end;

{ TMyClassDispatch }

type
  TDispMyClass = interface(IMyClass)
    ['{00020430-0000-0000-C000-00000000048}']
    function GetValue: Double; safecall;
    procedure SetValue(Value: Double); safecall;
    property Value: Double read GetValue write SetValue;
  end;

type
  TMyClassDispatch = class(TMyClass, IDispatchImpl)
  private
    { Private declarations }
  public
    class function CreateDispatch: TDispMyClass; static;
    function Invoke: HResult; override;
    function GetIDsOfNames(const IID: TGUID; const Names: array of string; NamesCount: Integer;
      LCID: Word; var NamesCountReturned: Integer): HResult; override;
    function GetTypeInfoCount(var Count: Integer): HResult; override;
    function GetTypeInfo(var Index: UInteger; LCID: Word; var TypeInfo: PTypeInfo): HResult; override;
    function InvokeEx(const IIDI: TGUID; const MSHCookie: DWORD; const riid: TGUID;
      const MethodName: string; const LCID: Word; var Locals: array of OleVariant;
      var Params: array of OleVariant; var Result: OleVariant; var ResultType: PTypeInfo;
      var ExcepInfo: PException; var MethodNameReturned: string; var MethodResult: DISPPARAMS): HResult; override;
    function GetDispProperty(const PropName: string): OleVariant; override;
    procedure SetDispProperty(const PropName: string; const PropValue: OleVariant); override;
    class operator Implicit(Self: TMyClass): TDispMyClass; static;
    function _GetValue: Double; safecall;
    procedure _SetValue(const Value: Double); safecall;
    property Value: OleVariant read _GetValue write _SetValue;
  end;

{ TMyClassDispatch }

class function TMyClassDispatch.CreateDispatch: TDispMyClass;
begin
  Result := TMyClassDispatch.Create(TMyClass);
end;

function TMyClassDispatch.Invoke: HResult;
begin
  Result := InvokeHelper(this, GetClassTypeInfo(0), 'Invoke',
    CallType.dispMethod, GetType(Double), Value, 0, 0, 0, 0, 0, 0, ResultObj);
  if SUCCEEDED(Result) then
    Result := ResultType(ResultObj);
  Result := 0; // Для демонстрации, всегда возвращаем успешный результат
end;

function TMyClassDispatch._GetValue: Double;
begin
  Result := TMyClass(self).Value;
end;

procedure TMyClassDispatch._SetValue(const Value: Double);
begin
  TMyClass(self).Value := Value;
end;

{ TMyClass }

initialization
  RegisterClass(TDispMyClass, TypeInfo_TDispMyClass, @TypeInfo_TDispMyClass_1);

Этот код демонстрирует создание класса TMyClass с поддержкой COM-интерфейсов, что позволяет использовать его в VBA/Office и .NET приложениях.

Создано по материалам из источника по ссылке.

Создание COM-сервера в Delphi для обеспечения доступа к функционалу ядра расчётов в Office и .NET через технологию Automation.


Комментарии и вопросы

Получайте свежие новости и обновления по Object Pascal, Delphi и Lazarus прямо в свой смартфон. Подпишитесь на наш Telegram-канал delphi_kansoftware и будьте в курсе последних тенденций в разработке под Linux, Windows, Android и iOS




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


:: Главная :: ActiveX ::


реклама


©KANSoftWare (разработка программного обеспечения, создание программ, создание интерактивных сайтов), 2007
Top.Mail.Ru

Время компиляции файла: 2024-12-22 20:14:06
2025-06-15 23:34:13/0.0036821365356445/0