Supposons que j'ai un ProgrammableFilter en paraview, qui reçoit deux entrées: mesh1 avec data et mesh2 without. En outre, je connais la permutation des points de mesh1 à mesh2. A l'intérieur du filtre, je peux accéder aux valeurs de points parComment utiliser numpy dans le filtre programmable dans ParaView
data0=inputs[0].GetPointData().GetArray('data')`
et d'obtenir une partie de la matrice en utilisant
subData=data0[0:6]
par exemple. Mais comment pourrais-je ajouter ce subData
à la sortie sans une boucle python?
Pour expérimenter avec le code, je créé un (pas si petit) exemple de travail:
#!/usr/bin/python
from paraview.simple import *
import numpy as np
import vtk
from vtk.util.numpy_support import numpy_to_vtk
#generate an arbitrary source with data
mesh2=Sphere()
mesh2.Center=[0.0, 0.0, 0.0]
mesh2.EndPhi=360
mesh2.EndTheta=360
mesh2.PhiResolution=100
mesh2.Radius=1.0
mesh2.StartPhi=0.0
mesh2.StartTheta=0.0
mesh2.ThetaResolution=100
mesh2.UpdatePipeline()
#add the data
mesh2Vtk=servermanager.Fetch(mesh2)
nPointsSphere=mesh2Vtk.GetNumberOfPoints()
mesh2Data=paraview.vtk.vtkFloatArray()
mesh2Data.SetNumberOfValues(nPointsSphere)
mesh2Data.SetName("mesh2Data")
#TODO: use numpy here?? do this with a ProgrammableFilter ?
data=np.random.rand(nPointsSphere,1)
for k in range(nPointsSphere):
mesh2Data.SetValue(k, data[k])
mesh2Vtk.GetPointData().AddArray(mesh2Data)
#send back to paraview server
#from https://public.kitware.com/pipermail/paraview/2011-February/020120.html
t=TrivialProducer()
filter= t.GetClientSideObject()
filter.SetOutput(mesh2Vtk)
t.UpdatePipeline()
w=CreateWriter('Sphere_withData.vtp')
w.UpdatePipeline()
Delete(w)
#create mesh1 without data
mesh1=Line()
mesh1.Point1=[0,0,0]
mesh1.Point2=[0,0,1]
mesh1.Resolution=5
mesh1.UpdatePipeline()
progFilter=ProgrammableFilter(mesh1)
progFilter.Input=[mesh1, t]
progFilter.Script="curT=inputs[1].GetPointData().GetArray('mesh2Data')"\
"\nglobIndices=range(0,6)"\
"\nsubT=curT[globIndices]"\
"\nswap=vtk.vtkFloatArray()"\
"\nswap.SetNumberOfValues(len(globIndices))"\
"\nswap.SetName('T')"\
"\n#TODO: how can i avoid this loop, i.e. write output.GetPointData().AddArray(converToVTK(subT))"\
"\nfor k in range(len(globIndices)):"\
"\n swap.SetValue(k,subT[k])"\
"\noutput.PointData.AddArray(swap)"
progFilter.UpdatePipeline()
w=CreateWriter('Line_withData.vtp')
w.UpdatePipeline()
Delete(w)
J'ai accepté la réponse, parce qu'il semble bon. Les deux scripts montrent même le problème suivant: Script de base 'run.py':
src1='file1.vtu'
r1=XMLUnstructuredGridReader(FileName=src1)
progFilter=ProgrammableFilter(r1)
progFilter.Input=[r1]
with open('script.py','r') as myFile:
progFilter.Script=myFile.read()
progFilter.UpdatePipeline()
progData=progFilter.GetPointDataInformation()
print progData.GetArray('T2').GetRange()
et le script pour le filtre programmable:
import vtk
import vtk.numpy_interface.dataset_adapter as dsa
import numpy as np
globIndices=inputs[0].GetPointData().GetArray('T')
subT=np.ones((globIndices.shape[0],1))
subTVtk=dsa.VTKArray(subT)
output.PointData.append(subTVtk, 'T2')
Avec cette combinaison, je reçois des messages d'erreur:
fichier "/usr/lib/python2.7/dist-packages/vtk/numpy_interface/dataset_adapter.py", ligne 652, en append self.VTKObject.AddArray (Arr)
TypeError: L'argument AddArray 1: méthode nécessite un objet VTK
File "run.py", à la ligne 15, dans
print progData.GetArray('T2').GetRange()
AttributeError: objet 'NoneType' n'a pas d'attribut 'GetRange'
Le premier message d'erreur semble être la raison de la seconde.
Vous avez un plus gros problème: l'utilisation de 'paraview.simple' dans un filtre programmable entraînera un comportement indéfini et n'est pas autorisée. Vous devez utiliser le code VTK et Numpy pur dans un filtre programmable. Le filtre programmable s'exécutera sur tous les processus s'exécutant du côté serveur. –
Désolé pour la confusion. J'ai essayé de construire un exemple de travail. Cet exemple est un script python, qui crée le filtre programmable. A l'intérieur du filtre, je n'utilise pas paraview.simple, juste vtk et numpy. Voir la ligne progFilter.Script = .. –
Vous avez raison. Désolé pour le bruit. Je vais ajouter une réponse ci-dessous. –