diff clang-tools-extra/clangd/support/Markup.h @ 173:0572611fdcc8 llvm10 llvm12

reorgnization done
author Shinji KONO <kono@ie.u-ryukyu.ac.jp>
date Mon, 25 May 2020 11:55:54 +0900
parents
children c4bab56944e8
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/clang-tools-extra/clangd/support/Markup.h	Mon May 25 11:55:54 2020 +0900
@@ -0,0 +1,131 @@
+//===--- Markup.h -------------------------------------------*- C++-*------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+//
+// A model of formatted text that can be rendered to plaintext or markdown.
+//
+//===----------------------------------------------------------------------===//
+#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANGD_SUPPORT_MARKUP_H
+#define LLVM_CLANG_TOOLS_EXTRA_CLANGD_SUPPORT_MARKUP_H
+
+#include "llvm/Support/raw_ostream.h"
+#include <cstddef>
+#include <memory>
+#include <string>
+#include <vector>
+
+namespace clang {
+namespace clangd {
+namespace markup {
+
+/// Holds text and knows how to lay it out. Multiple blocks can be grouped to
+/// form a document. Blocks include their own trailing newlines, container
+/// should trim them if need be.
+class Block {
+public:
+  virtual void renderMarkdown(llvm::raw_ostream &OS) const = 0;
+  virtual void renderPlainText(llvm::raw_ostream &OS) const = 0;
+  virtual std::unique_ptr<Block> clone() const = 0;
+  std::string asMarkdown() const;
+  std::string asPlainText() const;
+
+  virtual bool isRuler() const { return false; }
+  virtual ~Block() = default;
+};
+
+/// Represents parts of the markup that can contain strings, like inline code,
+/// code block or plain text.
+/// One must introduce different paragraphs to create separate blocks.
+class Paragraph : public Block {
+public:
+  void renderMarkdown(llvm::raw_ostream &OS) const override;
+  void renderPlainText(llvm::raw_ostream &OS) const override;
+  std::unique_ptr<Block> clone() const override;
+
+  /// Append plain text to the end of the string.
+  Paragraph &appendText(llvm::StringRef Text);
+
+  /// Append inline code, this translates to the ` block in markdown.
+  /// \p Preserve indicates the code span must be apparent even in plaintext.
+  Paragraph &appendCode(llvm::StringRef Code, bool Preserve = false);
+
+  /// Ensure there is space between the surrounding chunks.
+  /// Has no effect at the beginning or end of a paragraph.
+  Paragraph &appendSpace();
+
+private:
+  struct Chunk {
+    enum {
+      PlainText,
+      InlineCode,
+    } Kind = PlainText;
+    // Preserve chunk markers in plaintext.
+    bool Preserve = false;
+    std::string Contents;
+    // Whether this chunk should be surrounded by whitespace.
+    // Consecutive SpaceAfter and SpaceBefore will be collapsed into one space.
+    // Code spans don't usually set this: their spaces belong "inside" the span.
+    bool SpaceBefore = false;
+    bool SpaceAfter = false;
+  };
+  std::vector<Chunk> Chunks;
+};
+
+/// Represents a sequence of one or more documents. Knows how to print them in a
+/// list like format, e.g. by prepending with "- " and indentation.
+class BulletList : public Block {
+public:
+  void renderMarkdown(llvm::raw_ostream &OS) const override;
+  void renderPlainText(llvm::raw_ostream &OS) const override;
+  std::unique_ptr<Block> clone() const override;
+
+  class Document &addItem();
+
+private:
+  std::vector<class Document> Items;
+};
+
+/// A format-agnostic representation for structured text. Allows rendering into
+/// markdown and plaintext.
+class Document {
+public:
+  Document() = default;
+  Document(const Document &Other) { *this = Other; }
+  Document &operator=(const Document &);
+  Document(Document &&) = default;
+  Document &operator=(Document &&) = default;
+
+  void append(Document Other);
+
+  /// Adds a semantical block that will be separate from others.
+  Paragraph &addParagraph();
+  /// Inserts a horizontal separator to the document.
+  void addRuler();
+  /// Adds a block of code. This translates to a ``` block in markdown. In plain
+  /// text representation, the code block will be surrounded by newlines.
+  void addCodeBlock(std::string Code, std::string Language = "cpp");
+  /// Heading is a special type of paragraph that will be prepended with \p
+  /// Level many '#'s in markdown.
+  Paragraph &addHeading(size_t Level);
+
+  BulletList &addBulletList();
+
+  /// Doesn't contain any trailing newlines.
+  /// We try to make the markdown human-readable, e.g. avoid extra escaping.
+  /// At least one client (coc.nvim) displays the markdown verbatim!
+  std::string asMarkdown() const;
+  /// Doesn't contain any trailing newlines.
+  std::string asPlainText() const;
+
+private:
+  std::vector<std::unique_ptr<Block>> Children;
+};
+} // namespace markup
+} // namespace clangd
+} // namespace clang
+
+#endif