2016-02-10 5 views
1

Я должен декодировать STAD-файл cad, в котором 3d-круг может быть определен как сплайн. Я хочу иметь возможность декодировать, что сплайн представляет собой дугу или круг.определение дуги/круга из bspline

Сначала у меня есть элемент B_SPLINE_CURVE_WITH_KNOTS.


#307 = B_SPLINE_CURVE_WITH_KNOTS ('NONE', 3,(#114, #212, #179, #317, #91, #191, #141, #97, #150, #63, #121, #243, #75, #43, #15, #164, #315, #284, #302, #70, #269, #251, #151, #220, #178, #172, #248, #185, #156, #249, #300, #47, #124, #335, #360, #59, #357, #343, #12, #5, #112, #324, #344, #193, #329, #320, #313, #222, #51, #167, #286, #268, #310, #32, #267, #52, #66, #69),.UNSPECIFIED., .T., .F., (4, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 4), (0.0000000000000000000, 0.0003907630664662950000, 0.0007815261329325900100, 0.001172289199398885000, 0.001563052265865180000, 0.002344578398797811600, 0.003126104531730443300, 0.003516867598196761600, 0.003907630664663080300, 0.004298393731129399400, 0.004689156797595717700, 0.005079919864062035900, 0.005470682930528354200, 0.005861445996994673300, 0.006252209063460992400, 0.006642972129927311600, 0.007033735196393629000, 0.007815261329326231600, 0.008206024395792531700, 0.008596787462258833500, 0.008987550528725133500, 0.009378313595191433600, 0.009769076661657735300, 0.01015983972812403500, 0.01055060279459033500, 0.01094136586105663500, 0.01133212892752293700, 0.01172289199398923700, 0.01250441812692185600), .UNSPECIFIED.) ; 

Так что, если я прав, я декодируется:
58 контрольных точек
29 knot_multiciplities
29 узлов
степени 3
closed_curve аргумент = True

сейчас, идея будет преобразуйте его в кривую Безье, чтобы найти дугу/круги, но я застрял перед этими параметрами.

ответ

0

Вы можете разработать arc through 3 consecutive knots. Если дуга является постоянной для всех троек вашего bspline, кривая является самой дугой.

0

Дуга или полный круг не могут быть точно представлены интегральной кривой B-сплайна. Итак, если вы уверены, что кривая B-сплайна в файле STEP не является рациональной, то она представляет собой только дугу или полный круг. Если это так, то вы можете сделать следующее:

  • Sample некоторые точки на кривой B-сплайна,
  • ли наименьших квадратов прилегание считываемых точек, чтобы получить наиболее подходящее круг и отклонение, связанное с каждой выборочной точкой.
  • Если максимальное отклонение меньше определенного порога, тогда вы получаете свой круг/дугу. В противном случае эта кривая B-сплайна не является окружностью/дугой.

Этот подход будет работать независимо от того, имеется ли у вас рациональная или интегральная кривая B-сплайна.

0

Основной проблемой в первую очередь это понимание определения STEP BSPLINE_CURVE_WITH_KNOTS:

knot_multicplicites = (4, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2 , 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 4)

узлов = (+0,0000000000000000000, 0,0003907630664662950000, 0,0007815261329325900100, 0,001172289199398885000, 0,001563052265865180000, 0,002344578398797811600, 0,003126104531730443300, 0,003516867598196761600, 0,003907630664663080300, 0,004298393731129399400, 0,004689156797595717700, 0,005079919864062035900, 0,005470682930528354200, 0,005861445996994673300, 0,006252209063460992400, 0,006642972129927311600, 0.0070337351963936 29000, 0,007815261329326231600, +0,008206024395792531700, 0,008596787462258833500, +0,008987550528725133500, +0,009378313595191433600, +0,009769076661657735300, +0,01015983972812403500, +0,01055060279459033500, 0,01094136586105663500, +0,01133212892752293700, +0,01172289199398923700, 0,01250441812692185600)

Я полагаю, это означает, что узлы должны быть расшифрованы, как:

(0.000000000000000000,0.000000000000000000,0.000000000000000000 , 0,000000000000000000, 0.0003907630664662950000, 0.0003907630664662950000, 0.0007815261329325900100, 0.0007815261329325900100 ....

Но меня беспокоит то, что множественность (4) больше степени: 3! ,

+1

Очень часто для кубических сплайнов есть первый и последний узлы с множественностью = 4. Это не совсем правильно. Если вы выполните математику, вы обнаружите, что b-сплайн не зависит от первого и последнего узлов, поэтому они могут быть чем угодно, а множественность = 3 будет работать нормально. Ошибка, которая была сделана в оригинальной IGES стандарт, и с тех пор он был скопирован другими. – bubba

2

Каждый внутренний узел имеет кратность = 2. Это означает, что сплайн C_1 и касается ног управляющего многоугольника. В частности, если t[i-1], и t[i+1} представляют собой три узла, каждый из которых имеет кратность = 2, то сплайн касается касания ноги полигона в точке, которая делит ногу в отношении
t[i+1] - t[i] : t[i] - t[i-1]. На рисунке ниже, эти точки касания показаны как полые круги и красные круги контрольные точки:

enter image description here

В самом деле, в вашем конкретном примере, расстояние между узлом равномерно, для наиболее часть - есть много случаев, когда t[i+1] - t[i] = t[i] - t[i-1] = 0.000391. Это означает, что есть много мест, где сплайн касательный к ножке управления полигона на это середина.

Используя контрольные точки и точки касания, можно рассчитать конечные точки (Р и Q) и концевые касательные единицы длины (U и V). каждого кубического сегмент

enter image description here

Немного тригонометрии и векторная арифметика тогда даст вам радиус и центр соответствующей окружности. Пример псевдокода выглядит следующим образом. Это предполагает некоторые очевидные вектор-функцию, и это позволяет избежать использования функций тригонометрических:

// Input: 
// P: start point 
// Q: end point 
// U: start tangent (assumed to be of unit length) 
// V: end tangent (assumed to be of unit length) 

Vector C = Q - P; // chord vector 

// Test that tangent vectors make same angle with chord 
double UdotC = U*C;  
double VdotC = V*C;   
double epsilon = some small number, say around 0.000001; 
if (Math.Abs(UdotC - VdotC) > epsilon) throw; // Tangents not symmetric 

// Test that tangents and chord are coplanar 
Vector UcrossC = Vector.Cross(U, C); 
double det = V*UcrossC; 
if (det > epsilon) throw; // Tangents and chord not coplanar 

double CdotC = C*C; 
double radius = 0.5 * CdotC/Vector.Norm(UcrossC); 

double c2 = (UdotC*UdotC)/CdotC; 
Vector dW = 0.25*(UdotC/(1-c2))*(V - U); 
Position center = P + 0.5*C + dW; 

Если кружек создать таким образом, имеет равные центры и радиусы (в пределах некоторого разумного допуска), то это довольно безопасно предположить, что «Цель» сплайна - это круг.

Я думаю, что использование точек и тангенсов таким образом лучше, чем установка окружностей на произвольные точки на сплайне. Существует очень хороший шанс, что код в отправляющей системе построил сплайн так называемыми методами «Эрмита» (используя точки и касательные). Если это так, вполне вероятно, что точки и тангенсы, рассчитанные, как указано выше, будут точно соответствовать таковым исходного круга (если таковой имеется). Произвольно рассчитанные точки на сплайне не будут лежать точно на исходном круге, поэтому вы столкнетесь с гораздо более терпимыми проблемами.

+0

Не могли бы вы объяснить, почему сплайн касается касаний опорных полигонов на узлах? – jumper0x08