Just to complete Joseph's answer, this would be a basic example on how to do it with ETE.
from ete2 import (Tree, TreeStyle, add_face_to_node, ImgFace,
AttrFace, TextFace)
def tree_profile_layout(node):
if node.is_leaf():
add_face_to_node(AttrFace("name", fsize=20), node, 0, position="branch-right")
for col, value in enumerate(name2profile[node.name]):
if value == 1:
add_face_to_node(positiveFace, node, col, position="aligned")
else:
add_face_to_node(negativeFace, node, col, position="aligned")
# lets use some random tree and data
name2profile = {
"a": [1, 0, 1, 0, 1, 1, 1],
"b": [1, 0, 1, 0, 1, 0, 0],
"c": [1, 1, 1, 0, 0, 0, 0],
"d": [1, 0, 0, 0, 1, 0, 0],
}
table_header = ['col1', 'col2', 'col3', 'col4', 'col5', 'col6', 'col7']
t = Tree("((a,b), (c, d)):0;")
# load images used for table visualization
positiveFace = ImgFace("positive.png")
negativeFace = ImgFace("negative.png")
# configure basic tree drawing style
ts = TreeStyle()
ts.show_leaf_name = False # we handle this in the layout function
ts.layout_fn = tree_profile_layout
# set up table header. Text rotation is not available yet
for col, label in enumerate(table_header):
labelFace = TextFace(label, fsize=20, fgcolor="steelblue")
ts.aligned_header.add_face(labelFace, col)
t.show(tree_style=ts)
I love E.T.E. This is beautiful!