npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

react-marked-renderer

v2.0.1

Published

React Marked Renderer - React components for the marked library

Downloads

1,063

Readme

React Marked Renderer license codecov Main npm npm bundle size

A low-level component wrapper for marked that renders as React components instead of strings.

Check out the playground website to see how markdown is rendered with the default renderers or custom renderers and the API Documentation.

Installation

npm install react react-marked-renderer

Or with yarn:

yarn add react react-marked-renderer

Features

  • render almost everything that is available by GitHub flavored markdown out of the box
    • the only exception is rendering html code itself
  • allow custom renderers to implement complex components if desired or custom styles
  • allows code highlighting
    • allow code language aliases/resolution with getLanguage
    • in the browser with highlightElement (can be asynchronous)
    • in node environments with highlightCode (synchronous only)

Note: Since the marked.lexer does not support custom extensions, neither does this library. I would like to support this feature in the future.

Usage

The main component within this library is the Markdown component.

Check out the Markdown tests and Markdown snapshots to see the default functionality.

Simple Example

import { render } from "react-dom";
import { Markdown } from "react-marked-renderer";

const markdown = `# Heading 1

This is some text that will be rendered as a paragraph.

Markdown defaults to the github-flavored markdown.
`;

render(<Markdown markdown={markdown} />, document.getElementById("root"));

Custom Renderers

Since the default renderers add no styles, you can define your own renderers to add styles or additional functionality.

import { useState } from "react";
import { render } from "react-dom";
import {
  DEFAULT_MARKDOWN_RENDERERS,
  ListRenderer,
  Markdown,
  Renderers,
  getTokensText,
} from "react-marked-renderer";
import { BrowserRouter as Router, Link } from "react-router-dom";

const renderers: Renderers = {
  ...DEFAULT_MARKDOWN_RENDERERS,
  link: function CustomLink({ href, title, children }) {
    // make links use html5 history and not cause reloads
    return (
      <Link to={href} title={title}>
        {children}
      </Link>
    );
  },

  blockquote: function Blockquote({ children }) {
    return <blockquote className="custom">{children}</blockquote>;
  },

  task: function Task({ defaultChecked, tokens, children }) {
    // hooks can be used in these renderers
    const id = useSluggedId(`${getTokensText(tokens)}-task`);
    const [checked, setChecked] = useState(defaultChecked);
    return (
      <li className="task-item">
        <input
          id={id}
          checked={checked}
          onChange={(event) => setChecked(event.currentTarget.checked)}
        />
        <label htmlFor={d}>{children}</label>
      </li>
    );
  },

  list: function List(props) {
    // can get the current renderers as well
    const renderers = useRenderers();
    const { listitem: ListItem } = renderers;
    const item = <ListItem>Content</ListItem>;

    // or just return the default renderer
    return <ListRenderer {...props} />;
  },
};

render(
  <Router>
    <Markdown markdown={markdown} renderers={renderers} />
  </Router>,
  document.getElementById("root")
);

PrismJS Code Highlighting (Browser)

To be able to highlight code in the browser, provide a highlightElement function that will modify a <code> element to be highlighted:

import { render } from "react-dom";
import {
  DEFAULT_MARKDOWN_RENDERERS,
  Markdown,
  Renderers,
} from "react-marked-renderer";
import Prism from "prismjs";
// import prism theme/components or use `babel-plugin-prismjs`

const renderers: Renderers = {
  ...DEFAULT_MARKDOWN_RENDERERS,
  codespan: function CodeSpan({ children }) {
    // just so it gets some prism styling
    return <code className="language-none">{children}</code>;
  },
};

render(
  <Markdown
    markdown={markdown}
    renderers={renderers}
    highlightElement={Prism.highlightElement}
  />,
  document.getElementById("root")
);

PrismJS Code Highlighting (Node and Browser)

If you want to highlight code in a node environment or allow the code to be highlighted for SSR and in the browser, provide a highlightCode function:

import { render } from "react-dom";
import {
  DEFAULT_MARKDOWN_RENDERERS,
  DangerouslyHighlight,
  GetCodeLanguage,
  Markdown,
  Renderers,
} from "react-marked-renderer";
import Prism from "prismjs";

const renderers: Renderers = {
  ...DEFAULT_MARKDOWN_RENDERERS,
  codespan: function CodeSpan({ children }) {
    // just so it gets some prism styling
    return <code className="language-none">{children}</code>;
  },
};

const getLanguage: GetCodeLanguage = (lang, _rawCode) => {
  // allow aliases
  lang = lang === "sh" ? "shell" : lang;

  // if the Prism doesn't support the language, default to nothing instead
  // of crashing
  if (!Prism.languages[lang]) {
    return "none";
  }

  return lang;
};

const highlightCode: DangerouslyHighlightCode = (code, lang) =>
  Prism.highlight(code, Prism.languages[lang], lang);

render(
  <Markdown
    markdown={markdown}
    renderers={renderers}
    getLanguage={getLanguage}
    highlightCode={highlightCode}
  />,
  document.getElementById("root")
);

What's the use-case?

This library mostly came up since I like to write documentation sites in markdown, but also apply custom styles as well as linking to other documentation pages using html5 history (no full page reloads).