Skip to content

Instantly share code, notes, and snippets.

@Robert-96
Last active July 22, 2020 18:55
Show Gist options
  • Save Robert-96/5591eaa07cb56500505a5daa747e2d0b to your computer and use it in GitHub Desktop.
Save Robert-96/5591eaa07cb56500505a5daa747e2d0b to your computer and use it in GitHub Desktop.
Ember.Js: Build a Markdown component with ShowdownJs

Ember.Js: Build a Markdown component with ShowdownJs

With the help of ShowdownJs and HighlightJs you can build an Markdown component with syntax highlighting.

ShowdownJs is an easy to use Markdown to HTML converter, it can be used in both client side (browser) or server side (with nodejs).

HighlightJs is an JavaScript library for syntax highlighting on the web. It supports 189 languages and 94 styles.

Let's build component for rendering markdown with ShowdownJs and HighlightJs.

Table of contents

Create a MarkdownView component

Install the ShowdownJs library from npm or yarn:

# Using npm
$ npm install showdown --save-dev

# Using yarn
$ yarn add showdown --dev

Now you need create a <MarkdownView /> component, and use ShowdownJs to convert the markdown into HTML:

$ ember g component markdown-view -gc 
// app/components/markdown-view.js

import Component from '@glimmer/component';
import { htmlSafe } from '@ember/template';
import showdown from 'showdown';

const converter = new showdown.Converter()

export default class MarkdownViewComponent extends Component {
  get html() {
    return htmlSafe(converte.makeHtml(this.args.markdown))
  }
}
{{! app/components/markdown-view.hbs }}

{{html}}

You can easily pass in the markdown from one of your routes.

// app/routes/post.js
import Route from '@ember/routing/route';

export default class PostRoute extends Route {
  model() {
    return '# Hello Ember!';
  }
}
// templates/posts.hbs

<MarkdownView @markdown={{@model}} />

Add syntax highlighting using HighlightJs (Optional)

Let's add syntax highlighting to the <MarkdownView /> component using HighlightJs.

Install the HighlightJs library from npm or yarn:

# Using npm
$ npm install highlight.js --save-dev 

# Using yarn
$ yarn add highlight.js --dev 

Now you need update the <MarkdownView /> component:

// app/components/markdown-view.js

import Component from '@glimmer/component';
import { htmlSafe } from '@ember/template';
import showdown from 'showdown';
import hljs from 'highlight.js';

showdown.extension('highlight', function () {
  return [{
    type: "output",
    filter: function (text) {
      var left = "<pre><code\\b[^>]*>",
          right = "</code></pre>",
          flags = "g";

      var replacement = function (wholeMatch, match, left, right) {
        var lang = (left.match(/class="([^ "]+)/) || [])[1];
        left = left.slice(0, 18) + 'hljs ' + left.slice(18);

        if (lang && hljs.getLanguage(lang)) {
          return left + hljs.highlight(lang, match).value + right;
	} else {
          return wholeMatch;
	}
      };

      return showdown.helper.replaceRecursiveRegExp(text, replacement, left, right, flags);
    }
  }];
});

const converter = new showdown.Converter({extensions: ['highlight']})

export default class MarkdownViewComponent extends Component {
  get html() {
    return htmlSafe(converte.makeHtml(this.args.markdown))
  }
}

Finally, you need to import a Highlight.js theme. You can do that by importing the CSS file from node_modules in your ember-cli-build.js file with app.import:

// ember-cli-build.js

// .. 

module.exports = function(defaults) {
  // ... 
  
  app.import('node_modules/highlight.js/styles/default.css');
  
  return app.toTree();
};

You can found here a list of all Highlight.js themes and languages.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment