Я использую преобразование в Revit, чтобы показать виды возвышения отдельных лучей (с целью детализации). Это работает отлично, пока луч плоский (одинаковые начальные и конечные смещения), но если у меня есть наклонный луч, я вынужден "сгладить" конечные точки.
Я попытался определить единичный вектор вдоль фактических начальных/конечных точек и перпендикулярно этому вектору на плоскости XY, проходящей через определенный ".Rrigin" преобразования. Затем я использовал простые уравнения для определения нормали к этим двум векторам... двойной newx = сперва.Y * second.Z - первый.Z * second.Y; двойной новыйy = первый.Z * секунд.X - первый.X * секунд.Z; двойной новыйz = первый.X * секунд.Y - первый.Y * секунд.X; double vectlong = Math.Sqrt(newx * newx + newy * новый + новыйz * новыйz); XYZ normal = новый Autodesk.Revit.DB.XYZ(newx/vectlong, newy/vectlong, newz/vectlong);
Затем я использовал эти три вектора как ".set_Basis" 0, 1 и 2.
Этот код работает до тех пор, пока я заставляю начальную и конечную точки луча быть плоскими (что показывает, что сгенерированный "нормальный" действителен), но когда я удаляю код, чтобы сгладить и использовать фактические значения Z конечных точек наклонный луч, программа не работает, когда я пытаюсь использовать эти значения.
Образец SDK для генерации сечения через середину луча (CreateViewSection), похоже, нашел ту же проблему, но программист отказался и просто заставлял программу принимать только лучи, которые уже находятся на одной плоскости XY, что не действительно "правило" для балок.
Я экспортировал вычисленные значения моих трех векторов и проверил, что они все единичные длины и ортонормированные, что должно быть всем, что требуется для преобразования. Может ли кто-нибудь объяснить, почему эти базовые значения терпят неудачу?
Используйте этот код для установки преобразования сборки. Он правильно выравнивает начало сборки и ось так, чтобы вид сбоку всегда был выровнен по оси XYZ!
var assyTransform = Transform.Identity;
var beamInst = mainElement as FamilyInstance;
if( beamInst != null )
{
assyTransform = beamInst.GetTransform();
assyTransform.Origin = ( assyInstance.Location as LocationPoint ).Point;
}
if ( !assyInstance.GetTransform()
.AlmostEqual( assyTransform ) )
{
assyInstance.SetTransform( assyTransform );
return true;
}