docs: improve instructions to install Medusa UI in standalone projects (#13104)
This commit is contained in:
1 parent
f6736d9661
commit
54d9edc1ab
3 files changed
+210
-124
No files matched your search
@@ -83074,7 +83074,7 @@ const data = [
|
|||||||
{
|
{
|
||||||
id: "1",
|
id: "1",
|
||||||
title: "Shirt",
|
title: "Shirt",
|
||||||
price: 10
|
price: 10,
|
||||||
},
|
},
|
||||||
// other data...
|
// other data...
|
||||||
]
|
]
|
||||||
@@ -83113,7 +83113,7 @@ import {
|
|||||||
Then, inside the component that will render `DataTable`, create a table instance using the `useDataTable` hook:
|
Then, inside the component that will render `DataTable`, create a table instance using the `useDataTable` hook:
|
||||||
|
|
||||||
```tsx
|
```tsx
|
||||||
export default function ProductTable () {
|
export default function ProductTable() {
|
||||||
const table = useDataTable({
|
const table = useDataTable({
|
||||||
columns,
|
columns,
|
||||||
data,
|
data,
|
||||||
@@ -83137,7 +83137,7 @@ The `useDataTable` hook accepts an object with the following properties:
|
|||||||
Finally, render the `DataTable` component with the table instance created using the `useDataTable` hook:
|
Finally, render the `DataTable` component with the table instance created using the `useDataTable` hook:
|
||||||
|
|
||||||
```tsx
|
```tsx
|
||||||
export default function ProductTable () {
|
export default function ProductTable() {
|
||||||
// ...
|
// ...
|
||||||
return (
|
return (
|
||||||
<DataTable instance={table}>
|
<DataTable instance={table}>
|
||||||
@@ -83376,14 +83376,14 @@ const products = [
|
|||||||
id: "1",
|
id: "1",
|
||||||
title: "Shirt",
|
title: "Shirt",
|
||||||
price: 10,
|
price: 10,
|
||||||
is_active: true
|
is_active: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: "2",
|
id: "2",
|
||||||
title: "Pants",
|
title: "Pants",
|
||||||
price: 20,
|
price: 20,
|
||||||
is_active: true
|
is_active: true,
|
||||||
}
|
},
|
||||||
]
|
]
|
||||||
|
|
||||||
const columnHelper = createDataTableColumnHelper<typeof products[0]>()
|
const columnHelper = createDataTableColumnHelper<typeof products[0]>()
|
||||||
@@ -83398,7 +83398,7 @@ const columns = [
|
|||||||
{isActive ? "Active" : "Inactive"}
|
{isActive ? "Active" : "Inactive"}
|
||||||
</Badge>
|
</Badge>
|
||||||
)
|
)
|
||||||
}
|
},
|
||||||
}),
|
}),
|
||||||
// ...
|
// ...
|
||||||
]
|
]
|
||||||
@@ -83483,8 +83483,8 @@ const table = useDataTable({
|
|||||||
// ...
|
// ...
|
||||||
search: {
|
search: {
|
||||||
state: search,
|
state: search,
|
||||||
onSearchChange: setSearch
|
onSearchChange: setSearch,
|
||||||
}
|
},
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -83513,8 +83513,8 @@ const table = useDataTable({
|
|||||||
// Pass the state and onSearchChange to the table instance.
|
// Pass the state and onSearchChange to the table instance.
|
||||||
search: {
|
search: {
|
||||||
state: search,
|
state: search,
|
||||||
onSearchChange: setSearch
|
onSearchChange: setSearch,
|
||||||
}
|
},
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -83755,7 +83755,7 @@ const table = useDataTable({
|
|||||||
onPaginationChange: setPagination,
|
onPaginationChange: setPagination,
|
||||||
},
|
},
|
||||||
isLoading: false,
|
isLoading: false,
|
||||||
});
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
Finally, render the `DataTable.Pagination` component as part of the `DataTable`'s children:
|
Finally, render the `DataTable.Pagination` component as part of the `DataTable`'s children:
|
||||||
@@ -83914,8 +83914,8 @@ const filters = [
|
|||||||
label: "Title",
|
label: "Title",
|
||||||
options: products.map((product) => ({
|
options: products.map((product) => ({
|
||||||
label: product.title,
|
label: product.title,
|
||||||
value: product.title.toLowerCase()
|
value: product.title.toLowerCase(),
|
||||||
}))
|
})),
|
||||||
}),
|
}),
|
||||||
]
|
]
|
||||||
```
|
```
|
||||||
@@ -84008,7 +84008,7 @@ const table = useDataTable({
|
|||||||
state: filtering,
|
state: filtering,
|
||||||
onFilteringChange: setFiltering,
|
onFilteringChange: setFiltering,
|
||||||
},
|
},
|
||||||
filters
|
filters,
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -84196,24 +84196,24 @@ const filters = [
|
|||||||
label: "Today",
|
label: "Today",
|
||||||
value: {
|
value: {
|
||||||
$gte: new Date(new Date().setHours(0, 0, 0, 0)).toString(),
|
$gte: new Date(new Date().setHours(0, 0, 0, 0)).toString(),
|
||||||
$lte: new Date(new Date().setHours(23, 59, 59, 999)).toString()
|
$lte: new Date(new Date().setHours(23, 59, 59, 999)).toString(),
|
||||||
}
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: "Yesterday",
|
label: "Yesterday",
|
||||||
value: {
|
value: {
|
||||||
$gte: new Date(new Date().setHours(0, 0, 0, 0) - 24 * 60 * 60 * 1000).toString(),
|
$gte: new Date(new Date().setHours(0, 0, 0, 0) - 24 * 60 * 60 * 1000).toString(),
|
||||||
$lte: new Date(new Date().setHours(0, 0, 0, 0)).toString()
|
$lte: new Date(new Date().setHours(0, 0, 0, 0)).toString(),
|
||||||
}
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: "Last Week",
|
label: "Last Week",
|
||||||
value: {
|
value: {
|
||||||
$gte: new Date(new Date().setHours(0, 0, 0, 0) - 7 * 24 * 60 * 60 * 1000).toString(),
|
$gte: new Date(new Date().setHours(0, 0, 0, 0) - 7 * 24 * 60 * 60 * 1000).toString(),
|
||||||
$lte: new Date(new Date().setHours(0, 0, 0, 0)).toString()
|
$lte: new Date(new Date().setHours(0, 0, 0, 0)).toString(),
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
]
|
],
|
||||||
}),
|
}),
|
||||||
]
|
]
|
||||||
```
|
```
|
||||||
@@ -84382,7 +84382,7 @@ If you want to set initial filter values, you can set the initial state of the `
|
|||||||
|
|
||||||
```tsx
|
```tsx
|
||||||
const [filtering, setFiltering] = useState<DataTableFilteringState>({
|
const [filtering, setFiltering] = useState<DataTableFilteringState>({
|
||||||
title: ["shirt"]
|
title: ["shirt"],
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -84510,11 +84510,11 @@ Next, in the component rendering the `DataTable` component, create a state varia
|
|||||||
```tsx
|
```tsx
|
||||||
import {
|
import {
|
||||||
// ...
|
// ...
|
||||||
DataTableSortingState
|
DataTableSortingState,
|
||||||
} from "@medusajs/ui"
|
} from "@medusajs/ui"
|
||||||
|
|
||||||
export default function ProductTable () {
|
export default function ProductTable() {
|
||||||
const [sorting, setSorting] = useState<DataTableSortingState | null>(null);
|
const [sorting, setSorting] = useState<DataTableSortingState | null>(null)
|
||||||
|
|
||||||
const table = useDataTable({
|
const table = useDataTable({
|
||||||
// ...
|
// ...
|
||||||
@@ -84540,7 +84540,7 @@ You must also implement the sorting logic, such as sending the sorting condition
|
|||||||
For example, when using a simple array as in the example above, this is how you sort the data based on the sorting conditions:
|
For example, when using a simple array as in the example above, this is how you sort the data based on the sorting conditions:
|
||||||
|
|
||||||
```tsx
|
```tsx
|
||||||
const [sorting, setSorting] = useState<DataTableSortingState | null>(null);
|
const [sorting, setSorting] = useState<DataTableSortingState | null>(null)
|
||||||
|
|
||||||
const shownProducts = useMemo(() => {
|
const shownProducts = useMemo(() => {
|
||||||
if (!sorting) {
|
if (!sorting) {
|
||||||
@@ -84823,8 +84823,8 @@ const useCommands = () => {
|
|||||||
const productsToDeleteIds = Object.keys(selection)
|
const productsToDeleteIds = Object.keys(selection)
|
||||||
|
|
||||||
// TODO remove products from the server
|
// TODO remove products from the server
|
||||||
}
|
},
|
||||||
})
|
}),
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
@@ -88429,50 +88429,60 @@ npm install @medusajs/ui
|
|||||||
The configuration of the UI package is handled by the `@medusajs/admin` package. Therefore, you do not need to any additional configuration to use the UI package in your Admin extensions.
|
The configuration of the UI package is handled by the `@medusajs/admin` package. Therefore, you do not need to any additional configuration to use the UI package in your Admin extensions.
|
||||||
|
|
||||||
|
|
||||||
# Standalone Project
|
# Medusa UI Installation in Standalone Projects
|
||||||
|
|
||||||
How to install and use Medusa UI in a standalone project.
|
Learn how to install and use Medusa UI in a standalone project.
|
||||||
|
|
||||||
## Installation
|
Medusa UI is a React UI library that, while intended for usage within Medusa projects, can also be used in any React project.
|
||||||
|
|
||||||
|
The icons package is installed independently from Medusa UI. Learn how to install it in the [Icons](../icons/overview.mdx) guide.
|
||||||
|
|
||||||
|
## Medusa UI Compatibility
|
||||||
|
|
||||||
|
To use Medusa UI in your standalone project, you must have:
|
||||||
|
|
||||||
|
- React 18+ installed. Most React-based frameworks and libraries, such as Next.js and Vite, are compatible with this requirement.
|
||||||
|
- [Tailwind CSS](https://v3.tailwindcss.com/) installed. The components in Medusa UI are styled using Tailwind CSS, so you will need to install it in your project as well.
|
||||||
|
- Medusa UI was built with Tailwind CSS v3, but it may generally support v4 as well.
|
||||||
|
|
||||||
***
|
***
|
||||||
|
|
||||||
Medusa UI is a React UI library and while it's intended for usage within Medusa projects, it can also be used in any React project.
|
## Step 1: Install Medusa UI
|
||||||
|
|
||||||
### Install Medusa UI
|
In your standalone project, install the Medusa UI package with the following command:
|
||||||
|
|
||||||
Install the React UI library with the following command:
|
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
npm install @medusajs/ui
|
npm install @medusajs/ui
|
||||||
```
|
```
|
||||||
|
|
||||||
### Configuring Tailwind CSS
|
***
|
||||||
|
|
||||||
The components are styled using Tailwind CSS, and in order to use them, you will need to install Tailwind CSS in your project as well.
|
## Step 2: Install UI Presets
|
||||||
For more information on how to install Tailwind CSS, please refer to the [Tailwind CSS documentation](https://tailwindcss.com/docs/installation).
|
|
||||||
|
|
||||||
All of the classes used for Medusa UI are shipped as a Tailwind CSS customization.
|
Medusa UI customizes Tailwind CSS classes to implement its design system. So, you must also install the Medusa UI preset package.
|
||||||
You can install it with the following command:
|
|
||||||
|
To install the Medusa UI preset, run the following command:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
npm install @medusajs/ui-preset
|
npm install @medusajs/ui-preset
|
||||||
```
|
```
|
||||||
|
|
||||||
After you have installed Tailwind CSS and the Medusa UI preset, you need to add the following to your `tailwind.config.js`file:
|
***
|
||||||
|
|
||||||
```tsx
|
## Step 3: Configure Tailwind CSS
|
||||||
|
|
||||||
|
Next, you'll need to configure Tailwind CSS to use the Medusa UI preset and explicitly add the paths to the Medusa UI components as content files.
|
||||||
|
|
||||||
|
### Tailwind CSS v3 Configurations
|
||||||
|
|
||||||
|
In Tailwind CSS v3, which is the recommended version to use with Medusa UI, you need to add the following configurations to your `tailwind.config.js` or `tailwind.config.ts` file:
|
||||||
|
|
||||||
|
1. Add the Medusa UI preset to the `presets` array.
|
||||||
|
2. Ensure that the `content` field includes the path to the Medusa UI package.
|
||||||
|
|
||||||
|
```js title="tailwind.config.js"
|
||||||
module.exports = {
|
module.exports = {
|
||||||
presets: [require("@medusajs/ui-preset")],
|
presets: [require("@medusajs/ui-preset")],
|
||||||
// ...
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
In order for the styles to be applied correctly to the components, you will also need to ensure that
|
|
||||||
`@medusajs/ui` is included in the content field of your `tailwind.config.js` file:
|
|
||||||
|
|
||||||
```tsx
|
|
||||||
module.exports = {
|
|
||||||
content: [
|
content: [
|
||||||
// ...
|
// ...
|
||||||
"./node_modules/@medusajs/ui/dist/**/*.{js,jsx,ts,tsx}",
|
"./node_modules/@medusajs/ui/dist/**/*.{js,jsx,ts,tsx}",
|
||||||
@@ -88481,9 +88491,9 @@ module.exports = {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
If you are working within a monorepo, you may need to add the path to the `@medusajs/ui` package in your `tailwind.config.js` like so:
|
If your project is in a monorepo, you'll need to resolve the path to the `@medusajs/ui` package from the monorepo root:
|
||||||
|
|
||||||
```tsx
|
```tsx title="tailwind.config.js"
|
||||||
const path = require("path")
|
const path = require("path")
|
||||||
|
|
||||||
const uiPath = path.resolve(
|
const uiPath = path.resolve(
|
||||||
@@ -88493,6 +88503,7 @@ const uiPath = path.resolve(
|
|||||||
)
|
)
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
|
presets: [require("@medusajs/ui-preset")],
|
||||||
content: [
|
content: [
|
||||||
// ...
|
// ...
|
||||||
uiPath,
|
uiPath,
|
||||||
@@ -88502,26 +88513,55 @@ module.exports = {
|
|||||||
|
|
||||||
```
|
```
|
||||||
|
|
||||||
## Start building
|
### Tailwind CSS v4 Configurations
|
||||||
|
|
||||||
***
|
Medusa UI isn't officially compatible with Tailwind CSS v4 yet, so use it with caution.
|
||||||
|
|
||||||
You are now ready to start building your application with Medusa UI. You can import the components like so:
|
In your CSS file that imports Tailwind CSS, add the following `@config` and `@source` directives:
|
||||||
|
|
||||||
```tsx
|
```css
|
||||||
import { Button, Drawer } from "@medusajs/ui"
|
@import "tailwindcss";
|
||||||
|
@source "../node_modules/@medusajs/ui";
|
||||||
|
@config "@medusajs/ui-preset";
|
||||||
```
|
```
|
||||||
|
|
||||||
## Updating UI Packages
|
This will explicitly include the Medusa UI preset and its components in your Tailwind CSS build, and will apply the preset styles to your project.
|
||||||
|
|
||||||
***
|
***
|
||||||
|
|
||||||
Medusa's design-system packages, including `@medusajs/ui`, `@medusajs/ui-preset`, and `@medusajs/ui-icons`, are versioned independently. However, they're still part of the latest Medusa release. So, you can browse the [release notes](https://github.com/medusajs/medusa/releases) to see if there are any breaking changes to these packages.
|
## Step 4: Use Medusa UI in Standalone Projects
|
||||||
|
|
||||||
To update these packages, update their version in your `package.json` file and re-install dependencies. For example:
|
You can now start building your application with Medusa UI.
|
||||||
|
|
||||||
```bash
|
For example, you can use the `Button` in your custom components:
|
||||||
npm install @medusajs/ui
|
|
||||||
|
```tsx
|
||||||
|
import { Button } from "@medusajs/ui"
|
||||||
|
|
||||||
|
export function ButtonDemo() {
|
||||||
|
return <Button>Button</Button>
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Refer to the documentation of each component to learn about its props and usage.
|
||||||
|
|
||||||
|
***
|
||||||
|
|
||||||
|
## Update UI Packages in Standalone Projects
|
||||||
|
|
||||||
|
Medusa's design-system packages, including `@medusajs/ui` and `@medusajs/ui-preset`, are versioned independently from other `@medusajs/*` packages. However, they're still released as part of Medusa's releases.
|
||||||
|
|
||||||
|
So, to find latest updates and breaking changes to any of these packages, refer to the [release notes in the Medusa GitHub repository](https://github.com/medusajs/medusa/releases).
|
||||||
|
|
||||||
|
To update these packages in your standalone project, update their version in your `package.json` file and re-install dependencies. For example:
|
||||||
|
|
||||||
|
```json title="package.json"
|
||||||
|
{
|
||||||
|
"dependencies": {
|
||||||
|
"@medusajs/ui": "4.0.0",
|
||||||
|
"@medusajs/ui-preset": "4.0.0"
|
||||||
|
}
|
||||||
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -43,7 +43,7 @@ const data = [
|
|||||||
{
|
{
|
||||||
id: "1",
|
id: "1",
|
||||||
title: "Shirt",
|
title: "Shirt",
|
||||||
price: 10
|
price: 10,
|
||||||
},
|
},
|
||||||
// other data...
|
// other data...
|
||||||
]
|
]
|
||||||
@@ -82,7 +82,7 @@ import {
|
|||||||
Then, inside the component that will render `DataTable`, create a table instance using the `useDataTable` hook:
|
Then, inside the component that will render `DataTable`, create a table instance using the `useDataTable` hook:
|
||||||
|
|
||||||
```tsx
|
```tsx
|
||||||
export default function ProductTable () {
|
export default function ProductTable() {
|
||||||
const table = useDataTable({
|
const table = useDataTable({
|
||||||
columns,
|
columns,
|
||||||
data,
|
data,
|
||||||
@@ -106,7 +106,7 @@ The `useDataTable` hook accepts an object with the following properties:
|
|||||||
Finally, render the `DataTable` component with the table instance created using the `useDataTable` hook:
|
Finally, render the `DataTable` component with the table instance created using the `useDataTable` hook:
|
||||||
|
|
||||||
```tsx
|
```tsx
|
||||||
export default function ProductTable () {
|
export default function ProductTable() {
|
||||||
// ...
|
// ...
|
||||||
return (
|
return (
|
||||||
<DataTable instance={table}>
|
<DataTable instance={table}>
|
||||||
@@ -196,14 +196,14 @@ const products = [
|
|||||||
id: "1",
|
id: "1",
|
||||||
title: "Shirt",
|
title: "Shirt",
|
||||||
price: 10,
|
price: 10,
|
||||||
is_active: true
|
is_active: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: "2",
|
id: "2",
|
||||||
title: "Pants",
|
title: "Pants",
|
||||||
price: 20,
|
price: 20,
|
||||||
is_active: true
|
is_active: true,
|
||||||
}
|
},
|
||||||
]
|
]
|
||||||
|
|
||||||
const columnHelper = createDataTableColumnHelper<typeof products[0]>()
|
const columnHelper = createDataTableColumnHelper<typeof products[0]>()
|
||||||
@@ -218,7 +218,7 @@ const columns = [
|
|||||||
{isActive ? "Active" : "Inactive"}
|
{isActive ? "Active" : "Inactive"}
|
||||||
</Badge>
|
</Badge>
|
||||||
)
|
)
|
||||||
}
|
},
|
||||||
}),
|
}),
|
||||||
// ...
|
// ...
|
||||||
]
|
]
|
||||||
@@ -242,8 +242,8 @@ const table = useDataTable({
|
|||||||
// ...
|
// ...
|
||||||
search: {
|
search: {
|
||||||
state: search,
|
state: search,
|
||||||
onSearchChange: setSearch
|
onSearchChange: setSearch,
|
||||||
}
|
},
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -272,8 +272,8 @@ const table = useDataTable({
|
|||||||
// Pass the state and onSearchChange to the table instance.
|
// Pass the state and onSearchChange to the table instance.
|
||||||
search: {
|
search: {
|
||||||
state: search,
|
state: search,
|
||||||
onSearchChange: setSearch
|
onSearchChange: setSearch,
|
||||||
}
|
},
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -370,7 +370,7 @@ const table = useDataTable({
|
|||||||
onPaginationChange: setPagination,
|
onPaginationChange: setPagination,
|
||||||
},
|
},
|
||||||
isLoading: false,
|
isLoading: false,
|
||||||
});
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
Finally, render the `DataTable.Pagination` component as part of the `DataTable`'s children:
|
Finally, render the `DataTable.Pagination` component as part of the `DataTable`'s children:
|
||||||
@@ -427,8 +427,8 @@ const filters = [
|
|||||||
label: "Title",
|
label: "Title",
|
||||||
options: products.map((product) => ({
|
options: products.map((product) => ({
|
||||||
label: product.title,
|
label: product.title,
|
||||||
value: product.title.toLowerCase()
|
value: product.title.toLowerCase(),
|
||||||
}))
|
})),
|
||||||
}),
|
}),
|
||||||
]
|
]
|
||||||
```
|
```
|
||||||
@@ -525,7 +525,7 @@ const table = useDataTable({
|
|||||||
state: filtering,
|
state: filtering,
|
||||||
onFilteringChange: setFiltering,
|
onFilteringChange: setFiltering,
|
||||||
},
|
},
|
||||||
filters
|
filters,
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -575,24 +575,24 @@ const filters = [
|
|||||||
label: "Today",
|
label: "Today",
|
||||||
value: {
|
value: {
|
||||||
$gte: new Date(new Date().setHours(0, 0, 0, 0)).toString(),
|
$gte: new Date(new Date().setHours(0, 0, 0, 0)).toString(),
|
||||||
$lte: new Date(new Date().setHours(23, 59, 59, 999)).toString()
|
$lte: new Date(new Date().setHours(23, 59, 59, 999)).toString(),
|
||||||
}
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: "Yesterday",
|
label: "Yesterday",
|
||||||
value: {
|
value: {
|
||||||
$gte: new Date(new Date().setHours(0, 0, 0, 0) - 24 * 60 * 60 * 1000).toString(),
|
$gte: new Date(new Date().setHours(0, 0, 0, 0) - 24 * 60 * 60 * 1000).toString(),
|
||||||
$lte: new Date(new Date().setHours(0, 0, 0, 0)).toString()
|
$lte: new Date(new Date().setHours(0, 0, 0, 0)).toString(),
|
||||||
}
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: "Last Week",
|
label: "Last Week",
|
||||||
value: {
|
value: {
|
||||||
$gte: new Date(new Date().setHours(0, 0, 0, 0) - 7 * 24 * 60 * 60 * 1000).toString(),
|
$gte: new Date(new Date().setHours(0, 0, 0, 0) - 7 * 24 * 60 * 60 * 1000).toString(),
|
||||||
$lte: new Date(new Date().setHours(0, 0, 0, 0)).toString()
|
$lte: new Date(new Date().setHours(0, 0, 0, 0)).toString(),
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
]
|
],
|
||||||
}),
|
}),
|
||||||
]
|
]
|
||||||
```
|
```
|
||||||
@@ -653,7 +653,7 @@ If you want to set initial filter values, you can set the initial state of the `
|
|||||||
|
|
||||||
```tsx
|
```tsx
|
||||||
const [filtering, setFiltering] = useState<DataTableFilteringState>({
|
const [filtering, setFiltering] = useState<DataTableFilteringState>({
|
||||||
title: ["shirt"]
|
title: ["shirt"],
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -698,11 +698,11 @@ Next, in the component rendering the `DataTable` component, create a state varia
|
|||||||
```tsx
|
```tsx
|
||||||
import {
|
import {
|
||||||
// ...
|
// ...
|
||||||
DataTableSortingState
|
DataTableSortingState,
|
||||||
} from "@medusajs/ui"
|
} from "@medusajs/ui"
|
||||||
|
|
||||||
export default function ProductTable () {
|
export default function ProductTable() {
|
||||||
const [sorting, setSorting] = useState<DataTableSortingState | null>(null);
|
const [sorting, setSorting] = useState<DataTableSortingState | null>(null)
|
||||||
|
|
||||||
const table = useDataTable({
|
const table = useDataTable({
|
||||||
// ...
|
// ...
|
||||||
@@ -728,7 +728,7 @@ You must also implement the sorting logic, such as sending the sorting condition
|
|||||||
For example, when using a simple array as in the example above, this is how you sort the data based on the sorting conditions:
|
For example, when using a simple array as in the example above, this is how you sort the data based on the sorting conditions:
|
||||||
|
|
||||||
```tsx
|
```tsx
|
||||||
const [sorting, setSorting] = useState<DataTableSortingState | null>(null);
|
const [sorting, setSorting] = useState<DataTableSortingState | null>(null)
|
||||||
|
|
||||||
const shownProducts = useMemo(() => {
|
const shownProducts = useMemo(() => {
|
||||||
if (!sorting) {
|
if (!sorting) {
|
||||||
@@ -852,8 +852,8 @@ const useCommands = () => {
|
|||||||
const productsToDeleteIds = Object.keys(selection)
|
const productsToDeleteIds = Object.keys(selection)
|
||||||
|
|
||||||
// TODO remove products from the server
|
// TODO remove products from the server
|
||||||
}
|
},
|
||||||
})
|
}),
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|||||||
@@ -1,44 +1,58 @@
|
|||||||
---
|
---
|
||||||
title: "Standalone Project"
|
title: "Medusa UI Installation in Standalone Projects"
|
||||||
description: "How to install and use Medusa UI in a standalone project."
|
description: "Learn how to install and use Medusa UI in a standalone project."
|
||||||
---
|
---
|
||||||
|
|
||||||
## Installation
|
Medusa UI is a React UI library that, while intended for usage within Medusa projects, can also be used in any React project.
|
||||||
|
|
||||||
|
<Note>
|
||||||
|
|
||||||
|
The icons package is installed independently from Medusa UI. Learn how to install it in the [Icons](../icons/overview.mdx) guide.
|
||||||
|
|
||||||
|
</Note>
|
||||||
|
|
||||||
|
## Medusa UI Compatibility
|
||||||
|
|
||||||
|
To use Medusa UI in your standalone project, you must have:
|
||||||
|
|
||||||
|
- React 18+ installed. Most React-based frameworks and libraries, such as Next.js and Vite, are compatible with this requirement.
|
||||||
|
- [Tailwind CSS](https://v3.tailwindcss.com/) installed. The components in Medusa UI are styled using Tailwind CSS, so you will need to install it in your project as well.
|
||||||
|
- Medusa UI was built with Tailwind CSS v3, but it may generally support v4 as well.
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
Medusa UI is a React UI library and while it's intended for usage within Medusa projects, it can also be used in any React project.
|
## Step 1: Install Medusa UI
|
||||||
|
|
||||||
### Install Medusa UI
|
In your standalone project, install the Medusa UI package with the following command:
|
||||||
|
|
||||||
Install the React UI library with the following command:
|
|
||||||
|
|
||||||
<PackageInstall packageName="@medusajs/ui" />
|
<PackageInstall packageName="@medusajs/ui" />
|
||||||
|
|
||||||
### Configuring Tailwind CSS
|
---
|
||||||
|
|
||||||
The components are styled using Tailwind CSS, and in order to use them, you will need to install Tailwind CSS in your project as well.
|
## Step 2: Install UI Presets
|
||||||
For more information on how to install Tailwind CSS, please refer to the [Tailwind CSS documentation](https://tailwindcss.com/docs/installation).
|
|
||||||
|
|
||||||
All of the classes used for Medusa UI are shipped as a Tailwind CSS customization.
|
Medusa UI customizes Tailwind CSS classes to implement its design system. So, you must also install the Medusa UI preset package.
|
||||||
You can install it with the following command:
|
|
||||||
|
To install the Medusa UI preset, run the following command:
|
||||||
|
|
||||||
<PackageInstall packageName="@medusajs/ui-preset" devDependency />
|
<PackageInstall packageName="@medusajs/ui-preset" devDependency />
|
||||||
|
|
||||||
After you have installed Tailwind CSS and the Medusa UI preset, you need to add the following to your `tailwind.config.js`file:
|
---
|
||||||
|
|
||||||
```tsx
|
## Step 3: Configure Tailwind CSS
|
||||||
|
|
||||||
|
Next, you'll need to configure Tailwind CSS to use the Medusa UI preset and explicitly add the paths to the Medusa UI components as content files.
|
||||||
|
|
||||||
|
### Tailwind CSS v3 Configurations
|
||||||
|
|
||||||
|
In Tailwind CSS v3, which is the recommended version to use with Medusa UI, you need to add the following configurations to your `tailwind.config.js` or `tailwind.config.ts` file:
|
||||||
|
|
||||||
|
1. Add the Medusa UI preset to the `presets` array.
|
||||||
|
2. Ensure that the `content` field includes the path to the Medusa UI package.
|
||||||
|
|
||||||
|
```js title="tailwind.config.js"
|
||||||
module.exports = {
|
module.exports = {
|
||||||
presets: [require("@medusajs/ui-preset")],
|
presets: [require("@medusajs/ui-preset")],
|
||||||
// ...
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
In order for the styles to be applied correctly to the components, you will also need to ensure that
|
|
||||||
`@medusajs/ui` is included in the content field of your `tailwind.config.js` file:
|
|
||||||
|
|
||||||
```tsx
|
|
||||||
module.exports = {
|
|
||||||
content: [
|
content: [
|
||||||
// ...
|
// ...
|
||||||
"./node_modules/@medusajs/ui/dist/**/*.{js,jsx,ts,tsx}",
|
"./node_modules/@medusajs/ui/dist/**/*.{js,jsx,ts,tsx}",
|
||||||
@@ -47,9 +61,9 @@ module.exports = {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
If you are working within a monorepo, you may need to add the path to the `@medusajs/ui` package in your `tailwind.config.js` like so:
|
If your project is in a monorepo, you'll need to resolve the path to the `@medusajs/ui` package from the monorepo root:
|
||||||
|
|
||||||
```tsx
|
```tsx title="tailwind.config.js"
|
||||||
const path = require("path")
|
const path = require("path")
|
||||||
|
|
||||||
const uiPath = path.resolve(
|
const uiPath = path.resolve(
|
||||||
@@ -59,6 +73,7 @@ const uiPath = path.resolve(
|
|||||||
)
|
)
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
|
presets: [require("@medusajs/ui-preset")],
|
||||||
content: [
|
content: [
|
||||||
// ...
|
// ...
|
||||||
uiPath,
|
uiPath,
|
||||||
@@ -68,24 +83,55 @@ module.exports = {
|
|||||||
|
|
||||||
```
|
```
|
||||||
|
|
||||||
## Start building
|
### Tailwind CSS v4 Configurations
|
||||||
|
|
||||||
|
Medusa UI isn't officially compatible with Tailwind CSS v4 yet, so use it with caution.
|
||||||
|
|
||||||
|
In your CSS file that imports Tailwind CSS, add the following `@config` and `@source` directives:
|
||||||
|
|
||||||
|
```css
|
||||||
|
@import "tailwindcss";
|
||||||
|
@source "../node_modules/@medusajs/ui";
|
||||||
|
@config "@medusajs/ui-preset";
|
||||||
|
```
|
||||||
|
|
||||||
|
This will explicitly include the Medusa UI preset and its components in your Tailwind CSS build, and will apply the preset styles to your project.
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
You are now ready to start building your application with Medusa UI. You can import the components like so:
|
## Step 4: Use Medusa UI in Standalone Projects
|
||||||
|
|
||||||
|
You can now start building your application with Medusa UI.
|
||||||
|
|
||||||
|
For example, you can use the `Button` in your custom components:
|
||||||
|
|
||||||
```tsx
|
```tsx
|
||||||
import { Button, Drawer } from "@medusajs/ui"
|
import { Button } from "@medusajs/ui"
|
||||||
|
|
||||||
|
export function ButtonDemo() {
|
||||||
|
return <Button>Button</Button>
|
||||||
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
Refer to the documentation of each component to learn about its props and usage.
|
||||||
|
|
||||||
<Feedback title={"Install in Standalone Project"} />
|
<Feedback title={"Install in Standalone Project"} />
|
||||||
|
|
||||||
## Updating UI Packages
|
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
Medusa's design-system packages, including `@medusajs/ui`, `@medusajs/ui-preset`, and `@medusajs/ui-icons`, are versioned independently. However, they're still part of the latest Medusa release. So, you can browse the [release notes](https://github.com/medusajs/medusa/releases) to see if there are any breaking changes to these packages.
|
## Update UI Packages in Standalone Projects
|
||||||
|
|
||||||
To update these packages, update their version in your `package.json` file and re-install dependencies. For example:
|
Medusa's design-system packages, including `@medusajs/ui` and `@medusajs/ui-preset`, are versioned independently from other `@medusajs/*` packages. However, they're still released as part of Medusa's releases.
|
||||||
|
|
||||||
<PackageInstall packageName="@medusajs/ui" />
|
So, to find latest updates and breaking changes to any of these packages, refer to the [release notes in the Medusa GitHub repository](https://github.com/medusajs/medusa/releases).
|
||||||
|
|
||||||
|
To update these packages in your standalone project, update their version in your `package.json` file and re-install dependencies. For example:
|
||||||
|
|
||||||
|
```json title="package.json"
|
||||||
|
{
|
||||||
|
"dependencies": {
|
||||||
|
"@medusajs/ui": "4.0.0",
|
||||||
|
"@medusajs/ui-preset": "4.0.0"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
Reference in new issue
Block a user