0.1.6 • Published 7 months ago

@iandx/markit v0.1.6

Weekly downloads
-
License
-
Repository
-
Last release
7 months ago

Markit

A powerful markdown parser and renderer for react

  • 👐 build for high extensibility
  • ⚡️ yet still very fast
  • 💫 best practice for react
  • ✨ incremental parsing to avoid unnecessary dom re-render
  • 🎨 easy to customize

Install

npm install @iandx/markit

Quick start

import { ReactMarkit } from '@iandx/markit';
function App () {
    const content = '# Welcome to **use** *Markit*';
    return(
        <ReactMarkit content={content}/>
    )
}

Usage

ReactMarkit

  • Basic React component. Give it a content or children prop as its rendering content

    Use whichever you like

let content = "* this is a list"
const Markit1 = () => 
    <ReactMarkit content={content} />
const Markit2 = () =>
    <ReactMarkit>{content}<ReactMarkit/>

Markit

Global init markit

import {Markit} from "@iandx/markit"
Markit.init({
    tabSpaceNum: 2,
    softBreak: true,
    geneId: false
})
propertiestypedefaultdescription
tabSpaceNumnumber2a tab "\t" equals to how many spaces
softBreaknumbertrueif set "true", "\n" will be recognized as a soft break instead of a new line
geneIdnumberfalsegive each AST a unique id, useful for increnmental parsing

Default rules and drop rules

  • Inline

    typedescription
    Bold**bold**
    Italic*italic*
    Strike~~strike through~~
    Underline\<u>underline\<u>, _!also underline!_
    Code`code`
    Link[link title](link_url)
    Escapecharacter like \*, \_, \~
    Superscript\^superscript\^
    Subscript~subscript~
    Highlight\=\=hightlight\=\=
    HtmlTag\<anyTag>content</anyTag>
    Math\$latex math formula like \frac{1}{2}\$
    FootnoteSup[\^footnotesup] will link to the end of the page
    LinkTaglink tag will be a link if supply a link block

    if you don't want some provided inline features, you can easily drop it by using

    import {Markit} from "@iandx/markit"
    Markit.dropRule.inline(["Math", "LinkTag"])
  • block

    typeblockTypedescription
    Headingleaf# this is heading1this is also heading1\=\=\=\==
    Blockquoteleaf> blockquote>> level2
    CodeBlockleaf``` javascript function test() {console.log("hi")}`
    Dividerleaf----dashed
    Imageleaf![alt_content](url hover_title 50% center)
    MathBlockleaf\$\$Math block \sqrt{a}\$\$
    Latexleaf\$\$\$Latex block \sqrt{a}\$\$\$
    Footnoteleaf[^footnotesup]: content
    LinkTagBlockleaf[^linkTag]: replaced url
    Commentleaf// any comment
    UnorderedListcontainer* unordered list+ also unordered list- still unordered list
    OrderedListcontainer1. OrderedList1. will display 2 in this line
    CheckListcontainer- x GFM to-do list

    if you don't want some provided inline features, you can easily drop it by using

    import {Markit} from "@iandx/markit"
    Markit.dropRule.block(["Comment", "Image", "Divider"])

Add new rules

inline First we will introduce the structure of the syntax rule. Following are the properties.

tags An object to define syntax token. You may use the following properties to config.

  • leading A String which will be recognized as syntax token used before text, e.g. '##'
  • round A String which will be recognized as syntax token used around text, e.g. '**'
  • wrap A array which will be recognized as syntax token used in the left and right of the text. e.g. '',''
  • exact A String or a regular expression

trimText A callback function which recieves a raw text and usually returns the text after triming the tags. Note: using leading, round, wrap, the parser will help you trim the tags token by default

parseContent A callback function which recieve the trimmed text

getProps A callback function which recieve the raw text, get the additional props, then return.

recheckMatch A callback function which recieve the raw text to recheck if the raw text match the syntax token.

order

Now, you may use addRule to custom your own syntax.

addRule({name,rule,view})

  • name A string used to identify the rule.
  • rule A object introducing before to describe the custom syntax.
  • view A function which returns a React component matching your custom token.

Following is an example.

// add a block syntax
Markit.addRule.block({
    name: "CustomHeading",
    rule: {
        tags: {
            leading: /#{1,5} /, 
            exact: [/(?:\n|^).+?\n===+ */, /(?:\n|^).+? ?\n---+ */]
        },
    getProps: (raw) => {
        let headingLevel: number
        let hashHeadingMatch = raw.match(/^#+ /)
        if (hashHeadingMatch) {
        headingLevel = hashHeadingMatch![0].trim().length
        } else {
        let heading1Match = raw.match(/\n===+/)
        headingLevel = !!heading1Match ? 1 : 2
        }
        return {headingLevel}
    },
    trimText: raw => raw.replaceAll(/\n((===+)|(---+))/g, "").replaceAll(/^#{1,5} /g, ""),
    parseContent: text => text,
    recheckMatch: raw => {
        return true
    },
    blockType: "leaf"
    },
    view: (content: any, {headingLevel, blockProp}) =>
    Span(content+(!!blockProp ? blockProp.a:"")).fontSize(`${(5 - (headingLevel ?? 1)) * 6 + 15}px`)
    })

// add a inline syntax
Markit.addRule.inline({
    name: "Italic",
    rule: {
        tags: {
            round: "[em]",
            exact: [
                /\*(?!\s)(?:(?:[^*]*?(?:\*\*[^*]+?\*\*[^*]*?)+?)+?|[^*]+)\*/,
            ]
        },
        trimText: (text: string) => text.replace(/^\*|\*$/g, ""),
    },
    // view:  (content) => ()
})

you may use dropRuleto remove one of the syntax rule.

// remove a block syntax rule
Markit.dropRule.block(["Heading"])

// remove a inline syntax rule
Markit.dropRule.inline(["Italic"])

Advanced

MarkitView

API

Markit

API

functiondescriptionparameter
initto certain props init a Markitobject
parsereturn a markdonwerTree arraystring

Usage

import { Markit } from '@iandx/markit'

Markit.init({softBreak: false})
const markitASTs = Markit.parse('## Markit **fast** ')

MarkdonwerTree

Markit.parse will parse the text iteratively where there is a markdown syntax. We design a tree to contain the parsed result called MarkdonwerTrees.

Note: The type of leaf node must be "Text" or "Heading"

The node of MarkdonwerTree has the following properties.

propertiesdescriptiontypevalue
contentits children which are also the markdownTrees or string
idblock id
levelblock level or inline levelstring"block"/"inline"
propsadditional propertiesobject
rawthe text inclues markdown syntaxstring
typethe markdown type. e.g."OrderedList", "Heading"string

Custom Syntax

0.1.4

10 months ago

0.1.6

7 months ago

0.1.5

10 months ago

0.1.3

11 months ago

0.1.2

1 year ago

0.1.1

1 year ago

0.1.0

1 year ago

0.0.6

1 year ago

0.0.5

1 year ago

0.0.4

1 year ago

0.0.3

1 year ago

0.0.2

1 year ago

0.0.1

1 year ago