Theoretische Grundlagen zur Abstandsberechnung
Um die FE-Knoten zu finden, welche in der Nähe beziehungsweise auf der Linie liegen, muss der Abstand des Knotens zur Linie berechnet werden. Gegeben sind die Linie mit Anfangs- und Endpunkt (N0 und N1) und der Punkt P, dessen Abstand zur Linie ermittelt werden soll. Ein gängiger Weg für die Berechnung dieses Abstandes ist, dass eine Ebene aufgespannt wird, welche durch den Punkt P verläuft und senkrecht auf der Geraden steht. Dazu muss zunächst eine geeignete Geradengleichung aufgestellt werden. In diesem Fall bietet sich die Parameterform an, welche einen Richtungsvektor v beinhaltet. Dieser kann danach zum Aufstellen der Ebenengleichung verwendet werden.
Für den Stützvektor A wird der Anfangspunkt (Ortsvektor) der Linie verwendet und für den Richtungsvektor v die Differenz der beiden Ortsvektoren. Als Ebenengleichung wird die Normalform aus dem bereits erwähnten Grund verwendet.
Der Stützvektor P ist hier der zu untersuchende Ergebnispunkt Pres. Der Normalenvektor ist der Richtungsvektor der Geraden, da so die Ebene orthogonal zur Geraden ist. Bevor der Abstand berechnet werden kann, muss noch der Faktor s der Geraden ermittelt werden, an der die Ebene die Gerade schneidet. Dazu wird der Ortsvektor X in der Ebenengleichung durch die Geradengleichung ersetzt.
Nach s umgestellt und mit
Damit lässt sich nun über Gleichung 1 der Schnittpunkt S ermitteln.
Der Abstand d zwischen S und Pres wird mit Hilfe des vektoriellen Betrags der Differenz der beiden bestimmt.
Bild 01 zeigt die schematische Darstellung aller aufgeführten Elemente. Die blaue Fläche ist die zu untersuchende Fläche und die rote Fläche stellt die Schnittebene dar, welche mit Punkt Pres und Richtungsvektor
Umsetzung der Abstandsberechnung in einem Programm
Nachdem die Formeln zur Verfügung stehen, kann das entsprechende Programm erstellt werden. Für die Umsetzung wird EXCEL VBA verwendet. In Bild 02 ist die Nummerierung der Elemente zu sehen.
Zuerst muss die Verbindung zu RFEM aufgebaut werden. Danach wird das Interface zu den Modelldaten geholt. Da diese Vorgehensweise bereits in diversen anderen Beiträgen beschrieben wurde (siehe Links), wird hier nicht näher darauf eingegangen. Nachfolgend der Quellcode für den Anfang des Programms.
Sub selection_test2()
Dim line_no As Integer
Dim surface_no As Integer
Dim loadcase_no As Integer
Dim d_tol As Double
line_no = 11
surface_no = 1
loadcase_no = 1
d_tol = 0.001
' get interface from the opened model and lock the licence/program
Dim iModel As RFEM5.IModel2
Set iModel = GetObject(, "RFEM5.Model")
iModel.GetApplication.LockLicense
On Error GoTo e
Dim iModelData As RFEM5.IModelData2
Set iModelData = iModel.GetModelData
Bevor das Programm startet, werden zunächst die variablen gegebenen Parameter definiert. Dazu gehören die Liniennummer line_no der Linie, an der nach Ergebnissen gesucht werden soll, und natürlich die Flächennummer surface_no der Fläche, in der die Linie liegt. Des Weiteren wird noch die Nummer des Lastfalls loadcase_no benötigt, zu dem die Ergebnisse gehören. Da es sich um eine numerische Berechnung mit begrenzter Genauigkeit handelt, wird eine Toleranz d_tol benötigt, welche den maximalen Abstand zwischen Linie und Knoten vorgibt. Im Beispiel wurde eine Toleranz von einem Millimeter verwendet.
Da das Interface für die Modelldaten (IModelData) nun zur Verfügung steht, kann zuerst die Linie gesucht werden und damit auch deren Anfangs- und Endpunkt.
' get line
Dim ILin As RFEM5.ILine
Set ILin = iModelData.GetLine(line_no, AtNo)
Dim lin As RFEM5.RfLine
lin = ILin.GetData
' get nodes from line
Dim n(0 To 1) As RFEM5.Node
Dim ints() As Integer
ints = strToIntArr(lin.NodeList)
Dim iNd As RFEM5.INode
Set iNd = iModelData.GetNode(ints(0), AtNo)
n(0) = iNd.GetData
Set iNd = iModelData.GetNode(ints(UBound(ints, 1)), AtNo)
n(1) = iNd.GetData
Set iNd = Nothing
Sowohl die Knoten als auch die Linie werden einzeln direkt über deren Interface (INode beziehungsweise ILine) geholt. Die Extraktion der Knotennummern aus der Zeichenkette (RfLine.NodeList) erfolgt über die Funktion strToIntArr, welche in einem anderen Beitrag beschrieben wurde (siehe Links). Sie wandelt die Zeichenkette in ein Integer-Feld um.
Mit den jetzt gegebenen Punkten der Linie
Dim v As RFEM5.Point3D
v.X = N(1).X - N(0).X
v.Y = N(1).Y - N(0).Y
v.Z = N(1).Z - N(0).Z
Dim A As RFEM5.Point3D
A.X = N(0).X
A.Y = N(0).Y
A.Z = N(0).Z
Dim v2 As Double
v2 = v.X ^ 2 + v.Y ^ 2 + v.Z ^ 2
Dim P_res As RFEM5.Point3D
Dim s As Double
Dim d As Double
Es werden der Richtungsvektor
Berechnung des Abstandes in einer Schleife
In diesem Beispiel wurde die Verarbeitung der Ergebnisse auf Basis der FE-Knoten gewählt. Die Überprüfung des Abstandes erfolgt in einer Schleife über das Feld dieser Ergebnisse. Zuvor müssen diese Ergebnisse über das Interface ICalculation2 und dann IResults geholt werden. Innerhalb der Schleife wird zunächst der Punkt Pres mit den Koordinaten des Ergebniswertes beschrieben (dient der Übersichtlichkeit). Danach kann die direkte Berechnung der Gleichung (4) erfolgen. Nachdem s berechnet wurde, kann überprüft werden, ob der Wert kleiner Null oder größer Eins ist, da diese Werte außerhalb beziehungsweise vor und nach der Geraden liegen. Falls ein Wert innerhalb des Bereichs liegt, wird der Abstand mit Gleichung (6) berechnet.
' get results in fe-nodes
Dim iCalc As ICalculation2
Set iCalc = iModel.GetCalculation
Dim iRes As RFEM5.IResults
Set iRes = iCalc.GetResultsInFeNodes(LoadCaseType, loadcase_no)
Dim surfBaStr() As RFEM5.SurfaceBasicStresses
surfBaStr = iRes.GetSurfaceBasicStresses(surface_no, AtNo)
' loop through stresses and calculate distance to line
Dim i As Integer
For i = 0 To UBound(surfBaStr, 1)
P_res.X = surfBaStr(i).Coordinates.X
P_res.Y = surfBaStr(i).Coordinates.Y
P_res.Z = surfBaStr(i).Coordinates.Z
' calculate factor for line equation of intersection
s = ((P_res.X-A.X)*v.X + (P_res.Y-A.Y)*v.Y + (P_res.Z-A.Z)*v.Z) / v2
If s <= 1 + d_tol And s >= 0 - d_tol Then
' calculate distance of intersection point and fe-node
d = ((P_res.X-(A.X+s*v.X))^2
+(P_res.Y-(A.Y+s*v.Y))^2
+(P_res.Z-(A.Z+s*v.Z))^2)^0.5
If (d < d_tol) Then
' here you can process the found result point
End If
End If
Next i
Sowohl die Überprüfung des Faktors s als auch die des Abstandes d wird mit der Toleranz beaufschlagt, damit etwaige kleine Ungenauigkeiten nicht zum Ausschluss eines Ergebnisses führen.
Ergebnisse des Programms
Die vom Programm gefundenen Werte sind in der Tabelle dargestellt, dabei wurden die Werte auf zwei Stellen nach dem Komma gerundet.
σy+ [N/mm²] | Faktor s [-] |
---|---|
21,90 | 0,0 |
17,28 | 0,1 |
12,79 | 0,2 |
8,43 | 0,3 |
4,17 | 0,4 |
-0,04 | 0,5 |
-4,25 | 0,6 |
-8,51 | 0,7 |
-12,87 | 0,8 |
-17,36 | 0,9 |
-21,98 | 1,0 |
Dem gegenüber stehen die Werte aus dem Ergebnisverlauf an der entsprechenden Linie, welche in Bild 03 dargestellt werden.
Es ist deutlich zu erkennen, dass es sich um die gleichen Werte handelt und es zu einer hundertprozentigen Übereinstimmung kommt beziehungsweise alle Werte an der Linie gefunden wurden.
Zusammenfassung
Mit Hilfe der Vektorrechnung wurde ein Programm erstellt, welches in der Lage ist, Knoten entlang einer Linie zu finden. Mit diesem Algorithmus können neben Ergebnissen natürlich auch alle anderen geometrischen Elemente gesucht werden. Dies ist vor allem hilfreich, da die visuelle Selektion natürlich über die COM-Schnittstelle nicht möglich ist, so aber über eine Funktion auf anderem Weg möglich wird. Gerade für Programme, welche komplett im Hintergrund laufen, kann damit eine automatische Ergebnisauswertung erfolgen.