Некорректная подсветка объектов после переключения в модель

Автор Тема: Некорректная подсветка объектов после переключения в модель  (Прочитано 3557 раз)

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

Тема содержит сообщение с Решением. Нажмите здесь чтобы посмотреть его.

Оффлайн Александр ЛозаАвтор темы

  • ADN OPEN
  • Сообщений: 8
  • Карма: 0
На пользовательской палитре имеется некий перечень объектов (например, отображается handle, тип и лист, где размещен объект).
По двойному щелчку необходимо:
- установить текущий лист, где расположен объект.
- выбрать объект (т.е. объект должен быть подсвечен и иметь ручки выбора)
- выполнить zoom по объекту.

Проблема заключается в выборе объекта. Если объект расположен в листах, все работает хорошо. Но, если объект расположен в модели, получается следующая ситуация:
Если последний текущий layout - это лист (а не модель), то то после программной установки текущего layout (lm.CurrentLayout = LayoutName, т.е. "model"), объект выбирается, но на экране он не подсвечивается (отсутствует подсветка и ручки выбора). При этом, если вручную щелкнуть мышкой в области модели, то подсветка появляется.
Если я предварительно вручную устанавливаю правильный layout (в видео действия, после снятия флажка), то подсветка осуществляется корректно.
Видео прилагаю



Видимо, проблема похожа на описанную в https://adn-cis.org/forum/index.php?topic=415.0, но у меня ситуация другая.
SetFocus (возможно нужен handle именно окна Windows, отображающего графическое окно, а не приложения/документа?), UpdateScreen не помогают.
Выбор объектов осуществляется функцией         ed.SetImpliedSelection(idarr);
Ранее использовал с тем же результатом функцию Autodesk.AutoCAD.Internal.Utils.SelectObjects(idarr);
Пример тестового проекта и тестового dwg-файла (dwg-файл можно брать любой) прилагаю.
Тестовый проект создан с нуля именно для воспроизведения ситуации, в нем есть некие другие огрехи.
После загрузки  SelectObj.dll и выполнения команды TestSelectObject программа по текущему чертежу считывает перечень объектов (функция filldata) и отображает его в виде таблицы на палитре.
Далее, по двойному щелчку отрабатывает:
- функция SetCurrentLayout (в режиме блокировки отрабатывается lm.CurrentLayout = LayoutName;)
- функция FindAndZoomObject (отрабатывает код ed.SetImpliedSelection(idarr))

Ниже привожу код функции SetCurrentLayout и часть строчек из функции FindAndZoomObject

Код - C# [Выбрать]
  1.     public static void FindAndZoomObject(String Handle)
  2.     {
  3. ...
  4.         long ln = Convert.ToInt64(Handle, 16);
  5.         // Not create a Handle from the long integer
  6.         hn = new Handle(ln);
  7.         // And attempt to get an ObjectId for the Handle
  8.         id = db.GetObjectId(false, hn, 0);
  9. ....
  10. // Здесь начинается выбор элемента на экране
  11.       ObjectId[] idarr = new ObjectId[1];
  12.       idarr[0] = id;
  13.       DocumentLock lockDoc = doc.LockDocument();
  14.       using (lockDoc)
  15.       {
  16. //        SetFocusToActiveDocument();
  17. //        Autodesk.AutoCAD.Internal.Utils.SelectObjects(idarr);
  18.         ed.SetImpliedSelection(idarr);
  19.         ed.UpdateScreen();
  20. //        SetFocusToActiveDocument();
  21.       }
  22.     }//func
  23.  



Код - C# [Выбрать]
  1.     public static Boolean SetCurrentLayout(String LayoutName)
  2.     {
  3.       LayoutManager lm = LayoutManager.Current;
  4.       if (String.Compare(lm.CurrentLayout, LayoutName, true) != 0)
  5.       {
  6.         try
  7.         {
  8.           DocumentLock lockDoc = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument.LockDocument();
  9.           using (lockDoc)
  10.           {
  11.             lm.CurrentLayout = LayoutName;
  12.           }
  13.         }
  14.         catch (System.Exception ex1)
  15.         {
  16.           System.Windows.Forms.MessageBox.Show(String.Format("Ошибка установки Листа {0}. Текст ошибки {1}", LayoutName, ex1.Message));
  17.           return false;
  18.         }
  19.       }//if
  20.       return true;
  21.     }
« Последнее редактирование: 21-09-2020, 20:54:35 от Александр Ривилис »

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

  • Administrator
  • *****
  • Сообщений: 13830
  • Карма: 1784
  • Рыцарь ObjectARX
  • Skype: rivilis
Скажу сразу. Очень рекомендую оформить FindAndZoomObject в виде отдельной команды с флагами UsePickSet и Redraw, которую запускаете из dataGridView1_DoubleClick при помощи Document.SendStringToExecute
Не забывайте про правильное Форматирование кода на форуме
Создание и добавление Autodesk Screencast видео в сообщение на форуме
Если Вы задали вопрос и на форуме появился правильный ответ, то не забудьте про кнопку Решение

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

  • Administrator
  • *****
  • Сообщений: 13830
  • Карма: 1784
  • Рыцарь ObjectARX
  • Skype: rivilis
Ну и попробуй LAYOUTREGENCTL установить в 0
« Последнее редактирование: 21-09-2020, 21:03:24 от Александр Ривилис »
Не забывайте про правильное Форматирование кода на форуме
Создание и добавление Autodesk Screencast видео в сообщение на форуме
Если Вы задали вопрос и на форуме появился правильный ответ, то не забудьте про кнопку Решение

Отмечено как Решение Александр Ривилис 22-09-2020, 10:20:45

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

  • Administrator
  • *****
  • Сообщений: 13830
  • Карма: 1784
  • Рыцарь ObjectARX
  • Skype: rivilis
При LAYOUTREGENCTL == 2 (значение по умолчанию) срабатывает такой код:

Код - C# [Выбрать]
  1.       SetFocusToActiveDocument();
  2.       ed.Regen();
  3.       ed.SetImpliedSelection(idarr);
Не забывайте про правильное Форматирование кода на форуме
Создание и добавление Autodesk Screencast видео в сообщение на форуме
Если Вы задали вопрос и на форуме появился правильный ответ, то не забудьте про кнопку Решение

Оффлайн Александр ЛозаАвтор темы

  • ADN OPEN
  • Сообщений: 8
  • Карма: 0
Спасибо за оперативный ответ!
В принципе все решения рабочие, результат получился.

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

  • Administrator
  • *****
  • Сообщений: 13830
  • Карма: 1784
  • Рыцарь ObjectARX
  • Skype: rivilis
Спасибо за оперативный ответ!
В принципе все решения рабочие, результат получился.
OK. Я отметил моё последнее сообщение как решение, т.к. оно наиболее универсальное. Там еще можно поиграться с тем, что если нет переключения на модель, то нет необходимости выполнять ed.Regen(), который может быть достаточно длительным...
Не забывайте про правильное Форматирование кода на форуме
Создание и добавление Autodesk Screencast видео в сообщение на форуме
Если Вы задали вопрос и на форуме появился правильный ответ, то не забудьте про кнопку Решение

Оффлайн Александр ЛозаАвтор темы

  • ADN OPEN
  • Сообщений: 8
  • Карма: 0
Проверил на свежую голову первый способ (FindandZoomObject - вынести в отдельную команду).
Поведение оказалось странным - по щелчку с панели заработало (т.е. программное предварительно выделение SetImpliedSelection, а потом SendStringToExecute("FindandZoom"....). Но, если предварительно объект выделяю вручную и запускаю команду FindandZoomObject - было аналогичное поведение (объект оставался не выделенным, пока не щелкнул в экран). После добавления ed.Regen, стало нормально.
Команда FindandZoomObject выполняла следующее: найти выбранные элементы, взять первый, зуммировать по первому и опять подсветить.