Компас 13/14, компиляция плагина под x64 c помощью C++Builder XE3

Автор Vigor, 30.12.13, 12:18:06

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

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

Vigor

Здравствуйте товарищи!
Помогите плиз, если кто сталкивался...

У меня установленно: Компас 14 x32, Windows XP SP3 (x32), C++Builder XE3

-----------------
Проблема1:
----------------
Написал плагин используя kAPI5BC.lib и kAPI7BC.lib
при компиляции под Windows x32, плагин создается, подключается к компасу и и корректно работает

Удалил из проекта kAPI5BC.lib и kAPI7BC.lib и вместо них подключил kAPI5.lib и kAPI7.lib из папки SDK\Lib64 (взятой из установленного на другой машине Компаса 14 x64, kAPI5BC.lib и kAPI7BC.lib - в этой папке нет)
при компиляции под Windows x64, плагин компилируется, но при линковке выдает ошибки:
[ilink64 Error] Error: Unresolved external 'CreateKompasObject' referenced from E:\DATA\WIN64\RELEASE\MYLIB1.O
[ilink64 Error] Error: Unresolved external 'CreateKompasApplication' referenced from E:\DATA\WIN64\RELEASE\UNIT_FRMCALCULATESTOPPER.O
[ilink64 Error] Error: Public symbol 'DllEntryPoint' defined in both module E:\DATA\WIN64\RELEASE\MYLIB1.O and E:\DATA\WIN64\RELEASE\UNIT_FRMCALCULATESTOPPER.O
[ilink64 Error] Error: Public symbol 'DllEntryPoint' defined in both module E:\DATA\WIN64\RELEASE\MYLIB1.O and E:\DATA\WIN64\RELEASE\UNIT_FRMCALCULATESTOPPER.O

Вопрос, в чем может быть проблема?
PS: Пробовал компилировать под Windows x64 оставив  kAPI5BC.lib и kAPI7BC.lib из папки SDK\Lib - получаю теже ошибки при линковке, меняю платформу назначения на Windows x32 - ошибок нет.
PPS: Пути прописаны корректно

-----------------
Проблема2:
----------------
Плагин корректно работает под Компас 14 x32, но при подключении к Компас 13 x32 не отрабатывет функция обновления документа:
   //-----
   // Обнавляем документ
   // поехали
   KompasObjectPtr kompas( IDispatchPtr(::CreateKompasObject(), false/*AddRef*/) );

   //получим указатель на текущий графический документ
   ksDocument2DPtr doc( (ksDocument2D*)kompas->ActiveDocument2D(), false/*AddRef*/);

   //
   doc->ksRebuildDocument();

и так же не работает

   //-----
   // Получаем интерфейс приложения компас v7
   IApplicationPtr iKompasApp( IDispatchPtr(::CreateKompasApplication(), false/*AddRef*/ ) );

   // Получаем текущий документ как 2D1
   IKompasDocument2D1Ptr idoc = iKompasApp->ActiveDocument;

idoc->RebuildDocument();

Если в Компас 13  нажать F5, то все измения выполненые в плагине отображаются
Подчеркну, что в Компас 14 этот же код работает корректно, и обновление происходит из кода автоматически.
Никто не сталкивался с таким глюком?
PS: в плагине используется только  ф-ция idoc->AddVariable

PS

1. Для компиляции под х64 не достаточно подключить библиотеки lib из Компас х64, нужно изменить параметры проекта в Builder XE3. Какие конкретно сказать не могу, с Builder XE3 не работаю (поищите в интернете). Кроме того текст программы созданный под х32 не обязательно будет работать в х64, есть достаточно много отличий.
2. Библиотеки скомпилированные под текущую версию Компаса, не обязательно будут работать с более ранней версией Компаса, это не гарантируется! А если и будут, то могут быть ошибки в работе.


Vigor

13.01.14, 13:40:51 #2 Последнее редактирование: 13.01.14, 14:07:09 от Vigor
----------
1. Для компиляции под х64 не достаточно подключить библиотеки lib из Компас х64, нужно изменить параметры проекта в Builder XE3. Какие конкретно сказать не могу, с Builder XE3 не работаю (поищите в интернете). Кроме того текст программы созданный под х32 не обязательно будет работать в х64, есть достаточно много отличий.

- Я компилирую обычную dll для для Windows x64 без проблем, достаточно просто в билдере установить "Target Platform" в Win64, проблема возникает именно после подключения к проекту библиотек из lib64 и заголовочных файлов полученных из tlb. Компиляция проходит нормально, но возникает ошибка линковки.

По сути проблема в том, что при линковке линковщик не видит в файле  kAPI5.lib и kAPI7.lib нужных ф-ций (заметьте в папке lib64 файлов  kAPI5BC.lib и kAPI7BC.lib нет) поэтому и пишет:
[ilink64 Error] Error: Unresolved external 'CreateKompasApplication' referenced from E:\DATA\WIN64\RELEASE\UNIT_FRMCALCULATESTOPPER.O

Вопрос: есть ли у аскона инструкции как компилировать плагин для Компаса x64 в С++Builder?

----------
2. Библиотеки скомпилированные под текущую версию Компаса, не обязательно будут работать с более ранней версией Компаса, это не гарантируется! А если и будут, то могут быть ошибки в работе.

- Специально сейчас сделал тестовый проект используя tlb и lib для Компаса 13 x32 там точно такая же проблема, функия RebuildDocument(); не отрабатывает (приходится руками нажимать F5)! Хотя в Компас 14 все работает корректно!

Во вложение весь проект не влез (НАДО создать папку IMPORTS и вставить в нее cpp/h файлы полученные из TLB), привожу код сдесь:

//---------------------------------------------------------------------------
#include <vcl.h>
#pragma hdrstop

#include <windows.h>

#include "Imports\KompasAPI7_TLB.h"

// линкуем Библиотеки для Компаса просто добавляя файлы в проект из папки KOMPAS13_SDK_LIB
//#pragma link "kAPI5BC.lib"
//#pragma link "kAPI7BC.lib"


//extern "C" IDispatch* far __export WINAPI CreateKompasObject();

extern "C" IDispatch* far __export WINAPI CreateKompasApplication();


#pragma argsused
int WINAPI DllEntryPoint(HINSTANCE hinst, unsigned long reason, void* lpReserved)
{
  return 1;
}

extern "C" char * far __export __pascal LibraryName()
{
  return  "Тест API Компс3D 13";
}

extern "C" void far __export __pascal  LibraryEntry( unsigned int  )
{
   //-----
   // Получаем интерфейс приложения компас v7
   IApplicationPtr iKompasApp( IDispatchPtr(::CreateKompasApplication(), false/*AddRef*/ ) );

   // Получаем текущий документ как 2D1
   IKompasDocument2D1Ptr idoc = iKompasApp->ActiveDocument;

   // Проверяем
   if (!idoc)
   {
      ShowMessage("Ошибка: Документ должен быть 2D чертежем!");
      return;
   }

   IVariable7Ptr ivar;
   UnicodeString vname, vnote;

   vname = "my_variable";
   vnote = "мой комментарий";

   double val = 100.123;

   // Добавляем в документ
   idoc->AddVariable(vname.c_str(), val, vnote.c_str(), &ivar);
   ivar->Note = vnote.c_str();


   idoc->RebuildDocument();   // В компас 13 не работает!!!!

   ShowMessage("Ok");
}

Vigor

Немного поясню:

idoc->RebuildDocument();   // В компас 13 не работает!!!!

Я имею в виду, что после вызова этой ф-ции в окне переменных переменная  "my_variable" не появляется, она появляется только если после закрытия плагина вручную нажать F5. В компасе14 переменная появляется сразу после вызова  idoc->RebuildDocument(); т.е. все работает корректно.

Как вариант вместо  idoc->RebuildDocument();, можно попробовать так перестроить чертёж iKompasApp.ExecuteKompasCommand(ksCMRebuildSheet,False);

Vigor

Sabahs
iKompasApp.ExecuteKompasCommand(ksCMRebuildSheet,False);
К сожалению не помогает. После вызова появляется окно "Сообщение библиотеки" с текстом: "Команда не выполнена, т.к. она не доступна." и окно переменных не обновляется.

Народ, ну все-таки... может кто знает
Вопрос: есть ли у аскона инструкции как компилировать плагин для Компаса x64 в С++Builder?
в SDK инструкция только для x32

14.01.14, 16:35:30 #6 Последнее редактирование: 14.01.14, 16:51:02 от Sabahs
Насколько я понимаю, проект компилируется на файлах от V14?
Если верить справке, то функция AddVariable должна вернуть указатель на добавляемую переменную
idoc->AddVariable("my_variable",100.123,"мой комментарий",&ivar);, а затем обновляете документ, хотя в C++ возможно иначе.

В Delphi параметры функции выглядят так.

Vigor

Насколько я понимаю, проект компилируется на файлах от V14?
Я скомпилировал плагин используя tlb и lib от Компас14 - в v14 работает корректно, в V13 не работает  idoc->RebuildDocument();
потом скомпилировал плагин используя tlb и lib от Компас13 - итог тот же,  в v14 работает корректно, в V13 не работает  idoc->RebuildDocument();

Если верить справке, то функция AddVariable должна вернуть указатель на добавляемую переменную
idoc->AddVariable("my_variable",100.123,"мой комментарий",&ivar);, а затем обновляете документ, хотя в C++ возможно иначе.

В С++ добавляемая переменная возвращается по ссылке &ivar, но смысл не в этом, ф-ция idoc->AddVariable отрабатывает корректно, переменная в документ добавляется, а вот idoc->RebuildDocument(); в 13 версии окно переменных не обновляет. Скорее всего это баг Компаса, асконовцы в 13 версии просто забыли в ф-ции idoc->RebuildDocument() выполнить обновление окна с переменными документа, т.к. обновление общего окна компаса происходит (видно как промаргивает перерисовка), ну а в V14 вспомнили...

-- В общем, обошел этот баг эмуляцией нажатия клавиши F5

Остался вопрос по компиляции плагина в С++Builder под Компас x64: в папке SDK/lib64 нет файлов  kAPI5BC.lib и kAPI7BC.lib - может кто знает где их взять?
И вообще у Аскона есть инструкция для компиляции плагинов под Компас x64?? В папке SDK лежит только для x32

Можно ещё попробовать перед перестроением, обновить переменные IKompasDocument2D1::UpdateVariables.
Если проблема компиляции у Вас заключается только в неправильной работе функции RebuildDocument();, то это скорее всего проблема не компиляции, а просто, есть различия в работе API Компаса разных версий.

Vigor

Попробовал... вызов  IKompasDocument2D1::UpdateVariables тоже не помогает. В общем, проблема обходным путем решена, поэтому будем считать что это особенность Компас13  :)

Самый главный вопрос: кто-нибудь компилировал плагин под Компас x64 в C++Builder XE3/4/5? Товарищи поделитесь опытом, какие *.lib надо подключать и может что еще нужно?


Vigor

В общем, если следовать инструкции в SDK и подключать в проект KAPI7BC.LIB то в пустом проекте выдается ошибка:
[ilink64 Error] Fatal: Invalid object file 'E:\TEST_API\KOMPAS13_SDK_LIB\KAPI7BC.LIB'

Отсюда вывод:  KAPI7BC.LIB для x32 не подходит для компиляции в Win64, нужна KAPI7BC.LIB для x64, но в папке SDK\lib64 такого файла нет, неужели у АСКОНА нет поддержки C++Builder XE3/4/5 для Win64?

15.01.14, 14:43:49 #11 Последнее редактирование: 15.01.14, 14:56:34 от Sabahs
ЦитироватьОтсюда вывод:  KAPI7BC.LIB для x32 не подходит для компиляции в Win64, нужна KAPI7BC.LIB для x64, но в папке SDK\lib64 такого файла нет, неужели у АСКОНА нет поддержки C++Builder XE3/4/5 для Win64?
Естественно не подходит, для компиляции под 64-разрядный Компас файлы берутся из дистрибутива Компаса:
- в SDK 32-разрядного Компаса все файлы для платформы Win_32;
- в SDK 64-разрядного Компаса все файлы для платформы Win_64.
Также для каждой платформы необходимо настроить опции проекта.

Vigor

15.01.14, 15:20:27 #12 Последнее редактирование: 15.01.14, 15:38:01 от Vigor
в SDK 64-разрядного Компаса все файлы для платформы Win_64.
Так я и брал все файлы (KAPI7BC.LIB и tlb) из SDK для Компас x64,
+ еще пробовал KAPI7.LIB из SDK\lib64 (в Компас x32 такой папки вообще нет)

Опции и пути к *.lib, *.h,*cpp в проекте настроены правильно

Народ кто-нибудь вообще хоть раз реально компилировал плагин для Компас x64 на C++Builder XE3/4/5 ? :)

ЦитироватьКомпас x32 папки SDK\lib64 вообще нет
А зачем она там?
Компас х32 работает, как 32-разрядное приложение и ему всё равно, какой разрядности система на которой он работает.

Vigor

Кстати, сейчас сравнил KAPI7BC.LIB из SDK Компас x32 и SDK Компас x64.... они идентичны!
Sabahs не посмотрите у себя... у вас то же самое?

Эти файлы да, а вот KAPI7.LIB, который скорее всего при использовании API7 нужно подключать, отличаются.
+ Благодарностей: 1

Vigor

Sabahs большое спасибо за сравнение!
Но все равно пока не работает :)

В файле "Компиляция библиотек под K13.doc" из SDK для Компас x64 написано:

Builder C++ Automation
1. Задайте пути к подключаемым модулям. Для этого вызовите команды Project - Options... - Directories/Conditionals - Include path и Library path.
3. Отключите прежние файлы библиотек (файлы *.lib) и подключите kAPI5bc.lib. (для x32 я подключаю kAPI7bc.lib - все работает)
4. Удалите файлы ks_tlb.h, ks_tlb.cpp, ks_ocx.h, ks_ocx.cpp.
5. Подключите новую библиотеку (файл с расширением tlb). Для этого выполните следующие действия.
5.1. Вызовите команду Project - Import type library - Add.
5.2. Выберите файл kAPI5.tlb.
5.3. Выключите опцию Generate Component Wrapper.
6. Укажите путь к корневой папке размещения примеров (Unit dir name).
7. Нажмите кнопку Create Unit.
8. Переименуйте полученные файлы в ks_tlb.h, ks_tlb.cpp, ks_ocx.h, ks_ocx.cpp.
9. Отредактируйте в файле ks_tlb.cpp подключение ш файла.

Я Пробовал вместо  KAPI7BC.LIB подключать  KAPI7.LIB из папки SDK\lib64 взятой с установленного Компас3D x64, появляется ошибка:
[ilink64 Error] Fatal: Archive file 'E:\TEST_API\KOMPAS13_SDK_LIB\LIB64\KAPI7.LIB' lists no symbols in its dictionary.

После вашего сравнения так же попробовал вместо  KAPI7BC.LIB подключить KAPI7.LIB из папки SDK взятой с установленного Компас3D x64, появляется таже ошибка:
[ilink64 Error] Fatal: Archive file 'E:\TEST_API\KOMPAS13_SDK_LIB\LIB64\KAPI7.LIB' lists no symbols in its dictionary.

Я думаю что файлы KAPI5BC.LIB и KAPI7BC.LIB - созданы специально для Builder C++
А файлы KAPI5.LIB и KAPI7.LIB - скорее всего для Visual C++
Между собой они не совместимы... но для корректной линковки в C++Builder нужны x64 версии библиотек KAPI5BC.LIB и KAPI7BC.LIB но к сожалению KAPI7BC.LIB в SDK32 и SDK64 -одинаковые, т.е... получается в АСКОНе просто забыли сделать их 64-разрядную версию... а вот для KAPI5.LIB и KAPI7.LIB не забыли  :)

Вот и вопрос: где взять 64-разрядную версию KAPI5BC.LIB и KAPI7BC.LIB ?

Я на C++Builder не работаю и всех нюансов не могу знать.
У Вас скомпилированная библиотека для Компас х64, подключается и работает на Компас V14x64?

Vigor

Цитата: Sabahs от 15.01.14, 17:40:07
У Вас скомпилированная библиотека для Компас х64, подключается и работает на Компас V14x64?

Нет, библиотека для Компас х64 не компилируется ни с файлами (tlb lib) от Компас V14x64 ни с файлами от Компас V13x64, возникает ошибка при линковке
[ilink64 Error] Fatal: Invalid object file 'E:\TEST_API\KOMPAS13_SDK_LIB\KAPI7BC.LIB'

А Вы не пробовали создать файлы из kAPI7.tlb, переименовать их в KAPI7BC с соответствующими расширениями?