magu_
magu_

Reputation: 4856

How can I customize the offset in matplotlib

I would like to customize the offset use in matplotlib. Specifically:

Thank you for the answer, in case somebody encounters the same problem, here's the code I used to solve it:

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

class ScalarFormatter(ticker.ScalarFormatter):
    def __init__(self, useOffset=None, useMathText=None, useLocale=None):
        ticker.ScalarFormatter.__init__(self, useOffset, useMathText, useLocale)
        self._powerlimits = (0, 0)


    def _set_offset(self, range):
        mean_locs = np.mean(self.locs)

        if range / 2 < np.absolute(mean_locs):
            ave_oom = np.floor(np.log10(mean_locs))
            p10 = 10 ** np.floor(np.log10(range))
            self.offset = (np.ceil(np.mean(self.locs) / p10) * p10)
        else:
            self.offset = 0


    def get_offset(self, txt=''):
        if self.orderOfMagnitude:
            txt += u'\u00D7' + '1e%d' % self.orderOfMagnitude + ' '

        if self.offset:
            if self.offset > 0:
                txt += '+'
            txt += self.format_data(self.offset)

        return self.fix_minus(txt)

Upvotes: 1

Views: 1323

Answers (2)

burnpanck
burnpanck

Reputation: 2196

Indeed, as Andreus correctly answered, %.1e would give you what I would understand as scientific formatting of the tick values as printed on the axes. However, setting a FormatStrFormatter switches off what is called the scientific formatting feature of the default formatter, where the exponent is not formatted with each individual tick value, but rather as part of the so-called offset string. This is because that feature is only available with the default formatter class ticker.ScalarFormatter. That one unfortunately does not provide an interface to it's format string as far as I know. It would however provide a method set_powerlimits. I'd say your best bet would be to subclass ticker.ScalarFormatter and override the corresponding methods. Don't be affraid, that will not be too difficult, just have a look at the source code of matplotlib.ticker.ScalarFormatter and override whatever you need. I had a quick peek, here are my thoughts:

  • The tick format string is stored in an attribute .format, which is set in the method def _set_format(self, vmin, vmax):. You could just override the attribute .format manually, but that would get reset whenever the axis limits change. To be more robust, you would replace _set_format that does not do anything.

  • Similarly, the offset value is stored in an attribute .offset, and it is not displayed when offset is 0. That attribute is set by the function def _set_offset(self, range):. If you want to customise the limits when offset is applied, you have no option than to copy that function and adjust the limit value (possibly depending on some new offsetLimit attribute).

Upvotes: 2

Andreus
Andreus

Reputation: 2487

For scientific notation, %e and its variants ( python string formatting ).

For customizing limits, check axes.set_xlim() and axes.set_ylim().

Upvotes: 0

Related Questions