Prism code highlight

Code highlight with Mantine theme colors and styles
Import
License

Installation

Package depends on @mantine/core and @mantine/hooks.

Install with yarn:

yarn add @mantine/prism

Install with npm:

npm install @mantine/prism

Usage

Use Prism component to highlight code with Mantine theme styles. Component uses prism-react-renderer under the hood and supports light and dark theme, it is used in Mantine docs to display all code examples.

import { Button } from '@mantine/core';
function Demo() {
return <Button>Hello</Button>
}
import { Prism } from '@mantine/prism';
const demoCode = `import { Button } from '@mantine/core';
function Demo() {
return <Button>Hello</Button>
}`;
function Demo() {
return <Prism language="tsx">{demoCode}</Prism>;
}

Line numbers

Set withLineNumbers prop to display line numbers:

1
import { Button } from '@mantine/core';
2
3
function Demo() {
4
return <Button>Hello</Button>
5
}
import { Prism } from '@mantine/prism';
function Demo() {
return <Prism withLineNumbers language="tsx">{/* ...code */}</Prism>;
}

Lines highlight

To highlight individual lines use highlightLines prop with object containing line numbers as keys and highlight options as values. Highlight options include color from theme.colors and label which replaces line number:

1
import { Button } from '@mantine/core';
2
-
function Demo() {
-
return <Button>Hello</Button>
-
}
6
+
function Usage() {
+
return <ActionIcon>Hello</ActionIcon>;
+
}
import { Prism } from '@mantine/prism';
const deleted = { color: 'red', label: '-' };
const added = { color: 'green', label: '+' };
function Demo() {
return (
<Prism
language="tsx"
withLineNumbers
highlightLines={{
3: deleted,
4: deleted,
5: deleted,
7: added,
8: added,
9: added,
}}
>
{/* ...code */}
</Prism>
);
}

Copy button

To remove copy button set noCopy prop. Copy button labels can be changed with copyLabel and copiedLabel props:

import { Button } from '@mantine/core';
function Demo() {
return <Button>Hello</Button>
}
import { Button } from '@mantine/core';
function Demo() {
return <Button>Hello</Button>
}
import { Prism } from '@mantine/prism';
function Demo() {
return (
<>
<Prism noCopy language="tsx">{/* ...code */}</Prism>
<Prism
language="tsx"
copyLabel="Copy code to clipboard"
copiedLabel="Code copied to clipboard"
>
{/* ...code */}
</Prism>
</>
);
}

Native scrollbars

By default, Prism uses ScrollArea component to handle overflow content, to replace it with native scrollbars set scrollAreaComponent="div":

With ScrollArea component (default):
<p>
Long code that will force Prism to have a horizontal scrollbar, by default, scroll behavior is handled by ScrollArea component, but it can be changed to native browser scrollbars
</p>
With native scrollbars:
<p>
Long code that will force Prism to have a horizontal scrollbar, by default, scroll behavior is handled by ScrollArea component, but it can be changed to native browser scrollbars
</p>
import { Text } from '@mantine/core';
import { Prism } from '@mantine/prism';
const longCode = `
<p>
Long code that will force Prism to have a horizontal scrollbar, by default, scroll behavior is handled by ScrollArea component, but it can be changed to native browser scrollbars
</p>
`;
function Demo() {
return (
<>
<Text mb={5}>With ScrollArea component (default):</Text>
<Prism language="tsx">{longCode}</Prism>
<Text mb={5} mt="xl">With native scrollbars:</Text>
<Prism language="tsx" scrollAreaComponent="div">{longCode}</Prism>
</>
);
}

With tabs

To display multiple files use Prism.Tabs component, it supports the same props as Tabs component:

@font-face {
font-family: Chunkfive; src: url('Chunkfive.otf');
}
body, .usertext {
color: #F0F0F0; background: #600;
font-family: Chunkfive, sans;
--heading-1: 2rem/2rem Helvetica, sans-serif;
}
@import url(print.css);
@media print {
a[href^=http]::after {
content: attr(href)
}
}
@requires_authorization
def somefunc(param1='', param2=0):
r'''A docstring'''
if param1 > param2: # interesting
print 'Gre\'ater'
return (param2 - param1 + 1 + 0b10l) or None
class SomeClass:
pass
>>> message = '''interpreter
... prompt'''
import { Button } from '@mantine/core';
function Demo() {
return <Button>Hello</Button>
}

Force dark/light theme

You can force dark/light color scheme by setting colorScheme prop:

import { Button } from '@mantine/core';
function Demo() {
return <Button>Hello</Button>
}
import { Prism } from '@mantine/prism';
function Demo() {
return <Prism colorScheme="dark" language="tsx">{/* ...code */}</Prism>;
}

Custom themes

Use getPrismTheme prop to change prism colors. You can use premade themes from prism-react-renderer package or build your own using Mantine theme colors. getPrismTheme prop accepts a function with two arguments: first is Mantine theme object, second is color scheme (light or dark). The function must return prism theme object:

import { Button } from '@mantine/core';
function Demo() {
return <Button>Hello</Button>
}
import duotoneDark from 'prism-react-renderer/themes/duotoneDark';
import duotoneLight from 'prism-react-renderer/themes/duotoneLight';
import { Prism } from '@mantine/prism';
const demoCode = `import { Button } from '@mantine/core';
function Demo() {
return <Button>Hello</Button>
}`;
function Demo() {
return (
<Prism
language="tsx"
getPrismTheme={(_theme, colorScheme) =>
colorScheme === 'light' ? duotoneLight : duotoneDark
}
>
{demoCode}
</Prism>
);
}

Languages

Component supports all languages which are supported by prism-react-renderer:

package main
import "fmt"
func main() {
ch := make(chan float64)
ch <- 1.0e10 // magic number
x, ok := <- ch
defer fmt.Println(`exitting now`)
go println(len("hello world!"))
return
}
@requires_authorization
def somefunc(param1='', param2=0):
r'''A docstring'''
if param1 > param2: # interesting
print 'Gre\'ater'
return (param2 - param1 + 1 + 0b10l) or None
class SomeClass:
pass
>>> message = '''interpreter
... prompt'''
@font-face {
font-family: Chunkfive; src: url('Chunkfive.otf');
}
body, .usertext {
color: #F0F0F0; background: #600;
font-family: Chunkfive, sans;
--heading-1: 2rem/2rem Helvetica, sans-serif;
}
@import url(print.css);
@media print {
a[href^=http]::after {
content: attr(href)
}
}
CREATE TABLE "topic" (
"id" serial NOT NULL PRIMARY KEY,
"forum_id" integer NOT NULL,
"subject" varchar(255) NOT NULL
);
ALTER TABLE "topic"
ADD CONSTRAINT forum_id FOREIGN KEY ("forum_id")
REFERENCES "forum" ("id");
-- Initials
insert into "topic" ("forum_id", "subject")
values (2, 'D''artagnian');

Load additional languages

View Java language example on codesandbox

By default, prism-react-renderer only includes an arbitrary subset of the languages that Prism supports. You can add support for more by including their definitions from the main prismjs package:

import Prism from 'prism-react-renderer/prism';
(typeof global !== 'undefined' ? global : window).Prism = Prism;
require('prismjs/components/prism-kotlin');
require('prismjs/components/prism-csharp');

Prism component props

NameTypeDescription
children *
string
Code which will be highlighted
colorScheme
"light" | "dark"
Force color scheme, defaults to theme.colorScheme
copiedLabel
string
Copy button tooltip in copied state
copyLabel
string
Copy button tooltip
getPrismTheme
(theme: MantineTheme, colorScheme: "light" | "dark") => PrismTheme
Provide custom color scheme
highlightLines
Record<string, { color: DefaultMantineColor; label?: string; }>
Highlight line at given line number with color from theme.colors
language *
"c" | "go" | "markup" | "bash" | "clike" | "cpp" | "css" | "javascript" | "jsx" | "coffeescript" | "actionscript" | "css-extr" | "diff" | "git" | "graphql" | "handlebars" | "json" | "less" | "makefile" | "markdown" | "objectivec" | "ocaml" | "python" | "reason" | "sass" | "scss" | "sql" | "stylus" | "tsx" | "typescript" | "wasm" | "yaml"
Programming language that should be highlighted
noCopy
boolean
True to remove copy to clipboard button
radius
number | "xs" | "sm" | "md" | "lg" | "xl"
Key of theme.radius or any valid CSS value to set border-radius, theme.defaultRadius by default
scrollAreaComponent
any
Change scroll area component
trim
boolean
Defines whether the code should be trimmed, defaults to true
withLineNumbers
boolean
Display line numbers

Prism component Styles API

NameStatic selectorDescription
root.mantine-Prism-rootRoot element
scrollArea.mantine-Prism-scrollAreaScrollArea component wrapping pre element
code.mantine-Prism-codePre element which contains code
copy.mantine-Prism-copyCopy button wrapper
line.mantine-Prism-lineLine wrapper, contains line number and content
lineNumber.mantine-Prism-lineNumberLine number
lineContent.mantine-Prism-lineContentLine content