Геометрические операции над сборками и деталями

Автор Тема: Геометрические операции над сборками и деталями  (Прочитано 2356 раз)

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

Оффлайн VladislavАвтор темы

  • ADN OPEN
  • ***
  • Сообщений: 210
  • Карма: 0
Добрый день.
Мне необходимо повернуть всю сборку верхнего уровня (то есть фактически всю модель) вокруг одной из
координатных осей. Насколько я понял, делается это заданием свойства Transformation для каждой подсборки.
Но результат совсем не тот, который нужен. Подскажите пожалуйста, как выполнить поворот правильно.
Спасибо за ответы.

Оффлайн R.I.Chernov

  • ADN Club
  • *****
  • Сообщений: 565
  • Карма: 18
Не совсем понятно, в чем ваша проблема: вы не знаете команд, или знаете, но не получается получить с их помощью корректный результат?
Насколько я помню, поворот осуществляется относительно собственных осей деталей и подсборок, а не вокруг главной сборки, в которой они находятся. То есть вам их надо сначала повернуть, а потом рассчитать и задать, где будет находиться их начало координат после преобразования в координатах общей сборки.
В программировании я новичок...но ненадолго! ;)

Оффлайн VladislavАвтор темы

  • ADN OPEN
  • ***
  • Сообщений: 210
  • Карма: 0
   Не получается корректный результат. Я использую задание свойства Transformation.
Присваиваю ему значение матрицы поворота. Повернуть же необходимо сохранив относительное
расположение подсборок и деталей. Похоже, что я не знаю, именно как сохранить взаимное расположение.

Оффлайн R.I.Chernov

  • ADN Club
  • *****
  • Сообщений: 565
  • Карма: 18
Во вложении к сообщению сборка, с которой работает нижеуказанный код. Сразу поясню, я не пишу в VBA, потому не претендую на "красоту" выкладок. Самую важную информацию читайте в "паст скриптуме" сообщения.

Код - Visual Basic [Выбрать]
  1.     Dim oTG As TransientGeometry
  2.     Dim oXAxis As Vector
  3.     Dim oYAxis As Vector
  4.     Dim oZAxis As Vector
  5.     Dim oStPoint As Point
  6.     'координаты и углы поворотов
  7.    Dim X As Double: Dim Y As Double: Dim Z As Double
  8.     Dim X_rot As Double: Dim Y_rot As Double: Dim Z_rot As Double
  9.     Dim PI As Double
  10.  
  11. Sub rotation()
  12.     Dim oCD As AssemblyComponentDefinition
  13.     Set oCD = ThisApplication.ActiveDocument.ComponentDefinition
  14.     Dim oOcc_1 As ComponentOccurrence
  15.     Set oOcc_1 = oCD.Occurrences.ItemByName("1")
  16.     Dim oOcc_2 As ComponentOccurrence
  17.     Set oOcc_2 = oCD.Occurrences.ItemByName("2")    
  18.  
  19.     Set oTG = ThisApplication.TransientGeometry
  20.  
  21.     Set oXAxis = oTG.CreateVector(1, 0, 0)
  22.     Set oYAxis = oTG.CreateVector(0, 1, 0)
  23.     Set oZAxis = oTG.CreateVector(0, 0, 1)
  24.     Set oStPoint = oTG.CreatePoint(0, 0, 0)
  25.     PI = Atn(1) * 4
  26.    
  27.     'первый элемент на стартовую позицию
  28.    X = 0: Y = 1000: Z = 0
  29.     X_rot = PI / 2: Y_rot = 0: Z_rot = PI
  30.     Call Transform(oOcc_1, X, Y, Z, X_rot, Y_rot, Z_rot)
  31.    
  32.     'второй элемент на стартовую позицию
  33.    X = 0: Y = 1200: Z = 200
  34.     X_rot = 0: Y_rot = PI: Z_rot = 0
  35.     Call Transform(oOcc_2, X, Y, Z, X_rot, Y_rot, Z_rot)
  36.  
  37.     'тут выполнение программы стоит остановить, чтобы посмотреть что получилось :)
  38.    
  39.    
  40.     'первый элемент на конечную позицию
  41.    X = -1000: Y = 0: Z = 0
  42.     X_rot = PI / 2: Y_rot = 0: Z_rot = -PI / 2
  43.     Call Transform(oOcc_1, X, Y, Z, X_rot, Y_rot, Z_rot)
  44.  
  45.    
  46.     'второй элемент на конечную позицию
  47.    X = -1200: Y = 0: Z = 200
  48.     X_rot = 0: Y_rot = PI: Z_rot = PI / 2
  49.     Call Transform(oOcc_2, X, Y, Z, X_rot, Y_rot, Z_rot)
  50.    
  51.     ' обратите внимание, как координаты X и Y меняются значениями
  52.    ' а также на то, насколько сложно подобрать углы поворота относительно осей самих деталей
  53.    ' дабы получить простой поворот на 90 градусов относительно оси сборки
  54.    
  55.  
  56. End Sub
  57.  
  58. Sub Transform(occ As ComponentOccurrence, X As Double, Y As Double, Z As Double, X_rot As Double, Y_rot As Double, Z_rot As Double)
  59.     Dim oMatrix_rot As Matrix: Set oMatrix_rot = oTG.CreateMatrix
  60.     Dim oMatrix As Matrix: Set oMatrix = oTG.CreateMatrix
  61.  
  62.     Call oMatrix_rot.SetToRotation(X_rot, oXAxis, oStPoint)
  63.     Call oMatrix.TransformBy(oMatrix_rot)
  64.     Call oMatrix_rot.SetToRotation(Y_rot, oYAxis, oStPoint)
  65.     Call oMatrix.TransformBy(oMatrix_rot)
  66.     Call oMatrix_rot.SetToRotation(Z_rot, oZAxis, oStPoint)
  67.     Call oMatrix.TransformBy(oMatrix_rot)
  68.  
  69.     Call oMatrix.SetTranslation(oTG.CreateVector(X / 10, Y / 10, Z / 10))
  70.     Call occ.SetTransformWithoutConstraints(oMatrix)
  71. End Sub

П.С. Не поленился написать данный код, дабы продемонстрировать, насколько ваша задача трудна в выполнении, а главное, бессмысленна. Вместо того, чтобы городить вот этот программный разворот 100 деталей сборки в пространстве, можно убить в себе максималиста, запихнуть всю сборку целиком в другую сборку, внутри которой повернуть разом все элементы как вашей душе угодно. То есть осуществить это не средствами программирования, а с помощью правильного использования самой программы Inventor.

П.П.С. Если же все-таки вам принципиально выполнить задачу именно как поворот каждого элемента, тогда логично сделать получение координат после преобразования из текущих координат вхождений посредством тригонометрии. А стартовое позиционирование элементов (направление их осей) должно соответствовать положению этих элементов в итоговой сборке, тогда поворот будет осуществляться вокруг одной и той же одноименной оси, но, опять таки, лишь до первого преобразования, после второго и третьего начнется такая же путаница ))) Надеюсь я помог вам поменять стратегию выполнения задачи ))
В программировании я новичок...но ненадолго! ;)

Оффлайн mikazakov

  • ADN
  • *
  • Сообщений: 751
  • Карма: 195
  • Skype: mikazakov@mail.ru
Не поленился написать данный код,
Это точно  :D.

запихнуть всю сборку целиком в другую сборку, внутри которой повернуть разом все элементы как вашей душе угодно.
Рационально, если оно так подойдёт

Оффлайн xzenter

  • ADN OPEN
  • Сообщений: 29
  • Карма: 1
    • xzenter.com
  • Skype: xzenter
Правило на скорую руку (iLogic), поворот на 90 градусов вокруг выбранной оси:

Код - vb.net [Выбрать]
  1. Const PI = 3.14159265358979
  2.  
  3. Dim oAsmDoc As AssemblyDocument
  4. oAsmDoc = ThisApplication.ActiveDocument
  5.  
  6. Dim selectedWorkAxis As WorkAxis
  7. selectedWorkAxis = oAsmDoc.SelectSet(1)
  8.  
  9. Dim selectedComponent As ComponentOccurrence
  10. selectedComponent = oAsmDoc.SelectSet(2)
  11.  
  12. Dim oTG As TransientGeometry
  13. oTG = ThisApplication.TransientGeometry
  14.  
  15. Dim line As Line
  16. line = selectedWorkAxis.Line
  17.  
  18. Dim matrixRotate As Matrix
  19. matrixRotate = oTG.CreateMatrix()
  20. ' PI / 2 => 90 deg
  21. Call matrixRotate.SetToRotation(PI / 2, line.Direction.AsVector(), line.RootPoint)
  22.  
  23.  
  24. Dim matrix As Matrix
  25. matrix = selectedComponent.Transformation
  26.  
  27. Call matrix.PreMultiplyBy(matrixRotate)
  28. selectedComponent.Transformation = matrix
  29.  
  30.  
  31.  

Сначала нужно выделить ось вокруг которой будем поворачивать. Затем нужно выделить компонент, который хотим повернуть. Потом запустить правило. Правило только для одного компонента. Думаю, можно через цикл повернуть все компоненты

Оффлайн R.I.Chernov

  • ADN Club
  • *****
  • Сообщений: 565
  • Карма: 18
дабы продемонстрировать, насколько ваша задача трудна в выполнении
Прошу прощения, что ошибся и ввел вас в заблуждение. Я разбирался в вопросе не так хорошо, как мне казалось. Спасибо xzenter, что указал на это :). Ниже приведен код, осуществляющий необходимый вам поворот. Первые две функции для поворота, вторые две, для возвращения сборки на стартовую позицию. Сборка во вложении к сообщению.

   
Код - Visual Basic [Выбрать]
  1.     Dim oTG As TransientGeometry
  2.     Dim X As Double: Dim Y As Double: Dim Z As Double
  3.     Dim X_rot As Double: Dim Y_rot As Double: Dim Z_rot As Double
  4.     Dim PI As Double
  5.     Dim oMatrix As matrix
  6.     Dim oMatrix_rot As matrix
  7.    
  8. Sub rotation_v2()
  9.     Dim PI As Double: PI = Atn(1) * 4
  10.     Dim oCD As AssemblyComponentDefinition
  11.     Set oCD = ThisApplication.ActiveDocument.ComponentDefinition
  12.     Dim oOcc_1 As ComponentOccurrence
  13.     Set oOcc_1 = oCD.Occurrences.ItemByName("1")
  14.     Dim oOcc_2 As ComponentOccurrence
  15.     Set oOcc_2 = oCD.Occurrences.ItemByName("2")
  16.     Set oTG = ThisApplication.TransientGeometry
  17.     PI = Atn(1) * 4
  18.     Call Rotate_func(oOcc_1, 0, PI / 4, PI / 4)
  19.     Call Rotate_func(oOcc_2, 0, PI / 4, PI / 4)
  20. End Sub
  21.  
  22. Sub Rotate_func(occ As ComponentOccurrence, X_rot As Double, Y_rot As Double, Z_rot As Double)
  23.     Set oMatrix = oTG.CreateMatrix
  24.     Set oMatrix_rot = oTG.CreateMatrix
  25.     Call oMatrix.SetToRotation(X_rot, oTG.CreateVector(1, 0, 0), oTG.CreatePoint(0, 0, 0))
  26.     Call oMatrix_rot.TransformBy(oMatrix)
  27.     Call oMatrix.SetToRotation(Y_rot, oTG.CreateVector(0, 1, 0), oTG.CreatePoint(0, 0, 0))
  28.     Call oMatrix_rot.TransformBy(oMatrix)
  29.     Call oMatrix.SetToRotation(Z_rot, oTG.CreateVector(0, 0, 1), oTG.CreatePoint(0, 0, 0))
  30.     Call oMatrix_rot.TransformBy(oMatrix)
  31.  
  32.     Set oMatrix = occ.Transformation
  33.     Call oMatrix.PreMultiplyBy(oMatrix_rot)
  34.     occ.Transformation = oMatrix
  35. End Sub
  36.  
  37. Sub Start_pos()
  38.     Dim oCD As AssemblyComponentDefinition
  39.     Set oCD = ThisApplication.ActiveDocument.ComponentDefinition
  40.     Dim oOcc_1 As ComponentOccurrence
  41.     Set oOcc_1 = oCD.Occurrences.ItemByName("1")
  42.     Dim oOcc_2 As ComponentOccurrence
  43.     Set oOcc_2 = oCD.Occurrences.ItemByName("2")
  44.     Set oTG = ThisApplication.TransientGeometry
  45.     PI = Atn(1) * 4
  46.  
  47.     X = 0: Y = 1000: Z = 0
  48.     X_rot = PI / 2: Y_rot = 0: Z_rot = PI
  49.     Call Transform(oOcc_1, X, Y, Z, X_rot, Y_rot, Z_rot)
  50.     X = 0: Y = 1200: Z = 200
  51.     X_rot = 0: Y_rot = PI: Z_rot = 0
  52.     Call Transform(oOcc_2, X, Y, Z, X_rot, Y_rot, Z_rot)
  53. End Sub
  54.  
  55. Sub Transform(occ As ComponentOccurrence, X As Double, Y As Double, Z As Double, X_rot As Double, Y_rot As Double, Z_rot As Double)
  56.     Set oMatrix_rot = oTG.CreateMatrix
  57.     Set oMatrix = oTG.CreateMatrix
  58.  
  59.     Call oMatrix_rot.SetToRotation(X_rot, oTG.CreateVector(1, 0, 0), oTG.CreatePoint(0, 0, 0))
  60.     Call oMatrix.TransformBy(oMatrix_rot)
  61.     Call oMatrix_rot.SetToRotation(Y_rot, oTG.CreateVector(0, 1, 0), oTG.CreatePoint(0, 0, 0))
  62.     Call oMatrix.TransformBy(oMatrix_rot)
  63.     Call oMatrix_rot.SetToRotation(Z_rot, oTG.CreateVector(0, 0, 1), oTG.CreatePoint(0, 0, 0))
  64.     Call oMatrix.TransformBy(oMatrix_rot)
  65.  
  66.     Call oMatrix.SetTranslation(oTG.CreateVector(X / 10, Y / 10, Z / 10))
  67.     Call occ.SetTransformWithoutConstraints(oMatrix)
  68. End Sub
В программировании я новичок...но ненадолго! ;)

Оффлайн R.I.Chernov

  • ADN Club
  • *****
  • Сообщений: 565
  • Карма: 18
Напоследок хотел обратить ваше внимание на то, что в представленном коде поворот осуществляется сначала вокруг оси X, то, что получается поворачивается вокруг Y, и наконец все поворачивается вокруг Z. Вначале лично мне было достаточно сложно к этому привыкнуть.
В программировании я новичок...но ненадолго! ;)