kythe.io@v0.0.68-0.20240422202219-7225dbc01741/kythe/cxx/doc/markup_handler.h (about) 1 /* 2 * Copyright 2016 The Kythe Authors. All rights reserved. 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef KYTHE_CXX_DOC_MARKUP_HANDLER_H_ 18 #define KYTHE_CXX_DOC_MARKUP_HANDLER_H_ 19 20 #include <functional> 21 22 #include "kythe/proto/common.pb.h" 23 #include "kythe/proto/xref.pb.h" 24 25 namespace kythe { 26 class PrintableSpan { 27 public: 28 enum class Semantic : int { 29 TagBlock, ///< Text belongs to a new tag block. 30 Styled, ///< Text is styled according to `style_`. 31 Paragraph, ///< Text is a paragraph. 32 UnorderedList, ///< Text is an unordered (bulleted) list. 33 ListItem, ///< Text is an item in a list. 34 Brief, ///< Text is a brief subsection of a main description. 35 CodeRef, ///< Text is a reference to code and should be rendered monospace. 36 Markup, ///< Text used solely to direct the markup processor. May contain 37 ///< child spans that are relevant. This text is usually not 38 ///< rendered. 39 Raw, ///< Text may be passed through directly (modulo escaping). 40 CodeBlock, ///< Text is a block of code. 41 Uri, ///< Text is the URI component of a UriLink. 42 UriLink, ///< Text is a link to some (embedded) URI. There must be 43 ///< an embedded span with the Uri semantic. 44 Link, ///< Text is a link to some anchor. 45 Escaped ///< Text is (atomic and) escaped; e.g. ">". 46 }; 47 enum class TagBlockId : int { 48 Author, 49 Returns, 50 Since, 51 Version, 52 Param, 53 Throws, 54 See 55 }; 56 enum class Style : int { 57 Bold, 58 Italic, 59 H1, 60 H2, 61 H3, 62 H4, 63 H5, 64 H6, 65 Blockquote, 66 Big, 67 Small, 68 Superscript, 69 Subscript, 70 Underline 71 }; 72 PrintableSpan(size_t begin, size_t end, const proto::common::Link& link) 73 : begin_(begin), end_(end), link_(link), semantic_(Semantic::Link) {} 74 PrintableSpan(size_t begin, size_t end, Semantic sema) 75 : begin_(begin), end_(end), semantic_(sema) {} 76 PrintableSpan(size_t begin, size_t end, TagBlockId tag_id, size_t tag_ordinal) 77 : begin_(begin), 78 end_(end), 79 semantic_(Semantic::TagBlock), 80 tag_block_(tag_id, tag_ordinal) {} 81 PrintableSpan(size_t begin, size_t end, Style style) 82 : begin_(begin), end_(end), semantic_(Semantic::Styled), style_(style) {} 83 const bool operator<(const PrintableSpan& o) const { 84 return std::tie(begin_, o.end_, semantic_, tag_block_, style_) < 85 std::tie(o.begin_, end_, o.semantic_, tag_block_, style_); 86 } 87 bool is_valid() const { return begin_ < end_; } 88 const size_t begin() const { return begin_; } 89 const size_t end() const { return end_; } 90 void set_end(size_t end) { end_ = end; } 91 const proto::common::Link& link() const { return link_; } 92 Semantic semantic() const { return semantic_; } 93 Style style() const { return style_; } 94 std::pair<TagBlockId, size_t> tag_block() const { return tag_block_; } 95 96 private: 97 /// The beginning offset, in bytes, of the span. 98 size_t begin_; 99 /// The ending offset, in bytes, of the span. 100 size_t end_; 101 /// The link for the span. 102 proto::common::Link link_; 103 /// The semantic for the span. 104 Semantic semantic_; 105 /// The tag block ID for the span. 106 std::pair<TagBlockId, size_t> tag_block_ = 107 std::make_pair(TagBlockId::Author, 0); 108 /// The style for the span. 109 Style style_ = Style::Bold; 110 }; 111 112 class PrintableSpans { 113 public: 114 /// \brief Insert all spans from `more`. 115 /// Empty or negative-length spans are discarded. 116 void Merge(const PrintableSpans& more); 117 /// Construct a span and insert it. 118 template <typename... T> 119 void Emplace(T&&... span_args) { 120 spans_.emplace_back(span_args...); 121 } 122 /// \return the number of spans being stored. 123 const size_t size() const { return spans_.size(); } 124 const PrintableSpan& span(size_t index) const { return spans_[index]; } 125 PrintableSpan* mutable_span(size_t index) { return &spans_[index]; } 126 /// \brief Produces a debug representation of the stored spans. 127 std::string Dump(const std::string& annotated_buffer) const; 128 /// \brief Returns the index of the next tag block with the given tag block 129 /// ID. 130 size_t next_tag_block_id(PrintableSpan::TagBlockId block_id) { 131 return max_tag_block_[block_id]++; 132 } 133 134 private: 135 std::vector<PrintableSpan> spans_; 136 std::map<PrintableSpan::TagBlockId, size_t> max_tag_block_; 137 }; 138 139 class Printable { 140 public: 141 /// \brief Build a Printable from a protobuf. 142 /// \post The internal list of spans is sorted. 143 explicit Printable(const proto::Printable& from); 144 /// \pre The list of spans is sorted. 145 Printable(const std::string& text, PrintableSpans&& spans) 146 : text_(text), spans_(std::move(spans)) {} 147 /// \brief Return this Printable's list of spans. 148 PrintableSpans* mutable_spans() { return &spans_; } 149 /// \brief Return this Printable's list of spans. 150 const PrintableSpans& spans() const { return spans_; } 151 /// \brief The text of this Printable (unannotated with span markup). 152 const std::string& text() const { return text_; } 153 154 private: 155 /// \brief The text of the Printable. 156 std::string text_; 157 /// \brief Interesting spans in `text_`. 158 PrintableSpans spans_; 159 }; 160 161 /// \brief Appends markup-specific spans to `spans` from `printable`. 162 /// \param previous_spans Previously-emitted spans. After the MarkupHandler 163 /// runs, these will be merged with `spans`. 164 using MarkupHandler = std::function<void(const Printable& printable, 165 const PrintableSpans& previous_spans, 166 PrintableSpans* spans)>; 167 168 /// \brief Marks up `printable` using the sequence of handlers in `handlers`. 169 Printable HandleMarkup(const std::vector<MarkupHandler>& handlers, 170 const Printable& printable); 171 172 } // namespace kythe 173 174 #endif