12

The official document provided options to set cell alignment using to_html(justify='left/right') and it works. However, it is not clear how to justify non-header rows.

I've to use a hack to replace the HTML part

import pandas as pd
df = pd.DataFrame({'looooong_col':['1,234','234,567','3,456,789'],'short_col':[123,4,56]})
raw_html = df.to_html()
raw_html.replace('<tr>','<tr style="text-align: right;">')

So the modified html now is

<table border="1" class="dataframe">
  <thead>
    <tr style="text-align: right;">
      <th></th>
      <th>looooong_col</th>
      <th>short_col</th>
    </tr>
  </thead>
  <tbody>
    <tr style="text-align: right;">
      <th>0</th>
      <td>1,234</td>
      <td>123</td>
    </tr>
    <tr style="text-align: right;">
      <th>1</th>
      <td>234,567</td>
      <td>4</td>
    </tr>
    <tr style="text-align: right;">
      <th>2</th>
      <td>3,456,789</td>
      <td>56</td>
    </tr>
  </tbody>
</table>

and it rendered ok in http://htmledit.squarefree.com/ but not when I write it out to a html file, the cells are still left-justified.

How to fix this?

Brian Tompsett - 汤莱恩
  • 5,753
  • 72
  • 57
  • 129
X.X
  • 961
  • 2
  • 12
  • 16
  • Try CSS. See my solution here. [Align text in Pandas column](https://stackoverflow.com/questions/56046215/how-to-align-pandas-dataframe-column-number-text-in-jinja) – Zion Oyemade May 10 '19 at 13:49

6 Answers6

11

You can use the Styler functionality.

http://pandas.pydata.org/pandas-docs/stable/style.html

import pandas as pd
import numpy as np
df = pd.DataFrame(np.random.randn(6,4),columns=list('ABCD'))
s = df.style.set_properties(**{'text-align': 'right'})
s.render()

s.render() returns a string of the generated CSS / HTML. Note the generated HTML will not be clean, as the internals declare a separate style for each cell.

ashishsingal
  • 2,810
  • 3
  • 18
  • 26
  • more comprehensive setting see answer in http://stackoverflow.com/a/40993135/2944092 – X.X Jan 19 '17 at 23:50
  • 4
    I get AttributeError: 'Styler' object has no attribute 'style' – pceccon Oct 02 '20 at 18:37
  • Note that `Styler.render()` was deprecated in favour of `Styler.to_html()` as of pandas version 1.4.0. See https://pandas.pydata.org/docs/reference/api/pandas.io.formats.style.Styler.to_html.html – wlo Mar 13 '23 at 16:44
4

I know this is an old question, and I notice you're asking about how to do this when your numbers are in string format, i.e. ['1,234','234,567','3,456,789']

If however, you just had floats or a mix of floats and strings in the pandas dataframe, one way to do this would simply be

df.to_html().replace('<td>', '<td align="right">')

Personally I needed to do this, since I had the following formatting I wanted to get out of the process above it:

pd.options.display.float_format = '{:,.0f}'.format
df.to_html().replace('<td>', '<td align="right">')

Does the job perfectly and doesn't mess with my formatting the way that using the Sty

Yevgeniy Loboda
  • 161
  • 1
  • 1
  • 8
2

You may want to try to do the styling outside in the CSS instead.

If you're using MultiIndex you will be unable to use Styler.

For example, you could add the following before your table HTML:

<style>
table {text-align: center;}
table thead th {text-align: center;}
</style>
ProsperousHeart
  • 188
  • 1
  • 14
1

To center align all values in the column, this worked for me

dict(selector="td", props=[("text-align", "center")])
1

I like using the classes argument of DataFrame.to_html() in combination with some CSS for this type of task. In your case this could look something like this:

CSS

.my-table td {
    text-align: center;
}

pandas

raw_html = df.to_html(classes=["my-table"])

Output HTML

<table class="dataframe my-table">
    ...
<table>

This lets you add HTML classes to the table element rendered by DataFrame.to_html(), leaving the styling to the frontend (that's what CSS is for after all).

wlo
  • 673
  • 5
  • 16
  • CSS is the best solution. Note that each table gets a class="dataframe" by default. So one can set ` .dataframe { text-align: right; } th { min-width: 100px; }` in CSS. – MathKid Mar 15 '23 at 13:06
-7

This did the trick for me

df.to_html(justify='left')
anish
  • 88
  • 6
  • 5
    `df.to_html(justify='left')`, as stated in the original question, only works on the column headers, but not the rest of the dataframe. – KT12 Apr 10 '20 at 20:54