Сообщество программистов Autodesk в СНГ

ADN Club => AutoCAD .NET API => Тема начата: VitaliyB от 07-02-2022, 17:33:23

Название: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 17:33:23
Добрый день! Не могу понять следующую вещь: при выборе секущей рамкой (GetSelection) в момент, когда курсор включается для выделения секущей рамкой одновременно с этим АВТОМАТИЧЕСКИ выбирается один из ранее выделенных объектов этой же командой:
Вот сам код:
 
Код - C# [Выбрать]
  1. Document doc = acadApp.DocumentManager.MdiActiveDocument;
  2.             Database db = doc.Database;
  3.             Editor ed = doc.Editor;
  4.             TypedValue[] acTypValAr = new TypedValue[2];
  5. acTypValAr.SetValue(new TypedValue((int)DxfCode.Start, FiltrPerem.nameObj), 0);
  6. acTypValAr.SetValue(new TypedValue((int)DxfCode.LayerName, FiltrPerem.nameLayer), 1);
  7.                    
  8.                
  9.  
  10.                 // Назначение критериев фильтра объекту SelectionFilter
  11.                
  12.                 SelectionFilter acSelFtr = new SelectionFilter(acTypValAr);
  13.                 // Запрос выбора объектов на чертеже
  14.  
  15.                 PromptSelectionResult acSSPrompt;
  16.              
  17.                 acSSPrompt = ed.GetSelection(acSelFtr);
  18.  

(https://i.ibb.co/0Zy75yH/2022-02-07-17-28-56.png) (https://ibb.co/jGkNtkn)
pic code (https://imgbb.com/)
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 17:41:11
одновременно с этим АВТОМАТИЧЕСКИ выбирается один из ранее выделенных объектов этой же командой:
Если я правильно понял о чем ты, то так и должно быть. Нюансы могут быть связаны с контекстом выполнения и флагами команды (если команда выполняется из команды).
Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 17:43:01
почему? я же должен выбрать секущей рамкой объекты и только после этого они должны попасть в набор объектов?
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 17:45:16
почему? я же должен выбрать секущей рамкой объекты и только после этого они должны попасть в набор объектов?
Потому что сразу в набор попадают примитивы предварительного выбора, если они удовлетворяют фильтру. Ну а потом уже работает интерактивный выбор пользователем.
Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 17:47:29
а как сделать только интерактивный выбор пользователя в таком случае? чтобы сами примитивы не попадали в выбор?
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 17:48:05
Важно понимать контекст выполнения и флаги команды.
Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 17:53:27
Флаги - CommandFlags? не ставил...

Причем предварительно выбора не происходит, если в строке FiltrPerem.nameLayer - один слой. Если несколько через запятую происходит предварительный выбор без пользователя.

Код - C# [Выбрать]
  1. acTypValAr.SetValue(new TypedValue((int)DxfCode.LayerName, FiltrPerem.nameLayer), 1)


Код - C# [Выбрать]
  1. Document doc = acadApp.DocumentManager.MdiActiveDocument;
  2.             Database db = doc.Database;
  3.             Editor ed = doc.Editor;
  4.             TypedValue[] acTypValAr = new TypedValue[2];
  5. acTypValAr.SetValue(new TypedValue((int)DxfCode.Start, FiltrPerem.nameObj), 0);// имена объектов (примитивов) через запятую
  6. acTypValAr.SetValue(new TypedValue((int)DxfCode.LayerName, FiltrPerem.nameLayer), 1); //имена слоев через запятую
  7.                    
  8.                
  9.  
  10.                 // Назначение критериев фильтра объекту SelectionFilter
  11.                
  12.                 SelectionFilter acSelFtr = new SelectionFilter(acTypValAr);
  13.                 // Запрос выбора объектов на чертеже
  14.  
  15.                 PromptSelectionResult acSSPrompt;
  16.              
  17.                 acSSPrompt = ed.GetSelection(acSelFtr);
Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 18:05:26
У меня есть панель, где отображаются слои в listbox. Я выбираю там слои. Далее включаю команду для выбора объектов по фильтру, куда передаются имена выбранных слоев в панели. и вот в этом конкретном случае на экране нарисованы прямоугольника на слоях "1_11.02.2022_3_4_5" и на слоях "1_07.02.2022_3_4_5". Интересно, что без участия пользователя выбирается только один конкретный прямоугольник слоя "1_11.02.2022_3_4_5" (на чертеже их 2). Если критерием фильтра ставить имя слоя "1_07.02.2022_3_4_5" - не выбирается без пользователя ничего (т.е. как и задумывалось). Но когда в критерии фильтра попадает имя слоя "1_11.02.2022_3_4_5" - автокад сам выбирает один конкретный прямоугольник... Не понимаю, почему и как это победить.

(https://i.ibb.co/s1QR9mn/2022-02-07-17-58-53.png) (https://ibb.co/kD0B2Hj)
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 18:12:04
Флаги - CommandFlags? не ставил...
Не понял. И вообще не понял где именно выполняется этот обрывок кода.
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 18:14:55
Далее включаю команду для выбора объектов по фильтру
Что значит "включаешь"? Включать команду нельзя. Её можно только выполнить.
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 18:41:18
Но когда в критерии фильтра попадает имя слоя "1_11.02.2022_3_4_5" - автокад сам выбирает один конкретный прямоугольник... Не понимаю, почему и как это победить.
Учти, что некоторые знаки в именах слоёв, именах блоков и т.д. используются как шаблонные знаки. В твоем случае это точки. Чтобы они воспринимались как обычные знаки их нужно устранить. Для этой цели перед ними ставится знак "`". Т.е. в твоём случае это должна быть строка "1_11`.02`.2022_3_4_5". Ну а если в общем случае неизвестно есть ли шаблонные символы в строке, то можно их все устранить, добавив перед каждым символом  "`".

Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 21:31:31
Даже если записать в фильтре явно имя слоя, он все равно почему-то сам выбирает определенный прямоугольник.

Код - C# [Выбрать]
  1.  
  2.  
  3.                acTypValAr.SetValue(new TypedValue((int)DxfCode.Start, FiltrPerem.nameObj), 0);
  4.  
  5.                
  6.                 acTypValAr.SetValue(new TypedValue((int)DxfCode.LayerName, "1_11`.02`.2022_3_4_5"), 1);// ВОТ ТУТ ПРОБУЮ ЗАДАТЬ ИМЯ СЛОЯ ЯВНО
  7.                    
  8.                
  9.  
  10.                 // Назначение критериев фильтра объекту SelectionFilter
  11.                
  12.                 SelectionFilter acSelFtr = new SelectionFilter(acTypValAr);
  13.                 // Запрос выбора объектов на чертеже
  14.  
  15.                 PromptSelectionResult acSSPrompt;
  16.            
  17.                 acSSPrompt = ed.GetSelection(acSelFtr) // НА  ЭТОМ ЭТАПЕ ПЕРЕД ТЕМ, КАК ДАТЬ ПОЛЬЗОВАТЕЛЮ ВОСПОЛЬЗОВАТЬСЯ СЕКУЩЕЙ РАМКОЙ, АВТОКАД ПРЕДВАРИТЕЛЬНО ВЫБИРАЕТ ОДИН ИЗ ДВУХ ПРЯМОУГОЛЬНИКОВ, ПРИНАДЛЕЖАЩИХ СЛОЮ ;
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 21:42:29
VitaliyB,
Мы снова говорим на разных языках. Из того что ты написал непонятен контекст выполнения кода, выполняется ли он в контексте документа или приложения, есть ли набор предварительного выбора и т.д. По тому что ты написал выше я ничего сказать не могу.
Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 21:56:14
Постараюсь объяснить... Вот код данной команды:

Код - C# [Выбрать]
  1. [CommandMethod("вв_(ПТО_№2:выбор по фильтру)")]
  2.         public void Vibor_Setup()
  3.         {
  4.                
  5.             Document doc = acadApp.DocumentManager.MdiActiveDocument;
  6.             Database db = doc.Database;
  7.             Editor ed = doc.Editor;
  8.                         //выбираем объекты по заданным критериям
  9.                        
  10.             TypedValue[] acTypValAr = new TypedValue[2];
  11.             acTypValAr.SetValue(new TypedValue((int)DxfCode.Start, FiltrPerem.nameObj), 0); //фильтр по типам примитивов
  12.             acTypValAr.SetValue(new TypedValue((int)DxfCode.LayerName, FiltrPerem.nameLayer), 1); //фильтр по именам слоев
  13.                    
  14.                 // Назначение критериев фильтра объекту SelectionFilter
  15.                
  16.                 SelectionFilter acSelFtr = new SelectionFilter(acTypValAr);
  17.                 // Запрос выбора объектов на чертеже
  18.  
  19.                 PromptSelectionResult acSSPrompt;
  20.                
  21.                 acSSPrompt = ed.GetSelection(acSelFtr);
  22.  
  23.  
  24.                 try
  25.                  {
  26.                     using (Transaction trans = db.TransactionManager.StartTransaction())
  27.                     {
  28.  
  29.                        
  30.                        
  31.                         List<ObjectId> objects = new List<ObjectId>();
  32.  
  33.                                                         //перебираем выбранные объекты и заносим в public List'ы для дальнейшего использования
  34.                                                        
  35.                     foreach (ObjectId asObjId in acSSPrompt.Value.GetObjectIds())
  36.                         {
  37.                                                         objects.Add(asObjId)
  38.                                                 }
  39.  
  40.                    
  41.                         ed.SetImpliedSelection(objects.ToArray());
  42.                         ac_Vibor.objects.Clear();
  43.                         ac_Vibor.objects.AddRange(objects.ToArray());//список объектов, который в дальнейшем будет использоваться при вызове других команд
  44.  
  45.  
  46.  
  47.                         trans.Commit();
  48.                        
  49.                     }
  50.  
  51.                 }
  52.                 catch (System.NullReferenceException)
  53.                 {
  54.                     ed.WriteMessage("\nНичего не найдено!!!");
  55.                 }
  56.  
  57.                 catch (Autodesk.AutoCAD.Runtime.Exception ex)
  58.                 {
  59.                     acadApp.ShowAlertDialog(ex.Message);
  60.                 }
  61.            
  62.            
  63.         }
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 22:00:51
VitaliyB,
1. Не издевайся над AutoCAD'ом - давай нормальные имена командам. Очень желательно только английские буквы, цифры и символы подчеркивания.
2. Вот это всё портит в твоём коде: ed.SetImpliedSelection(...).  Зачем оно???
3. Как запускается эта команда? Ты же запускаешь её из палитры?
4. Не вижу зачем в твоём коде используется транзакция.
Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 22:03:19
2. уже не помню, давно писал  :-\ но проблему, с которой я борюсь удаление этой строчки не решает
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 22:06:32
2. уже не помню, давно писал  :-\ но проблему, с которой я борюсь удаление этой строчки не решает
Эта строчка добавляет объекты в набор предварительного выбора. Впрочем, так как у тебя в этой команде не установлены флаги Redraw и UsePickSet, то возможно всё еще хуже.
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 22:07:06
3. Как запускается эта команда? Ты же запускаешь её из палитры?
Код запуска этой команды можно увидеть?
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 22:12:42
И еще. Ознакомься с этой темой: https://adn-cis.org/forum/index.php?topic=415.0
Похоже что у тебя аналогичная проблема.
Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 22:14:02
нет, я запускаю ее через командную строку - ввожу команду "вв_(ПТО_№2:выбор по фильтру)". в палитре я выбираю набор слоев и примитивов, которые передаются в фильтры для этой команды (параметры FiltrPerem.nameObj и FiltrPerem.nameLayer)


Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 22:14:38
(https://i.ibb.co/9pshfrQ/2022-02-07-22-11-11.png) (https://ibb.co/fX49Kxj)
img чем открыть (https://ru.imgbb.com/)
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 22:17:29
VitaliyB,
Посмотри ссылку, которую я дал тебе выше.
Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 22:22:52
уже смотрю, спасибо!
кстати, поменял имя команды на "CommandMethod("вв_2_выбор_по_фильтру")" - и прямоугольник перестал выбираться сам... в этом есть какая-то логика?  :o
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 22:45:37
VitaliyB,
Ааааааааааааааааааааааааааааа! Ну ты даёшь! Имя команды ни в коем случае не может содержать пробелы!!! Только сейчас это заметил. Пробел равносилен нажатию клавиши ENTER на клавиатуре. Т.е. фактически после запуска твоей команды в момент, когда у пользователя должен запрашиваться выбор объектов, происходит нажатие клавиши ENTER.
Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 23:04:43
Ох, действительно, и слона не заметил и всю голову сломал. Буду тестировать теперь на практических задачах. Надеюсь, дело было в этом. Спасибо!
Александр, может быть подскажите еще, где можно почитать про CommandFlags толковые описания?
Название: Re: Выбор объектов с фильтром
Отправлено: Александр Ривилис от 07-02-2022, 23:12:45
Александр, может быть подскажите еще, где можно почитать про CommandFlags толковые описания?
Например в документации ObjectARX SDK Docs. Вот здесь это описано: https://help.autodesk.com/view/OARX/2022/ENU/?guid=GUID-F77E8FE0-8034-4704-93BD-F717608F8223
Название: Re: Выбор объектов с фильтром
Отправлено: VitaliyB от 07-02-2022, 23:20:41
спасибо!