mwouts / itables

Pandas DataFrames as Interactive DataTables
https://mwouts.github.io/itables/
MIT License
710 stars 53 forks source link

Some text is not visible in Jupyterlab dark theme #255

Closed YongcaiHuang closed 2 months ago

YongcaiHuang commented 2 months ago

Some text is not visible in Jupyterlab dark theme when extending the DataTables withSearchPanes and 'SearchBuilder'.

https://github.com/mwouts/itables/assets/97007177/1de46669-4453-48cc-9750-9f626368fc50

example codes:

import pandas as pd
from itables import show

df = {
    "Col A": ["A", "B", "C"],
    "Col B": [1, 2, 3]
}
df = pd.DataFrame(df)
show(df,layout={"top1": "searchBuilder"})
mwouts commented 2 months ago

Thanks @EricHUANG970823 for reporting this. @AllanJard, I confirm that I can reproduce this with the following steps

  1. Open the doc page on Binder: https://mybinder.org/v2/gh/mwouts/itables/main?urlpath=lab/tree/docs/extensions.md
  2. In the Menu, select Settings / Theme / JupyterLab Dark
  3. Then in the Menu again: Run / Run all cells

There is probably an incompatibility between the dark theme of Jupyter, and the default datatables CSS. I see the following issues:

Note that the dark mode of datatables.net doesn't have this issue. The dark mode of https://mwouts.github.io/itables/extensions.html seems to be ok too (although that the tables have a grey background there), except for SearchPanes where the panes have a white background as in Jupyter Lab with the black theme.

AllanJard commented 2 months ago

I'm not sure how to tell what version of SearchBuilder is being included on the page, but it looks like it might be an old version? 1.7.1 is the current release. I haven't checked yet, but the other software such as FixedColumns might also need to be updated?

mwouts commented 2 months ago

I expect that the dt_for_itables package contains SearchBuilder in version 1.7.0, e.g. it was the most recent version as of when I released itables==2.0.0 a few weeks back. Let me try updating all the dependencies and see how it goes!

mwouts commented 2 months ago

I have prepared an update, which can be tested with this link: https://mybinder.org/v2/gh/mwouts/itables/update_datatables_2.0.5?urlpath=lab/tree/docs/extensions.md, but I think it still has the same issue. I am not sure what is the best way to investigate this kind of CSS issues - is there any good tutorial out there to help me understand where that text gets its color from?

AllanJard commented 2 months ago

Normally, you would right click on the element and select "Inspect" - the browser will show where the styles are coming from. If there is a difference between that and the DataTables examples, then you can compare and constract the styles applied in the two. However, Notebooks appears to hijack the right click, so you need to open the developer tools using your browser's menu (e.g. in Firefox it is the hamburger menu -> More Tools -> Web developer tools).

In this case I can see the colour is coming from:

image

In going that, I realised what was happening - DataTables' styles require that class="dark" is placed on the <html> element in order to work for dark mode (doing that allows the option of overriding rather than just accepting the default).

Adding that into the notebook, let's it work:

image

mwouts commented 2 months ago

Awesome, thanks @AllanJard for digging into this! I don't control the html component, but I see that you have documented how to do this programmatically at https://datatables.net/manual/styling/dark-mode#Auto-detection, I will give it a try asap!

mwouts commented 2 months ago

I am seeing some success with

from IPython.display import HTML
HTML("""
<script>
    if (document.body.dataset.jpThemeLight === undefined ?
        window.matchMedia('(prefers-color-scheme: dark)').matches :
        document.body.dataset.jpThemeLight == "false") {
        document.querySelector('html').classList.add('dark');
    }
    else {
        document.querySelector('html').classList.remove('dark');
    }
</script>
""")

That's a good start, however I would prefer the style to be updated too when I change the theme in Jupyter (but I am not sure how to achieve that).

mwouts commented 2 months ago

BTW it seems that the above does not address the dark mode for the documentation ( https://mwouts.github.io/itables/ ) for which the dark mode sets two data attributes mode and theme to "dark" on the html element :sweat_smile:

mwouts commented 2 months ago

@AllanJard , if I take a step back, I see that we had a similar issue with the search box in the past, that was initially fixed with this css from #234:

.itables select, .itables input {
    color: inherit;
}

Then we transitioned to datatables==2.0 and that css became unnecessary, so I infer that you were able to set the style for this components in a way that works for both light and dark themes.

You probably see my question coming... would it be possible to adjust the extensions so that the style works well in both light and dark themes without setting the "dark" class?

AllanJard commented 2 months ago

Yes, I think I basically have the same thing in the DataTables default CSS.

So when I originally wrote the dark mode for DataTables I did have it just 100% determined on the end user's system preference. But that conflicted with a lot of websites which didn't have dark mode support themselves, but the user had dark mode enabled in their OS preferences. The table was virtually invisible!

The solution was to use the dark class on the :root element. It meant that the dev needed to excitability acknowledge that dark mode was enabled and supported. But equally it meant you could override it and use "light" mode as well if preferred (you can see this on datatables.net where you can select between the two, but by default it will pick up your OS selection).

The downside is that it does require an intervention by the dev (yourself :)) to allow dark mode to work (which I think is correct, since other parts of the site will need that support as well, as discussed above). So at the moment, no, I'm afraid if you want dark mode in DataTables there is no option but to set the dark class on the :root element (or modify the default DataTables CSS).

mwouts commented 2 months ago

Thanks Allan, yes no problem, I think that I can make this works in JupyterLab with e.g. this script (not sure if there is a better thing than setInterval to check for theme changes?)

Technically this also works for my documentation website, e.g. the background of the controls becomes dark when I switch the dark theme, but the table looks weird. That is a different issue, more related to Jupyter Book, and I will investigate it at https://github.com/mwouts/itables/issues/262.

AllanJard commented 2 months ago

There must be some kind of hook or something from JupyterLab to say when the mode is changed. Or perhaps you can add an event listener on top of their own to the button used to toggle the change. Running a function every 300mS on the page isn't an optimal solution - although if there is no other choice, it might need to be that way. You might need to reach out to the JupyterLab folks to see if they fire an event or provide some other API for the mode toggle.

mwouts commented 2 months ago

Thanks Allan for your help on this! In the end I have gone for a script without setInterval, so the style will be correct when the page is first displayed. The user will have to rerun the init_notebook_mode cell when then want to change the theme, which I guess won't happen much.