• Добро пожаловать на Форум пользователей ПО АСКОН. Пожалуйста, авторизуйтесь.
 

Уважаемые пользователи,

Хотим проинформировать вас о режиме работы регистрации на нашем сайте.

Зарегистрироваться возможно в рабочие дни, с 8:00 до 20:00 (мск).

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

Благодарим вас за понимание и сотрудничество. Мы ценим ваше терпение и стремимся предоставить вам лучший опыт использования нашего сервиса.

С уважением,
Команда Ascon

Как работать одновременно с API 5 и API 7

Автор Votarik, 07.08.21, 22:40:28

« назад - далее »

0 Пользователи и 2 гостей просматривают эту тему.

Votarik

Есть библиотека dll, в которой я использую  API 5.(Привязка к событию сохранения, получение объёма ,габаритных размеров, площади поверхности детали). Есть вторая часть, которую я написал через API 7(потому что не знаю как это можно реализовать через API 5) (Получение кол-ва размеров детали и запись их в свойство). При попытке использовать один и тот же входной объект в KompasObject(API 5) и IApplication(API 7) получаю ошибку. Копирование входного объекта(не создание 2 ссылки, а именно копирование) и попытка получить KompasObject и IApplication с разных объектов тоже не увенчалась успехом. Помогло только получение IApplication отдельно через (IApplication)Marshal.GetActiveObject("Kompas.Application.7"). Так вроде работает пока запущен только 1 компас. Но при запуске второго приложения компас Marshal.GetActiveObject захватывает только первый запущенный Компас даже если активен второй Компас. В итоге я вижу 2 пути решения или заставить API 5 работать вместе с API 7 или переписать кусок кода написанный через API 7;
IApplication kompas = (IApplication)Marshal.GetActiveObject("Kompas.Application.7");
Document3D doc = (Document3D)kompas;
IPart7 model = (IPart7)doc;
ISymbols3DContainer Param = (ISymbols3DContainer)model;
int l = Param.LineDimensions3D.Count;
int a = Param.AngleDimensions3D.Count;
int d = Param.DiametralDimensions3D.Count;
int r = Param.RadialDimensions3D.Count;
int summ = a + l + d + r;
StringBuilder text = new StringBuilder();
text.Append($"{l} линейных размера\n");
text.Append($"{a} угловых размера\n");
text.Append($"{d} диаметральных размера\n");
text.Append($"{r} радиальных размера\n");
text.Append($"Всего {summ} размера\n");
IPropertyMng propertyMng = (IPropertyMng)kompas;
var properties = propertyMng.GetProperties(doc);
bool isExist = false;
foreach (var item in properties)
       {
        if (item.Name == "Количество размеров")
        {
           isExist = true;
           IPropertyKeeper propertyKeeper = (IPropertyKeeper)model;
           propertyKeeper.SetPropertyValue((_Property)item, summ, false);
           item.Update();
       }
      }
if (!isExist)
   {
     IProperty prop = propertyMng.AddProperty(null, null);
     prop.Name = "Количество размеров";
     prop.ReadOnly = true;
     IPropertyKeeper propertyKeeper = (IPropertyKeeper)model;
     propertyKeeper.SetPropertyValue((_Property)prop, summ, false);
     prop.Update();
   }
     kompas.MessageBoxEx($"{text}", $"{model.Name}", 50);

Vi2

    [uuid(E36BC97C-39D6-4402-9C25-C7008A217E02),helpstring("Интерфейс приложения КОМПАС 3D.")]
    dispinterface KompasObject {
...
            [id(0x00000067), helpstring("Получить указатель интерфейса приложения API версии 7.")]
            IDispatch* ksGetApplication7();
...
            [id(0x0000006c), helpstring("Найти или создать объект LPUNKNOWN API7Dual, 3D COM, API5Auto.")]
            IUnknown* TransferInterface(IUnknown* obj, long apiNewType, long objNewType);
}
...
    [uuid(6B0B5194-4ACD-4095-9BC1-11179FBBB05A),helpstring("Интерфейс приложения КОМПАС 3D.")]
    coclass Application {
        [default] dispinterface KompasObject;
        [default, source] dispinterface ksKompasObjectNotify;
    };
Из этого, если у тебя есть интерфейс приложения Компас в АПИ5, то ты можешь получить его же в АПИ7 через вызов ksGetApplication7. Если у тебя есть интерфейс в АПИ5/АПИ7, то ты можешь получить его интерфейс в АПИ7/АПИ5 через TransferInterface.

PS
Вот примерный код на VB

    Dim obj5 As Kompas6API5.Application
    Dim obj7 As KompasAPI7.IApplication
    Set obj5 = GetObject(, "Kompas.Application.5") ' это эквивалент Marshal.GetActiveObject
    ' здесь можно и CreateObject
    ' Set obj5 = CreateObject("Kompas.Application.5")
    Set obj7 = obj5.ksGetApplication7

Votarik

Цитата: Vi2 от 09.08.21, 10:07:51    [uuid(E36BC97C-39D6-4402-9C25-C7008A217E02),helpstring("Интерфейс приложения КОМПАС 3D.")]
    dispinterface KompasObject {
...
            [id(0x00000067), helpstring("Получить указатель интерфейса приложения API версии 7.")]
            IDispatch* ksGetApplication7();
...
            [id(0x0000006c), helpstring("Найти или создать объект LPUNKNOWN API7Dual, 3D COM, API5Auto.")]
            IUnknown* TransferInterface(IUnknown* obj, long apiNewType, long objNewType);
}
...
    [uuid(6B0B5194-4ACD-4095-9BC1-11179FBBB05A),helpstring("Интерфейс приложения КОМПАС 3D.")]
    coclass Application {
        [default] dispinterface KompasObject;
        [default, source] dispinterface ksKompasObjectNotify;
    };
Из этого, если у тебя есть интерфейс приложения Компас в АПИ5, то ты можешь получить его же в АПИ7 через вызов ksGetApplication7. Если у тебя есть интерфейс в АПИ5/АПИ7, то ты можешь получить его интерфейс в АПИ7/АПИ5 через TransferInterface.

PS
Вот примерный код на VB

    Dim obj5 As Kompas6API5.Application
    Dim obj7 As KompasAPI7.IApplication
    Set obj5 = GetObject(, "Kompas.Application.5") ' это эквивалент Marshal.GetActiveObject
    ' здесь можно и CreateObject
    ' Set obj5 = CreateObject("Kompas.Application.5")
    Set obj7 = obj5.ksGetApplication7


Вот прям огромное спасибо за ksGetApplication7! Всё решилось в 1 строчку)
IApplication Kompas7 = Kompas5.ksGetApplication7(); // Kompas5 переменная типа KompasObject