//////////////////////////////////////////////////////
// Time-Monitor-Script
//////////////////////////////////////////////////////
// This general script monitors a value and plots it
// in regular intervals. When launched, a Lineplot is
// created and values are ploted on the right-most
// channel regularly. Previous values are shifted to
// the left. The following key-strokes are registered:
// Start or ReStart the measurement
//
Pause or UnPause the measurement
// Stop the script
// <+> Double plot range
// <-> Half plot range
//////////////////////////////////////////////////////
// To customize the script, derive a new class from
// CMonitor class and override the following three
// methods:
//
// number GetCurrentPlotValue( object self )
// Return the value to be plotted at time of call
//
// string GetCurrentPlotLabel( object self )
// Return the legend label of the plotted value
//
// string GetCurrentValueUnit( object self )
// Return the intensity unit for the graph
//////////////////////////////////////////////////////
class CMonitor
{
number wtime_sec, taskID, WListenerID, KeyListenerID
image plot
number GetCurrentPlotValue( object self ) {return random();}
string GetCurrentPlotLabel( object self ) {return "Random value";}
string GetCurrentValueUnit( object self ) {return "unit";}
void TUpdate( object self )
{
plot.SetStringNote( "Measurement last point", GetTime(1) )
number nch = plot.ImageGetDimensionSize(0)
plot.slice1(0,0,0,0,nch-1,1) = plot.slice1(1,0,0,0,nch-1,1)
plot[0,nch-1,1,nch] = self.GetCurrentPlotValue()
}
void Reset( object self ){ plot = 0;}
object StartMeasure( object self )
{
if ( taskID )
RemoveMainThreadTask( taskID )
taskID = self.AddMainThreadPeriodicTask( "TUpdate", wtime_sec )
}
object StopMeasure( object self )
{
RemoveMainThreadTask( taskID )
taskID = 0
}
void ResizePlot( object self, number factor )
{
number nch = plot.ImageGetDimensionSize( 0 )
number newCh = trunc( nCh * factor )
if ( newCh < 2 ) newCH = 2
number lastP = nCh < newCh ? nCh : newCh
image plotCopy := plot.ImageClone()
plot.ImageResize( 1, newCH )
plot.ImageSetDimensionCalibration( 0, -wtime_sec * newCH, wtime_sec, "sec", 0 )
plot.slice1( newCh - lastP, 0, 0, 0, lastP, 1 ) = plotCopy.slice1( nCh - lastP, 0, 0, 0, lastP, 1 )
plot.ImageGetImageDisplay( 0 ).LinePlotImageDisplaySetDisplayedChannels( 0, newCH )
}
void WClose( object self, number e_fl, DocumentWindow Win )
{
result( GetTime( 1 ) + ": Script window closed.\n" )
self.StopMeasure()
}
number KeyListenAction( object self, ImageDisplay disp, object keydesc )
{
if ( keydesc.MatchesKeyDescriptor( "esc" ) )
{
self.StopMeasure()
disp.ImageDisplayRemoveKeyHandler( KeyListenerID )
documentWindow win = disp.ImageDisplayGetImage().ImageGetOrCreateImageDocument().ImageDocumentGetwindow()
win.WindowRemoveWindowListener( WListenerID )
result( GetTime(1) + ": Script stopped\n" )
}
else if ( keydesc.MatchesKeyDescriptor( "s" ) )
{
if ( taskID )
{
self.StopMeasure()
self.Reset()
self.StartMeasure()
result( GetTime(1) + ": Measurement Re-Started\n" )
}
else
{
self.StartMeasure()
result( GetTime(1) + ": Measurement Started\n" )
}
}
else if ( keydesc.MatchesKeyDescriptor( "p" ) )
{
if ( taskID )
{
self.StopMeasure()
result( GetTime(1) + ": Measurement Paused\n" )
}
else
{
self.StartMeasure()
result( GetTime(1) + ": Measurement Continued\n" )
}
}
else if ( keydesc.MatchesKeyDescriptor( "add" ) )
{
self.ResizePlot( 2 )
}
else if ( keydesc.MatchesKeyDescriptor( "subtract" ) )
{
self.ResizePlot( 0.5 )
}
else
return 0
return 1
}
object Init( object self, number waitTime_sec, number bufferChannels )
{
wtime_sec = waitTime_sec
plot := RealImage( "Value Graph", 4, bufferChannels )
plot.ImageSetDimensionCalibration( 0, -waitTime_sec * bufferChannels, waitTime_sec, "sec", 0 )
plot.ImageSetIntensityUnitString( self.GetCurrentValueUnit() )
plot.ShowImage()
DocumentWindow win = plot.imageGetOrCreateImageDocument().ImageDocumentGetWindow()
ImageDisplay disp = plot.ImageGetImageDisplay( 0 )
disp.LinePlotImageDisplaySetLegendShown( 1 )
disp.LinePlotImageDisplaySetSliceDrawingStyle( 0, 1 )
disp.LinePlotImageDisplaySetSliceLineThickness( 0, 3 )
object sliceID = disp.ImageDisplayGetSliceIDByIndex( 0 )
disp.ImageDisplaySetSliceLabelByID( sliceID, self.GetCurrentPlotLabel() )
WListenerID = win.WindowAddWindowListener( self, "window_about_to_close:WClose;" )
KeyListenerID = disp.ImageDisplayAddKeyHandler( self, "KeyListenAction" )
return self
}
}
////////////////////////////////////////////////
// Memory-Monitor-Script
////////////////////////////////////////////////
// Plot the size of the largest contiguous free
// memory block over time.
Class CMemMonitor : CMonitor
{
number GetCurrentPlotValue( object self )
{
return ApplicationGetLargestFreeMemoryBlock()
}
string GetCurrentPlotLabel( object self )
{
return "Free Memory"
}
string GetCurrentValueUnit( object self )
{
return "Byte"
}
}
// Start the monitor
alloc(CMemMonitor).Init(0.2,100)