From 7132584996d820b279bb418d9fe3736f27bc02c9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20G=C3=B6ls?= <6608231+Abrynos@users.noreply.github.com> Date: Fri, 15 Mar 2024 11:28:48 +0100 Subject: [PATCH 1/2] Add bootstrap alert renderer --- .../Bootstrap/BootstrapAlertRenderer.cs | 72 +++++++++++++++++++ .../Bootstrap/BootstrapExtension.cs | 14 +++- 2 files changed, 84 insertions(+), 2 deletions(-) create mode 100644 src/Markdig/Extensions/Bootstrap/BootstrapAlertRenderer.cs diff --git a/src/Markdig/Extensions/Bootstrap/BootstrapAlertRenderer.cs b/src/Markdig/Extensions/Bootstrap/BootstrapAlertRenderer.cs new file mode 100644 index 000000000..8e26d68f1 --- /dev/null +++ b/src/Markdig/Extensions/Bootstrap/BootstrapAlertRenderer.cs @@ -0,0 +1,72 @@ +// Copyright (c) Alexandre Mutel. All rights reserved. +// This file is licensed under the BSD-Clause 2 license. +// See the license.txt file in the project root for more information. + +using System.Linq; +using Markdig.Extensions.Alerts; +using Markdig.Renderers; +using Markdig.Renderers.Html; +using Markdig.Syntax; + +namespace Markdig.Extensions.Bootstrap; + +/// +/// A HTML renderer for a that adds bootstrap classes. +/// +/// +public class BootstrapAlertRenderer : HtmlObjectRenderer +{ + /// + /// Creates a new instance of this renderer. + /// + public BootstrapAlertRenderer() { } + + /// + protected override void Write(HtmlRenderer renderer, AlertBlock obj) + { + AddAttributes(obj); + var lastParagraph = obj.Descendants().OfType().LastOrDefault(); + lastParagraph?.GetAttributes().AddProperty("style", "margin-bottom: 0"); + + renderer.EnsureLine(); + if (renderer.EnableHtmlForBlock) + { + renderer.Write("'); + } + + var savedImplicitParagraph = renderer.ImplicitParagraph; + renderer.ImplicitParagraph = false; + renderer.WriteChildren(obj); + renderer.ImplicitParagraph = savedImplicitParagraph; + if (renderer.EnableHtmlForBlock) + { + renderer.WriteLine(""); + } + + renderer.EnsureLine(); + } + + private static void AddAttributes(AlertBlock obj) + { + var attributes = obj.GetAttributes(); + attributes.AddClass("alert"); + attributes.AddProperty("role", "alert"); + + string? @class = obj.Kind.AsSpan() switch + { + "NOTE" => "alert-primary", + "TIP" => "alert-success", + "IMPORTANT" => "alert-info", + "WARNING" => "alert-warning", + "CAUTION" => "alert-danger", + _ => null + }; + + if (@class is not null) + { + attributes.AddClass(@class); + } + } +} \ No newline at end of file diff --git a/src/Markdig/Extensions/Bootstrap/BootstrapExtension.cs b/src/Markdig/Extensions/Bootstrap/BootstrapExtension.cs index 8344f0a3a..b67890fd2 100644 --- a/src/Markdig/Extensions/Bootstrap/BootstrapExtension.cs +++ b/src/Markdig/Extensions/Bootstrap/BootstrapExtension.cs @@ -1,7 +1,8 @@ // Copyright (c) Alexandre Mutel. All rights reserved. -// This file is licensed under the BSD-Clause 2 license. +// This file is licensed under the BSD-Clause 2 license. // See the license.txt file in the project root for more information. +using Markdig.Extensions.Alerts; using Markdig.Renderers; using Markdig.Renderers.Html; using Markdig.Syntax; @@ -24,6 +25,15 @@ public void Setup(MarkdownPipelineBuilder pipeline) public void Setup(MarkdownPipeline pipeline, IMarkdownRenderer renderer) { + if (renderer is HtmlRenderer htmlRenderer) + { + // We only want to add our renderer if we already support alert blocks + if (htmlRenderer.ObjectRenderers.Contains()) + { + // Needs to be inserted before the original renderer + htmlRenderer.ObjectRenderers.Insert(0, new BootstrapAlertRenderer()); + } + } } private static void PipelineOnDocumentProcessed(MarkdownDocument document) @@ -43,7 +53,7 @@ private static void PipelineOnDocumentProcessed(MarkdownDocument document) { node.GetAttributes().AddClass("table"); } - else if (node is QuoteBlock) + else if (node is QuoteBlock and not AlertBlock) { node.GetAttributes().AddClass("blockquote"); } From f9e96bc9c9526e6bdae6cb50d53418144958f05b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20G=C3=B6ls?= <6608231+Abrynos@users.noreply.github.com> Date: Mon, 18 Mar 2024 07:48:22 +0100 Subject: [PATCH 2/2] Apply feedback --- .../Bootstrap/BootstrapAlertRenderer.cs | 72 ------------------- .../Bootstrap/BootstrapExtension.cs | 36 ++++++++-- 2 files changed, 31 insertions(+), 77 deletions(-) delete mode 100644 src/Markdig/Extensions/Bootstrap/BootstrapAlertRenderer.cs diff --git a/src/Markdig/Extensions/Bootstrap/BootstrapAlertRenderer.cs b/src/Markdig/Extensions/Bootstrap/BootstrapAlertRenderer.cs deleted file mode 100644 index 8e26d68f1..000000000 --- a/src/Markdig/Extensions/Bootstrap/BootstrapAlertRenderer.cs +++ /dev/null @@ -1,72 +0,0 @@ -// Copyright (c) Alexandre Mutel. All rights reserved. -// This file is licensed under the BSD-Clause 2 license. -// See the license.txt file in the project root for more information. - -using System.Linq; -using Markdig.Extensions.Alerts; -using Markdig.Renderers; -using Markdig.Renderers.Html; -using Markdig.Syntax; - -namespace Markdig.Extensions.Bootstrap; - -/// -/// A HTML renderer for a that adds bootstrap classes. -/// -/// -public class BootstrapAlertRenderer : HtmlObjectRenderer -{ - /// - /// Creates a new instance of this renderer. - /// - public BootstrapAlertRenderer() { } - - /// - protected override void Write(HtmlRenderer renderer, AlertBlock obj) - { - AddAttributes(obj); - var lastParagraph = obj.Descendants().OfType().LastOrDefault(); - lastParagraph?.GetAttributes().AddProperty("style", "margin-bottom: 0"); - - renderer.EnsureLine(); - if (renderer.EnableHtmlForBlock) - { - renderer.Write("'); - } - - var savedImplicitParagraph = renderer.ImplicitParagraph; - renderer.ImplicitParagraph = false; - renderer.WriteChildren(obj); - renderer.ImplicitParagraph = savedImplicitParagraph; - if (renderer.EnableHtmlForBlock) - { - renderer.WriteLine(""); - } - - renderer.EnsureLine(); - } - - private static void AddAttributes(AlertBlock obj) - { - var attributes = obj.GetAttributes(); - attributes.AddClass("alert"); - attributes.AddProperty("role", "alert"); - - string? @class = obj.Kind.AsSpan() switch - { - "NOTE" => "alert-primary", - "TIP" => "alert-success", - "IMPORTANT" => "alert-info", - "WARNING" => "alert-warning", - "CAUTION" => "alert-danger", - _ => null - }; - - if (@class is not null) - { - attributes.AddClass(@class); - } - } -} \ No newline at end of file diff --git a/src/Markdig/Extensions/Bootstrap/BootstrapExtension.cs b/src/Markdig/Extensions/Bootstrap/BootstrapExtension.cs index b67890fd2..560cc7bf0 100644 --- a/src/Markdig/Extensions/Bootstrap/BootstrapExtension.cs +++ b/src/Markdig/Extensions/Bootstrap/BootstrapExtension.cs @@ -2,6 +2,7 @@ // This file is licensed under the BSD-Clause 2 license. // See the license.txt file in the project root for more information. +using System.Linq; using Markdig.Extensions.Alerts; using Markdig.Renderers; using Markdig.Renderers.Html; @@ -27,12 +28,14 @@ public void Setup(MarkdownPipeline pipeline, IMarkdownRenderer renderer) { if (renderer is HtmlRenderer htmlRenderer) { - // We only want to add our renderer if we already support alert blocks - if (htmlRenderer.ObjectRenderers.Contains()) + var alertRenderer = htmlRenderer.ObjectRenderers.OfType().FirstOrDefault(); + if (alertRenderer == null) { - // Needs to be inserted before the original renderer - htmlRenderer.ObjectRenderers.Insert(0, new BootstrapAlertRenderer()); + alertRenderer = new AlertBlockRenderer(); + renderer.ObjectRenderers.InsertBefore(new AlertBlockRenderer()); } + + alertRenderer.RenderKind = (_, _) => { }; } } @@ -53,7 +56,30 @@ private static void PipelineOnDocumentProcessed(MarkdownDocument document) { node.GetAttributes().AddClass("table"); } - else if (node is QuoteBlock and not AlertBlock) + else if (node is AlertBlock alertBlock) // Needs to be before QuoteBlock + { + var attributes = node.GetAttributes(); + attributes.AddClass("alert"); + attributes.AddProperty("role", "alert"); + string? @class = alertBlock.Kind.AsSpan() switch + { + "NOTE" => "alert-primary", + "TIP" => "alert-success", + "IMPORTANT" => "alert-info", + "WARNING" => "alert-warning", + "CAUTION" => "alert-danger", + _ => null, + }; + + if (@class is not null) + { + attributes.AddClass(@class); + } + + var lastParagraph = alertBlock.Descendants().OfType().LastOrDefault(); + lastParagraph?.GetAttributes().AddClass("mb-0"); + } + else if (node is QuoteBlock) { node.GetAttributes().AddClass("blockquote"); }