1

I am trying to plot a function with a multiplicative offset on the y axis, and fixed number of digits. For consistency between multiple plots, I would want the offset to show even if it is 1e0.

Inspired by the answer to this question, I tried the following:

import numpy as np
import matplotlib.pyplot as plt
import matplotlib.ticker

class OOMFormatter(matplotlib.ticker.ScalarFormatter):
    def __init__(self, order=0, fformat="%1.1f", offset=True, mathText=False):
        self.oom = order
        self.fformat = fformat
        matplotlib.ticker.ScalarFormatter.__init__(self,useOffset=offset,useMathText=mathText)
    def _set_order_of_magnitude(self):
        self.orderOfMagnitude = self.oom
    def _set_format(self, vmin=None, vmax=None):
        self.format = self.fformat
        if self._useMathText:
            self.format = r'$\mathdefault{%s}$' % self.format


x = np.linspace(0, 1,10)
fig, ax = plt.subplots(1, 2)

ax[0].plot(x,x)
ax[0].yaxis.set_major_formatter(OOMFormatter(0, "%1.1f"))
ax[0].ticklabel_format(axis='y', style='sci', scilimits=(0,0))

ax[1].plot(x,100*x)
ax[1].yaxis.set_major_formatter(OOMFormatter(2, "%1.1f"))
ax[1].ticklabel_format(axis='y', style='sci', scilimits=(0,0))

plt.tight_layout()
plt.show()

Which produces the following plot:

two plots side by side showing the identity function. First one do not have a multiplier whereas second one does.

As you see, the right-hand plot has a 1e2 factor, whereas in the left-hand plot, no offset is shown. How could I force matplotlib to show 1e0 on the left-hand plot's y-axis, so that my plots remain consistent?

pauloss
  • 47
  • 9
  • 1
    You could try setting `self.oom = order if order != 0.0 else 0.00001` in `__init__` – JohanC Aug 09 '21 at 19:48
  • I was convinced I had tried something along these lines but apparently not. It works perfectly, thanks a lot! (Maybe you can post your comment as an answer so that I can accept it?) – pauloss Aug 09 '21 at 20:21

0 Answers0