DEV Community

Cover image for Rendering markdown in Vue 3
Matija Novosel
Matija Novosel

Posted on • Originally published at matijanovosel.com

Rendering markdown in Vue 3

Introduction

Markdown can be incredibly useful for displaying and storing formatted text. For instance the famous readme.md files that can come with a repository.

The syntax is simple - yet effective. A rudimentary example for instance would be a table:

| Syntax    | Description |
| --------- | ----------- |
| Header    | Title       |
| Paragraph | Text        |
Enter fullscreen mode Exit fullscreen mode

Which results in the following:

Syntax Description
Header Title
Paragraph Text

Or perhaps, a list:

- Bacon
- Ham
- Eggs
Enter fullscreen mode Exit fullscreen mode

Touché:

  • Bacon
  • Ham
  • Eggs

So, how does one turn the unformatted markdown text into something more suited for the viewing eyes?

Thankfully someone had already made a tool for this called markdown-it, otherwise you'd have to make your own parser which would be a pain.

Markdown-it

Markdown-it is a javascript markdown parser, exported as a function which produces pure HTML that someone can use however they like. Also it has a great array of plugins and features, as explained on the GitHub page.

Making a Vue component out of it is incredibly easy, the only requirement being that you install and import the markdown-it function and use the render method after setting a few parameters.

Requirements and plugins

First things first - installing the dependencies.

The most important one being markdown-it itself:

npm i markdown-it

or

yarn add markdown-it

The other, more useful, plugins are recommended as some features are not supported by markdown-it by default:

Writing the component

After importing the markdown-it package and its plugins, one can generate an output using the render method:

import MarkdownIt from "markdown-it";

const markdown = new MarkdownIt();

markdown.render("# Header");
Enter fullscreen mode Exit fullscreen mode

Which should, as a result, produce the following:

<h1>Header</h1>
Enter fullscreen mode Exit fullscreen mode

You can also throw in the plugins we mentioned before:

const markdown = new MarkdownIt()
  .use(MarkdownItAbbr)
  .use(MarkdownItAnchor)
  .use(MarkdownItFootnote)
  .use(MarkdownItHighlightjs)
  .use(MarkdownItSub)
  .use(MarkdownItSup)
  .use(MarkdownItTasklists);
Enter fullscreen mode Exit fullscreen mode

The rest is just defining a string prop the component should use to display the desired text and using the regular Vue syntax:

<template>
  <div v-html="markdown.render(source)" />
</template>

<script setup lang="ts">
import MarkdownIt from "markdown-it";
import MarkdownItAbbr from "markdown-it-abbr";
import MarkdownItAnchor from "markdown-it-anchor";
import MarkdownItFootnote from "markdown-it-footnote";
import MarkdownItHighlightjs from "markdown-it-highlightjs";
import MarkdownItSub from "markdown-it-sub";
import MarkdownItSup from "markdown-it-sup";
import MarkdownItTasklists from "markdown-it-task-lists";
import MarkdownItTOC from "markdown-it-toc-done-right";

const markdown = new MarkdownIt()
  .use(MarkdownItAbbr)
  .use(MarkdownItAnchor)
  .use(MarkdownItFootnote)
  .use(MarkdownItHighlightjs)
  .use(MarkdownItSub)
  .use(MarkdownItSup)
  .use(MarkdownItTasklists)
  .use(MarkdownItTOC);

defineProps({
  source: {
    type: String,
    default: ""
  }
});
</script>
Enter fullscreen mode Exit fullscreen mode

And use as so:

<MarkdownRenderer :source="'# Hi!!'" />
Enter fullscreen mode Exit fullscreen mode

Top comments (0)