...
Initialize class members:
Code Block |
---|
|
def __init__ ( self ):
# initialize data
self.address = "AmoITof-0|Acqiris-0"
self.data = []
self.counter = 0
|
If you're curious to see any of the Acqiris configuration, e.g. how many channels do we have, you can inspect the AcqConfig object:
Code Block |
---|
|
def beginjob ( self, evt, env ) :
cfg = env.getConfig( _pdsdata.xtc.TypeId.Type.Id_AcqConfig, self.address )
self.num = cfg.nbrChannels()
|
The read the event waveform data (an array) and append it to the self.data list:
Code Block |
---|
|
def event ( self, evt, env ) :
channel = 0
acqData = evt.getAcqValue( self.address, channel, env)
if acqData :
self.counter+=1
wf = acqData.waveform() # returns a waveform array of numpy.ndarray type.
self.data.append(wf)
|
At the end of the job, take the average and plot it:
Code Block |
---|
|
def endjob( self, env ) :
data = np.array(self.data) # this is an array of shape (Nevents, nSamples)
# take the mean of all events for each sampling time
xs = np.mean(data, axis=0)
plt.plot(xs)
plt.xlabel('Seconds')
plt.ylabel('Volts')
plt.show()
|
Which gives you a plot like this
...
Princeton camera image
When plotting with MatPlotLib, we don't need to set the limits of the histogram manually, thus we don't need to read the Princeton configuration for this. If we want to sum the image from several events, we must first define and initialize some variables:
Code Block |
---|
|
def __init__ ( self ):
# initialize data
self.address = "SxrEndstation-0|Princeton-0"
self.data = None
|
In each event, we add the image array returned from the getPrincetonValue function:
Code Block |
---|
| none |
---|
| none |
---|
title | getPrincetonValue |
---|
|
def event ( self, evt, env ) :
frame = evt.getPrincetonValue( self.address, env)
if frame :
# accumulate the data
if self.data is None :
self.data = np.float_(frame.data())
else :
self.data += frame.data()
|
...
Note that imsave saves the image only, pixel by pixel. If you want a view of the figure itself, lower resolution, you can save it from the interactive window you get from plt.show().
CsPad data
...
PnCCD image
Code Block |
---|
| none |
---|
| none |
---|
title | getPnCcdValue |
---|
|
def event(self,evt,env):
try:
frame = evt.getPnCcdValue( self.source, env )
image = frame.data()
except:
pass
|
Other image (FCCD*,Opal,PIM)
These all use the generic getFrameValue function:
Code Block |
---|
| none |
---|
| none |
---|
title | getFrameValue |
---|
|
def event(self,evt,env):
try:
frame = evt.getFrameValue( self.source )
image = frame.data()
except:
pass
|
FCCD (Fast CCD) image
The Fast CCD is read out as two 8-bit images, therefore you need this extra line to convert it to the right format.
Code Block |
---|
| none |
---|
| none |
---|
title | getFrameValue |
---|
|
def event(self,evt,env):
try:
frame = evt.getFrameValue( self.source )
image = frame.data()
except:
pass
# convert to 16-bit integer
image.dtype = np.uint16
|
CsPad data
Here's an example of getting CsPad data from an event:
Code Block |
---|
| none |
---|
| none |
---|
title | getCsPadQuads |
---|
|
def event(self,evt,env):
quads = evt.getCsPadQuads(self.img_source, env)
if not quads :
print '*** cspad information is missing ***'
return
# dump information about quadrants
print "Number of quadrants: %d" % len(quads)
for q in quads:
print " Quadrant %d" % q.quad()
print " virtual_channel: %s" % q.virtual_channel()
print " lane: %s" % q.lane()
print " tid: %s" % q.tid()
print " acq_count: %s" % q.acq_count()
print " op_code: %s" % q.op_code()
print " seq_count: %s" % q.seq_count()
print " ticks: %s" % q.ticks()
print " fiducials: %s" % q.fiducials()
print " frame_type: %s" % q.frame_type()
print " sb_temp: %s" % map(q.sb_temp, range(4))
# image data as 3-dimentional array
data = q.data()
|
...