Esempio n. 1
0
    def updateDisplay(self):
        self._plot.title = self.titleString()
        if self.subTitleString():
            self._plot.subTitle = self.subTitleString()
        self._plot.xlabel = self.xaxisName()
        self._plot.ylabel = self.yaxisName()
        if self.normalized:
            self._plot.ylabel += " (norm: %s)" % self.normalized

        self.plotcurves = []
        self.addAllCurves()
        if self.timeaxis:
            self._plot.viewport = (.1, .85, .18, .88)
            self._axes.setXtickCallback(self.xtickCallBack)
            self._plot.offsetXLabel = -.08

        scale = self.yaxisScale()
        if scale:
            axes = self._plot.getAxes(0)
            curwin = axes.getWindow()
            if not curwin:
                curwin = [0, 1, scale[0], scale[1]]
                curves = axes.getCurves()
                xmins = []
                xmaxs = []
                for c in curves:
                    if c.visible:
                        xmins.append(min(c.x))
                        xmaxs.append(max(c.x))
                if xmins and xmaxs:
                    curwin[0] = min(xmins)
                    curwin[1] = max(xmaxs)
            axes.setWindow(curwin[0], curwin[1], scale[0], scale[1])
        InteractiveGRWidget.update(self)
Esempio n. 2
0
 def pointsAdded(self, series):
     plotcurve = self.series2curve[series]
     plotcurve.x = series.x
     plotcurve.y = series.y
     plotcurve.legend = series.title
     self._axes.addCurves(plotcurve)
     InteractiveGRWidget.update(self)
Esempio n. 3
0
    def initUi(self):
        # axes setup
        self.widget = InteractiveGRWidget(self)
        self.plot = Plot(viewport=(.1, .95, .25, .95))
        self.axes = NicosTimePlotAxes(self.plot._viewport)
        self.axes.setWindow(0, 1, 0, 1)
        self.plot.addAxes(self.axes)
        self.plot.setLegend(True)
        self.plot.setLegendWidth(0.07)
        self.plot.offsetXLabel = -.2
        self.axes.setXtickCallback(self.xtickCallBack)
        self.widget.addPlot(self.plot)
        layout = QHBoxLayout(self)
        layout.addWidget(self.widget)
        layout.setContentsMargins(0, 0, 0, 0)
        self.setLayout(layout)

        self.curves = []

        # event support
        self.widget.cbm.addHandler(LegendEvent.ROI_CLICKED,
                                   self.on_legendItemClicked, LegendEvent)
        self.widget.cbm.addHandler(MouseEvent.MOUSE_MOVE, self.on_mouseMove)

        self.timeSeriesUpdate.connect(self.on_timeSeriesUpdate)
Esempio n. 4
0
    def __init__(self, parent, window, timeaxis=False):
        InteractiveGRWidget.__init__(self, parent)
        NicosPlot.__init__(self, window, timeaxis=timeaxis)

        self.timeaxis = timeaxis or (self.axescls == NicosTimePlotAxes)
        self.leftTurnedLegend = True
        self.statusMessage = None
        self.mouselocation = None
        self._cursor = self.cursor()
        self._mouseSelEnabled = self.getMouseSelectionEnabled()
        self._markertype = gr.MARKERTYPE_OMARK

        dictPrintType = dict(gr.PRINT_TYPE)
        for prtype in [gr.PRINT_JPEG, gr.PRINT_TIF]:
            dictPrintType.pop(prtype)
        self._saveTypes = (";;".join(dictPrintType.values()) + ";;" +
                           ";;".join(gr.GRAPHIC_TYPE.values()))
        self._saveName = None
        self._color = ColorIndexGenerator()
        self._plot = Plot(viewport=(.1, .85, .15, .88))
        self._plot.setLegendWidth(0.05)
        self._axes = self.axescls(viewport=self._plot.viewport)
        self._axes.backgroundColor = 0
        self._plot.addAxes(self._axes)
        self._plot.title = self.titleString()
        self.addPlot(self._plot)

        guiConn = GUIConnector(self)
        guiConn.connect(LegendEvent.ROI_CLICKED, self.on_legendItemClicked,
                        LegendEvent)
        guiConn.connect(ROIEvent.ROI_CLICKED, self.on_roiItemClicked, ROIEvent)
        guiConn.connect(MouseEvent.MOUSE_PRESS, self.on_fitPicker_selected)
        guiConn.connect(MouseEvent.MOUSE_MOVE, self.on_mouseMove)
        self.logXinDomain.connect(self.on_logXinDomain)
        self.logYinDomain.connect(self.on_logYinDomain)
        self.setLegend(True)
        self.updateDisplay()
Esempio n. 5
0
 def __init__(self, widget, **kwds):
     InteractiveGRWidget.__init__(self, widget, **kwds)
     self.widget = widget
     self.adjustSelectRect = self._noadjustSelectRect
Esempio n. 6
0
class TrendPlot(NicosWidget, QWidget):

    designer_description = 'A trend plotter for one or more devices'
    designer_icon = ':/plotter'

    widgetInfo = pyqtSignal(str)
    timeSeriesUpdate = pyqtSignal(object)

    # colors = [Qt.red, Qt.darkGreen, Qt.blue, Qt.black, Qt.magenta, Qt.cyan,
    #           Qt.darkGray]

    devices = PropDef(
        'devices', 'QStringList', [], '''
List of devices or cache keys that the plot should display.

For devices use device name. For keys use cache key with "." or "/" separator,
e.g. T.heaterpower.

To access items of a sequence, use subscript notation, e.g. T.userlimits[0]
''')
    names = PropDef(
        'names', 'QStringList', [], 'Names for the plot curves, '
        'defaults to the device names/keys.')
    legend = PropDef('legend', bool, False, 'If a legend should be shown.')
    plotwindow = PropDef(
        'plotwindow', int, 3600, 'The range of time in '
        'seconds that should be represented by the plot.')
    plotinterval = PropDef(
        'plotinterval', float, 2, 'The minimum time in '
        'seconds between two points that should be '
        'plotted.')
    height = PropDef(
        'height', int, 10, 'Height of the plot widget in units '
        'of app font character width.')
    width = PropDef(
        'width', int, 30, 'Width of the plot widget in units '
        'of app font character width.')

    # pylint: disable=W0231
    def __init__(self, parent, designMode=False):
        self.ncurves = 0
        self.ctimers = {}
        self.keyindices = {}
        self.plotcurves = {}
        self.series = {}
        self.legendobj = None

        # X label settings, default values for default window of 3600s
        self._showdate = False
        self._showsecs = False

        QWidget.__init__(self, parent)
        NicosWidget.__init__(self)

    def initUi(self):
        # axes setup
        self.widget = InteractiveGRWidget(self)
        self.plot = Plot(viewport=(.1, .95, .25, .95))
        self.axes = NicosTimePlotAxes(self.plot._viewport)
        self.axes.setWindow(0, 1, 0, 1)
        self.plot.addAxes(self.axes)
        self.plot.setLegend(True)
        self.plot.setLegendWidth(0.07)
        self.plot.offsetXLabel = -.2
        self.axes.setXtickCallback(self.xtickCallBack)
        self.widget.addPlot(self.plot)
        layout = QHBoxLayout(self)
        layout.addWidget(self.widget)
        layout.setContentsMargins(0, 0, 0, 0)
        self.setLayout(layout)

        self.curves = []

        # event support
        self.widget.cbm.addHandler(LegendEvent.ROI_CLICKED,
                                   self.on_legendItemClicked, LegendEvent)
        self.widget.cbm.addHandler(MouseEvent.MOUSE_MOVE, self.on_mouseMove)

        self.timeSeriesUpdate.connect(self.on_timeSeriesUpdate)

    def xtickCallBack(self, x, y, _svalue, value):
        gr.setcharup(-1., 1.)
        gr.settextalign(gr.TEXT_HALIGN_RIGHT, gr.TEXT_VALIGN_TOP)
        dx = .02
        timeVal = localtime(value)
        if self._showdate:
            gr.text(x + dx, y - 0.01, strftime(DATEFMT, timeVal))
        if self._showsecs:
            gr.text(x - dx, y - 0.01, strftime(TIMEFMT, timeVal))
        else:
            gr.text(x - dx, y - 0.01, strftime(SHORTTIMEFMT, timeVal))
        gr.setcharup(0., 1.)

    def propertyUpdated(self, pname, value):
        if pname == 'plotwindow':
            self._showdate = value > 24 * 3600
            self._showsecs = value < 300
        elif pname in ('width', 'height'):
            self.setMinimumSize(
                QSize(self._scale * (self.props['width'] + .5),
                      self._scale * (self.props['height'] + .5)))
        elif pname == 'legend':
            self.plot.setLegend(value)
        NicosWidget.propertyUpdated(self, pname, value)

    def setFont(self, font):
        pass  # TODO: can't set font for GR right now

    def on_mouseMove(self, event):
        wc = event.getWC(self.plot.viewport)
        ts = strftime(DATEFMT + ' ' + TIMEFMT, localtime(wc.x))
        msg = 't = %s, y = %g' % (ts, wc.y)
        self.widgetInfo.emit(msg)

    def on_legendItemClicked(self, event):
        if event.getButtons() & MouseEvent.LEFT_BUTTON:
            event.curve.visible = not event.curve.visible
            self.update()

    def on_timeSeriesUpdate(self, series):
        curve = self.plotcurves[series]
        curve.x = series.x
        curve.y = series.y
        c = self.axes.getCurves()
        dy = abs(c.ymin - c.ymax) * 0.05
        self.axes.setWindow(c.xmin, c.xmax, c.ymin - dy, c.ymax + dy)
        self.widget.update()
        self.ctimers[curve].start(5000)

    def on_keyChange(self, key, value, time, expired):
        if key not in self.keyindices or value is None:
            return
        for index in self.keyindices[key]:
            series = self.series[key, index]
            # restrict time of value to 1 minute past at
            # maximum, so that it doesn't get culled by the windowing
            time = max(time, currenttime() - 60)
            if index:
                try:
                    fvalue = functools.reduce(operator.getitem, index, value)
                    series.add_value(time, fvalue)
                except Exception:
                    pass
            else:
                series.add_value(time, value)

    def addcurve(self, key, index, title, scale, offset):
        series = TimeSeries(key, self.props['plotinterval'], scale, offset,
                            self.props['plotwindow'], self)
        series.init_empty()
        curve = PlotCurve([currenttime()], [0], legend=title)
        self.plotcurves[series] = curve
        self.ncurves += 1
        self.curves.append(curve)
        self.axes.addCurves(curve)
        self.series[key, index] = series
        self.widget.update()

        # record the current value at least every 5 seconds, to avoid curves
        # not updating if the value doesn't change
        def update():
            series.synthesize_value()

        self.ctimers[curve] = QTimer(singleShot=True)
        self.ctimers[curve].timeout.connect(update)

    def registerKeys(self):
        for key, name in zip_longest(self.props['devices'],
                                     self.props['names']):
            if name is None:
                name = key
            key, index, scale, offset = extractKeyAndIndex(key)
            keyid = self._source.register(self, key)
            self.keyindices.setdefault(keyid, []).append(index)
            self.addcurve(keyid, index, name, scale, offset)