Conditional formatting of column based on the max/min values within the column

Hello, I have just started using Streamlit and AgGrid and think it is great. One aspect I would like to implement is to use a heat map for each column to highlight extreme values. I have seen many example of using fix values to conditional format a column such as

function(params){
    if (params.value == '0') {
        return {
            'color': 'black', 
            'backgroundColor': 'orange',
        }
    }
    if (params.value < '0') {
        return{
            'color': 'white',
            'backgroundColor': 'red',
        }
    }
    if (params.value > '0') {
        return{
            'color': 'white',
            'backgroundColor': 'green',
        }
    }
}

but what I would like is to dynamically scale the values based on the max / min in the column to conditionally format each cell rather than the fixed values in the jscode.

Does anyone have any suggestions of how to approach this.

Many thanks

David

2 Likes

Did you find an answer to this as it is something I’m struggling with also

solved it…

import streamlit as st
import pandas as pd
import numpy as np
import matplotlib as mpl
from st_aggrid import AgGrid, GridOptionsBuilder, JsCode, GridUpdateMode


def jscode_format(theshold_low, theshold_high, cmap):


    js_string = f"""
    if ( params.value >= '{theshold_low}' && params.value < '{theshold_high}' ) {{
        return {{
            'color': 'black', 
            'backgroundColor': 'RGB({cmap[0]*255},{cmap[1]*255},{cmap[2]*255},{cmap[3]})',
        }}
    }}
    """

    return js_string


def generate_colormap_js(data:pd.Series, q_count = 3, colormap_name='viridis'):

    cmap = mpl.colormaps[colormap_name]

    q_range = data.quantile(np.arange(0, 1.0, 1.0/q_count)).values
    js_string_all = str()
    for i in range(1, q_count):
        #  print(i, q_range[i], cmap(i/q_count))
        js_string = jscode_format(q_range[i-1], q_range[i], cmap(i/q_count))
        js_string_all += js_string

    return js_string_all


def main():
    st.title('Ag-Grid with Continuous Colormap in Streamlit')

    # Sample data
    data = {
        'A': np.random.randn(100),
        'B': np.random.randn(100),
        'C': np.random.randn(100)
    }
    df = pd.DataFrame(data)

    gb = GridOptionsBuilder.from_dataframe(df)


    for col in df.columns:
        cellstyle_jscode = f"""
            function(params){{
                {generate_colormap_js(df[col], q_count=len(df[col].unique()))}
            }}
        """
        # cellstyle_jscode = cellstyle_jscode.replace('\n', '')   
        gb.configure_column(col, cellStyle=JsCode(cellstyle_jscode))



    gb.configure_pagination(enabled=True)
    # gb.configure_columns(data, cellStyle= cellstyle_jscode)
    grid_options = gb.build()

    # Ag-Grid
    AgGrid(
        df,
        gridOptions=grid_options,
        enable_enterprise_modules=False,
        allow_unsafe_jscode=True,  # Set it to True to allow jsfunction to be injected,
        update_mode = GridUpdateMode.SELECTION_CHANGED,
        reload_data=True
    )
    

This topic was automatically closed 2 days after the last reply. New replies are no longer allowed.