import gradio as gr import pandas as pd import os # Load data from CSV files DATA_DIR = "data" def load_csv_data(filename): """Load data from CSV file""" filepath = os.path.join(DATA_DIR, filename) if os.path.exists(filepath): return pd.read_csv(filepath) else: return pd.DataFrame() # Load datasets CLASSIFICATION_DF = load_csv_data("classification.csv") DETECTION_DF = load_csv_data("detection.csv") SEGMENTATION_DF = load_csv_data("segmentation.csv") def filter_and_search(df, search, datasets, models, organizations, columns): filtered = df.copy() if search: mask = filtered.apply(lambda row: row.astype(str).str.contains(search, case=False).any(), axis=1) filtered = filtered[mask] if datasets: filtered = filtered[filtered["Dataset"].isin(datasets)] if models: filtered = filtered[filtered["Model"].isin(models)] if organizations: filtered = filtered[filtered["Organization"].isin(organizations)] if columns: display_cols = [col for col in columns if col in filtered.columns] filtered = filtered[display_cols] return filtered def build_tab(df, name): """Build a leaderboard tab from a DataFrame""" if df.empty: return gr.TabItem(name) # Pivot the dataframe to have columns like "Dataset1 (Metric1)", "Dataset1 (Metric2)", etc. datasets = sorted(df["Dataset"].unique().tolist()) models = sorted(df["Model"].unique().tolist()) organizations = sorted(df["Organization"].unique().tolist()) metric_cols = [col for col in df.columns if col not in ["Model", "Organization", "Dataset", "Author", "Author Link"]] # Create pivoted dataframe pivoted_data = [] for model in models: for org in organizations: model_org_data = df[(df["Model"] == model) & (df["Organization"] == org)] if not model_org_data.empty: # Get Author and Author Link from the first entry (they should be the same for model+org) author = model_org_data["Author"].values[0] author_link = model_org_data["Author Link"].values[0] # Format as markdown link if author_link exists if pd.notna(author_link) and author_link.strip(): author_display = f"[{author}]({author_link})" else: author_display = author row = {"Model": model, "Organization": org, "Author": author_display} for dataset in datasets: dataset_data = model_org_data[model_org_data["Dataset"] == dataset] if not dataset_data.empty: for metric in metric_cols: col_name = f"{dataset} ({metric})" row[col_name] = dataset_data[metric].values[0] else: for metric in metric_cols: col_name = f"{dataset} ({metric})" row[col_name] = "-" pivoted_data.append(row) pivoted_df = pd.DataFrame(pivoted_data) # Build column list for selector metric_combo_cols = [] for dataset in datasets: for metric in metric_cols: metric_combo_cols.append(f"{dataset} ({metric})") all_cols = ["Model", "Organization", "Author"] + metric_combo_cols with gr.TabItem(name, elem_id="llm-benchmark-tab-table"): with gr.Row(): with gr.Column(scale=4): search_bar = gr.Textbox( label="Search", placeholder="Separate multiple queries with ';'", elem_id="search-bar" ) # Column selector for base columns only (not dataset+metric combos) base_cols = ["Model", "Organization", "Author"] col_selector = gr.CheckboxGroup( choices=base_cols, value=base_cols, label="Select Columns to Display:", elem_classes="column-select" ) # Set datatype to 'markdown' for Author column to enable clickable links datatypes = [] for col in pivoted_df.columns: if col == "Author": datatypes.append("markdown") else: datatypes.append("str") table = gr.Dataframe( value=pivoted_df, elem_id="leaderboard-table", interactive=False, wrap=True, datatype=datatypes ) with gr.Column(scale=1): gr.Markdown("**Model types**") model_filter = gr.CheckboxGroup( choices=models, value=models, label="", elem_classes="filter-group" ) gr.Markdown("**Organizations**") org_filter = gr.CheckboxGroup( choices=organizations, value=organizations, label="", elem_classes="filter-group" ) gr.Markdown("**Datasets**") dataset_filter = gr.CheckboxGroup( choices=datasets, value=datasets, label="", elem_classes="filter-group" ) gr.Markdown("**Metrics**") metric_filter = gr.CheckboxGroup( choices=metric_cols, value=metric_cols, label="", elem_classes="filter-group" ) def update(search, md, org, dset, metrics, cols): filtered = pivoted_df.copy() if search: mask = filtered.apply(lambda row: row.astype(str).str.contains(search, case=False).any(), axis=1) filtered = filtered[mask] if md: filtered = filtered[filtered["Model"].isin(md)] if org: filtered = filtered[filtered["Organization"].isin(org)] # Build display columns based on selected base columns and dataset/metric filters display_cols = [] # Add selected base columns for col in cols: if col in base_cols: display_cols.append(col) # Add metric columns that match selected datasets and metrics for col in metric_combo_cols: # Check if this column matches selected datasets and metrics col_dataset = col.split(" (")[0] col_metric = col.split(" (")[1].rstrip(")") if col_dataset in dset and col_metric in metrics: display_cols.append(col) filtered = filtered[display_cols] return filtered search_bar.change(update, [search_bar, model_filter, org_filter, dataset_filter, metric_filter, col_selector], table) model_filter.change(update, [search_bar, model_filter, org_filter, dataset_filter, metric_filter, col_selector], table) org_filter.change(update, [search_bar, model_filter, org_filter, dataset_filter, metric_filter, col_selector], table) dataset_filter.change(update, [search_bar, model_filter, org_filter, dataset_filter, metric_filter, col_selector], table) metric_filter.change(update, [search_bar, model_filter, org_filter, dataset_filter, metric_filter, col_selector], table) col_selector.change(update, [search_bar, model_filter, org_filter, dataset_filter, metric_filter, col_selector], table) custom_css = """ .markdown-text { font-size: 16px !important; } #leaderboard-table { margin-top: 15px; } #leaderboard-table table { width: 100%; table-layout: auto; } #leaderboard-table thead th { font-weight: bold; text-align: center; padding: 12px 8px; white-space: normal; word-wrap: break-word; } #leaderboard-table tbody td { text-align: center; padding: 10px 8px; white-space: nowrap; } #leaderboard-table tbody td:first-child { text-align: left; font-weight: 500; min-width: 120px; max-width: 200px; white-space: nowrap; } #leaderboard-table thead th:first-child { text-align: left; font-weight: bold; min-width: 120px; max-width: 200px; white-space: nowrap; } #leaderboard-table tbody td:nth-child(2), #leaderboard-table thead th:nth-child(2) { text-align: left; min-width: 100px; } #leaderboard-table tbody td:nth-child(3), #leaderboard-table thead th:nth-child(3) { text-align: left; min-width: 120px; } /* Style links in Author column */ #leaderboard-table a { color: #0066cc; text-decoration: none; } #leaderboard-table a:hover { text-decoration: underline; } #search-bar { margin-bottom: 0px; } #search-bar textarea { border: 1px solid #e0e0e0 !important; border-radius: 8px !important; } .tab-buttons button { font-size: 20px; } .filter-group { margin-bottom: 1em; } .filter-group label { font-size: 14px; } .column-select { margin-bottom: 1.5em; } .column-select label { display: flex; flex-wrap: wrap; gap: 0.5em; } .column-select label > span { display: inline-flex; align-items: center; } """ TITLE = """