diff --git a/Cargo.lock b/Cargo.lock index 496051a..5408e17 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2315,7 +2315,7 @@ checksum = "fe0f37c9e8f3c5a4a66ad655a93c74daac4ad00c441533bf5c6e7990bb42604e" [[package]] name = "snekdown" -version = "0.33.2" +version = "0.33.3" dependencies = [ "asciimath-rs", "base64 0.12.3", diff --git a/Cargo.toml b/Cargo.toml index aecb5dc..6714646 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,9 +1,9 @@ [package] name = "snekdown" -version = "0.33.2" +version = "0.33.3" authors = ["trivernis "] edition = "2018" -license-file = "LICENSE" +license = "GPL-3.0" readme = "README.md" description = "A parser for the custom snekdown markdown syntax" repository = "https://github.com/Trivernis/snekdown" diff --git a/README.md b/README.md index a57061d..6622eb9 100644 --- a/README.md +++ b/README.md @@ -1,465 +1,90 @@ -# ![](https://i.imgur.com/FpdXqiT.png) Snekdown - More than just Markdown ![](https://img.shields.io/discord/729250668162056313) - +

+ +

+

Snekdown

+

+More than just Markdown +

+

+ + + + +
+
+Documentation | +Releases +

+ +- - - + +## Description This projects goal is to implement a fast markdown parser with an extended syntax fitted for my needs. -## Installation - -You need a working rust installation, for example by using [rustup](http://rustup.rs). - -```sh -cargo install snekdown -``` - -With pdf rendering - -```sh -cargo install snekdown --features pdf -``` - -## Usage - -``` -snekdown 0.30.5 - -USAGE: - snekdown - -FLAGS: - -h, --help Prints help information - -V, --version Prints version information - -SUBCOMMANDS: - clear-cache Clears the cache directory - help Prints this message or the help of the given subcommand(s) - render Parse and render the document - watch Watch the document and its imports and render on change -``` - -### Rendering - -``` -Parse and render the document - -USAGE: - snekdown render [OPTIONS] - -FLAGS: - -h, --help Prints help information - -V, --version Prints version information - -OPTIONS: - -f, --format the output format [default: html] - -ARGS: - Path to the input file - Path for the output file - -``` - -### Watching - -``` -Watch the document and its imports and render on change - -USAGE: - snekdown watch [OPTIONS] - -FLAGS: - -h, --help Prints help information - -V, --version Prints version information - -OPTIONS: - --debounce The amount of time in milliseconds to wait after changes before rendering [default: - 500] - -f, --format the output format [default: html] - -ARGS: - Path to the input file - Path for the output file -``` - - -## Syntax - -### Images - -```md -Simple Syntax -!(url) - -Extended syntax with a description -![description](url) - -Extended syntax with metadata to specify the size -![description](url)[metadata] - -Extended syntax with metadata and no description -!(url)[metadata] -``` - -When generating the html file the images are base64 embedded. To turn off this behaviour -set the config parameter `embed-external` to `false`. - -### Quotes - -```md -Simple (default) Syntax -> This is a quote - -Multiline -> This is a -> Multiline Quote - -Quote with metadata (e.g. Author) -[author=Trivernis year=2020 display='{{author}} - {{year}}']> This is a quote with metadata -``` - - -### Imports - -Imports can be used to import a different document to be attached to the main document. -Imports are parsed via multithreading. - -```md -<[path] - -<[document.md] - -<[style.css][type=stylesheet] -``` - -The parser differentiates four different types of imported files. - -- `document` - The default import which is just another snekdown document -- `stylesheet` - CSS Stylesheets that are inclued when rendering -- `bibliography` - A file including bibliography -- `config`/`manifest` - A config file that contains metadata - -If no type is provided the parser guesses the type of file from the extension. - -### Tables - -Tables MUST start with a pipe character `|` - -```md -Standalone header: -| header | header | header - -Header with rows -| header | header | header -|--------|--------|------- -| row | row | row -``` - -### Placeholders - -Placeholders can be used to insert special elements in a specific place. -Placeholders are always case insensitive. - -```md -Insert the table of contents -[[TOC]] - -Insert the bibliography list -[[BIB]] - -Insert the glossary -[[GLS]] - -Insert the current date -[[date]] - -Insert the current time -[[time]] -``` - -### Metadata - -Additional metadata can be provided for some elements. - -```md -String value -[key = value] - -String value -[key = "String value"] +## Core Features -Integer value -[key = 123] +- Imports +- Bibliography & Glossary +- AsciiMath +- Placeholders +- Advanced Images -Float value -[key = 1.23] -Boolean -[key] - -Boolean -[key = false] - -Placeholder -[key = [[placeholder]]] -``` - -Metadata can also be defined in a separate toml file with simple key-value pairs. -The file `Manifest.toml` will always be included by default. -Example: - -```toml -# document metadata -[metadata] -# language setting of the document -language = 'en' - -# author of the document -author = 'author' - -# Title of the document -title = 'title' - -# A short description for the document preview -description = ''' -Description -''' - -# Keywords to find the document -keywords = ['HTML', 'Snekdown'] - - -# features used in the document -[features] - -# if external sources (images, stylesheets, MathJax) -# should be embedded into the document (default: true) -embed_external = true - -# If SmartArrows should be used (default: true) -smart_arrows = true -include_mathjax = true - - -[imports] -# those files won't get imported -ignored_imports = [] - -# stylesheets that should be included -included_stylesheets = ['style.css'] - -# bibliography that should be included -included_bibliography = ['Bibliography.toml'] - -# glossary that sould be included -included_glossaries = ['Glossary.toml'] - - -# settings related to pdf rendering -[pdf] - -# If the header and footer of the pdf should be displayed (default: true) -display_header_footer = true - -# PDF header template of each page (default: '
') -header_template = '
' - -# PDF footer template of each page (default: see chromium_pdf assets) -footer_template = ''' -
- / -
''' - -# The scale at which the website is rendered into pdf. -page_scale = 1.0 - -# margin of the pdf document -[pdf.margin] - -# Top margin of the pdf. Should be between 0 and 1. (default: 0.5) -top = 0.5 - -# Bottom margin of the pdf. Should be between 0 and 1. (default: 0.5) -bottom = 0.5 - -# Left margin of the pdf. Should be between 0 and 1. -left = 0 - -# Right margin of the pdf. Should be between 0 and 1. -right = 0 - - -# image settings -[images] - -# Force convert images to the specified format. -# Supported formats are png, jpeg, gif, bmp, (ico needs size <= 256), avif, pnm -# (default: keep original) -format = "png" - -# the max width for the images. -# if an image is larger than that it get's resized. -# (default: none) -max_width = 700 - -# the max width for the images. -# if an image is larger than that it get's resized. -# (default: none) -max_height = 500 - - -# Visual adjustments -[style] -# how bibliography references should be displayed -bib_ref_display = '{{number}}' - -# the chosen theme for the document -# one of: GithubLight, SolarizedLight, OceanLight, SolarizedDark, OceanDark, MagicDark -theme = 'GithubLight' - -# custom metadata -# String -> String Mappings -[custom_attributes] -custom_key1 = "Custom Value" -``` - -The `[Section]` keys are not relevant as the structure gets flattened before the values are read. - - -#### Usage - -``` -Hide a section (including subsections) in the TOC -#[toc-hidden] Section - -Set the size of an image -!(url)[width = 42%, height=auto, brightness=10, contrast=1.2, huerotate=180, invert, grayscale] - -Set the source of a quote -[author=Me date=[[date]] display="{{author}} - {{date}}"]> It's me - -Set options for placeholders -[[toc]][ordered] -``` - -### Centered Text - -``` -|| These two lines -|| are centered -``` +## Installation -### Inline - -```md -*Italic* -**Bold** -~~Striked~~ -_Underlined_ -^Superscript^ -`Monospace` -:Emoji: -§[#0C0]Colored text§[] §[red] red §[] -``` +### Binaries -## Bibliography +You can download prebuilt binaries on the [Releases](https://github.com/Trivernis/snekdown/releases) Page. -Bibliography entries can be defined and referenced anywhere in the document. -Definition: -```md -[SD_BOOK]:[type=book, author=Snek, title = "Snekdown Book" date="20.08.2020", publisher=Snek] -[SD_GITHUB]: https://github.com/trivernis/snekdown -``` +### Arch Linux -Usage: -``` -There is a book about snekdown[^SD_BOOK] and a github repo[^SD_GITHUB]. -``` +Snekdown is available in [the AUR](https://aur.archlinux.org/packages/snekdown). -Entries can also be defined in a separate toml file with the following data layout: -```toml -# snekdown.toml -[BIB_KEY] -key = "value" +### Cargo -[SD_BOOK] -type = "book" -author = "Snek" -title = "Snekdown Book" -date = "20.08.2020" -publisher = "Snek" +You need a working rust installation, for example by using [rustup](http://rustup.rs). -[SD_GITHUB] -type = "website" -url = "https://github.com/trivernis/snekdown" +```sh +cargo install snekdown ``` -The valid types for entries and required fields can be found on in the [bibliographix README](https://github.com/Trivernis/bibliographix#bibliography-types-and-fields). - -Bibliography entries are not rendered. To render a list of used bibliography insert the -`bib` placeholder at the place you want it to be rendered. - - -## Glossary - -Glossary entries are to be defined in a `glossary.toml` file or any other toml file -that is imported as type `glossary`. -The definition of glossary entries has to follow the following structure - -```toml -[SHORT] -long = "Long Form" -description = "The description of the entry" +With pdf rendering -# Example -[HTML] -long = "Hypertext Markup Language" -description = "The markup language of the web" +```sh +cargo install snekdown --features pdf ``` -Those glossary entries can be referenced in the snekdown file as follows: - -```md -~HTML is widely used for websites. -The format ~HTML is not considered a programming language by some definitions. -~~HTML -``` +## Usage -The first occurence of the glossary entry (`~HTML`) always uses the long form. -The second will always be the short form. The long form can be enforced by using two -(`~~HTML`) tildes. -The glossary list can be inserted with the `[[GLS]]` placeholder. +Use `snekdown help` and `snekdown --help` for more information. -## Math +### Rendering -Snekdown allows the embedding of [AsciiMath](http://asciimath.org/): -The AsciiMath parser is provided in the [asciimath-rs](https://github.com/Trivernis/asciimath-rs) crate +`snekdown render ` -``` -inline math $$ a^2 + b^2 = c^2 $$ +### Watching -Block Math -$$$ -A = [[1, 2],[3,4]] -$$$ -``` +`snekdown watch ` -The expression get's converted into MathML which is then converted by MathJax when loaded in -the browser. -## Smart Arrows +## Editors -Snekdown automatically renders the sequences `-->`, `==>`, `<--`, `<==`, `<-->`, `<==>` as -their respective unicode arrows (similar to [markdown-it-smartarrows](https://github.com/adam-p/markdown-it-smartarrows)). -This behavior can be turned off by setting the config parameter `smart-arrows` to `false` -(the config needs to be imported before the arrows are used for that to work). +I've created a [VisualStudio Code extension](https://marketplace.visualstudio.com/items?itemName=trivernis.snekdown) for Snekdown. +This extension provides a preview of snekdown files, exports and other commands similar to the +cli. The source code can be found [here](https://github.com/Trivernis/snekdown-vscode-extension). ## Roadmap The end goal is to have a markup language with features similar to LaTeX. +### Short Term + - [x] Checkboxes - [x] Emojis (\:emoji:) - [x] Colors @@ -471,9 +96,19 @@ The end goal is to have a markup language with features similar to LaTeX. - [x] Chromium based pdf rendering - [x] Custom Stylesheets - [x] Smart arrows -- [ ] Custom Elements via templates (50%) - [ ] Cross References - [ ] Figures - [ ] EPUB Rendering - [ ] Text sizes -- [ ] Title pages \ No newline at end of file +- [ ] Title pages + + +### Long Term + +- Rewrite of the whole parsing process +- Custom Elements via templates + + +## License + +This project is licensed under GPL 3.0. See LICENSE for more information. \ No newline at end of file diff --git a/src/elements/mod.rs b/src/elements/mod.rs index dffbd25..0fe2999 100644 --- a/src/elements/mod.rs +++ b/src/elements/mod.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + pub mod tokens; use crate::format::PlaceholderTemplate; @@ -188,6 +194,7 @@ pub enum Inline { CharacterCode(CharacterCode), LineBreak, Arrow(Arrow), + Anchor(Anchor), } #[derive(Clone, Debug)] diff --git a/src/elements/tokens.rs b/src/elements/tokens.rs index d62a64f..c3d3ac7 100644 --- a/src/elements/tokens.rs +++ b/src/elements/tokens.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + #![allow(unused)] pub(crate) const BACKSLASH: char = '\\'; @@ -33,6 +39,7 @@ pub(crate) const L_BRACE: char = '}'; pub(crate) const PERCENT: char = '%'; pub(crate) const COMMA: char = ','; pub(crate) const MATH: char = '$'; +pub(crate) const DOLLAR: char = '$'; pub(crate) const AMPERSAND: char = '&'; pub(crate) const QUESTION_MARK: char = '?'; @@ -82,6 +89,18 @@ pub(crate) const CHARACTER_STOP: char = SEMICOLON; pub(crate) const GLOSSARY_REF_START: char = TILDE; +// Reference Anchors + +pub(crate) const ANCHOR_START: &'static [char] = &[R_BRACKET, QUESTION_MARK]; +pub(crate) const ANCHOR_STOP: char = L_BRACKET; + +// References + +pub(crate) const REF_START: &'static [char] = &[R_BRACKET, DOLLAR]; +pub(crate) const REF_STOP: char = L_BRACKET; +pub(crate) const REF_DESC_START: char = R_PARENTH; +pub(crate) const REF_DESC_STOP: char = L_PARENTH; + // Arrows pub(crate) const A_RIGHT_ARROW: &'static [char] = &['-', '-', '>']; @@ -130,6 +149,8 @@ pub(crate) const INLINE_SPECIAL_SEQUENCES: &'static [&'static [char]] = &[ A_RIGHT_ARROW, A_LEFT_ARROW, A_LEFT_RIGHT_ARROW, + ANCHOR_START, + REF_START, ]; pub(crate) const LIST_SPECIAL_CHARS: [char; 14] = [ diff --git a/src/format/assets/base.scss b/src/format/assets/base.scss index ea31aa2..dba9a59 100644 --- a/src/format/assets/base.scss +++ b/src/format/assets/base.scss @@ -1,3 +1,9 @@ +/*! + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + body { background-color: $body-background; overflow-x: hidden; diff --git a/src/format/assets/dark-magic.scss b/src/format/assets/dark-magic.scss index f1cac35..fccdfdd 100644 --- a/src/format/assets/dark-magic.scss +++ b/src/format/assets/dark-magic.scss @@ -1,3 +1,9 @@ +/*! + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + $background-color: #1e1d2c; $background-color-variant-1: lighten($background-color, 7%); $background-color-variant-2: lighten($background-color, 14%); diff --git a/src/format/assets/dark-ocean.scss b/src/format/assets/dark-ocean.scss index 510f274..c1be4b4 100644 --- a/src/format/assets/dark-ocean.scss +++ b/src/format/assets/dark-ocean.scss @@ -1,3 +1,9 @@ +/*! + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + $background-color: darken(#2b303b, 8%); $background-color-variant-1: lighten($background-color, 7%); $background-color-variant-2: lighten($background-color, 14%); diff --git a/src/format/assets/dark-solarized.scss b/src/format/assets/dark-solarized.scss index a067a27..6f14ea9 100644 --- a/src/format/assets/dark-solarized.scss +++ b/src/format/assets/dark-solarized.scss @@ -1,3 +1,9 @@ +/*! + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + $background-color: darken(#002b36, 5%); $background-color-variant-1: lighten($background-color, 7%); $background-color-variant-2: lighten($background-color, 14%); diff --git a/src/format/assets/light-github.scss b/src/format/assets/light-github.scss index 05d74cb..8c46349 100644 --- a/src/format/assets/light-github.scss +++ b/src/format/assets/light-github.scss @@ -1,3 +1,9 @@ +/*! + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + $background-color: #FFF; $background-color-variant-1: darken($background-color, 7%); $background-color-variant-2: darken($background-color, 14%); diff --git a/src/format/assets/light-ocean.scss b/src/format/assets/light-ocean.scss index af7aef2..49aa725 100644 --- a/src/format/assets/light-ocean.scss +++ b/src/format/assets/light-ocean.scss @@ -1,3 +1,9 @@ +/*! + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + $background-color: #FFF; $background-color-variant-1: darken($background-color, 7%); $background-color-variant-2: darken($background-color, 14%); diff --git a/src/format/assets/light-solarized.scss b/src/format/assets/light-solarized.scss index dcfbb87..840e017 100644 --- a/src/format/assets/light-solarized.scss +++ b/src/format/assets/light-solarized.scss @@ -1,3 +1,9 @@ +/*! + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + $background-color: #fff8f0; $background-color-variant-1: darken($background-color, 4%); $background-color-variant-2: darken($background-color, 8%); diff --git a/src/format/chromium_pdf/assets/default-footer-template.html b/src/format/chromium_pdf/assets/default-footer-template.html index a22b698..1c1ee01 100644 --- a/src/format/chromium_pdf/assets/default-footer-template.html +++ b/src/format/chromium_pdf/assets/default-footer-template.html @@ -1,3 +1,9 @@ + +
/
\ No newline at end of file diff --git a/src/format/chromium_pdf/mod.rs b/src/format/chromium_pdf/mod.rs index 4d2576e..761824e 100644 --- a/src/format/chromium_pdf/mod.rs +++ b/src/format/chromium_pdf/mod.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + use crate::elements::Document; use crate::format::chromium_pdf::result::{PdfRenderingError, PdfRenderingResult}; use crate::format::html::html_writer::HTMLWriter; diff --git a/src/format/chromium_pdf/result.rs b/src/format/chromium_pdf/result.rs index 31256de..486b3f0 100644 --- a/src/format/chromium_pdf/result.rs +++ b/src/format/chromium_pdf/result.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + use std::error::Error; use std::fmt::{self, Display}; use std::io; diff --git a/src/format/html/html_writer.rs b/src/format/html/html_writer.rs index 1a518b3..f583942 100644 --- a/src/format/html/html_writer.rs +++ b/src/format/html/html_writer.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + use crate::settings::style_settings::Theme; use std::io; use std::io::Write; diff --git a/src/format/html/mod.rs b/src/format/html/mod.rs index 7c72de5..c3c4398 100644 --- a/src/format/html/mod.rs +++ b/src/format/html/mod.rs @@ -1,2 +1,8 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + pub mod html_writer; pub mod to_html; diff --git a/src/format/html/to_html.rs b/src/format/html/to_html.rs index d99e29d..ef282d3 100644 --- a/src/format/html/to_html.rs +++ b/src/format/html/to_html.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + use crate::elements::*; use crate::format::html::html_writer::HTMLWriter; use crate::format::style::{get_code_theme_for_theme, get_css_for_theme}; @@ -62,6 +68,7 @@ impl ToHtml for Inline { Inline::CharacterCode(code) => code.to_html(writer), Inline::GlossaryReference(gloss) => gloss.lock().to_html(writer), Inline::Arrow(a) => a.to_html(writer), + Inline::Anchor(a) => a.to_html(writer), } } } diff --git a/src/format/mod.rs b/src/format/mod.rs index 6fc2726..943f592 100644 --- a/src/format/mod.rs +++ b/src/format/mod.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + use regex::Regex; use std::collections::HashMap; diff --git a/src/format/style.rs b/src/format/style.rs index c73eb9c..e251135 100644 --- a/src/format/style.rs +++ b/src/format/style.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + use crate::settings::style_settings::Theme; use std::time::Instant; use syntect::highlighting::ThemeSet; diff --git a/src/lib.rs b/src/lib.rs index 5f5aa8b..b7df9f1 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + pub mod elements; pub mod format; pub mod parser; diff --git a/src/main.rs b/src/main.rs index 7c160a0..14e26f5 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + use colored::Colorize; use env_logger::Env; use log::{Level, LevelFilter}; diff --git a/src/parser/block.rs b/src/parser/block.rs index 2a640e0..cb6ce04 100644 --- a/src/parser/block.rs +++ b/src/parser/block.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + use super::ParseResult; use crate::elements::tokens::*; use crate::elements::{ diff --git a/src/parser/inline.rs b/src/parser/inline.rs index aa7bcaf..fdf6f9c 100644 --- a/src/parser/inline.rs +++ b/src/parser/inline.rs @@ -1,3 +1,9 @@ +/* + * Snekdown - Custom Markdown flavour and parser + * Copyright (C) 2021 Trivernis + * See LICENSE for more information. + */ + use super::{ParseError, ParseResult}; use crate::elements::tokens::*; use crate::elements::BibReference; @@ -39,6 +45,7 @@ pub(crate) trait ParseInline { fn parse_template(&mut self) -> ParseResult