Exemplo n.º 1
0
    def _restore_selection(self, state):
        # type: (SelectionState) -> bool
        """
        Restore the (manual) node selection state.

        Return True if successful; False otherwise.
        """
        linkmatrix = self.linkmatrix
        if self.selection_method == 0 and self.root:
            selected, linksaved = state
            linkstruct = np.array(linksaved, dtype=float)
            selected = set(selected)  # type: Set[Tuple[int]]
            if not selected:
                return False
            if linkmatrix.shape[0] != linkstruct.shape[0]:
                return False
            # check that the linkage matrix structure matches. Use isclose for
            # the height column to account for inexact floating point math
            # (e.g. summation order in different ?gemm implementations for
            # euclidean distances, ...)
            if np.any(linkstruct[:, :2] != linkmatrix[:, :2]) or \
                    not np.all(np.isclose(linkstruct[:, 2], linkstruct[:, 2])):
                return False
            selection = []
            indices = np.array([n.value.index for n in leaves(self.root)],
                               dtype=int)
            # mapping from ranges to display (pruned) nodes
            mapping = {
                node.value.range: node
                for node in postorder(self._displayed_root)
            }
            for node in postorder(self.root):  # type: Tree
                r = tuple(indices[node.value.first:node.value.last])
                if r in selected:
                    if node.value.range not in mapping:
                        # the node was pruned from display and cannot be
                        # selected
                        break
                    selection.append(mapping[node.value.range])
                    selected.remove(r)
                if not selected:
                    break  # found all, nothing more to do
            if selection and selected:
                # Could not restore all selected nodes (only partial match)
                return False

            self._set_selected_nodes(selection)
            return True
        return False
 def set_root(self, root):
     """ Set the root cluster.
     
     :param root: Root cluster.
     :type root: :class:`Orange.clustering.hierarchical.HierarchicalCluster`
      
     """
     self.clear()
     self.root_cluster = root
     self.dendrogram_items = {}
     self.cluster_parent = {}
     self.selected_items = {}
     if root:
         items = []
         for cluster in hierarchical.postorder(self.root_cluster):
             item = DendrogramItem(cluster, parent=self, orientation=self.orientation)
              
             for branch in cluster.branches or []:
                 branch_item = self.dendrogram_items[branch] 
                 self.cluster_parent[branch] = cluster
             items.append(GraphicsRectLayoutItem(item))
             self.dendrogram_items[cluster] = item
             
         self.layout().setDendrogram(root, items)
         
         self.resize(self.layout().sizeHint(Qt.PreferredSize))
         self.layout().activate()
         self.emit(SIGNAL("dendrogramLayoutChanged()"))
Exemplo n.º 3
0
    def setRoot(self, root):
        # type: (Tree) -> None
        """
        Set the root cluster tree node for display.

        Parameters
        ----------
        root : Tree
            The tree root node.
        """
        self.clear()
        self._root = root
        if root is not None:
            foreground = self.palette().color(QPalette.Foreground)
            pen = make_pen(foreground,
                           width=1,
                           cosmetic=True,
                           join_style=Qt.MiterJoin)
            for node in postorder(root):
                item = DendrogramWidget.ClusterGraphicsItem(self._itemgroup)
                item.setAcceptHoverEvents(True)
                item.setPen(pen)
                item.node = node
                for branch in node.branches:
                    assert branch in self._items
                    self._cluster_parent[branch] = node
                self._items[node] = item

            self._relayout()
            self._rescale()
        self.updateGeometry()
 def test_pre_post_order(self):
     tree = hierarchical.Tree
     root = tree("A", (tree("B"), tree("C")))
     self.assertEqual([n.value for n in hierarchical.postorder(root)],
                      ["B", "C", "A"])
     self.assertEqual([n.value for n in hierarchical.preorder(root)],
                      ["A", "B", "C"])
Exemplo n.º 5
0
    def set_root(self, root):
        """ Set the root cluster.
        
        :param root: Root cluster.
        :type root: :class:`Orange.clustering.hierarchical.HierarchicalCluster`
         
        """
        self.clear()
        self.root_cluster = root
        self.dendrogram_items = {}
        self.cluster_parent = {}
        self.selected_items = {}
        if root:
            items = []
            for cluster in hierarchical.postorder(self.root_cluster):
                item = DendrogramItem(cluster,
                                      parent=self,
                                      orientation=self.orientation)

                for branch in cluster.branches or []:
                    branch_item = self.dendrogram_items[branch]
                    self.cluster_parent[branch] = cluster
                items.append(GraphicsRectLayoutItem(item))
                self.dendrogram_items[cluster] = item

            self.layout().setDendrogram(root, items)

            self.resize(self.layout().sizeHint(Qt.PreferredSize))
            self.layout().activate()
            self.emit(SIGNAL("dendrogramLayoutChanged()"))
Exemplo n.º 6
0
    def _relayout(self):
        if self._root is None:
            return

        scale = self._height_scale_factor()
        base = scale * self._root.value.height
        self._layout = dendrogram_path(self._root,
                                       self.orientation,
                                       scaleh=scale)
        for node_geom in postorder(self._layout):
            node, geom = node_geom.value
            item = self._items[node]
            item.element = geom
            # the untransformed source path
            item.sourcePath = path_toQtPath(geom)
            r = item.sourcePath.boundingRect()

            if self.orientation == Left:
                r.setRight(base)
            elif self.orientation == Right:
                r.setLeft(0)
            elif self.orientation == Top:
                r.setBottom(base)
            else:
                r.setTop(0)

            hitarea = QPainterPath()
            hitarea.addRect(r)
            item.sourceAreaShape = hitarea
            item.setGeometryData(item.sourcePath, item.sourceAreaShape)
            item.setZValue(-node.value.height)
 def test_pre_post_order(self):
     tree = hierarchical.Tree
     root = tree("A", (tree("B"), tree("C")))
     self.assertEqual([n.value for n in hierarchical.postorder(root)],
                      ["B", "C", "A"])
     self.assertEqual([n.value for n in hierarchical.preorder(root)],
                      ["A", "B", "C"])
Exemplo n.º 8
0
    def _relayout(self):
        if not self._root:
            return

        self._layout = dendrogram_path(self._root, self.orientation)
        for node_geom in postorder(self._layout):
            node, geom = node_geom.value
            item = self._items[node]
            item.element = geom

            item.setPath(Path_toQtPath(geom))
            item.setZValue(-node.value.height)
            item.setPen(QPen(Qt.blue))
            r = item.boundingRect()
            base = self._root.value.height

            if self.orientation == Left:
                r.setRight(base)
            elif self.orientation == Right:
                r.setLeft(0)
            elif self.orientation == Top:
                r.setBottom(base)
            else:
                r.setTop(0)
            item.setRect(r)
Exemplo n.º 9
0
def dendrogram_layout(tree, expand_leaves=False):
    coords = []
    cluster_geometry = {}
    leaf_idx = 0
    for node in postorder(tree):
        cluster = node.value
        if node.is_leaf:
            if expand_leaves:
                start, end = float(cluster.first), float(cluster.last - 1)
            else:
                start = end = leaf_idx
                leaf_idx += 1
            center = (start + end) / 2.0
            cluster_geometry[node] = (start, center, end)
            coords.append((node, (start, center, end)))
        else:
            left = node.left
            right = node.right
            left_center = cluster_geometry[left][1]
            right_center = cluster_geometry[right][1]
            start, end = left_center, right_center
            center = (start + end) / 2.0
            cluster_geometry[node] = (start, center, end)
            coords.append((node, (start, center, end)))

    return coords
    def _relayout(self):
        if not self._root:
            return

        self._layout = dendrogram_path(self._root, self.orientation)
        for node_geom in postorder(self._layout):
            node, geom = node_geom.value
            item = self._items[node]
            item.element = geom

            item.setPath(Path_toQtPath(geom))
            item.setZValue(-node.value.height)
            item.setPen(QPen(Qt.blue))
            r = item.boundingRect()
            base = self._root.value.height

            if self.orientation == Left:
                r.setRight(base)
            elif self.orientation == Right:
                r.setLeft(0)
            elif self.orientation == Top:
                r.setBottom(base)
            else:
                r.setTop(0)
            item.setRect(r)
def dendrogram_layout(tree, expand_leaves=False):
    coords = []
    cluster_geometry = {}
    leaf_idx = 0
    for node in postorder(tree):
        cluster = node.value
        if node.is_leaf:
            if expand_leaves:
                start, end = float(cluster.first), float(cluster.last - 1)
            else:
                start = end = leaf_idx
                leaf_idx += 1
            center = (start + end) / 2.0
            cluster_geometry[node] = (start, center, end)
            coords.append((node, (start, center, end)))
        else:
            left = node.left
            right = node.right
            left_center = cluster_geometry[left][1]
            right_center = cluster_geometry[right][1]
            start, end = left_center, right_center
            center = (start + end) / 2.0
            cluster_geometry[node] = (start, center, end)
            coords.append((node, (start, center, end)))

    return coords
Exemplo n.º 12
0
    def set_root(self, root):
        """Set the root cluster.

        :param Tree root: Root tree.
        """
        self.clear()
        self._root = root
        if root:
            pen = make_pen(Qt.blue,
                           width=1,
                           cosmetic=True,
                           join_style=Qt.MiterJoin)
            for node in postorder(root):
                item = DendrogramWidget.ClusterGraphicsItem(self._itemgroup)
                item.setAcceptHoverEvents(True)
                item.setPen(pen)
                item.node = node
                item.installSceneEventFilter(self)
                for branch in node.branches:
                    assert branch in self._items
                    self._cluster_parent[branch] = node
                self._items[node] = item

            self.updateGeometry()
            self._relayout()
            self._rescale()
Exemplo n.º 13
0
        def set_color(item: DendrogramWidget.ClusterGraphicsItem,
                      color: QColor):
            def branches(item):
                return [self._items[ch] for ch in item.node.branches]

            for it in postorder(item, branches):
                it.setPen(update_pen(it.pen(), brush=color))
Exemplo n.º 14
0
    def _set_hover_item(self, item):
        """Set the currently highlighted item."""
        if self._highlighted_item is item:
            return

        def branches(item):
            return [self._items[ch] for ch in item.node.branches]

        if self._highlighted_item:
            pen = make_pen(Qt.blue, width=1, cosmetic=True)
            for it in postorder(self._highlighted_item, branches):
                it.setPen(pen)

        self._highlighted_item = item
        if item:
            hpen = make_pen(Qt.blue, width=2, cosmetic=True)
            for it in postorder(item, branches):
                it.setPen(hpen)
    def _set_hover_item(self, item):
        """Set the currently highlighted item."""
        if self._highlighted_item is item:
            return

        def branches(item):
            return [self._items[ch] for ch in item.node.branches]

        if self._highlighted_item:
            pen = make_pen(Qt.blue, width=1, cosmetic=True)
            for it in postorder(self._highlighted_item, branches):
                it.setPen(pen)

        self._highlighted_item = item
        if item:
            hpen = make_pen(Qt.blue, width=2, cosmetic=True)
            for it in postorder(item, branches):
                it.setPen(hpen)
 def leaf_items(self):
     """ Iterate over the dendrogram leaf items (instances of :class:`DendrogramItem`).
     """
     if self.root_cluster:
         clusters = hierarchical.postorder(self.root_cluster)
     else:
         clusters = []
     for cluster in clusters:
         if not cluster.branches:
             yield self.dendrogram_items[cluster] 
Exemplo n.º 17
0
 def leaf_items(self):
     """ Iterate over the dendrogram leaf items (instances of :class:`DendrogramItem`).
     """
     if self.root_cluster:
         clusters = hierarchical.postorder(self.root_cluster)
     else:
         clusters = []
     for cluster in clusters:
         if not cluster.branches:
             yield self.dendrogram_items[cluster]
    def test_order(self):
        post = list(hierarchical.postorder(self.cluster))
        seen = set()

        for n in post:
            self.assertTrue(all(ch in seen for ch in n.branches))
            seen.add(n)

        pre = list(hierarchical.preorder(self.cluster))
        seen = set()
        for n in pre:
            self.assertTrue(all(ch not in seen for ch in n.branches))
            seen.add(n)
    def test_order(self):
        post = list(hierarchical.postorder(self.cluster))
        seen = set()

        for n in post:
            self.assertTrue(all(ch in seen for ch in n.branches))
            seen.add(n)

        pre = list(hierarchical.preorder(self.cluster))
        seen = set()
        for n in pre:
            self.assertTrue(all(ch not in seen for ch in n.branches))
            seen.add(n)
Exemplo n.º 20
0
 def _save_selection(self):
     # Save the current manual node selection state
     selection_state = None
     if self.selection_method == 0 and self.root:
         assert self.linkmatrix is not None
         linkmat = [(int(_0), int(_1), _2)
                    for _0, _1, _2 in self.linkmatrix[:, :3].tolist()]
         nodes_ = self.dendrogram.selected_nodes()
         # match the display (pruned) nodes back (by ranges)
         mapping = {node.value.range: node for node in postorder(self.root)}
         nodes = [mapping[node.value.range] for node in nodes_]
         indices = [tuple(node.value.index for node in leaves(node))
                    for node in nodes]
         if nodes:
             selection_state = (indices, linkmat)
     return selection_state
Exemplo n.º 21
0
    def set_root(self, root):
        """Set the root cluster.

        :param Tree root: Root tree.
        """
        self.clear()
        self._root = root
        if root:
            pen = make_pen(Qt.blue, width=1, cosmetic=True, join_style=Qt.MiterJoin)
            for node in postorder(root):
                item = DendrogramWidget.ClusterGraphicsItem(self._itemgroup)
                item.setAcceptHoverEvents(True)
                item.setPen(pen)
                item.node = node
                item.installSceneEventFilter(self)
                for branch in node.branches:
                    assert branch in self._items
                    self._cluster_parent[branch] = node
                self._items[node] = item

            self.updateGeometry()
            self._relayout()
            self._rescale()
 def set_root(self, root):
     """ Set the root cluster.
     
     :param root: Root cluster.
     :type root: :class:`Orange.clustering.hierarchical.HierarchicalCluster`
      
     """
     self.clear()
     self.root_cluster = root
     self.dendrogram_items = {}
     self.cluster_parent = {}
     if root:
         items = []
         for cluster in hierarchical.postorder(self.root_cluster):
             item = RadialDendrogramItem(cluster)
             for branch in cluster.branches or []:
                 branch_item = self.dendrogram_items[branch] 
                 self.cluster_parent[branch] = cluster
             items.append(GraphicsRectLayoutItem(item))
             self.dendrogram_items[cluster] = item
             
         self.layout().setDendrogram(root, items)
         
         self.layout().activate()
Exemplo n.º 23
0
    def _rescale(self):
        if self._root is None:
            return

        scale = self._height_scale_factor()
        base = scale * self._root.value.height
        crect = self.contentsRect()
        leaf_count = len(list(leaves(self._root)))
        if self.orientation in [Left, Right]:
            drect = QSizeF(base, leaf_count)
        else:
            drect = QSizeF(leaf_count, base)

        eps = np.finfo(np.float64).eps

        if abs(drect.width()) < eps:
            sx = 1.0
        else:
            sx = crect.width() / drect.width()

        if abs(drect.height()) < eps:
            sy = 1.0
        else:
            sy = crect.height() / drect.height()

        transform = QTransform().scale(sx, sy)
        self._transform = transform
        self._itemgroup.setPos(crect.topLeft())
        self._itemgroup.setGeometry(crect)
        for node_geom in postorder(self._layout):
            node, _ = node_geom.value
            item = self._items[node]
            item.setGeometryData(transform.map(item.sourcePath),
                                 transform.map(item.sourceAreaShape))
        self._selection_items = None
        self._update_selection_items()
Exemplo n.º 24
0
    def set_root(self, root):
        """ Set the root cluster.
        
        :param root: Root cluster.
        :type root: :class:`Orange.clustering.hierarchical.HierarchicalCluster`
         
        """
        self.clear()
        self.root_cluster = root
        self.dendrogram_items = {}
        self.cluster_parent = {}
        if root:
            items = []
            for cluster in hierarchical.postorder(self.root_cluster):
                item = RadialDendrogramItem(cluster)
                for branch in cluster.branches or []:
                    branch_item = self.dendrogram_items[branch]
                    self.cluster_parent[branch] = cluster
                items.append(GraphicsRectLayoutItem(item))
                self.dendrogram_items[cluster] = item

            self.layout().setDendrogram(root, items)

            self.layout().activate()
Exemplo n.º 25
0
 def test_order(self):
     post = hier.postorder(self.cluster)
     pre = hier.preorder(self.cluster)
Exemplo n.º 26
0
        def set_pen(item, pen):
            def branches(item):
                return [self._items[ch] for ch in item.node.branches]

            for it in postorder(item, branches):
                it.setPen(pen)
Exemplo n.º 27
0
 def test_order(self):
     post = hier.postorder(self.cluster)
     pre = hier.preorder(self.cluster)