Release 1.39.0
[boost.git] / Boost_1_39_0 / tools / quickbook / phrase.hpp
blob4760e7fc752cee1589ff1e4d1c42d70ecdaacf7a
1 /*=============================================================================
2 Copyright (c) 2002 2004 2006 Joel de Guzman
3 Copyright (c) 2004 Eric Niebler
4 http://spirit.sourceforge.net/
6 Use, modification and distribution is subject to the Boost Software
7 License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
8 http://www.boost.org/LICENSE_1_0.txt)
9 =============================================================================*/
10 #if !defined(BOOST_SPIRIT_QUICKBOOK_PHRASE_HPP)
11 #define BOOST_SPIRIT_QUICKBOOK_PHRASE_HPP
13 #include "detail/utils.hpp"
14 #include <boost/spirit/include/classic_core.hpp>
15 #include <boost/spirit/include/classic_confix.hpp>
16 #include <boost/spirit/include/classic_chset.hpp>
17 #include <boost/spirit/include/classic_assign_actor.hpp>
18 #include <boost/spirit/include/classic_if.hpp>
20 namespace quickbook
22 using namespace boost::spirit::classic;
24 template <typename Rule, typename Action>
25 inline void
26 simple_markup(
27 Rule& simple
28 , char mark
29 , Action const& action
30 , Rule const& close
33 simple =
34 mark >>
37 graph_p // A single char. e.g. *c*
38 >> eps_p(mark
39 >> (space_p | punct_p | end_p))
40 // space_p, punct_p or end_p
41 ) // must follow mark
43 ( graph_p >> // graph_p must follow mark
44 *(anychar_p -
45 ( (graph_p >> mark) // Make sure that we don't go
46 | close // past a single block
48 ) >> graph_p // graph_p must precede mark
49 >> eps_p(mark
50 >> (space_p | punct_p | end_p))
51 // space_p, punct_p or end_p
52 ) // must follow mark
53 ) [action]
54 >> mark
58 template <typename Actions>
59 struct phrase_grammar : grammar<phrase_grammar<Actions> >
61 phrase_grammar(Actions& actions, bool& no_eols)
62 : no_eols(no_eols), actions(actions) {}
64 template <typename Scanner>
65 struct definition
67 definition(phrase_grammar const& self)
69 using detail::var;
70 Actions& actions = self.actions;
72 space =
73 *(space_p | comment)
76 blank =
77 *(blank_p | comment)
80 eol = blank >> eol_p
83 phrase_end =
84 ']' |
85 if_p(var(self.no_eols))
87 eol >> eol // Make sure that we don't go
88 ] // past a single block, except
89 ; // when preformatted.
91 hard_space =
92 (eps_p - (alnum_p | '_')) >> space // must not be preceded by
93 ; // alpha-numeric or underscore
95 comment =
96 "[/" >> *(dummy_block | (anychar_p - ']')) >> ']'
99 dummy_block =
100 '[' >> *(dummy_block | (anychar_p - ']')) >> ']'
103 common =
104 macro
105 | phrase_markup
106 | code_block
107 | inline_code
108 | simple_format
109 | escape
110 | comment
113 macro =
114 eps_p(actions.macro // must not be followed by
115 >> (eps_p - (alpha_p | '_'))) // alpha or underscore
116 >> actions.macro [actions.do_macro]
119 template_args =
120 template_arg [push_back_a(actions.template_info)]
121 >> *(
122 ".." >> template_arg [push_back_a(actions.template_info)]
126 static const bool true_ = true;
127 static const bool false_ = false;
129 template_ =
131 ch_p('`') [assign_a(actions.template_escape,true_)]
133 eps_p [assign_a(actions.template_escape,false_)]
137 (eps_p(punct_p)
138 >> actions.templates.scope
139 ) [push_back_a(actions.template_info)]
140 >> !template_args
141 ) | (
142 (actions.templates.scope
143 >> eps_p
144 ) [push_back_a(actions.template_info)]
145 >> !(hard_space
146 >> template_args)
150 brackets =
151 '[' >> +template_arg >> ']'
154 template_arg =
155 +(brackets | (anychar_p - (str_p("..") | ']')))
158 inline_code =
159 '`' >>
161 *(anychar_p -
162 ( '`'
163 | (eol >> eol) // Make sure that we don't go
164 ) // past a single block
165 ) >> eps_p('`')
166 ) [actions.inline_code]
167 >> '`'
170 code_block =
172 "```" >>
174 *(anychar_p - "```")
175 >> eps_p("```")
176 ) [actions.code_block]
177 >> "```"
180 "``" >>
182 *(anychar_p - "``")
183 >> eps_p("``")
184 ) [actions.code_block]
185 >> "``"
189 simple_format =
190 simple_bold
191 | simple_italic
192 | simple_underline
193 | simple_teletype
196 simple_markup(simple_bold,
197 '*', actions.simple_bold, phrase_end);
198 simple_markup(simple_italic,
199 '/', actions.simple_italic, phrase_end);
200 simple_markup(simple_underline,
201 '_', actions.simple_underline, phrase_end);
202 simple_markup(simple_teletype,
203 '=', actions.simple_teletype, phrase_end);
205 phrase =
206 *( common
207 | comment
208 | (anychar_p - phrase_end) [actions.plain_char]
212 phrase_markup =
214 >> ( cond_phrase
215 | image
216 | url
217 | link
218 | anchor
219 | source_mode
220 | funcref
221 | classref
222 | memberref
223 | enumref
224 | macroref
225 | headerref
226 | conceptref
227 | globalref
228 | bold
229 | italic
230 | underline
231 | teletype
232 | strikethrough
233 | quote
234 | replaceable
235 | footnote
236 | template_ [actions.do_template]
237 | str_p("br") [actions.break_]
239 >> ']'
242 escape =
243 str_p("\\n") [actions.break_]
244 | "\\ " // ignore an escaped char
245 | '\\' >> punct_p [actions.raw_char]
247 ("'''" >> !eol) [actions.escape_pre]
248 >> *(anychar_p - "'''") [actions.raw_char]
249 >> str_p("'''") [actions.escape_post]
253 macro_identifier =
254 +(anychar_p - (space_p | ']'))
257 cond_phrase =
258 '?' >> blank
259 >> macro_identifier [actions.cond_phrase_pre]
260 >> (!phrase) [actions.cond_phrase_post]
263 image =
264 '$' >> blank
265 >> (*(anychar_p -
266 phrase_end)) [actions.image]
269 url =
271 >> (*(anychar_p -
272 (']' | hard_space))) [actions.url_pre]
273 >> ( eps_p(']')
274 | (hard_space >> phrase)
275 ) [actions.url_post]
278 link =
279 "link" >> hard_space
280 >> (*(anychar_p -
281 (']' | hard_space))) [actions.link_pre]
282 >> ( eps_p(']')
283 | (hard_space >> phrase)
284 ) [actions.link_post]
287 anchor =
289 >> blank
290 >> ( *(anychar_p -
291 phrase_end)
292 ) [actions.anchor]
295 funcref =
296 "funcref" >> hard_space
297 >> (*(anychar_p -
298 (']' | hard_space))) [actions.funcref_pre]
299 >> ( eps_p(']')
300 | (hard_space >> phrase)
301 ) [actions.funcref_post]
304 classref =
305 "classref" >> hard_space
306 >> (*(anychar_p -
307 (']' | hard_space))) [actions.classref_pre]
308 >> ( eps_p(']')
309 | (hard_space >> phrase)
310 ) [actions.classref_post]
313 memberref =
314 "memberref" >> hard_space
315 >> (*(anychar_p -
316 (']' | hard_space))) [actions.memberref_pre]
317 >> ( eps_p(']')
318 | (hard_space >> phrase)
319 ) [actions.memberref_post]
322 enumref =
323 "enumref" >> hard_space
324 >> (*(anychar_p -
325 (']' | hard_space))) [actions.enumref_pre]
326 >> ( eps_p(']')
327 | (hard_space >> phrase)
328 ) [actions.enumref_post]
331 macroref =
332 "macroref" >> hard_space
333 >> (*(anychar_p -
334 (']' | hard_space))) [actions.macroref_pre]
335 >> ( eps_p(']')
336 | (hard_space >> phrase)
337 ) [actions.macroref_post]
340 headerref =
341 "headerref" >> hard_space
342 >> (*(anychar_p -
343 (']' | hard_space))) [actions.headerref_pre]
344 >> ( eps_p(']')
345 | (hard_space >> phrase)
346 ) [actions.headerref_post]
349 conceptref =
350 "conceptref" >> hard_space
351 >> (*(anychar_p -
352 (']' | hard_space))) [actions.conceptref_pre]
353 >> ( eps_p(']')
354 | (hard_space >> phrase)
355 ) [actions.conceptref_post]
358 globalref =
359 "globalref" >> hard_space
360 >> (*(anychar_p -
361 (']' | hard_space))) [actions.globalref_pre]
362 >> ( eps_p(']')
363 | (hard_space >> phrase)
364 ) [actions.globalref_post]
367 bold =
368 ch_p('*') [actions.bold_pre]
369 >> blank >> phrase [actions.bold_post]
372 italic =
373 ch_p('\'') [actions.italic_pre]
374 >> blank >> phrase [actions.italic_post]
377 underline =
378 ch_p('_') [actions.underline_pre]
379 >> blank >> phrase [actions.underline_post]
382 teletype =
383 ch_p('^') [actions.teletype_pre]
384 >> blank >> phrase [actions.teletype_post]
387 strikethrough =
388 ch_p('-') [actions.strikethrough_pre]
389 >> blank >> phrase [actions.strikethrough_post]
392 quote =
393 ch_p('"') [actions.quote_pre]
394 >> blank >> phrase [actions.quote_post]
397 replaceable =
398 ch_p('~') [actions.replaceable_pre]
399 >> blank >> phrase [actions.replaceable_post]
402 source_mode =
404 str_p("c++")
405 | "python"
406 ) [assign_a(actions.source_mode)]
409 footnote =
410 str_p("footnote") [actions.footnote_pre]
411 >> blank >> phrase [actions.footnote_post]
415 rule<Scanner> space, blank, comment, phrase, phrase_markup, image,
416 phrase_end, bold, italic, underline, teletype,
417 strikethrough, escape, url, common, funcref, classref,
418 memberref, enumref, macroref, headerref, conceptref, globalref,
419 anchor, link, hard_space, eol, inline_code, simple_format,
420 simple_bold, simple_italic, simple_underline,
421 simple_teletype, source_mode, template_, template_arg,
422 quote, code_block, footnote, replaceable, macro,
423 brackets, template_args, dummy_block, cond_phrase,
424 macro_identifier
427 rule<Scanner> const&
428 start() const { return common; }
431 bool& no_eols;
432 Actions& actions;
435 template <typename Actions>
436 struct simple_phrase_grammar
437 : public grammar<simple_phrase_grammar<Actions> >
439 simple_phrase_grammar(Actions& actions)
440 : actions(actions) {}
442 template <typename Scanner>
443 struct definition
445 definition(simple_phrase_grammar const& self)
446 : unused(false), common(self.actions, unused)
448 Actions& actions = self.actions;
450 phrase =
451 *( common
452 | comment
453 | (anychar_p - ']') [actions.plain_char]
457 comment =
458 "[/" >> *(dummy_block | (anychar_p - ']')) >> ']'
461 dummy_block =
462 '[' >> *(dummy_block | (anychar_p - ']')) >> ']'
466 bool unused;
467 rule<Scanner> phrase, comment, dummy_block;
468 phrase_grammar<Actions> common;
470 rule<Scanner> const&
471 start() const { return phrase; }
474 Actions& actions;
478 #endif // BOOST_SPIRIT_QUICKBOOK_PHRASE_HPP