Selezione tramite commento
Il metodo probabilmente più semplice è che, durante la creazione degli elementi, siano stati assegnati dei commenti che poi possono essere ricercati specificamente. Di seguito viene mostrata una funzione esemplare che cerca i membri secondo il loro commento e restituisce i numeri di membri trovati:
Function getMemberNosByComment(members() As RFEM5.Member, comment As String) As Integer()
Dim intArr() As Integer
Dim i As Long
Dim j As Long
j = 0
ReDim intArr(0 To 0)
' ciclo sui membri
For i = 0 To UBound(members, 1)
If (members(i).comment = comment) Then
' aumenta la dimensione dell'array intero di 1
ReDim Preserve intArr(0 To j)
intArr(j) = members(i).no
j = j + 1
End If
Next i
' restituisce l'array intero
getMemberNosByComment = intArr
End Function
La funzione ha un ciclo sui membri passati e, se c'è una corrispondenza tra la stringa in "comment" e il commento del membro, il numero del membro viene aggiunto al campo intero. Alla fine, viene restituito il campo intero con tutti i numeri dei membri.
Selezione di nodi finali del membro
La selezione degli elementi nel programma, e quindi anche tramite l'interfaccia COM, avviene utilizzando le stringhe. Ad esempio, per una linea, i nodi correlati vengono passati tramite una stringa in cui i numeri dei nodi sono salvati separati da una virgola. L'uso delle stringhe richiede la conversione in valori numerici e viceversa durante la programmazione. Di seguito quindi la funzione, che può convertire i numeri dei membri ottenuti dalla funzione sopra in una stringa. I numeri dei membri vengono convertiti singolarmente in caratteri tramite la funzione CStr e, dopo ogni numero, viene aggiunta una virgola alla stringa. La virgola superflua alla fine della stringa viene ignorata da RFEM/RSTAB e può quindi rimanere.
Function intArrToStr(intArr() As Integer) As String
Dim str As String
Dim i As Long
For i = 0 To UBound(intArr, 1)
str = str + CStr(intArr(i)) + ","
Next i
intArrToStr = str
End Function
Grazie a questa funzione, ora è possibile selezionare i membri filtrati tramite commento tramite l'interfaccia COM.
' selezionare membri tramite commento
Dim mems() As RFEM5.Member
Dim mem_nos() As Integer
Dim str As String
str = "test comment"
mem_nos = getMemberNosByComment(mems, str)
iModelData.EnableSelections (True)
str = intArrToStr(mem_nos)
iModelData.SelectObjects MemberObject, str
Spesso non basta solo selezionare determinati elementi, ma sono necessari elementi subordinati. Di seguito viene mostrato in modo esemplare il metodo per trovare i nodi iniziali di un membro. Poiché in RFEM il procedimento è un po' più complesso rispetto a RSTAB, poiché qui ogni membro è associato a una linea, è stato scelto questo metodo.
Innanzitutto, bisogna trovare i numeri delle linee corrispondenti ai membri. La seguente funzione presuppone che siano già disponibili dei numeri di membri e cerca i numeri di linee associati.
Function getLineNosByMemberNos(members() As RFEM5.Member, member_nos() As Integer) As Integer()
Dim intArr() As Integer
Dim i As Long
Dim j As Long
Dim k As Long
k = 0
ReDim intArr(0 To 0)
For i = 0 To UBound(members, 1)
For j = 0 To UBound(member_nos, 1)
If (members(i).no = member_nos(j)) Then
' aumenta la dimensione dell'array di 1
ReDim Preserve intArr(0 To k)
intArr(k) = members(i).LineNo
k = k + 1
' esce dal ciclo sui member_nos
Exit For
End If
Next j
Next i
getLineNosByMemberNos = intArr
End Function
Questa funzione possiede due cicli annidati. Il ciclo principale attraversa i membri e il ciclo subordinato i numeri dei membri. Per ogni membro, il campo con numeri dei membri viene completamente traversato. Per accelerare questo processo, il ciclo interno viene lasciato non appena si verifica una corrispondenza tra i numeri dei membri. Se si verifica una corrispondenza, il campo con i numeri delle linee viene esteso di un elemento e il nuovo numero viene aggiunto (k è l'indice per i numeri di linee trovati).
Affinché il nodo iniziale della linea o del membro venga trovato, è necessaria un'altra funzione. Questa funzione deve attraversare le linee e, in caso di corrispondenza con i numeri delle linee dati, leggere il nodo iniziale. Poiché i numeri dei nodi sono memorizzati in una stringa, è ora necessaria una funzione che converta la stringa in un campo numerico.
Function strToIntArr(intList As String) As Integer()
' possibili caratteri "1-9 ; - ,"
' esempio: 1-4,5;100 > 1,2,3,4,5,100
Dim ints() As Integer
Dim tmpInts() As Integer
ReDim ints(0)
Dim span As Boolean
Dim curInt As String
curInt = ""
Dim i As Integer
i = 0
Dim j As Integer
Dim curChar As String
Do While (i < Len(intList))
curChar = Mid(intList, i + 1, 1)
' se la stringa contiene "-" una serie è segnalata
If (curChar = "-") Then
span = True
tmpInts = ints
ReDim Preserve tmpInts(0 To UBound(tmpInts, 1) + 1)
tmpInts(UBound(tmpInts, 1) - 1) = CInt(curInt)
ints = tmpInts
curInt = ""
' se l'ultimo carattere è raggiunto o una virgola o un punto e virgola è il carattere successivo
ElseIf ((curChar = ",") Or (curChar = ";") Or (i = Len(intList) - 1)) Then
' l'ultimo carattere è raggiunto, il numero o la serie è terminato
If (i = Len(intList) - 1) Then
curInt = curInt & curChar
End If
' gestisce la serie
If span Then
' crea tutti i numeri tra la serie
Dim firstNum As Integer
Dim lastNum As Integer
firstNum = ints(UBound(ints, 1) - 1)
lastNum = CInt(curInt)
curInt = ""
If (firstNum > lastNum) Then
Dim tmp1 As Integer
tmp1 = lastNum
lastNum = firstNum
firstNum = tmp1
ints(UBound(ints, 1) - 1) = firstNum
End If
' estende ints e aggiunge nuovi numeri all'array
tmpInts = ints
ReDim Preserve tmpInts(0 To UBound(tmpInts, 1) + (lastNum - firstNum))
For j = 0 To (lastNum - firstNum) - 1
tmpInts(UBound(ints, 1) + j) = j + firstNum + 1
Next j
ints = tmpInts
span = False
' aggiunge una nuova cifra
Else
' estende ints e aggiunge un nuovo numero a ints
tmpInts = ints
ReDim Preserve tmpInts(0 To UBound(tmpInts, 1) + 1)
tmpInts(UBound(tmpInts, 1) - 1) = CInt(curInt)
ints = tmpInts
curInt = ""
End If
Else
curInt = curInt & curChar
End If
i = i + 1
Loop
' l'array è un elemento troppo lungo e viene ridotto
ReDim Preserve ints(0 To UBound(ints, 1) - 1)
strToIntArr = ints
End Function
Questa funzione attraversa la stringa e esamina ciascun carattere. Se si tratta di un numero o di più, questi vengono raccolti fino a quando non si raggiunge la fine o un altro carattere. Quando si raggiunge un trattino, viene riconosciuta una serie di numeri e i numeri intermedi vengono generati automaticamente.
La funzione effettiva per estrarre il punto iniziale di una linea può ora essere creata e risulta molto chiara.
Function getLineStartNodeNosByLineNos(lines() As RFEM5.RfLine, line_nos() As Integer) As Integer()
Dim intArr() As Integer
Dim tmpIntArr() As Integer
Dim str As String
Dim i As Long
Dim j As Long
Dim k As Long
k = 0
ReDim intArr(0 To 0)
For i = 0 To UBound(line_nos, 1)
For j = 0 To UBound(lines, 1)
If (lines(j).no = line_nos(i)) Then
' aggiunge il numero di linea trovato all'array
ReDim Preserve intArr(0 To k)
str = lines(j).NodeList
tmpIntArr = strToIntArr(str)
intArr(k) = tmpIntArr(0)
k = k + 1
' esce dal ciclo su line_nos_cpy
Exit For
End If
Next j
Next i
getLineStartNodeNosByLineNos = intArr
End Function
Anche qui ci sono di nuovo due cicli annidati, come nella funzione getLineNosByMemberNos. Questa volta l'ordine è di grande importanza, altrimenti viene persa l'assegnazione dei nodi alle linee. Il ciclo esterno attraversa i numeri delle linee e, se si verifica una corrispondenza con una linea all'interno del ciclo interno, i numeri dei nodi vengono estratti tramite la funzione strToIntArr, di cui viene usato qui il primo.
L'intero processo per ottenere i nodi iniziali appare quindi come segue. Innanzitutto, vengono recuperati i numeri delle linee dai membri con i numeri dei membri corrispondenti e poi i nodi iniziali delle linee.
' selezionare i nodi iniziali dai membri
' ottenere i numeri delle linee da tutti i membri
Dim line_nos() As Integer
line_nos = getLineNosByMemberNos(mems, mem_nos)
' ottenere i numeri iniziali da tutte le linee
Dim stNodes_nos() As Integer
stNodes_nos = getLineStartNodeNosByLineNos(lines, line_nos)
Sommario e prospettive
La funzione getLineNosByMemberNos costituisce la base per ulteriori funzioni di selezione, come anche per la funzione getLineStartNodeNosByLineNos. Seguendo questo schema, è possibile anche trovare i carichi associati ai membri. Come strumenti sono poi disponibili le funzioni strToIntArr e intArrToStr, con l'aiuto delle quali la selezione basata su stringhe di RFEM può essere convertita in array numerici.
Un'altra possibilità è la selezione tramite coordinate. Ad esempio, è possibile specificare uno spazio definito e selezionare tutti gli elementi all'interno di questo spazio. Questo tipo di selezione verrà descritto in un articolo successivo.