Связь между объектами чертежа. Есть ли какие-нибудь инструменты?

Автор Тема: Связь между объектами чертежа. Есть ли какие-нибудь инструменты?  (Прочитано 83464 раз)

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

Оффлайн Александр Ривилис

  • Administrator
  • *****
  • Сообщений: 13882
  • Карма: 1787
  • Рыцарь ObjectARX
  • Skype: rivilis
Попробовал сохранить объект IdMapping в событии BeginDeepClone и прочитать его в событии EndDeepClone - объект IdMapping между этими событиями не изменился (хотя, особой надежды не было)
Объект IdMapping сохранять смысла я не вижу. Наверное нужно сохранять Id'сы для всех пар, а в EndDeepClone получать для них Handle'ы
Не забывайте про правильное Форматирование кода на форуме
Создание и добавление Autodesk Screencast видео в сообщение на форуме
Если Вы задали вопрос и на форуме появился правильный ответ, то не забудьте про кнопку Решение

Оффлайн Дмитрий ЗагорулькинАвтор темы

  • ADN
  • *
  • Сообщений: 2531
  • Карма: 737
Ок, попробую сохранять Ids...
А когда у нас идет наполнение БД из файла без его открытия (например, методом ReadDwgFile) хендлы объектов чертежа сохраняются?

Оффлайн Дима_

  • ADN Club
  • ****
  • Сообщений: 473
  • Карма: 66
Наверное нужно сохранять Id'сы для всех пар
Вот тут я точно не вижу смысла. Могут измениться объекты - но id сами по себе точно не "испортяться" - другое дело, что они могут потерять актуальность (то есть на момент завершения они уже станут  другими - но это нам все равно никак не поможет).

Оффлайн Александр Ривилис

  • Administrator
  • *****
  • Сообщений: 13882
  • Карма: 1787
  • Рыцарь ObjectARX
  • Skype: rivilis
А когда у нас идет наполнение БД из файла без его открытия (например, методом ReadDwgFile) хендлы объектов чертежа сохраняются?
Конечно.
Не забывайте про правильное Форматирование кода на форуме
Создание и добавление Autodesk Screencast видео в сообщение на форуме
Если Вы задали вопрос и на форуме появился правильный ответ, то не забудьте про кнопку Решение

Оффлайн Дмитрий ЗагорулькинАвтор темы

  • ADN
  • *
  • Сообщений: 2531
  • Карма: 737
Сохранение Id тоже не дало результата...
Может быть, при вставке из буфера, создаваемая временная БД наполняется из временного файла каким-то нестандартным способом, объектам которой зачем-то присваиваются хендлы, не конфликтующие с хендлами принимающего чертежа. При этом, база получается нестандартной и поэтому не получается ее сохранить в файл. Как вам такая теория? :)

Оффлайн Александр Ривилис

  • Administrator
  • *****
  • Сообщений: 13882
  • Карма: 1787
  • Рыцарь ObjectARX
  • Skype: rivilis
Теория совершенно не нравится. Не конфликтующие хендлы должны появится только при вставке в принимающий чертеж.
Не забывайте про правильное Форматирование кода на форуме
Создание и добавление Autodesk Screencast видео в сообщение на форуме
Если Вы задали вопрос и на форуме появился правильный ответ, то не забудьте про кнопку Решение

Оффлайн Дима_

  • ADN Club
  • ****
  • Сообщений: 473
  • Карма: 66
Так по ObjectId прослеживается или нет (именно первое копирование-вставка)??

Оффлайн Дмитрий ЗагорулькинАвтор темы

  • ADN
  • *
  • Сообщений: 2531
  • Карма: 737
Это я молодец, оказывается. Путь для сохранения кривой указывал.
Сохранил я эту временную БД в файл в момент ее полной инициализации, открыл - а там у объектов "правильные" хендлы.  :o

Дима_, насчет ID не понял, они в разных сеансах-то различны, не говоря уж про разные чертежи...

Оффлайн Александр Ривилис

  • Administrator
  • *****
  • Сообщений: 13882
  • Карма: 1787
  • Рыцарь ObjectARX
  • Skype: rivilis
И? Не знаю как Дима_, а я уже совсем запутался.
Не забывайте про правильное Форматирование кода на форуме
Создание и добавление Autodesk Screencast видео в сообщение на форуме
Если Вы задали вопрос и на форуме появился правильный ответ, то не забудьте про кнопку Решение

Оффлайн Дмитрий ЗагорулькинАвтор темы

  • ADN
  • *
  • Сообщений: 2531
  • Карма: 737
Я тоже ничего не понимаю.
В соответствии с моим списком:
- создается пустая база данных (исходная БД)
- в нее читаются данные из временного ДВГ файла. Хендлы моих объектов тут правильные, судя по промежуточному сохранению
- выполняется вставка блока в чертеж (БД назначения) А вот тут хендлы уже неправильные, судя по данным из обработчиков событий
- запрашивается точка вставки
- исходная БД уничтожается
- взрывается блок

Оффлайн Дима_

  • ADN Club
  • ****
  • Сообщений: 473
  • Карма: 66
И? Не знаю как Дима_, а я уже совсем запутался.
Да я тоже (с учетом что паралельно как-бы работаю - но телефон свирепо насвистывает входящие emailики) - мысль про ид сейчас проверю сам и если цепочка будет покажу лог.

Оффлайн Дима_

  • ADN Club
  • ****
  • Сообщений: 473
  • Карма: 66
Код (суть скопипастил у Дмитрия):
Код - C# [Выбрать]
  1. module AcadApp
  2. open Autodesk.AutoCAD.ApplicationServices
  3. open Autodesk.AutoCAD.Runtime
  4. open Autodesk.AutoCAD.DatabaseServices
  5. open Autodesk.AutoCAD.EditorInput
  6. open Autodesk.AutoCAD.Geometry
  7.                            
  8. let Init()=
  9.   let doc=Application.DocumentManager.MdiActiveDocument
  10.   doc,doc.Editor,doc.Database,doc.TransactionManager.StartTransaction
  11.  
  12. [<CommandMethod "Test">]
  13. let Test()=
  14.   let doc,ed,db,trf=Init()
  15.   let LogedDb (db:Database)=
  16.     let PrintIdm (idm:IdMapping)=
  17.       "\nFrom "+idm.OriginalDatabase.Filename+
  18.       "\nTo "+idm.DestinationDatabase.Filename+"\n"+
  19.       (idm|>Seq.cast<IdPair>|>Seq.filter (fun idp->idp.Key.ObjectClass.DxfName="CIRCLE")
  20.           |>Seq.map (fun idp->string(idp.Key.Handle)+string(idp.Key)+"->"+
  21.                                      string(idp.Value.Handle)+string(idp.Value)+"; ")
  22.           |>Seq.reduce (+))|>ed.WriteMessage
  23.     db.BeginDeepCloneTranslation.Add(fun ev->ev.IdMapping|>PrintIdm)
  24.   Database.GetAllDatabases()|>Seq.iter (LogedDb)
  25.   Database.DatabaseConstructed.AddHandler(fun db _ ->db:?>Database|>LogedDb)
то есть смотрим как "превращаются" handl'а и id - чтобы убрать "мусор" смотрим только за кругами.
Лог (создаем круг и делаем копирование и две вставки):

Команда: _circle Центр круга или [3Т/2Т/ККР (кас кас радиус)]: *Прервано*
Команда: netload
Команда: test
Команда: _circle Центр круга или [3Т/2Т/ККР (кас кас радиус)]:
Радиус круга или [Диаметр]:
Команда: (cdr (assoc 5 (entget (entlast))))
"1FB"
Команда: _copyclip найдено: 1

From C:\Users\Дима\AppData\Local\Autodesk\AutoCAD
2010\R18.0\rus\template\acadiso.dwt
To
1FB(2129671192)->4F(2129686136);

Команда: _pasteclip
From C:\Users\1F43~1\AppData\Local\Temp\A$C53B37EF2.DWG
To C:\Users\Дима\AppData\Local\Autodesk\AutoCAD
2010\R18.0\rus\template\acadiso.dwt
1FD(2129686136)->1FD(2129671208); Точка вставки:
From C:\Users\Дима\AppData\Local\Autodesk\AutoCAD
2010\R18.0\rus\template\acadiso.dwt
To C:\Users\Дима\AppData\Local\Autodesk\AutoCAD
2010\R18.0\rus\template\acadiso.dwt
1FD(2129671208)->202(2129671248);

Команда: (cdr (assoc 5 (entget (entlast))))
"202"

Команда: _pasteclip
From C:\Users\1F43~1\AppData\Local\Temp\A$C53B37EF2.DWG
To C:\Users\Дима\AppData\Local\Autodesk\AutoCAD
2010\R18.0\rus\template\acadiso.dwt
204(2129706616)->204(2129671264); Точка вставки:
From C:\Users\Дима\AppData\Local\Autodesk\AutoCAD
2010\R18.0\rus\template\acadiso.dwt
To C:\Users\Дима\AppData\Local\Autodesk\AutoCAD
2010\R18.0\rus\template\acadiso.dwt
204(2129671264)->209(2129671304);
Команда: (cdr (assoc 5 (entget (entlast))))
"209"
то есть имея исходный handle 1Fb - через Id он легко прослеживается до конечного 202
1FB(2129671192)->4F(2129686136); 1FD(2129686136)->1FD(2129671208); 1FD(2129671208)->202(2129671248);
То есть мы видим, что у id 2129686136 меняеться handle (скорее он неверно определяеться при "заборе из буфера" - то есть мы запрашиваем систему handle у "неиниционизированного" объекта - он выдает "первый свободный" но т.к. он видимо не записывается - то и следующему объекту выдается тот-же - отсюда и коллизия) но это разумеется только при первой вставке (по id второй раз так не прокатит - смотри лог - появляеться "новорожденный" объект появление которого не отловленно).
Как вариант вижу только попробывать обновлять содержимое буфера при каждой вставке самим сосбой (запоминая ID объектов идущих в пустую базу).

Оффлайн Дмитрий ЗагорулькинАвтор темы

  • ADN
  • *
  • Сообщений: 2531
  • Карма: 737
У меня нет слов :)
Спасибо! Сейчас опробую и, надеюсь, что закончу эту трехдневную эпопею с поиском пропавших хендлов :)

Оффлайн Александр Ривилис

  • Administrator
  • *****
  • Сообщений: 13882
  • Карма: 1787
  • Рыцарь ObjectARX
  • Skype: rivilis
Дима_ Спасибо. В общем ты подтвердил то, о чем я говорил, т.е. что Handle для результирующего объекта в момент BeginDeepCloneTranslation не определен. Т.е. в этой схеме хендлы действительны только слева от ->

Фактически:
1FB(2129671192) ->  4F(2129686136);
1FD(2129686136) -> 1FD(2129671208);
1FD(2129671208) -> 202(2129671248);


Не забывайте про правильное Форматирование кода на форуме
Создание и добавление Autodesk Screencast видео в сообщение на форуме
Если Вы задали вопрос и на форуме появился правильный ответ, то не забудьте про кнопку Решение

Оффлайн Дмитрий ЗагорулькинАвтор темы

  • ADN
  • *
  • Сообщений: 2531
  • Карма: 737
Общими усилиями, таки, получилось :)
Сделал инструмент для добавления ссылок между объектами в чертеж.
Если объекты копировать в чертеже любыми командами: копирование, зеркало и т.п., то связи к новым объектам тоже добавляются.
Если объекты копировать в другой чертеж - аналогично.
Связи в чертеже сохраняются только после сохранения чертежа.
Исходники - в приложенном архиве. Рядом скомпилированная сборка для AutoCAD 2014 x64. При загрузке инициализируется автоматически. Командой TestAddReference можно добавить ссылку одного объекта на другой, командой TestGetReferencedObject - проверить связь объекта с другим.
В исходниках есть папка Notes - там я старался довольно подробно изложить основные идеи + подробно комментировал код.
Пока не все реализовал, что хочу, буду дальше допиливать под свои нужды.