public SectionRef(MarkdownParagraph.Heading mdh, string filename) { Level = mdh.size; var spans = mdh.body; if (spans.Length == 1 && spans.First().IsLiteral) { Title = MarkdownUtilities.UnescapeLiteral(spans.First() as MarkdownSpan.Literal).Trim(); if (char.IsDigit(Title[0]) || (Title[0] >= 'A' && Title[0] <= 'D' && Title[1] == '.')) { var titleParts = Title.Split(new[] { ' ' }, 2); Number = titleParts[0]; TitleWithoutNumber = titleParts[1]; } else { Number = null; TitleWithoutNumber = Title; } } else { throw new NotSupportedException($"Heading must be a single literal. Got: {mdh.body}"); } foreach (var c in Title) { if (c >= 'a' && c <= 'z') { Url += c; } else if (c >= 'A' && c <= 'Z') { Url += char.ToLowerInvariant(c); } else if (c >= '0' && c <= '9') { Url += c; } else if (c == '-' || c == '_') { Url += c; } else if (c == ' ') { Url += '-'; } } Url = filename + "#" + Url; BookmarkName = $"_Toc{count:00000}"; count++; Loc = new SourceLocation(filename, this, mdh, null); }
static int GetSectionOrderingKey(MarkdownDocument doc) { if (doc.Paragraphs.FirstOrDefault() is not MarkdownParagraph.Heading heading) { throw new ArgumentException("Document does not start with a heading"); } if (heading.body.SingleOrDefault() is not MarkdownSpan.Literal literal) { throw new ArgumentException("Heading is not a literal"); } string title = MarkdownUtilities.UnescapeLiteral(literal); return(title switch { "Foreword" => - 10, "Introduction" => - 5, string mainSection when char.IsDigit(mainSection[0]) => int.Parse(mainSection.Split(' ')[0]), string annex when annex.StartsWith("Annex ") => 1000 + annex[6], _ => throw new ArgumentException($"Unexpected section title: {title}") });