Reputation: 174
I am using matplotlib table to create a heatmap that contains different values. While creating the table, ticks are not aligned at the center of each cell in both x-axis and y-axis.
I want to create something like this.
But rather I am getting ticks that are not uniform in both axes. Ticks starts at the middle of the cell from bottom-left column and gets distorted while moving to top and right cell.
I am using this code to generate this matplotlip table.
import numpy as np
import matplotlib as mpl
import matplotlib.pyplot as plt
from matplotlib.colors import ListedColormap, LinearSegmentedColormap
import os
import sys
from matplotlib.table import Table
fig,ax=plt.subplots(figsize=(15,15))
tb = Table(ax,bbox=[0,0,1,1])
nrows, ncols = 20,20
width, height = 1.0 / ncols, 1.0 / nrows
headers = 20
data = np.zeros((nrows, ncols))
ax.set_xticks(np.arange(0.5,headers+0.5))
ax.set_yticks(np.arange(0.5,headers+0.5))
ax.xaxis.set_tick_params(labelsize=12)
ax.yaxis.set_tick_params(labelsize=12)
for (i,j),val in np.ndenumerate(data):
tb.add_cell(i, j, width, height)
tb.add_cell(i, j, width, height, loc='center')
tb.auto_set_font_size(False)
tb.set_fontsize(15)
ax.add_table(tb)
ax.set_aspect('equal')
plt.show()
Is there anything I am missing?
Upvotes: 2
Views: 1692
Reputation: 35185
The answers have been accepted through a lot of trial and error, but we're changing the idea and color mapping. How about customizing it and using a heat map to solve the problem? It would be convenient to process various things. I will share it with you for your reference.
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.colors
mat = np.random.rand(10,10)
# RGB -> Hex
# ['rgb(0,0,205)', 'rgb(50,205,50)', 'rgb(255,69,0)'] -> ['#0000cd', '#32cd32', '#ff4500']
# ['mediumblue', 'limegreen', 'orangered'])
rgb_c = [(0,0,205), (50,205,50), (255,69,0)]
# RGB convert to Hex
cols = ['#%02x%02x%02x' % (c[0],c[1],c[2]) for c in rgb_c]
cm = matplotlib.colors.ListedColormap(cols)
fig, ax = plt.subplots()
heatmap = ax.pcolor(mat, cmap=cm)
ax.set_aspect('equal')
plt.show()
Upvotes: 0
Reputation: 723
this will do the work
plt.ylim(0,headers)
plt.xlim(0,headers)
also adding this line plt.xticks(rotation=90)
will help you rotate values in the xaxis and avoid overlapping
full program will be like
import numpy as np
import matplotlib as mpl
import matplotlib.pyplot as plt
from matplotlib.colors import ListedColormap, LinearSegmentedColormap
import os
import sys
from matplotlib.table import Table
fig, ax = plt.subplots(figsize=(15, 15))#
tb = Table(ax, bbox=[0, 0, 1, 1])
nrows, ncols = 20,20
width, height = 1.0 / ncols, 1.0 / nrows
headers = 20
data = np.zeros((nrows, ncols))
ax.set_xticks(np.arange(0.5,headers+0.5))
ax.set_yticks(np.arange(0.5,headers+0.5))
plt.ylim(0,headers)
plt.xlim(0,headers)
plt.xticks(rotation=90)
ax.xaxis.set_tick_params(labelsize=12)
ax.yaxis.set_tick_params(labelsize=12)
for (i, j), val in np.ndenumerate(data):
tb.add_cell(i, j, width, height)
tb.add_cell(i, j, width, height, loc='center')
tb.auto_set_font_size(False)
tb.set_fontsize(15)
ax.add_table(tb)
ax.set_aspect('equal')
plt.show()
output
Upvotes: 3
Reputation: 2402
Have you heard of seaborn? This is a plotting library built on top of matplotlib that takes care of those things for you. They have a function heatmap
which does exactly this, and handles the placing of the ticks automatically: https://seaborn.pydata.org/generated/seaborn.heatmap.html#seaborn.heatmap
Example:
import seaborn as sns
ax = sns.heatmap(np.zeros(20,20))
plt.show()
You can then play with the ticklabels and modify them at will like you would do on any matplotlib plot. For example, ax.set_xticklabels(np.arange(0.5, 20, 0.5))
will rename your x-ticks like on your picture.
Upvotes: 1