Releases: mantinedev/mantine
9.0.2
What's Changed
[@mantine/schedule]Change default events border-radius to sm[@mantine/dates]DateTimePicker: Fix formatting not working withwithSecondsset ontimePickerPropsonly[@mantine/core]Textarea: Fix error thrown on resize in some cases[@mantine/modals]Fixmodals.closeAll()called from comtext modal causing infinite rerendering[@mantine/tiptap]RichTextEditor: Fix invisible caret in empty task list items[@mantine/schedule]Fix rrule package imports bot being compatible with esm only bundlers[@mantine/schedule]FixonEventClickcalled when event is resizing[@mantine/core]Fix incorrect default colors resolver for custom colors in light variant
New Contributors
- @dkpark10 made their first contribution in #8807
- @sdelpercio made their first contribution in #8826
Full Changelog: 9.0.1...9.0.2
9.0.1
What's Changed
[@mantine/core]LoadingOverlay: Fix double overlay visible with dark color scheme (#8811)[@mantine/core]RingProgress: Add missing viewBox (#8806)[@mantine/core]Input: AddrootRefprop support[@mantine/core]Combobox: FixrefPropnot working onCombobox.Target(#8798)[@mantine/mcp-server]Fix stdio transport to comply with MCP spec (#8792)[@mantine/core]Input: Fixaria-invalid="false"attribute being set (#8785)[@mantine/core]Slider: Fix incorrect orientation inheritance from the parent markup (#8791)[@mantine/core]Fix incorrect default placeholder size in PasswordInput and other components (#8793)[@mantine/core]Badge: Fix text being cut off with some fonts (#8788)[@mantine/hooks]use-scroller: Fix element dynamic resizing not being handled correctly (#8800)[@mantine/core]FixCheckbox.Group,Switch.Group,Radio.GroupandChip.Groupnot working with generic primitive values (#8801)[@mantine/core]Popover: Fix missingwithProps(#8802)[@mantine/core]Accordion: Fix focus ring being cut off (#8797)[@mantine/charts]Add option to fully customize reference lines label (#8790)[@mantine/core]Fixloadingprop not being handled correctly in TagsInput and MultiSelect (#8803)
Full Changelog: 9.0.0...9.0.1
9.0.0 🤩
View changelog with demos on mantine.dev website
Migration guide
This changelog covers breaking changes and new features in Mantine 9.0.
To migrate your application to Mantine 9.0, follow 8.x → 9.x migration guide.
Peer dependencies requirements updates
Starting from Mantine 9.0, the following dependencies are required:
- React 19.2+ for all
@mantine/*packages - Tiptap 3+ for
@mantine/tiptap(migration guide) - Recharts 3+ for
@mantine/charts(no migration required)
New @mantine/schedule package
New @mantine/schedule package provides a complete set of
calendar scheduling components for React applications. It includes multiple view levels,
drag-and-drop event management, and extensive customization options.
Schedule
Schedule is a unified container component that combines all views with built-in navigation and view switching. Drag events to reschedule them:
import { useState } from 'react';
import dayjs from 'dayjs';
import { Schedule, ScheduleEventData } from '@mantine/schedule';
const today = dayjs().format('YYYY-MM-DD');
const tomorrow = dayjs().add(1, 'day').format('YYYY-MM-DD');
const initialEvents: ScheduleEventData[] = [
{
id: 1,
title: 'Morning Standup',
start: `${today} 09:00:00`,
end: `${today} 09:30:00`,
color: 'blue',
},
{
id: 2,
title: 'Team Meeting',
start: `${today} 10:00:00`,
end: `${today} 11:30:00`,
color: 'green',
},
{
id: 3,
title: 'Lunch Break',
start: `${today} 12:00:00`,
end: `${today} 13:00:00`,
color: 'orange',
},
{
id: 4,
title: 'Code Review',
start: `${tomorrow} 14:00:00`,
end: `${tomorrow} 15:00:00`,
color: 'violet',
},
{
id: 5,
title: 'Client Call',
start: `${tomorrow} 15:30:00`,
end: `${tomorrow} 16:30:00`,
color: 'cyan',
},
{
id: 6,
title: 'All Day Conference',
start: `${today} 00:00:00`,
end: dayjs(today).add(1, 'day').startOf('day').format('YYYY-MM-DD HH:mm:ss'),
color: 'red',
},
];
function Demo() {
const [events, setEvents] = useState(initialEvents);
const handleEventDrop = ({ eventId, newStart, newEnd }: { eventId: string | number; newStart: string; newEnd: string }) => {
setEvents((prev) =>
prev.map((event) =>
event.id === eventId ? { ...event, start: newStart, end: newEnd } : event
)
);
};
return (
<Schedule
events={events}
withEventsDragAndDrop
onEventDrop={handleEventDrop}
/>
);
}DayView
DayView displays a single day with configurable time slots, all-day event section, current time indicator, and business hours highlighting. Drag events to reschedule them:
import { useState } from 'react';
import dayjs from 'dayjs';
import { DayView, ScheduleEventData } from '@mantine/schedule';
const today = dayjs().format('YYYY-MM-DD');
const initialEvents: ScheduleEventData[] = [
{
id: 1,
title: 'Morning Standup',
start: `${today} 09:00:00`,
end: `${today} 09:30:00`,
color: 'blue',
},
{
id: 2,
title: 'Team Meeting',
start: `${today} 11:00:00`,
end: `${today} 12:00:00`,
color: 'green',
},
{
id: 3,
title: 'Code Review',
start: `${today} 14:00:00`,
end: `${today} 15:00:00`,
color: 'violet',
},
];
function Demo() {
const [events, setEvents] = useState(initialEvents);
const handleEventDrop = ({ eventId, newStart, newEnd }: { eventId: string | number; newStart: string; newEnd: string }) => {
setEvents((prev) =>
prev.map((event) =>
event.id === eventId ? { ...event, start: newStart, end: newEnd } : event
)
);
};
return (
<DayView
date={new Date()}
events={events}
startTime="08:00:00"
endTime="18:00:00"
withEventsDragAndDrop
onEventDrop={handleEventDrop}
/>
);
}WeekView
WeekView shows a weekly calendar grid with time slots, week numbers, weekend day toggling, and multi-day event spanning. Drag events across days and time slots:
import { useState } from 'react';
import dayjs from 'dayjs';
import { WeekView, ScheduleEventData } from '@mantine/schedule';
const today = dayjs().format('YYYY-MM-DD');
const tomorrow = dayjs().add(1, 'day').format('YYYY-MM-DD');
const initialEvents: ScheduleEventData[] = [
{
id: 1,
title: 'Morning Standup',
start: `${today} 09:00:00`,
end: `${today} 09:30:00`,
color: 'blue',
},
{
id: 2,
title: 'Team Meeting',
start: `${tomorrow} 11:00:00`,
end: `${tomorrow} 12:00:00`,
color: 'green',
},
{
id: 3,
title: 'Code Review',
start: `${today} 14:00:00`,
end: `${today} 15:00:00`,
color: 'violet',
},
{
id: 4,
title: 'Company Holiday',
start: dayjs(getStartOfWeek({ date: today, firstDayOfWeek: 1 })).format('YYYY-MM-DD HH:mm:ss'),
end: dayjs(getStartOfWeek({ date: today, firstDayOfWeek: 1 }))
.add(2, 'day')
.format('YYYY-MM-DD HH:mm:ss'),
color: 'red',
},
{
id: 5,
title: 'Release Day',
start: dayjs(getStartOfWeek({ date: today, firstDayOfWeek: 1 })).format('YYYY-MM-DD HH:mm:ss'),
end: dayjs(getStartOfWeek({ date: today, firstDayOfWeek: 1 }))
.add(2, 'day')
.format('YYYY-MM-DD HH:mm:ss'),
color: 'orange',
},
];
function Demo() {
const [events, setEvents] = useState(initialEvents);
const handleEventDrop = ({ eventId, newStart, newEnd }: { eventId: string | number; newStart: string; newEnd: string }) => {
setEvents((prev) =>
prev.map((event) =>
event.id === eventId ? { ...event, start: newStart, end: newEnd } : event
)
);
};
return (
<WeekView
date={new Date()}
events={events}
startTime="08:00:00"
endTime="18:00:00"
withEventsDragAndDrop
onEventDrop={handleEventDrop}
/>
);
}MonthView
MonthView displays a monthly calendar grid with event overflow handling, outside days display, and week numbers. Drag events to different days:
import { useState } from 'react';
import dayjs from 'dayjs';
import { MonthView, ScheduleEventData } from '@mantine/schedule';
const today = dayjs().format('YYYY-MM-DD');
const initialEvents: ScheduleEventData[] = [
{
id: 1,
title: 'Team Meeting',
start: `${today} 09:00:00`,
end: `${today} 10:30:00`,
color: 'blue',
},
{
id: 2,
title: 'Project Deadline',
start: dayjs().add(5, 'day').format('YYYY-MM-DD 00:00:00'),
end: dayjs().add(6, 'day').startOf('day').format('YYYY-MM-DD HH:mm:ss'),
color: 'red',
},
];
function Demo() {
const [events, setEvents] = useState(initialEvents);
const handleEventDrop = ({ eventId, newStart, newEnd }: { eventId: string | number; newStart: string; newEnd: string }) => {
setEvents((prev) =>
prev.map((event) =>
event.id === eventId ? { ...event, start: newStart, end: newEnd } : event
)
);
};
return <MonthView date={new Date()} events={events} withEventsDragAndDrop onEventDrop={handleEventDrop} />;
}YearView
YearView provides a 12-month year overview organized by quarters with day-level event indicators:
// Demo.tsx
import dayjs from 'dayjs';
import { useState } from 'react';
import { YearView } from '@mantine/schedule';
import { events } from './data';
function Demo() {
const [date, setDate] = useState(dayjs().format('YYYY-MM-DD'));
return (
<YearView
date={date}
onDateChange={setDate}
events={events}
/>
);
}
// data.ts
import dayjs from 'dayjs';
const thisYear = dayjs().format('YYYY');
const events = [
{
id: 1,
title: 'New Year',
start: \\\`\\\${thisYear}-01-01 00:00:00\\\`,
end: dayjs(\\\`\\\${thisYear}-01-01\\\`).add(1, 'day').startOf('day').format('YYYY-MM-DD HH:mm:ss'),
color: 'blue',
},
{
id: 2,
title: 'Spring Event',
start: \\\`\\\${thisYear}-03-15 00:00:00\\\`,
end: dayjs(\\\`\\\${thisYear}-03-15\\\`).add(1, 'day').startOf('day').format('YYYY-MM-DD HH:mm:ss'),
color: 'green',
},
];MobileMonthView
MobileMonthView is a mobile-optimized month view with event details panel for the selected day:
// Demo.tsx
import dayjs from 'dayjs';
import { useState } from 'react';
import { MobileMonthView } from '@mantine/schedule';
import { events } from './data';
function Demo() {
const [date, setDate] = useState(dayjs().format('YYYY-MM-DD'));
const [selectedDate, setSelectedDate] = useState<string | null>(dayjs().format('YYYY-MM-DD'));
return (
<MobileMonthView
date={date}
onDateChange={setDate}
selectedDate={selectedDate}
onSelectedDateChange={setSelectedDate}
events={regularEvents}
/>
);
}
// data.ts
import dayjs from 'dayjs';
const thisMonth = dayjs().format('YYYY-MM');
export const events = [
{
id: 1,
title: 'Team Meeting',
start: \`\${thisMonth}-05 09:00:00\`,
end: \`\${thisMonth}-05 10:00:00\`,
color: 'blue',
},
{
id: 2,
title: 'Project Review',
start: \`\${thisMonth}-05 14:00:00\`,
end: \`\${thisMonth}-05 15:30:00\`,
color: 'green',
},
{
id: 3,
t...8.3.18
This is the last 8.x release. You are welcome to test 9.0 alpha version and provide feedback before its release on March 31 – https://alpha.mantine.dev/changelog/9-0-0/
[@mantine/core]PasswordInput: Fix styles api props not resolving correctly in theme (#8716)
8.3.17
8.3.16
What's Changed
[@mantine/modals]FixonClosebeing called multiple times (#8727)[@mantine/core]Tooltip: Fix component not throwing erro when used with string (#8694)[@mantine/core]NumberInput: Fix incorrect decimal separator parsing inonPaste[@mantine/core]AppShell: Fixlayout="alt"not working withmode="static"[@mantine/stotlight]Fix actions list being rendered when nothing found message was not set (#8592)
Full Changelog: 8.3.15...8.3.16
8.3.15
What's Changed
[@mantine/dropzone]Updatereact-dropzoneto 15.0.0 (#8667)[@mantine/core]TagsInput: Fix duplicate checking bypass with splitChars (#8686)[@mantine/charts]Allow ChartTooltipvalueFormatterto returnReact.ReactNode(#8650)[@mantine/dates]DatePicker: Fix placeholder selector missing in Styles API (#8663)[@mantine/core]Add missing factory types exports (#8677)[@mantine/core]Fix inert attribute being ignored by Checkbox and Switch components (#8668)
Full Changelog: 8.3.14...8.3.15
9.0.0-alpha.0
View changelog with demos on alpha.mantine.dev website
Alpha version
This is the first alpha version of Mantine 9. You are welcome to review changes and provide feedback.
Support Mantine development
You can now sponsor Mantine development with OpenCollective.
All funds are used to improve Mantine and create new features and components.
Migration guide
This changelog covers breaking changes and new features in Mantine 9.0.
To migrate your application to Mantine 9.0, follow 8.x → 9.x migration guide.
Peer dependencies requirements updates
Starting from Mantine 9.0, the following dependencies are required:
- React 19+ for all
@mantine/*packages - Tiptap 3+ for
@mantine/tiptap(migration guide) - Recharts 3+ for
@mantine/charts(no migration required)
Namespace types exports
All Mantine components and hooks now provide namespace exports for related types.
For example, use-disclosure hook types can now be accessed like this:
import { useDisclosure } from '@mantine/hooks';
const options: useDisclosure.Options = {
onOpen: () => console.log('open'),
onClose: () => console.log('close'),
};
function Demo() {
const [opened, handlers] = useDisclosure(options);
}Example of using namespace types with Button props type:
import { Button } from '@mantine/core';
const buttonProps: Button.Props = {
variant: 'filled',
size: 'md',
disabled: false,
};
function Demo() {
return <Button {...buttonProps}>Click me</Button>;
}New @mantine/schedule package
New @mantine/schedule package provides a complete set of
calendar scheduling components for React applications. It includes multiple view levels,
drag-and-drop event management, and extensive customization options.
Components included:
- Schedule – unified container component that combines all views with built-in navigation and view switching
- DayView – single day view with configurable time slots, all-day event section, current time indicator, and business hours highlighting
- WeekView – weekly calendar grid with time slots, week numbers, weekend day toggling, and multi-day event spanning
- MonthView – monthly calendar grid with event overflow handling, outside days display, and week numbers
- YearView – 12-month year overview organized by quarters with day-level event indicators
- MobileMonthView – mobile-optimized month view with event details panel for the selected day
Key features:
- Drag and drop – drag events to reschedule them across time slots and days. Supports conditional dragging with
canDragEventcallback, and drag-to-select time ranges withwithDragSlotSelect - Multiple interaction modes –
defaultmode enables all interactions (click, drag, navigation),staticmode renders a read-only calendar - Responsive layout –
layout="responsive"automatically switches toYearViewandMobileMonthViewon smaller screens - Custom event rendering – use
renderEventBodyorrenderEventto fully customize how events are displayed in all views - Time configuration – configurable start/end times, time slot intervals, time label formats, and business hours highlighting
- Internationalization – full label customization through the
labelsprop, locale-aware date formatting via dayjs - Click handlers –
onTimeSlotClick,onAllDaySlotClick,onDayClick, andonEventClickfor building interactive scheduling interfaces - Styles API – full support for
classNames,styles, andunstyledprops, along with CSS variables for theming
To get started, follow the getting started guide.
Collapse horizontal orientation
Collapse component now supports horizontal orientation:
import { Button, Collapse, Stack, Typography } from '@mantine/core';
import { useDisclosure } from '@mantine/hooks';
function Demo() {
const [expanded, handlers] = useDisclosure(false);
return (
<Stack h={240} align="flex-start">
<Button onClick={handlers.toggle} w="fit-content">
{expanded ? 'Collapse' : 'Expand'}
</Button>
<Collapse expanded={expanded} orientation="horizontal">
<Typography bg="var(--mantine-color-blue-light)" p="xs" bdrs="md" w={200}>
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt
ut labore et dolore magna aliqua.
</Typography>
</Collapse>
</Stack>
);
}use-collapse and use-horizontal-collapse hooks
New use-collapse hook is the hook version of Collapse component.
It allows animation of height from 0 to auto and vice versa.
import { Button, Typography } from '@mantine/core';
import { useCollapse, useDisclosure } from '@mantine/hooks';
function Demo() {
const [expanded, handlers] = useDisclosure(false);
const getCollapseProps = useCollapse({ expanded });
return (
<>
<Button onClick={handlers.toggle} mb="md">
{expanded ? 'Collapse' : 'Expand'}
</Button>
<div {...getCollapseProps()}>
<Typography bg="var(--mantine-color-blue-light)" p="xs" bdrs="md">
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt
ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation
ullamco laboris nisi ut aliquip ex ea commodo consequat.
</Typography>
</div>
</>
);
}use-horizontal-collapse works the same way as use-collapse but animates width instead of height:
import { Button, Stack, Typography } from '@mantine/core';
import { useDisclosure, useHorizontalCollapse } from '@mantine/hooks';
function Demo() {
const [expanded, handlers] = useDisclosure(false);
const { getCollapseProps } = useHorizontalCollapse({ expanded });
return (
<Stack h={240}>
<Button onClick={handlers.toggle} w="fit-content">
{expanded ? 'Collapse' : 'Expand'}
</Button>
<div {...getCollapseProps()}>
<Typography bg="var(--mantine-color-blue-light)" p="xs" bdrs="md" w={200}>
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt
ut labore et dolore magna aliqua.
</Typography>
</div>
</Stack>
);
}use-floating-window hook
New use-floating-window hook allows creating floating draggable
elements:
import { Button, CloseButton, Group, Paper, Portal, Text } from '@mantine/core';
import { useDisclosure, useFloatingWindow } from '@mantine/hooks';
function Demo() {
const [visible, handlers] = useDisclosure();
const floatingWindow = useFloatingWindow({
constrainToViewport: true,
constrainOffset: 20,
excludeDragHandleSelector: 'button',
initialPosition: { top: 300, left: 20 },
});
return (
<>
<Button onClick={handlers.toggle} variant="default">
{visible ? 'Hide' : 'Show'} floating window
</Button>
{visible && (
<Portal>
<Paper
w={280}
p="md"
withBorder
radius="md"
pos="fixed"
style={{ cursor: 'move', transition: 'box-shadow 70ms ease', zIndex: 400 }}
shadow={floatingWindow.isDragging ? 'md' : undefined}
ref={floatingWindow.ref}
>
<Group justify="space-between" mb="md">
<Text>Usage demo</Text>
<CloseButton onClick={handlers.close} />
</Group>
<Text fz="sm">This is a floating window. You can drag it around.</Text>
</Paper>
</Portal>
)}
</>
);
}FloatingWindow component
FloatingWindow provides component API for use-floating-window hook:
import { Button, CloseButton, FloatingWindow, Group, Text } from '@mantine/core';
import { useDisclosure } from '@mantine/hooks';
function Demo() {
const [visible, handlers] = useDisclosure();
return (
<>
<Button onClick={handlers.toggle} variant="default">
{visible ? 'Hide' : 'Show'} floating window
</Button>
{visible && (
<FloatingWindow
w={280}
p="md"
withBorder
radius="md"
excludeDragHandleSelector="button"
initialPosition={{ top: 300, left: 20 }}
style={{ cursor: 'move' }}
>
<Group justify="space-between" mb="md">
<Text>Usage demo</Text>
<CloseButton onClick={handlers.close} />
</Group>
<Text fz="sm">This is a floating window. You can drag it around.</Text>
</FloatingWindow>
)}
</>
);
}OverflowList component
New OverflowList component displays list of items and collapses the overflowing items into a single element:
...8.3.14
What's Changed
[@mantine/core]Switch: Fix checkbox not being recognized by Playwright (#8370, #8645)[@mantine/core]MultiSelect: Fix click on chevron not opening dropdown when clearable is enabled (#8641)[@mantine/modals]Fix types of context modals inferred incorrectly (#8625)[@mantine/core]MultiSelect: Fix clear button overlapping with pills (#8634)
New Contributors
- @ckhe1215 made their first contribution in #8634
- @RaphalRiad made their first contribution in #8625
Full Changelog: 8.3.13...8.3.14
8.3.13
What's Changed
[@mantine/core]AddopenOnFocusprop to Combobox based components (#5893, #8623)[@mantine/dates]TimePicker: Fix clearing in uncontrolled mode not updating to empty value (#8622)[@mantine/core]ScrollArea: Fix Shift + wheel scroll not working correctly on Windows (#8619)[@mantine/core]AddselectFirstOptionOnDropdownOpento Combobox based components (#8597)[@mantine/core]ScrollArea: FixonBottomReachednot being called when used in zoomed-in viewports (#8616)[@mantine/core]Popover: Fixaria-controlsattribute being set on the target element when the dropdown is not mounted (#8595)[@mantine/core]RangeSlider: Fix incorrect Styles API name (#8601)[@mantine/core]ScrollArea: FixoverscrollBehaviorprop not working in ScrollArea.Autosize component (#8611)
New Contributors
- @AgentRBY made their first contribution in #8601
- @jonathanhuynh70 made their first contribution in #8595
- @robert-j-webb made their first contribution in #8616
- @Alan-Gomes made their first contribution in #8597
- @pggggggggh made their first contribution in #8622
- @harry-ignite made their first contribution in #8623
Full Changelog: 8.3.12...8.3.13