← GDG /

#276 gdtest_scale_to_fit

#276 gdtest_scale_to_fit OK CONFIG
Scale-to-fit config system for wide HTML output
Tests the 3-level scale-to-fit configuration system: global config targeting by CSS selector, page-level frontmatter overrides, and manual div wrapping. Uses GT tables of varying widths (4-16 cols) and a custom _repr_html_ widget to verify correct scaling behavior, ID-based targeting, and override precedence.
View Site → Build Log ๐Ÿงช Test Coverage

Build Mode

● Has great-docs.yml

This package ships a pre-supplied config. The great-docs init step is skipped and great-docs build uses the spec-defined configuration directly. Tests specific config options and their rendered output.

Dimensions

G7 M4 N1
G7Blended UG homepagelanding
M4Subdirectory UGuser_guide
N1Examples sectionsections

Source Files

๐Ÿ“ gdtest_scale_to_fit/
๐Ÿ“„ __init__.py
"""A test package for scale-to-fit auto-scaling."""

__version__ = "0.1.0"
__all__ = [
    "make_wide_table",
    "make_narrow_table",
    "make_medium_table",
    "CustomWidget",
]


def make_wide_table():
    """
    Create a wide GT table with 12 columns.

    Returns
    -------
    GT
        A GT table with many columns that overflows its container.

    Examples
    --------
    ```{python}
    from gdtest_scale_to_fit import make_wide_table
    make_wide_table()
    ```
    """
    from great_tables import GT
    import pandas as pd

    df = pd.DataFrame({
        f"Col_{i:02d}": [f"val_{r}_{i}" for r in range(4)]
        for i in range(1, 13)
    })
    return (
        GT(df, id="wide_gt")
        .tab_header(title="Wide Table (12 cols)")
        .cols_width(**{f"Col_{i:02d}": "110px" for i in range(1, 13)})
        .tab_options(quarto_disable_processing=True)
    )


def make_narrow_table():
    """
    Create a narrow GT table with 3 columns.

    Returns
    -------
    GT
        A GT table that fits comfortably in its container.
    """
    from great_tables import GT
    import pandas as pd

    df = pd.DataFrame({
        "Name": ["Alice", "Bob"],
        "Score": [95, 87],
        "Grade": ["A", "B+"],
    })
    return (
        GT(df, id="narrow_gt")
        .tab_header(title="Narrow Table (3 cols)")
        .tab_options(quarto_disable_processing=True)
    )


def make_medium_table():
    """
    Create a medium GT table with 8 columns.

    Returns
    -------
    GT
        A GT table that is moderately wide.
    """
    from great_tables import GT
    import pandas as pd

    df = pd.DataFrame({
        f"Metric_{i}": [round(i * 1.5 + r * 0.3, 1) for r in range(5)]
        for i in range(1, 9)
    })
    return (
        GT(df, id="medium_gt")
        .tab_header(title="Medium Table (8 cols)")
        .cols_width(**{f"Metric_{i}": "120px" for i in range(1, 9)})
        .tab_options(quarto_disable_processing=True)
    )


class CustomWidget:
    """
    A custom widget with ``_repr_html_`` for scale-to-fit testing.

    This produces a wide HTML block that is NOT a GT table, verifying
    that scale-to-fit works for arbitrary ``_repr_html_`` objects.

    Parameters
    ----------
    width
        CSS width of the widget (e.g., ``"1500px"``).
    widget_id
        HTML ``id`` attribute for targeting.
    """

    def __init__(self, width: str = "1500px", widget_id: str = "custom_html"):
        self.width = width
        self.widget_id = widget_id

    def _repr_html_(self) -> str:
        """Render as wide HTML block."""
        return (
            f'<div id="{self.widget_id}" '
            f'style="width:{self.width};background:#e8f4fd;'
            f'border:2px solid #2196F3;padding:16px;'
            f'font-family:monospace;">'
            f'<strong>CustomWidget</strong> &mdash; '
            f'width: {self.width}, id: {self.widget_id}'
            f'</div>'
        )
๐Ÿ“ user_guide/
๐Ÿ“„ 01-global-targeting.qmd
---
title: Global Config Targeting
---

## Wide GT Table (12 columns)

This GT table has `id="wide_gt"` and should be auto-scaled
because the global config has `scale_to_fit: ["#wide_gt", ...]`.

```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"Col_{i:02d}": [f"val_{r}_{i}" for r in range(4)]
    for i in range(1, 13)
})

(
    GT(df, id="wide_gt")
    .tab_header(title="Wide Table (12 cols)")
    .cols_width(**{f"Col_{i:02d}": "110px" for i in range(1, 13)})
    .tab_options(quarto_disable_processing=True)
)
```

## Custom HTML Widget

This `_repr_html_` object has `id="custom_html"` and should also
be auto-scaled by the global config.

```{python}
#| echo: false
from gdtest_scale_to_fit import CustomWidget
CustomWidget(width='1500px', widget_id='custom_html')
```

## Narrow GT Table (not targeted)

This table has `id="narrow_gt"` which is NOT in the global
`scale_to_fit` list, so it should NOT be auto-scaled.

```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    "Name": ["Alice", "Bob"],
    "Score": [95, 87],
    "Grade": ["A", "B+"],
})

(
    GT(df, id="narrow_gt")
    .tab_header(title="Narrow Table (3 cols)")
    .tab_options(quarto_disable_processing=True)
)
```
๐Ÿ“„ 02-page-override.qmd
---
title: Page-Level Override
scale-to-fit:
  - "#page_gt"
scale-to-fit-min-scale: mobile
---

## Medium GT Table (page-targeted)

This page has `scale-to-fit: ["#page_gt"]` in its frontmatter,
which overrides the global config. Only `#page_gt` should scale.

```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"Metric_{i}": [round(i * 1.5 + r * 0.3, 1) for r in range(5)]
    for i in range(1, 9)
})

(
    GT(df, id="page_gt")
    .tab_header(title="Page-Targeted Table (8 cols)")
    .cols_width(**{f"Metric_{i}": "120px" for i in range(1, 9)})
    .tab_options(quarto_disable_processing=True)
)
```

## Wide GT Table (NOT targeted on this page)

This table has `id="wide_gt_2"` which matches nothing on this page
(the page override replaces the global selectors).

```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"Col_{i:02d}": [f"val_{r}_{i}" for r in range(4)]
    for i in range(1, 13)
})

(
    GT(df, id="wide_gt_2")
    .tab_header(title="Wide Table 2 (not targeted here)")
    .cols_width(**{f"Col_{i:02d}": "110px" for i in range(1, 13)})
    .tab_options(quarto_disable_processing=True)
)
```
๐Ÿ“„ 03-manual-div.qmd
---
title: Manual Div Wrapping
---

## Manually Scaled Table

This table is wrapped in a `:::{.scale-to-fit}` div.
No config or frontmatter needed.

:::{.scale-to-fit}
```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"Field_{i}": [f"data_{r}_{i}" for r in range(3)]
    for i in range(1, 11)
})

(
    GT(df, id="manual_gt")
    .tab_header(title="Manual Scale (10 cols)")
    .cols_width(**{f"Field_{i}": "110px" for i in range(1, 11)})
    .tab_options(quarto_disable_processing=True)
)
```
:::

## Unwrapped Table (for comparison)

This table is NOT wrapped and NOT targeted by any selector.

```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"X_{i}": [i * 10 + r for r in range(3)]
    for i in range(1, 11)
})

(
    GT(df, id="unwrapped_gt")
    .tab_header(title="Unwrapped Table (10 cols, no scaling)")
    .cols_width(**{f"X_{i}": "110px" for i in range(1, 11)})
    .tab_options(quarto_disable_processing=True)
)
```
๐Ÿ“„ 04-per-div-min-scale.qmd
---
title: Per-Div Min Scale
---

## Wide Table with Numeric Threshold

This table is inside a `.scale-to-fit` div with
`data-min-scale="0.5"`, which overrides the global
`tablet` keyword threshold.

:::{.scale-to-fit data-min-scale="0.5"}
```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"Col_{i:02d}": [f"val_{r}_{i}" for r in range(4)]
    for i in range(1, 13)
})

(
    GT(df, id="perdiv_numeric")
    .tab_header(title="Per-Div Numeric Threshold (0.5)")
    .cols_width(**{f"Col_{i:02d}": "110px" for i in range(1, 13)})
    .tab_options(quarto_disable_processing=True)
)
```
:::

## Wide Table with Keyword Threshold

This table is inside a `.scale-to-fit` div with
`data-min-scale="mobile"`, so it only scrolls on
viewports at or below 576 px.

:::{.scale-to-fit data-min-scale="mobile"}
```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"Col_{i:02d}": [f"val_{r}_{i}" for r in range(4)]
    for i in range(1, 13)
})

(
    GT(df, id="perdiv_keyword")
    .tab_header(title="Per-Div Keyword Threshold (mobile)")
    .cols_width(**{f"Col_{i:02d}": "110px" for i in range(1, 13)})
    .tab_options(quarto_disable_processing=True)
)
```
:::

## Wide Table without Per-Div Override

This table uses a plain `.scale-to-fit` div with no
`data-min-scale`, so it inherits the global `tablet` threshold.

:::{.scale-to-fit}
```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"Col_{i:02d}": [f"val_{r}_{i}" for r in range(4)]
    for i in range(1, 13)
})

(
    GT(df, id="perdiv_inherit")
    .tab_header(title="Plain Div (inherits global threshold)")
    .cols_width(**{f"Col_{i:02d}": "110px" for i in range(1, 13)})
    .tab_options(quarto_disable_processing=True)
)
```
:::
๐Ÿ“„ 05-width-comparison.qmd
---
title: Width Comparison
---

This page shows GT tables of increasing widths for visual
comparison. None are auto-scaled (no matching selectors).

## 4-Column Table

```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"C{i}": [f"v{r}{i}" for r in range(3)]
    for i in range(1, 5)
})
GT(df, id='cmp_4').tab_header(title='4 Columns').tab_options(quarto_disable_processing=True)
```

## 8-Column Table

```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"C{i}": [f"v{r}{i}" for r in range(3)]
    for i in range(1, 9)
})
GT(df, id='cmp_8').tab_header(title='8 Columns').tab_options(quarto_disable_processing=True)
```

## 12-Column Table

```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"C{i}": [f"v{r}{i}" for r in range(3)]
    for i in range(1, 13)
})
GT(df, id='cmp_12').tab_header(title='12 Columns').tab_options(quarto_disable_processing=True)
```

## 16-Column Table

```{python}
#| echo: false
from great_tables import GT
import pandas as pd

df = pd.DataFrame({
    f"C{i}": [f"v{r}{i}" for r in range(3)]
    for i in range(1, 17)
})
GT(df, id='cmp_16').tab_header(title='16 Columns').tab_options(quarto_disable_processing=True)
```
๐Ÿ“„ README.md
# gdtest-scale-to-fit

Test the 3-level scale-to-fit system for wide HTML output.
๐Ÿ“„ great-docs.yml
scale_to_fit:
  - "#wide_gt"
  - "#custom_html"
scale_to_fit_min_scale: tablet