def pie_label(self, x, y, label):
     if not label:
         return
     text = QGraphicsSimpleTextItem(label)
     for cut in range(1, len(label)):
         if text.boundingRect().width() < 0.95 * SCALE:
             break
         text = QGraphicsSimpleTextItem(label[:-cut] + "...")
     text.setPos(x - text.boundingRect().width() / 2, y + 0.5 * SCALE)
     self.scene.addItem(text)
Example #2
0
    def __init__(self, name, values, scale, name_offset, offset, labels=None):
        super().__init__()

        # leading label
        font = name.document().defaultFont()
        if self.bold_label:
            font.setWeight(QFont.Bold)
        name.setFont(font)
        name.setPos(name_offset, -10)
        name.setParentItem(self)

        # prediction marker
        self.dot = self.DOT_ITEM_CLS(self.DOT_RADIUS, scale, offset, values[0],
                                     values[-1])
        self.dot.setParentItem(self)

        # pylint: disable=unused-variable
        # line
        line = QGraphicsLineItem(min(values) * scale + offset, 0,
                                 max(values) * scale + offset, 0,
                                 self)

        if labels is None:
            labels = [str(abs(v) if v == -0 else v) for v in values]

        old_x_tick = None
        shown_items = []
        w = QGraphicsSimpleTextItem(labels[0]).boundingRect().width()
        text_finish = values[0] * scale - w + offset - 10
        for i, (label, value) in enumerate(zip(labels, values)):
            text = QGraphicsSimpleTextItem(label)
            x_text = value * scale - text.boundingRect().width() / 2 + offset
            if text_finish > x_text - 10:
                y_text, y_tick = self.DOT_RADIUS * 0.7, 0
                text_finish = values[0] * scale + offset
            else:
                y_text = - text.boundingRect().height() - self.DOT_RADIUS * 0.7
                y_tick = - self.tick_height
                text_finish = x_text + text.boundingRect().width()
            text.setPos(x_text, y_text)
            if not collides(text, shown_items):
                text.setParentItem(self)
                shown_items.append(text)

            x_tick = value * scale - self.tick_width / 2 + offset
            tick = QGraphicsRectItem(
                x_tick, y_tick, self.tick_width, self.tick_height,
                self)
            tick.setBrush(QColor(Qt.black))

            if self.half_tick_height and i:
                x = x_tick - (x_tick - old_x_tick) / 2
                half_tick = QGraphicsLineItem(x, - self.half_tick_height, x, 0,
                                              self)
            old_x_tick = x_tick
 def get_needed_offset(self, explanations):
     max_n = 0
     word = ""
     max_v = 0
     val = ""
     for e in explanations:
         if max_n < len(str(e._metas[0])):
             word = str(e._metas[0])
             max_n = len(str(e._metas[0]))
         if max_v < len(str(e._metas[1])):
             val = str(e._metas[1])
             max_v = len(str(e._metas[1]))
     w = QGraphicsSimpleTextItem(word, None)
     v = QGraphicsSimpleTextItem(val, None)
     return w.boundingRect().width(), v.boundingRect().width()
Example #4
0
 def centered_text(val, pos):
     t = QGraphicsSimpleTextItem(
         "%.*f" % (attr.number_of_decimals + 1, val), labels)
     t.setFont(self._label_font)
     bbox = t.boundingRect()
     t.setPos(pos - bbox.width() / 2, 22)
     return t
Example #5
0
    def display_changed_disc(self):
        self.clear_scene()
        self.attr_labels = [QGraphicsSimpleTextItem(lab)
                            for lab in self.label_txts_all]

        if not self.stretched:
            if self.group_var:
                self.labels = [
                    QGraphicsTextItem("{}".format(int(sum(cont))))
                    for cont in self.conts]
            else:
                self.labels = [
                    QGraphicsTextItem(str(int(sum(self.dist))))]

        self.draw_axis_disc()
        if self.group_var:
            self.boxes = [self.strudel(cont, i) for i, cont in enumerate(self.conts)]
        else:
            self.boxes = [self.strudel(self.dist)]

        for row, box in enumerate(self.boxes):
            y = (-len(self.boxes) + row) * 40 + 10

            label = self.attr_labels[row]
            b = label.boundingRect()
            label.setPos(-b.width() - 10, y - b.height() / 2)
            self.box_scene.addItem(label)
            if not self.stretched:
                label = self.labels[row]
                b = label.boundingRect()
                if self.group_var:
                    right = self.scale_x * sum(self.conts[row])
                else:
                    right = self.scale_x * sum(self.dist)
                label.setPos(right + 10, y - b.height() / 2)
                self.box_scene.addItem(label)

            if self.attribute is not self.group_var:
                for text_item, bar_part in zip(box[1::2], box[::2]):
                    label = QGraphicsSimpleTextItem(
                        text_item.toPlainText())
                    label.setPos(bar_part.boundingRect().x(),
                                 y - label.boundingRect().height() - 8)
                    self.box_scene.addItem(label)
            for item in box:
                if isinstance(item, QGraphicsTextItem):
                    continue
                self.box_scene.addItem(item)
                item.setPos(0, y)
        self.box_scene.setSceneRect(-self.label_width - 5,
                                    -30 - len(self.boxes) * 40,
                                    self.scene_width, len(self.boxes * 40) + 90)
        self.infot1.setText("")
        self.select_box_items()
Example #6
0
 def mean_label(self, stat, attr, val_name):
     label = QGraphicsItemGroup()
     t = QGraphicsSimpleTextItem("%.*f" % (attr.number_of_decimals + 1, stat.mean), label)
     t.setFont(self._label_font)
     bbox = t.boundingRect()
     w2, h = bbox.width() / 2, bbox.height()
     t.setPos(-w2, -h)
     tpm = QGraphicsSimpleTextItem(" \u00b1 " + "%.*f" % (attr.number_of_decimals + 1, stat.dev), label)
     tpm.setFont(self._label_font)
     tpm.setPos(w2, -h)
     if val_name:
         vnm = QGraphicsSimpleTextItem(val_name + ": ", label)
         vnm.setFont(self._label_font)
         vnm.setBrush(self._attr_brush)
         vb = vnm.boundingRect()
         label.min_x = -w2 - vb.width()
         vnm.setPos(label.min_x, -h)
     else:
         label.min_x = -w2
     return label
Example #7
0
    def __init__(self, name, data_extremes, values, scale, name_offset, offset):
        super().__init__()
        data_start, data_stop = data_extremes[0], data_extremes[1]
        labels = [str(np.round(data_start + (data_stop - data_start) * i /
                               (self.n_tck - 1), 1)) for i in range(self.n_tck)]

        # leading label
        font = name.document().defaultFont()
        name.setFont(font)
        name.setPos(name_offset, -10)
        name.setParentItem(self)

        # labels
        ascending = data_start < data_stop
        y_start, y_stop = (self.y_diff, 0) if ascending else (0, self.y_diff)
        for i in range(self.n_tck):
            text = QGraphicsSimpleTextItem(labels[i], self)
            w = text.boundingRect().width()
            y = y_start + (y_stop - y_start) / (self.n_tck - 1) * i
            text.setPos(-5 - w, y - 8)
            tick = QGraphicsLineItem(-2, y, 2, y, self)

        # prediction marker
        self.dot = Continuous2DMovableDotItem(
            self.DOT_RADIUS, scale, offset, values[0], values[-1], y_start, y_stop)
        self.dot.tooltip_labels = labels
        self.dot.tooltip_values = values
        self.dot.setParentItem(self)
        h_line = QGraphicsLineItem(values[0] * scale + offset, self.y_diff / 2,
                                   values[-1] * scale + offset, self.y_diff / 2,
                                   self)
        pen = QPen(Qt.DashLine)
        pen.setBrush(QColor(Qt.red))
        h_line.setPen(pen)
        self.dot.horizontal_line = h_line

        # pylint: disable=unused-variable
        # line
        line = QGraphicsLineItem(values[0] * scale + offset, y_start,
                                 values[-1] * scale + offset, y_stop,
                                 self)

        # ticks
        for value in values:
            diff_ = np.nan_to_num(values[-1] - values[0])
            k = (value - values[0]) / diff_ if diff_ else 0
            y_tick = (y_stop - y_start) * k + y_start - self.tick_height / 2
            x_tick = value * scale - self.tick_width / 2 + offset
            tick = QGraphicsRectItem(
                x_tick, y_tick, self.tick_width, self.tick_height,
                self)
            tick.setBrush(QColor(Qt.black))

        # rect
        rect = QGraphicsRectItem(
            values[0] * scale + offset, -self.y_diff * 0.125,
            values[-1] * scale + offset, self.y_diff * 1.25,
            self)
        pen = QPen(Qt.DotLine)
        pen.setBrush(QColor(50, 150, 200, 255))
        rect.setPen(pen)
        self.setPreferredSize(self.preferredWidth(), self.y_diff * 1.5)
Example #8
0
 def centered_text(val, pos):
     t = QGraphicsSimpleTextItem(attr.str_val(val), labels)
     t.setFont(self._label_font)
     bbox = t.boundingRect()
     t.setPos(pos - bbox.width() / 2, 22)
     return t
Example #9
0
    def __init__(self, name, data_extremes, values, scale, name_offset, offset):
        super().__init__()
        data_start, data_stop = data_extremes[0], data_extremes[1]
        labels = [str(np.round(data_start + (data_stop - data_start) * i /
                               (self.n_tck - 1), 1)) for i in range(self.n_tck)]

        # leading label
        font = name.document().defaultFont()
        name.setFont(font)
        name.setPos(name_offset, -10)
        name.setParentItem(self)

        # labels
        ascending = data_start < data_stop
        y_start, y_stop = (self.y_diff, 0) if ascending else (0, self.y_diff)
        for i in range(self.n_tck):
            text = QGraphicsSimpleTextItem(labels[i], self)
            w = text.boundingRect().width()
            y = y_start + (y_stop - y_start) / (self.n_tck - 1) * i
            text.setPos(-5 - w, y - 8)
            tick = QGraphicsLineItem(-2, y, 2, y, self)

        # prediction marker
        self.dot = Continuous2DMovableDotItem(
            self.DOT_RADIUS, scale, offset, values[0], values[-1], y_start, y_stop)
        self.dot.tooltip_labels = labels
        self.dot.tooltip_values = values
        self.dot.setParentItem(self)
        h_line = QGraphicsLineItem(values[0] * scale + offset, self.y_diff / 2,
                                   values[-1] * scale + offset, self.y_diff / 2,
                                   self)
        pen = QPen(Qt.DashLine)
        pen.setBrush(QColor(Qt.red))
        h_line.setPen(pen)
        self.dot.horizontal_line = h_line

        # pylint: disable=unused-variable
        # line
        line = QGraphicsLineItem(values[0] * scale + offset, y_start,
                                 values[-1] * scale + offset, y_stop,
                                 self)

        # ticks
        for value in values:
            diff_ = np.nan_to_num(values[-1] - values[0])
            k = (value - values[0]) / diff_ if diff_ else 0
            y_tick = (y_stop - y_start) * k + y_start - self.tick_height / 2
            x_tick = value * scale - self.tick_width / 2 + offset
            tick = QGraphicsRectItem(
                x_tick, y_tick, self.tick_width, self.tick_height,
                self)
            tick.setBrush(QColor(Qt.black))

        # rect
        rect = QGraphicsRectItem(
            values[0] * scale + offset, -self.y_diff * 0.125,
            values[-1] * scale + offset, self.y_diff * 1.25,
            self)
        pen = QPen(Qt.DotLine)
        pen.setBrush(QColor(50, 150, 200, 255))
        rect.setPen(pen)
        self.setPreferredSize(self.preferredWidth(), self.y_diff * 1.5)
class VariableItem(QGraphicsItemGroup):
    MAX_ATTR_LEN = 25
    MAX_LABEL_LEN = 150
    VALUE_FONT_SETTING = {Updater.SIZE_LABEL: 12,
                          Updater.IS_ITALIC_LABEL: True}

    def __init__(self, parent, label: str):
        self.__name: str = None
        self.__value: Optional[str] = None
        self.__name_item = QGraphicsSimpleTextItem()
        self.__value_item = QGraphicsSimpleTextItem()
        font = Updater.change_font(QFont(), self.VALUE_FONT_SETTING)
        self.__value_item.setFont(font)
        self.__max_len = self.MAX_LABEL_LEN
        super().__init__(parent)
        self._set_data(label)

    @property
    def items(self):
        return self.__name_item, self.__value_item

    def boundingRect(self):
        name_br = self.__name_item.boundingRect()
        width = name_br.width()
        height = name_br.height()
        if self.__value_item is not None:
            value_br = self.__value_item.boundingRect()
            width = max(width, value_br.width())
            height += value_br.height()
        return QRectF(-width, 0, width, height)

    def updateGeometry(self):
        self.__elide()
        self.__align_center()
        self.__align_right()

    def set_max_len(self, length: int):
        self.__max_len = length
        self.updateGeometry()

    def _set_data(self, label: str):
        split = label.split("=")
        self.__name = split[0]
        self.__name_item.setToolTip(self.__name)
        self.updateGeometry()  # align before adding to group
        self.addToGroup(self.__name_item)
        if len(split) > 1:
            self.__value = split[1]
            self.__value_item.setToolTip(self.__value)
            self.updateGeometry()  # align before adding to group
            self.addToGroup(self.__value_item)

    def __elide(self):
        fm = QFontMetrics(self.__name_item.font())
        text = fm.elidedText(self.__name, Qt.ElideRight, self.__max_len)
        self.__name_item.setText(text)
        if self.__value is not None:
            fm = QFontMetrics(self.__value_item.font())
            text = fm.elidedText(self.__value, Qt.ElideRight, self.__max_len)
            self.__value_item.setText(text)

    def __align_center(self):
        if self.__value is not None:
            self.__value_item.setY(self.__name_item.boundingRect().height())

    def __align_right(self):
        self.__name_item.setX(-self.__name_item.boundingRect().width())
        if self.__value is not None:
            self.__value_item.setX(-self.__value_item.boundingRect().width())