| Правила | Регистрация | Пользователи | Поиск | Сообщения за день | Все разделы прочитаны |  Справка по форуму | Файлообменник |

Вернуться   Форум DWG.RU > Программное обеспечение > Программирование > Почему некорректно работает vla-intersectwith?

Почему некорректно работает vla-intersectwith?

Ответ
Поиск в этой теме
Непрочитано 20.07.2006, 12:46 #1
Почему некорректно работает vla-intersectwith?
Кулик Алексей aka kpblc
Moderator
 
LISP, C# (ACAD 200[9,12,13,14])
 
С.-Петербург
Регистрация: 25.08.2003
Сообщений: 38,811

Попробуйте запустить следующий код:
Код:
[Выделить все]
  (vlax-safearray->list
    (vlax-variant-value
      (vla-intersectwith
	(vla-adddimaligned
	  (vla-get-modelspace
	    (vla-get-activedocument (vlax-get-acad-object))
	    ) ;_ end of vla-get-modelspace
	  (vlax-3d-point '(100. 100. 0.))
	  (vlax-3d-point '(300. 500. 0.))
	  (vlax-3d-point '(800. 900. 0.))
	  ) ;_ end of vla-adddimaligned
	(vla-addline
	  (vla-get-modelspace
	    (vla-get-activedocument (vlax-get-acad-object))
	    ) ;_ end of vla-get-modelspace
	  (vlax-3d-point '(50. -70. 0.))
	  (vlax-3d-point '(580. 520. 0.))
	  ) ;_ end of vla-addline
	acextendnone
	) ;_ end of vla-IntersectWith
      ) ;_ end of vlax-variant-value
    ) ;_ end of vlax-safearray->list
Какие у кого результаты получаются? Потому как у меня полная лажа:
ACAD 2005 Eng + SP1 + мои лиспы : одна точка
ACAD 2005 Eng + SP1 чистый : две точки
ADT 2005 Eng + SP1 + мои лиспы : две точки
ADT 2005 End + SP1 чистый : две точки
ADT 2005 Eng As AutoCAD + SP1 + мои лиспы : одна точка
ADT 2005 Eng As AutoCAD + SP1 чистый : две точки
ADT 2006 Rus + SP1 + мои лиспы : две точки
ADT 2006 Rus + SP1 чистый : две точки
ADT 2006 Rus As AutoCAD + SP1 + мои лиспы: две точки
ADT 2006 Rus As AutoCAD + SP1 чистый : две точки
То есть ошибка "плавает". Лиспы одни и те же, грузятся с одного и того же места.
Чей это глюк - мой или ActiveX? Что может так подрубить эту функцию?
__________________

---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Просмотров: 9821
 
Непрочитано 20.07.2006, 13:14
#2
aldt


 
Регистрация: 12.02.2006
Сообщений: 114


ACAD 2007 Eng
(100.0 -14.3396 0.0 541.118 476.716 0.0)
aldt вне форума  
 
Непрочитано 20.07.2006, 13:31
#3
VVA

Инженер LISP
 
Регистрация: 11.05.2005
Минск
Сообщений: 6,910
<phrase 1= Отправить сообщение для VVA с помощью Skype™


Acad 2004 Rus Новый файл
(100.0 -14.3396 0.0 541.118 476.716 0.0)
Интересно девки поляшут:
В приложенном файле этот же код выдает
(100.0 -14.3396 0.0 540.581 476.119 0.0)
Почему десятые не совпадают :?:
[ATTACH]1153387872.dwg[/ATTACH]
VVA вне форума  
 
Автор темы   Непрочитано 20.07.2006, 13:38
#4
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 38,811


Во-во, состояние странное (хотя и выдает по 2 точки...)
__________________

---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 20.07.2006, 14:35
#5
VVA

Инженер LISP
 
Регистрация: 11.05.2005
Минск
Сообщений: 6,910
<phrase 1= Отправить сообщение для VVA с помощью Skype™


В порядке бреда

Код:
[Выделить все]
(setq dim (vla-adddimaligned 
     (vla-get-modelspace 
       (vla-get-activedocument (vlax-get-acad-object)) 
       ) ;_ end of vla-get-modelspace 
     (vlax-3d-point '(100. 100. 0.)) 
     (vlax-3d-point '(300. 500. 0.)) 
     (vlax-3d-point '(800. 900. 0.)) 
     ))
(setq lin (vla-addline 
     (vla-get-modelspace 
       (vla-get-activedocument (vlax-get-acad-object)) 
       ) ;_ end of vla-get-modelspace 
     (vlax-3d-point '(50. -70. 0.)) 
     (vlax-3d-point '(580. 520. 0.)) 
     ))
(setq edim (handent (vla-get-Handle dim)))
(setq dimbl (vla-item (vla-get-blocks *kpblc-activedoc*)(cdr (assoc 2 (entget edim)))))

(vlax-for item dimbl
(terpri)
(princ (vla-get-ObjectName item))
(princ " =")
  (if
  (VL-CATCH-ALL-ERROR-P
    (VL-CATCH-ALL-APPLY
      '(lambda ( )
	 (if (vlax-method-applicable-p item "IntersectWith")
	   (princ (vlax-safearray->list (vlax-variant-value
		(vla-intersectwith item lin acextendnone))))))))
  (princ " error ")))
И пересчитать точки. Правда пока не знаю как. Но по крайней мере видно что 2 отрезка дают пересечение
VVA вне форума  
 
Автор темы   Непрочитано 20.07.2006, 14:50
#6
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 38,811


Пересечение-то они дают, хорошая идея. Только почему там еще и пересечение блоков участвует, я не очень догнал, если честно. Придется учитывать дополнительно. Все равно thnx.
===
Добавлено.
VVA, я тебе уже говорил, что ты гений?
__________________

---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 20.07.2006, 22:23
#7
Лентяй

Project Engineer
 
Регистрация: 05.01.2005
Лос Анджелес
Сообщений: 1,392


Цитата:
Сообщение от kpblc
Пересечение-то они дают, хорошая идея. Только почему там еще и пересечение блоков участвует, я не очень догнал, если честно.
Участвует потому, что метод vla-IntersectWith учитывает и блоки, но (ВНИМАМНИЕ!) учитывает не пересечение ЭЛЕМЕНТОВ БЛОКОВ, а их ГАБАРИТОВ (boundaries), получаемых методом vla-getBoundingBox.
Лентяй вне форума  
 
Автор темы   Непрочитано 21.07.2006, 09:10
#8
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 38,811


Я попросту ввел проверку на имя объекта. А за объяснения отдельный thanx
__________________

---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 21.07.2006, 09:47
#9
VVA

Инженер LISP
 
Регистрация: 11.05.2005
Минск
Сообщений: 6,910
<phrase 1= Отправить сообщение для VVA с помощью Skype™


Если надо, то с блоками можно поступить так же

Код:
[Выделить все]
;|============== lib:GetInters ====================
*  Возвращает все пересечения между двумя объектами
*  Один из элементов может быть блоком
   Arguments [Type]:
   FstO = Первый объет  [VLA-OBJECT]
   NxtO = Второй объект [VLA-OBJECT]
   Mde = Тип пересечения [INT]
         Constants:
         - acExtendNone           Does not extend either object.
         - acExtendThisEntity     Extends the FstO object.
         - acExtendOtherEntity    Extends the NxtO object.
         - acExtendBoth           Extends both objects.
  Возвращает [Type]:
   > Список точек '((1.0 1.0 0.0)...[list]
   > Nil если пересечений не найдено
 Notes:
   - Один из элементов должен быть не блок
=======================================================|; 
(defun lib:GetInters (FstO NxtO Mde / IntLst PtLst)
 (cond
   ((and (= (vla-get-ObjectName FstO) "AcDbBlockReference")
	 (not (vlax-property-available-p FstO 'Path))) ;_not Xref
    (setq PtLst (lib:GetBlockInters FstO NxtO Mde)))
   ((and (= (vla-get-ObjectName NxtO) "AcDbBlockReference")
	 (not (vlax-property-available-p NxtO 'Path))) ;_not Xref
    (setq PtLst (lib:GetBlockInters NxtO FstO Mde)))
   ((or ;_Xref
    (vlax-property-available-p FstO 'Path)
    (vlax-property-available-p NxtO 'Path))
    (setq PtLst nil))
   (t
    (setq IntLst (vlax-invoke FstO 'IntersectWith NxtO Mde))
    (if IntLst
      (setq PtLst (lib:group-by-num IntLst 3))
      (setq PtLst nil))
    ))
  PtLst
  )
;|========== Function lib:GetBlockInters =========================
; Returns all intersection points between a Block and an object.
; Copyright:
;   ©2001-2002 MENZI ENGINEERING GmbH, Switzerland
; Arguments [Type]:
;   Blk = Block object [VLA-OBJECT]
;   Obj = Object [VLA-OBJECT]
;   Mde = Intersection mode [INT]
;         Constants:
;         - acExtendNone           Does not extend either object.
;         - acExtendThisEntity     Extends the Fst object.
;         - acExtendOtherEntity    Extends the Nxt object.
;         - acExtendBoth           Extends both objects.
; Return [Type]:
;   > list of points '((1.0 1.0 0.0)...[list]
;   > Nil if no intersection found
; Notes:
;   - Because of a (reported) bug in A2k4/A2k5/A2k6, the used explode method
;     will fail on NUS blocks. No limitations in A2k, A2ki and A2k2
|; 
(defun lib:GetBlockInters  (Blk Obj Mde / ObjNme PntLst TmpVal)
 (foreach memb (vlax-invoke Blk 'Explode)
  (setq ObjNme (vla-get-ObjectName memb))
  (cond
   ((or
     (not (vlax-method-applicable-p memb 'IntersectWith))
     (and
      (eq ObjNme "AcDbHatch")
      (eq (strcase (vla-get-PatternName memb)) "SOLID")
     )
     (eq ObjNme "AcDb3dSolid")
    )
   )
   ((eq ObjNme "AcDbBlockReference")
    (if (setq TmpVal (lib:GetBlockInters memb Obj Mde))
     (setq PntLst (append PntLst TmpVal))
    )
   )
   (T
    (if (setq TmpVal (lib:GetInters memb Obj Mde))
     (setq PntLst (append PntLst TmpVal))
    )
   )
  )
  (vla-Delete memb)
 )
 PntLst
)
(defun lib:group-by-num (lst num / ls ret)
(if (= (rem (length lst) num ) 0)
 (progn (setq ls nil)
  (repeat (/ (length lst) num)
    (repeat num (setq ls (cons (car lst) ls) lst (cdr lst)))
  (setq ret (append ret (list (reverse ls))) ls nil)))) ret)
Там правда есть такая запись
; Notes:
; - Because of a (reported) bug in A2k4/A2k5/A2k6, the used explode method
; will fail on NUS blocks. No limitations in A2k, A2ki and A2k2
Может кто знает, что за NUS blocks?

Последний раз редактировалось VVA, 03.11.2010 в 09:20. Причина: ф-ция lib:group-by-num
VVA вне форума  
 
Автор темы   Непрочитано 21.07.2006, 09:51
#10
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 38,811


Non-Uniformly Scaled
Масштабированные с разными коэффициентами по разным осям
__________________

---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 01.11.2010, 15:52
#11
Tonic


 
Регистрация: 26.06.2007
Воронеж
Сообщений: 151


Vla-IntersectWith как-то странно работает там, где вопросов не должно возникать. Ведь если линия пересекает блок "насквозь", Vla-IntersectWith должен вернуть 2 точки пересечения с границами этого блока!
Тем не менее, у меня этот метод выдаёт то 2 точки, то 4 точки (дважды одни и те же точки), то вообще 0!
В качестве подопытных объектов использовались 3 варианта блоков: в виде квадрата (отрезками) с окружностью внутри; квадрат (отрезками) с парой полилиний внутри; окружность (в виде блока).

Код:
[Выделить все]
(vl-load-com)
(setq temp_line (vlax-ename->vla-object (car (entsel))) temp_block (vlax-ename->vla-object (car (entsel))))
(setq inter nil inter (vla-intersectwith temp_line temp_block acExtendNone))
(vlax-safearray-get-u-bound (vlax-variant-value inter) 1)
AutoCAD 2011. Эта функция ненормальная или я что-то не так делаю?

Последний раз редактировалось Tonic, 01.11.2010 в 16:20.
Tonic вне форума  
 
Непрочитано 02.11.2010, 17:46
#12
Tonic


 
Регистрация: 26.06.2007
Воронеж
Сообщений: 151


Обнаруживаются странные вещи. При запуске программы Евгения Елпанова:
Код:
[Выделить все]
(defun inters_block (/ ENT I INTER_LST)
(setq ent
(vlax-ename->vla-object
(car
(entsel "\nУкажите линию, полилинию или дугу "))))
(foreach a1
(vlax-safearray->list
(vlax-variant-value
(vla-explode
(vlax-ename->vla-object
(car (entsel "\nУкажите блок "))))))
(if(not(vl-catch-all-error-p
(setq
i(vl-catch-all-apply
(function vlax-safearray->list)
(list (vlax-variant-value
(VLA-INTERSECTWITH ent a1 0)))))))
(foreach a2
(mapcar (function
(lambda (x1 x2 x3)
(list x1 x2 x3))) i (cdr i) (cddr i))
(setq inter_lst (cons a2 inter_lst))))
(vla-delete a1)
(vlax-release-object a1))
inter_lst
)
для блока, в который входит один лишь примитив - circle, получается список пересечений с линией такого вида:

Код:
[Выделить все]
((-11542.2 440.491 0.0)
 (0.0 -11542.2 440.491)
 (841.311 0.0 -11542.2)
 (-11840.4 841.311 0.0))
Судя по совпадению некоторых чисел, метод VLA-INTERSECTWITH сходит с ума. В особенности удивляет координата Z в двухмерной плоскости.

У кого-нибудь есть соображения по поводу работы этого метода, да и вообще способа нахождения пересечения линии с блоком?
Tonic вне форума  
 
Непрочитано 02.11.2010, 18:54
#13
VVA

Инженер LISP
 
Регистрация: 11.05.2005
Минск
Сообщений: 6,910
<phrase 1= Отправить сообщение для VVA с помощью Skype™


Приложи тогда уже и файлик с полилинией и блоком, в который входит лишь circle
__________________
Как использовать код на Лиспе читаем здесь
VVA вне форума  
 
Автор темы   Непрочитано 02.11.2010, 18:56
#14
Кулик Алексей aka kpblc
Moderator

LISP, C# (ACAD 200[9,12,13,14])
 
Регистрация: 25.08.2003
С.-Петербург
Сообщений: 38,811


По моему опыту - IntersectWith корректно работает только с элементарными объектами, находящимися в одном пространстве. В пространстве модели, в пространстве листа, в пространстве блока.
__________________

---
Обращение ко мне - на "ты".
Все, что сказано - личное мнение.
Кулик Алексей aka kpblc вне форума  
 
Непрочитано 02.11.2010, 19:02
#15
VVA

Инженер LISP
 
Регистрация: 11.05.2005
Минск
Сообщений: 6,910
<phrase 1= Отправить сообщение для VVA с помощью Skype™


Tonic, lib:GetBlockInters c поста #9 пробовал? там IntersectWith применяется к примитивам блока, а не к самому блоку.
__________________
Как использовать код на Лиспе читаем здесь
VVA вне форума  
 
Непрочитано 02.11.2010, 21:50
#16
Tonic


 
Регистрация: 26.06.2007
Воронеж
Сообщений: 151


Цитата:
Сообщение от VVA Посмотреть сообщение
lib:GetBlockInters c поста #9 пробовал?
Там используется функция lib:group-by-num, которой нет в коде.
Цитата:
Сообщение от VVA Посмотреть сообщение
там IntersectWith применяется к примитивам блока, а не к самому блоку
Ну так и в коде Евгения этот метод применяется к объектам, полученным с помощью vla-explode - и всё равно некорректно работает!
Цитата:
Сообщение от VVA Посмотреть сообщение
Приложи тогда уже и файлик с полилинией и блоком, в который входит лишь circle
Цитата:
Сообщение от VVA Посмотреть сообщение
Приложи тогда уже и файлик с полилинией и блоком, в который входит лишь circle
Дело не в каком-то конкретном блоке. Достаточно создать любой круг, затем добавить его в _-block и сразу вставить. Перечеркнуть отрезком - и всё, шаблон готов. В результате получается 4 непонятных точки.
Цитата:
Сообщение от Кулик Алексей aka kpblc Посмотреть сообщение
По моему опыту - IntersectWith корректно работает только с элементарными объектами, находящимися в одном пространстве. В пространстве модели, в пространстве листа, в пространстве блока.
А что значит "в пространстве блока"? Всё же странно: со многими блоками работает корректно... может, дело в окружности, входящей в блок? Так нет - ведь ищется пересечение с границами блока, а не его примитивами (я имею ввиду не приведённый кода, а сам метод).

Есть какие-либо другие алгоритмы замены этого метода?
Tonic вне форума  
 
Непрочитано 03.11.2010, 09:26
#17
VVA

Инженер LISP
 
Регистрация: 11.05.2005
Минск
Сообщений: 6,910
<phrase 1= Отправить сообщение для VVA с помощью Skype™


Цитата:
Сообщение от Tonic Посмотреть сообщение
Там используется функция lib:group-by-num, которой нет в коде.
Добавил

Цитата:
Сообщение от Tonic Посмотреть сообщение
Достаточно создать любой круг, затем добавить его в _-block и сразу вставить. Перечеркнуть отрезком - и всё, шаблон готов. В результате получается 4 непонятных точки.
Все сделал как ты и говорил. Поэтому и прошу файлик
Цитата:
Команда: (lib:GetBlockInters (vlax-ename->vla-object (car(entsel "\nSelect block: "))) (vlax-ename->vla-object (car(entsel "\nSelect line: "))) acExtendNone)

Select block:
Select line: ((354.209 262.04 0.0) (373.203 235.856 0.0))
__________________
Как использовать код на Лиспе читаем здесь
VVA вне форума  
 
Непрочитано 03.11.2010, 09:53
#18
Tonic


 
Регистрация: 26.06.2007
Воронеж
Сообщений: 151


VVA, с Вашим кодом действительно правильно работает. Ну, кроме вылета на блоках со штриховкой - там надо написать
Код:
[Выделить все]
(eq (strcase (vla-get-PatternName memb)) "_SOLID")
Но всё же такая, вроде бы, несложная задача, как поиск крайних точек пересечения блока и линии не кажется такой простой. Я имею ввиду задачу вроде разрыва линии в месте её пересечения с блоком. Чем хорош метод IntersectWith, так это тем, что он находит либо одну, либо две точки (в зависимости от того, вышла ли линия за пределы блока после пересечения с ним или нет), хоть и имеется большая погрешность в границах (из-за того, что ищется пересечения с "рамкой" блока). А в случае, когда идёт перебор точек пересечения со всеми объёктами блока, ситуация становится непонятной и требующей длинных алгоритмов поиска нужных границ.
Tonic вне форума  
 
Непрочитано 03.11.2010, 10:18
#19
VVA

Инженер LISP
 
Регистрация: 11.05.2005
Минск
Сообщений: 6,910
<phrase 1= Отправить сообщение для VVA с помощью Skype™


Цитата:
Сообщение от Tonic Посмотреть сообщение
Я имею ввиду задачу вроде разрыва линии в месте её пересечения с блоком.
Хитрый блок тебе в помощь
__________________
Как использовать код на Лиспе читаем здесь
VVA вне форума  
 
Непрочитано 03.11.2010, 10:43
#20
Tonic


 
Регистрация: 26.06.2007
Воронеж
Сообщений: 151


Цитата:
Сообщение от VVA Посмотреть сообщение
Хитрый блок тебе в помощь
Идея интересная, но Express Tools для Wipeout'а может и не оказаться. Тогда, видимо, блок перестанет быть таким уж хитрым и снова станет бесхитростным.
Tonic вне форума  
Ответ
Вернуться   Форум DWG.RU > Программное обеспечение > Программирование > Почему некорректно работает vla-intersectwith?

Инженерная печать чертежей и проектной документации до А0+
Размещение рекламы
Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск