## Version 2.4.0 Release announcement for Dash Mantine Components v2.4.0 Category: Releases November 6, 2025 Based on Mantine 8.3.6 ### Version 2.4.1 December 20, 2025 Based on Mantine 8.3.10 See [Changelog](https://github.com/snehilvj/dash-mantine-components/releases/tag/2.4.1) ### New: Copy to Clipboard Components The new `CopyButton` and `CustomCopyButton` components are similar to `dcc.Clipboard`, but with full Mantine styling and customization. - Customizable icons, colors, and labels for the copied state - Support for copying from another component using `target_id` - Trigger copying in callbacks with `triggerCopy=True` - Build fully custom copy-to-clipboard buttons with `CustomCopyButton` Check out the new [Copy Button docs](/components/copybutton). #### Example: Styling the CopyButton ```python import dash_mantine_components as dmc from dash_iconify import DashIconify component = dmc.Group([ dmc.CopyButton( value="https://www.dash-mantine-components.com/", children="Copy URL", copiedChildren="Copied!", color="blue", copiedColor="teal" ), dmc.CopyButton( value="This text is copied", children=DashIconify(icon="tabler:clipboard"), copiedChildren=DashIconify(icon="tabler:check"), color="blue", copiedColor="teal", variant="outline" ), dmc.CopyButton( value="This text is copied", children=DashIconify(icon="fa-regular:copy"), copiedChildren=DashIconify(icon="fa-regular:check-circle"), color="gray", copiedColor="dark", variant="transparent" ) ]) ``` --- #### Example: Copy from another component: Need a quick way to say “No”? Fetch a random excuse from [No-as-a-Service](https://github.com/hotheadhacker/no-as-a-service) and copy it with a single click. ```python import requests from dash import Input, Output, callback import dash_mantine_components as dmc from dash_iconify import DashIconify component = dmc.Box([ dmc.Button("Get rejection reason", id="new-reason-btn", mb="lg"), dmc.Group([ dmc.Text(id="reason-text", mt=10), dmc.CopyButton( target_id="reason-text", children=DashIconify(icon="fa-regular:copy"), copiedChildren=DashIconify(icon="fa-regular:check-circle"), color="blue", copiedColor="teal", variant="outline", size="xs" ) ], align="flex-start", wrap="nowrap",) ]) @callback( Output("reason-text", "children"), Input("new-reason-btn", "n_clicks"), running=[(Output("new-reason-btn", "loading"), True, False)], ) def fetch_reason(_): try: res = requests.get("https://naas.isalman.dev/no") res.raise_for_status() return res.json().get("reason", "No reason found.") except Exception: return "No reason. Just No." ``` ### More chart props now support functions The `AreaChart`, `BarChart`, `BubbleChart`, `CompositeChart`, `LineChart`, and `ScatterChart` now accept functions for these props: * `xAxisProps`, `yAxisProps`, `gridProps`, `rightYAxisProps` (all charts) * `zAxisProps` (`BubbleChart` only) See the [Functions As Props guide](/functions-as-props) for details. #### Example: format x-axis tick labels This example uses a JavaScript function to format x-axis tick labels for datetime values. ```python import dash_mantine_components as dmc from dash import Dash from datetime import datetime data = [ {"date": datetime(2025, 3, 22), "Apples": 2890, "Oranges": 2338, "Tomatoes": 2452}, {"date": datetime(2025, 3, 23), "Apples": 2756, "Oranges": 2103, "Tomatoes": 2402}, {"date": datetime(2025, 3, 24), "Apples": 3322, "Oranges": 986, "Tomatoes": 1821}, {"date": datetime(2025, 3, 25), "Apples": 3470, "Oranges": 2108, "Tomatoes": 2809}, {"date": datetime(2025, 3, 26), "Apples": 3129, "Oranges": 1726, "Tomatoes": 2290} ] component = dmc.AreaChart( h=300, dataKey="date", data=data, series = [ {"name": "Apples", "color": "indigo.6"}, {"name": "Oranges", "color": "blue.6"}, {"name": "Tomatoes", "color": "teal.6"} ], curveType="Monotone", tickLine="xy", withGradient=False, withDots=False, xAxisProps={"tickFormatter": {"function": "formatDatetime"}}, valueFormatter={"function": "formatNumberIntl"}, ) ``` ```javascript var dmcfuncs = window.dashMantineFunctions = window.dashMantineFunctions || {}; dmcfuncs.formatDatetime = function (datetimeStr) { const date = new Date(datetimeStr); return date.toLocaleDateString('en-US', { month: 'short', day: 'numeric', year: 'numeric' }); }; ``` ### New RichTextEditor features - Code highlighting is now available - New Props: `editable`, `focus` Thanks for the PR [@chgiesse](https://github.com/chgiesse) - Access Editor API in a clientside callback See examples of all the new features in the [RichTextEditor docs](/components/richtexteditor) #### Example: Editable prop Note the toolbar is hidden when the editor is read-only ```python import dash_mantine_components as dmc from dash import Input, Output, callback component = dmc.Box([ dmc.Switch( id="rte-toggle-editable", label="Editable", checked=True, ), dmc.RichTextEditor( id="rte-editable", html="

This editor can be toggled between editable and read-only mode.

", editable=True, toolbar={ "controlsGroups": [ [ "Bold", "Italic", "Underline", "Strikethrough", "CodeBlock" ], ], }, ), ]) @callback( Output("rte-editable", "editable"), Input("rte-toggle-editable", "checked"), ) def toggle_editable(checked): return checked ``` #### Example: Accessing Editor clientside Get full access to the editor API in clientside callbacks, including executing commands, inspecting content, and updating the editor state. ```python import dash_mantine_components as dmc from dash import Dash, Input, Output, clientside_callback component = dmc.Box([ dmc.RichTextEditor( id="get-editor-id", toolbar={ "controlsGroups": [ [ "Bold", "Italic", "Underline", "Strikethrough", ], ], }, html="

Try typing some text in this editor. Click the button below to see your character and word count.

" ), dmc.Button("Get Stats", id="btn-rte-stats", n_clicks=0), dmc.Box(id="stats"), ]) clientside_callback( """ function(n_clicks) { if (n_clicks > 0) { const editor = dash_mantine_components.getEditor('get-editor-id'); if (editor) { const text = editor.getText(); const chars = text.length; const words = text.split(/\\s+/).filter(Boolean).length; return `Characters: ${chars} | Words: ${words}`; } } return dash_clientside.no_update; } """, Output("stats", "children"), Input("btn-rte-stats", "n_clicks"), ) ``` ### AI-friendly documentation LLM-friendly documentation is now available for Dash Mantine Components. It follows the `llms.txt` standard, enabling AI tools like ChatGPT, Cursor, Windsurf, and Claude to better understand DMC components and props. New in this release: * Generate a custom `llms.txt` file that includes only the components you use — improving AI accuracy and response speed. * Each docs page now includes a "Copy for LLMs" button for copying AI-friendly content directly into a chat. See the [LLMs section](/llms) for full details and customization options. ### Other notable updates * Mantine patch updates from 8.3.1 through 8.3.10. See the [Mantine Releases](https://github.com/mantinedev/mantine/releases) for details. * Improved rendering in several components, including the `Stepper`. Thanks to @chgiesse for [PR #664](https://github.com/snehilvj/dash-mantine-components/pull/664). In 2.4.1: * Added `anchorProps` to `Anchor` allowing to pass any valid attribute (like `download`) to the `Anchor` component. Thanks to @jksinton for [PR #676](https://github.com/snehilvj/dash-mantine-components/pull/676). * Added `withAlignedLabels` prop to support offsetting the selected check icon in `Select` and `MultiSelect` * Updated to TipTap 3.14.0 ### Thanks Special thanks to: * [@chgiesse](https://github.com/chgiesse) for contributing two PRs in this release * [@jksinton](https://github.com/jksinton) first time contributor, for ading `anchorProps` prop to `Anchor` * [@BSd3v](https://github.com/BSd3v) for providing help and guidance along the way * [@alexcjohnson](https://github.com/alexcjohnson) for thoughtful feedback during code reviews