Last active
March 16, 2016 22:33
-
-
Save jakejscott/dfd22a747919c4d7042e to your computer and use it in GitHub Desktop.
Revisions
-
jakejscott revised this gist
Mar 16, 2016 . 1 changed file with 108 additions and 0 deletions.There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -0,0 +1,108 @@ using System; using System.Text; namespace ConsoleApp { public static class Slug { public static string Create(bool toLower, params string[] values) { return Create(toLower, String.Join("-", values)); } public static string Create(bool toLower, string value) { if (value == null) return ""; var normalised = value.Normalize(NormalizationForm.FormKD); const int maxlen = 80; int len = normalised.Length; bool prevDash = false; var sb = new StringBuilder(len); char c; for (int i = 0; i < len; i++) { c = normalised[i]; if ((c >= 'a' && c <= 'z') || (c >= '0' && c <= '9')) { if (prevDash) { sb.Append('-'); prevDash = false; } sb.Append(c); } else if (c >= 'A' && c <= 'Z') { if (prevDash) { sb.Append('-'); prevDash = false; } // tricky way to convert to lowercase if (toLower) sb.Append((char)(c | 32)); else sb.Append(c); } else if (c == ' ' || c == ',' || c == '.' || c == '/' || c == '\\' || c == '-' || c == '_' || c == '=') { if (!prevDash && sb.Length > 0) { prevDash = true; } } else { string swap = ConvertEdgeCases(c, toLower); if (swap != null) { if (prevDash) { sb.Append('-'); prevDash = false; } sb.Append(swap); } } if (sb.Length == maxlen) break; } return sb.ToString(); } static string ConvertEdgeCases(char c, bool toLower) { string swap = null; switch (c) { case 'ı': swap = "i"; break; case 'ł': swap = "l"; break; case 'Ł': swap = toLower ? "l" : "L"; break; case 'đ': swap = "d"; break; case 'ß': swap = "ss"; break; case 'ø': swap = "o"; break; case 'Þ': swap = "th"; break; } return swap; } } } -
jakejscott created this gist
Mar 16, 2016 .There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -0,0 +1,114 @@ using System; using System.Collections.Generic; using System.IO; using System.Linq; using CommonMark; using CommonMark.Formatters; using CommonMark.Syntax; namespace ConsoleApp { public class Program { // blocks are elemets like paragraphs and lists, inlines are // elements like emphasis, links, images. public static void Main(string[] args) { CommonMarkSettings.Default.OutputDelegate = (document, textWriter, settings) => { var formatter = new CustomHtmlFormatter(document, textWriter, settings); formatter.WriteDocument(document); }; using (var reader = new StreamReader("./README.md")) { var document = CommonMarkConverter.Parse(reader); using (var writer = new StringWriter()) { // write the HTML output CommonMarkConverter.ProcessStage3(document, writer); Console.WriteLine(writer.ToString()); } } Console.ReadLine(); } private class CustomHtmlFormatter : HtmlFormatter { private readonly List<EnumeratorEntry> headings; public CustomHtmlFormatter(Block block, TextWriter target, CommonMarkSettings settings) : base(target, settings) { headings = block.AsEnumerable().Where( x => x.IsOpening && x.Block != null && x.Block.Tag == BlockTag.AtxHeading && x.Block.InlineContent != null ).ToList(); } protected override void WriteBlock(Block block, bool isOpening, bool isClosing, out bool ignoreChildNodes) { if (block.Tag == BlockTag.AtxHeading && block.InlineContent != null) { // // Add anchorable id to each heading // ignoreChildNodes = false; if (isOpening) { var slug = Slug.Create(true, block.InlineContent.LiteralContent); Write(string.Format("<h{0} id=\"{1}\">", block.Heading.Level, slug)); } if (isClosing) { Write(string.Format("</h{0}>", block.Heading.Level)); } } else if (block.Tag == BlockTag.Paragraph && block.InlineContent != null && block.InlineContent.LiteralContent == "{:toc}" && headings.Any()) { // // Injects a table of contents. // ignoreChildNodes = true; if (isOpening) { WriteLine(); Write("<ul>"); foreach (var heading in headings) { var text = heading.Block.InlineContent.LiteralContent; var slug = Slug.Create(true, text); WriteLine(); Write(string.Format("<li href=\"#{0}\">", slug)); Write(text); Write("</li>"); } } if (isClosing) { WriteLine(); Write("</ul>"); WriteLine(); } } else { base.WriteBlock(block, isOpening, isClosing, out ignoreChildNodes); } } } } }