Объекты слоя указанием API

Автор antiflamberg, 15.01.24, 15:48:39

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

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

antiflamberg

Всем доброго времени суток!
Есть задача: сделать всю компоновочную геометрию на чертеже тонкими линиями.
Мой алгоритм:
1. Так как компоновочная геометрия проецируется на 1 слой по умолчанию, то перебираю все виды, выделяю все объекты слоя (1).
2. Собрать все объекты в массив и изменить параметр толщины линии на тонкую (до этого еще не дошел).

По первому пункту сразу проблемы: на больших чертежах, где много линий слишком низкая производительность кода. Руками при выборе функции "Выделить"--> "Объекты слоя указанием" получается намного быстрее. А потом из этого массива надо вычистить все ненужные объекты, перебор выйдет слишком медленный.
Возможно кто-то сможет подсказать более оптимальный способ решения этой проблемы. Спасибо!

Кусок кода ниже

from win32com.client import gencache, Dispatch

#  Получи константы
kompas6_constants = gencache.EnsureModule("{75C9F5D0-B5B8-4526-8681-9903C567D2ED}", 0, 1, 0).constants
#  Подключим описание интерфейсов API7
kompas_api7_module = gencache.EnsureModule('{69AC2981-37C0-4379-84FD-5DD2F3C0A520}', 0, 1, 0)
application = Dispatch('Kompas.Application.7')  # или KompasObject.ksGetApplication7()

kompas_document = application.ActiveDocument
kompas_document_2d = kompas_api7_module.IKompasDocument2D(kompas_document)
kompas_document_2d_1 = kompas_api7_module.IKompasDocument2D1(kompas_document_2d)

chooseMng = kompas_document_2d_1.ChooseManager


dimension_type = [kompas6_constants.ksDrLineSeg, kompas6_constants.ksDrCircle, kompas6_constants.ksDrArc]

# менеджер выбора
selection_manager = kompas_document_2d_1.SelectionManager

# Менеджер слоев и видов графического документа.
viewsAndLayersManager = kompas_document_2d.ViewsAndLayersManager
views = viewsAndLayersManager.Views

count_views = views.Count

#layer = layers.Layer(1)

iSelectedObjects = tuple

for i in range(count_views):
     print("Вид " + str(i))
     view = views.View(i)
     layers = view.Layers
     layer = layers.Layer(1)
     selection_manager.Select(layer)

iSelectedObjects = selection_manager.SelectedObjects

#for item in iSelectedObjects:
#    if isinstance(iSelectedObjects, tuple):



Вират Лакх

Зачем вам chooseMng и selection_manager? Зачем выбираете слой? selection_manager.Select(layer) А потом получаете то, что выбрали.
Зачем dimension_type? Который равен [kompas6_constants.ksDrLineSeg, kompas6_constants.ksDrCircle, kompas6_constants.ksDrArc] - переменная называется вроде как типы размеров, а перечислены отрезок, окружность и дуга. Для чего они?
Это вообще что такое?! iSelectedObjects = tuple

ILayerFilterCondition вообще не в тему?
Интересно, что "ObjectCount - Количество объектов в слое" есть, а доступа к объектам слоя как-то не видно.
А если через API5 и итератор? Может там есть по объектам слоя...
https://help.ascon.ru/KOMPAS_SDK/22/ru-RU/ksiterator_kscreateiterator.html?q=ksCreateIterator
Объекты все равно перебирать.
+ Благодарностей: 1

antiflamberg

#2
Цитата: Вират Лакх от 15.01.24, 17:12:33Зачем вам chooseMng и selection_manager? Зачем выбираете слой? selection_manager.Select(layer) А потом получаете то, что выбрали.
Зачем dimension_type? Который равен [kompas6_constants.ksDrLineSeg, kompas6_constants.ksDrCircle, kompas6_constants.ksDrArc] - переменная называется вроде как типы размеров, а перечислены отрезок, окружность и дуга. Для чего они?
Это вообще что такое?! iSelectedObjects = tuple

ILayerFilterCondition вообще не в тему?
Интересно, что "ObjectCount - Количество объектов в слое" есть, а доступа к объектам слоя как-то не видно.
А если через API5 и итератор? Может там есть по объектам слоя...
https://help.ascon.ru/KOMPAS_SDK/22/ru-RU/ksiterator_kscreateiterator.html?q=ksCreateIterator
Объекты все равно перебирать.
ChoseManager - забыл удалить, после тестов.
Selection manager - для выделения объектов в виде--> слое
dimension_type* название переменной заимствованной в чужом коде (так как это и есть мой принцип написания макросов), саму переменную хотел использовать как фильтр. А именно: выделить массив объектов (item) и перебрать их на вхождение к данным типам. Так как менять толщину линии нужно не у всех объектов, а только у отрезков, дуг, кривых и т.п.
iSelectedObjects = tuple # создал пустой кортеж. Сейчас атавизм уже, не нужный, забыл убрать
Api5 попробую спасибо, просто для меня его работа еще менее понятна.
Буду думать, так или иначе.


antiflamberg

Еще так пытался, но тут только одни линии на одном виде еще медленнее выделяются...
Что будет с чертежами на 30+ видом и подумать страшно.

from win32com.client import gencache, Dispatch

#  Получи константы
kompas6_constants = gencache.EnsureModule("{75C9F5D0-B5B8-4526-8681-9903C567D2ED}", 0, 1, 0).constants
#  Подключим описание интерфейсов API7
kompas_api7_module = gencache.EnsureModule('{69AC2981-37C0-4379-84FD-5DD2F3C0A520}', 0, 1, 0)
application = Dispatch('Kompas.Application.7') # или KompasObject.ksGetApplication7()

kompas_document = application.ActiveDocument
kompas_document_2d = kompas_api7_module.IKompasDocument2D(kompas_document)
kompas_document_2d_1 = kompas_api7_module.IKompasDocument2D1(kompas_document_2d)
selection_manager = kompas_document_2d_1.SelectionManager

# Менеджер слоев и видов графического документа.
views_and_layers_manager = kompas_document_2d.ViewsAndLayersManager
# Интерфейс коллекции видов графического документа.IDrawingContainer
views = views_and_layers_manager.Views
view = views.View(2)

layers = view.Layers
layer = layers.Layer(1)

# Интерфейс контейнера объектов вида графического документа
drawing_container = kompas_api7_module.IDrawingContainer(view)
objects = drawing_container.Objects(kompas6_constants.ksDrLineSeg)

for obj in objects:
    if obj.LayerNumber == 1:
        selection_manager.Select(obj)

Вират Лакх

Цитата: antiflamberg от 15.01.24, 20:55:01Selection manager - для выделения объектов в виде--> слое
Зачем вы хотите их выделять? Это долго, тем более каждый объект, а не все разом. Вы же потом руками с ними ничего не собираетесь делать. Их можно получить и работать с ними без выделения.
Цитата: antiflamberg от 15.01.24, 20:55:01iSelectedObjects = tuple # создал пустой кортеж.
Тогда это должно было быть со скобками: iSelectedObjects = tuple()

drawing_container.Objects - может врать. Проверьте на ассоциативном виде, где ещё дорисовано что-то руками.
Из-за этого для таких дел я использую итератор. Вот такие методы:
ksIterator = KompasObject.GetIterator()
ksIterator.ksCreateIterator(тип объектов, родитель объектов)
ksIterator.ksMoveIterator('F')
ksIterator.ksMoveIterator('N')
ksIterator.ksDeleteIterator()
+ Благодарностей: 1

antiflamberg

Цитата: Вират Лакх от 16.01.24, 05:30:11Зачем вы хотите их выделять? Это долго, тем более каждый объект, а не все разом. ...
В этом моя ошибка, спасибо.
Цитата: Вират Лакх от 16.01.24, 05:30:11drawing_container.Objects - может врать. Проверьте на ассоциативном виде, где ещё дорисовано что-то руками.
Из-за этого для таких дел я использую итератор. Вот такие методы:
ksIterator = KompasObject.GetIterator()
ksIterator.ksCreateIterator(тип объектов, родитель объектов)
ksIterator.ksMoveIterator('F')
ksIterator.ksMoveIterator('N')
ksIterator.ksDeleteIterator()
Все понял, буду пытаться.

lavgirb

Цитата: antiflamberg от 15.01.24, 15:48:39Есть задача: сделать всю компоновочную геометрию на чертеже тонкими линиями.
Если задача не программная, а реальная.
Вручную выделить все окружности, отрезки, дуги командой меню Выделить > По свойствам...
И на вкладке Параметры одним махом присвоить всем тонкую линию. Заняло не более 10 с.
Программно, наверное, быстрее и не сделать.
Нет?

antiflamberg

Цитата: lavgirb от 16.01.24, 09:26:03Если задача не программная, а реальная.
Вручную выделить все окружности, отрезки, дуги командой меню Выделить > По свойствам...
И на вкладке Параметры одним махом присвоить всем тонкую линию. Заняло не более 10 с.
Программно, наверное, быстрее и не сделать.
Нет?

Задача реальная: нужно выделить на одном из слоев на всех видах все толстые линии и сделать их тонкими.

lavgirb

Цитата: antiflamberg от 16.01.24, 10:19:30Задача реальная: нужно выделить на одном из слоев на всех видах все толстые линии и сделать их тонкими.
Тогда могут подойти штатные средства Выделить > По свойствам...
Для всех видов виды не указываем, для слоя указываем слой (на скриншоте не указан, со слоями пока не работаю)
После выделения на вкладке Параметры указать стиль Тонкая

выделить.jpg

antiflamberg

При выборе слоя вот такая чушь:
1.png
Если как то можно это обойти - скажите.

lavgirb

Наверное надо выделить Дуги и для них указать слой. Аналогично для отрезков, окружностей и прочего.
+ Благодарностей: 1

lavgirb

Вспомнил, кажется, каждый вид имеет свои слои. Наверное мой совет не подходящий. (
Жаль, что для выбора имеется только = и <>. И отсутствует частичное совпадение.
+ Благодарностей: 1

antiflamberg

Добрые люди, написал вот такой код:
from win32com.client import Dispatch, gencache, VARIANT

# #  Получи константы
kompas6_constants = gencache.EnsureModule("{75C9F5D0-B5B8-4526-8681-9903C567D2ED}", 0, 1, 0).constants
kompas6_constants_3d = gencache.EnsureModule("{2CAF168C-7961-4B90-9DA2-701419BEEFE3}", 0, 1, 0).constants

#  Получи API интерфейсов версии 5
kompas6_api5_module = gencache.EnsureModule("{0422828C-F174-495E-AC5D-D31014DBBE87}", 0, 1, 0)
kompas_object = Dispatch('Kompas.Application.5', None, kompas6_api5_module.KompasObject.CLSID)

#  Получи API интерфейсов версии 7
kompas_api7_module = gencache.EnsureModule("{69AC2981-37C0-4379-84FD-5DD2F3C0A520}", 0, 1, 0)
kompas_api_object = kompas_object.ksGetApplication7()

application = kompas_api_object.Application


kompas_document = application.ActiveDocument
kompas_document_2d = kompas_api7_module.IKompasDocument2D(kompas_document)
kompas_document_2d_1 = kompas_api7_module.IKompasDocument2D1(kompas_document_2d)

# Менеджер слоев и видов графического документа.
views_and_layers_manager = kompas_document_2d.ViewsAndLayersManager
# Интерфейс коллекции видов графического документа.IDrawingContainer
views = views_and_layers_manager.Views
view = views.View(3)

iDrawingContainer = kompas_api7_module.IDrawingContainer(view)
Objects = iDrawingContainer.Objects(0)
#ILineSegments = iDrawingContainer.LineSegments

for obj in Objects:
    if obj.LayerNumber == 1:
        tip = obj.DrawingObjectType
        #print(tip)
        if tip == 1:
            obj.Style = 1
            #print(style)
            obj.Update()

Вопрос: почему не меняется стиль линии в чертеже?

Михаил88

Если вид разрушить то будет работать. С ассоциативным видом почему то не срабатывает.
+ Благодарностей: 1

antiflamberg

Цитата: Михаил88 от 29.01.24, 07:45:35Если вид разрушить то будет работать. С ассоциативным видом почему то не срабатывает.
Спасибо!
с ассоциативными видами круто работает:
IAssociationView = kompas_api7_module.IAssociationView(view)
IAssociationView.VisibleLinesStyle = 5
Только как это сделать по слоям - непонятно..
+ Благодарностей: 1