|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r75896 - branches/quickbook-dev/tools/quickbook/src
From: dnljms_at_[hidden]
Date: 2011-12-11 06:15:10
Author: danieljames
Date: 2011-12-11 06:15:09 EST (Sun, 11 Dec 2011)
New Revision: 75896
URL: http://svn.boost.org/trac/boost/changeset/75896
Log:
Quickbook: Stateful actions class for syntax highlighter.
Text files modified:
branches/quickbook-dev/tools/quickbook/src/syntax_highlight.cpp | 316 +++++++++++++++++++++------------------
1 files changed, 170 insertions(+), 146 deletions(-)
Modified: branches/quickbook-dev/tools/quickbook/src/syntax_highlight.cpp
==============================================================================
--- branches/quickbook-dev/tools/quickbook/src/syntax_highlight.cpp (original)
+++ branches/quickbook-dev/tools/quickbook/src/syntax_highlight.cpp 2011-12-11 06:15:09 EST (Sun, 11 Dec 2011)
@@ -26,98 +26,90 @@
// It's named differently to distinguish it from the syntax highlighting
// actions, declared below.
- // Syntax Highlight Actions
-
- struct span
+ template <typename T, typename Value>
+ struct member_action_value
{
- // Decorates c++ code fragments
+ typedef void(T::*member_function)(Value);
- span(char const* name, collector& out)
- : name(name), out(out) {}
+ T& l;
+ member_function mf;
- void operator()(parse_iterator first, parse_iterator last) const;
+ member_action_value(T& l, member_function mf) : l(l), mf(mf) {}
- char const* name;
- collector& out;
+ void operator()(Value v) const {
+ (l.*mf)(v);
+ }
};
- struct span_start
+ template <typename T>
+ struct member_action
{
- span_start(char const* name, collector& out)
- : name(name), out(out) {}
+ typedef void(T::*member_function)(parse_iterator, parse_iterator);
- void operator()(parse_iterator first, parse_iterator last) const;
+ T& l;
+ member_function mf;
- char const* name;
- collector& out;
- };
+ member_action(T& l, member_function mf) : l(l), mf(mf) {}
- struct span_end
- {
- span_end(collector& out)
- : out(out) {}
-
- void operator()(parse_iterator first, parse_iterator last) const;
-
- collector& out;
+ void operator()(parse_iterator first, parse_iterator last) const {
+ (l.*mf)(first, last);
+ }
};
- struct unexpected_char
+ template <typename T, typename Arg1>
+ struct member_action1
{
- // Handles unexpected chars in c++ syntax
+ typedef void(T::*member_function)(parse_iterator, parse_iterator, Arg1);
- unexpected_char(
- collector& out
- , quickbook::actions& escape_actions)
- : out(out)
- , escape_actions(escape_actions) {}
+ T& l;
+ member_function mf;
- void operator()(parse_iterator first, parse_iterator last) const;
+ member_action1(T& l, member_function mf) : l(l), mf(mf) {}
- collector& out;
- quickbook::actions& escape_actions;
- };
-
- struct plain_char
- {
- // Prints a single plain char.
- // Converts '<' to "<"... etc See utils.hpp
+ struct impl
+ {
+ member_action1 a;
+ Arg1 value;
- plain_char(collector& out)
- : out(out) {}
+ impl(member_action1& a, Arg1 value) :
+ a(a), value(value)
+ {}
- void operator()(char ch) const;
- void operator()(parse_iterator first, parse_iterator last) const;
+ void operator()(parse_iterator first, parse_iterator last) const {
+ (a.l.*a.mf)(first, last, value);
+ }
+ };
- collector& out;
+ impl operator()(Arg1 a1) {
+ return impl(*this, a1);
+ }
};
- struct pre_escape_back
- {
- // Escapes back from code to quickbook (Pre)
-
- pre_escape_back(actions& escape_actions)
- : escape_actions(escape_actions) {}
-
- void operator()(parse_iterator first, parse_iterator last) const;
-
- actions& escape_actions;
- };
+ // Syntax Highlight Actions
- struct post_escape_back
+ struct syntax_highlight_actions
{
- // Escapes back from code to quickbook (Post)
-
- post_escape_back(collector& out, actions& escape_actions)
- : out(out), escape_actions(escape_actions) {}
-
- void operator()(parse_iterator first, parse_iterator last) const;
+ quickbook::collector out;
+ quickbook::actions& escape_actions;
+ do_macro_action do_macro_impl;
- collector& out;
- actions& escape_actions;
+ syntax_highlight_actions(quickbook::actions& escape_actions) :
+ out(), escape_actions(escape_actions),
+ do_macro_impl(out, escape_actions)
+ {}
+
+ void span(parse_iterator, parse_iterator, char const*);
+ void span_start(parse_iterator, parse_iterator, char const*);
+ void span_end(parse_iterator, parse_iterator);
+ void unexpected_char(parse_iterator, parse_iterator);
+ void plain_char(parse_iterator, parse_iterator);
+ void pre_escape_back(parse_iterator, parse_iterator);
+ void post_escape_back(parse_iterator, parse_iterator);
+ void do_macro(std::string const&);
};
- void span::operator()(parse_iterator first, parse_iterator last) const
+ void syntax_highlight_actions::span(parse_iterator first,
+ parse_iterator last, char const* name)
{
out << "<phrase role=\"" << name << "\">";
while (first != last)
@@ -125,21 +117,24 @@
out << "</phrase>";
}
- void span_start::operator()(parse_iterator first, parse_iterator last) const
+ void syntax_highlight_actions::span_start(parse_iterator first,
+ parse_iterator last, char const* name)
{
out << "<phrase role=\"" << name << "\">";
while (first != last)
detail::print_char(*first++, out.get());
}
- void span_end::operator()(parse_iterator first, parse_iterator last) const
+ void syntax_highlight_actions::span_end(parse_iterator first,
+ parse_iterator last)
{
while (first != last)
detail::print_char(*first++, out.get());
out << "</phrase>";
}
- void unexpected_char::operator()(parse_iterator first, parse_iterator last) const
+ void syntax_highlight_actions::unexpected_char(parse_iterator first,
+ parse_iterator last)
{
file_position const pos = escape_actions.current_file->position_of(first.base());
@@ -155,28 +150,31 @@
out << "</phrase>";
}
- void plain_char::operator()(char ch) const
- {
- detail::print_char(ch, out.get());
- }
-
- void plain_char::operator()(parse_iterator first, parse_iterator last) const
+ void syntax_highlight_actions::plain_char(parse_iterator first,
+ parse_iterator last)
{
while (first != last)
detail::print_char(*first++, out.get());
}
- void pre_escape_back::operator()(parse_iterator, parse_iterator) const
+ void syntax_highlight_actions::pre_escape_back(parse_iterator,
+ parse_iterator)
{
escape_actions.phrase.push(); // save the stream
}
- void post_escape_back::operator()(parse_iterator, parse_iterator) const
+ void syntax_highlight_actions::post_escape_back(parse_iterator,
+ parse_iterator)
{
out << escape_actions.phrase.str();
escape_actions.phrase.pop(); // restore the stream
}
+ void syntax_highlight_actions::do_macro(std::string const& v)
+ {
+ do_macro_impl(v);
+ }
+
// Syntax
struct keywords_holder
@@ -225,45 +223,56 @@
}
// Grammar for C++ highlighting
- struct cpp_highlight
- : public cl::grammar<cpp_highlight>
+ struct cpp_highlight : public cl::grammar<cpp_highlight>
{
- cpp_highlight(collector& out, actions& escape_actions)
- : out(out), escape_actions(escape_actions) {}
+ cpp_highlight(syntax_highlight_actions& actions)
+ : actions(actions) {}
template <typename Scanner>
struct definition
{
definition(cpp_highlight const& self)
- : g(self.escape_actions.grammar())
+ : g(self.actions.escape_actions.grammar())
{
+ member_action1<syntax_highlight_actions, char const*>
+ span(self.actions, &syntax_highlight_actions::span),
+ span_start(self.actions, &syntax_highlight_actions::span_start);
+ member_action<syntax_highlight_actions>
+ span_end(self.actions, &syntax_highlight_actions::span_end),
+ unexpected_char(self.actions, &syntax_highlight_actions::unexpected_char),
+ plain_char(self.actions, &syntax_highlight_actions::plain_char),
+ pre_escape_back(self.actions, &syntax_highlight_actions::pre_escape_back),
+ post_escape_back(self.actions, &syntax_highlight_actions::post_escape_back);
+ member_action_value<syntax_highlight_actions, std::string const&>
+ do_macro(self.actions, &syntax_highlight_actions::do_macro);
+
program
=
- *( (+cl::space_p) [plain_char(self.out)]
+ *( (+cl::space_p) [plain_char]
| macro
| escape
- | preprocessor [span("preprocessor", self.out)]
+ | preprocessor [span("preprocessor")]
| comment
- | keyword [span("keyword", self.out)]
- | identifier [span("identifier", self.out)]
- | special [span("special", self.out)]
- | string_ [span("string", self.out)]
- | char_ [span("char", self.out)]
- | number [span("number", self.out)]
- | cl::repeat_p(1)[cl::anychar_p]
- [unexpected_char(self.out, self.escape_actions)]
+ | keyword [span("keyword")]
+ | identifier [span("identifier")]
+ | special [span("special")]
+ | string_ [span("string")]
+ | char_ [span("char")]
+ | number [span("number")]
+ | cl::repeat_p(1)[cl::anychar_p] [unexpected_char]
)
;
macro =
// must not be followed by alpha or underscore
- cl::eps_p(self.escape_actions.macro
+ cl::eps_p(self.actions.escape_actions.macro
>> (cl::eps_p - (cl::alpha_p | '_')))
- >> self.escape_actions.macro [do_macro_action(self.out, self.escape_actions)]
+ >> self.actions.escape_actions.macro
+ [do_macro]
;
escape =
- cl::str_p("``") [pre_escape_back(self.escape_actions)]
+ cl::str_p("``") [pre_escape_back]
>>
(
(
@@ -275,10 +284,10 @@
)
|
(
- cl::eps_p [self.escape_actions.error]
+ cl::eps_p [self.actions.escape_actions.error]
>> *cl::anychar_p
)
- ) [post_escape_back(self.out, self.escape_actions)]
+ ) [post_escape_back]
;
preprocessor
@@ -286,18 +295,18 @@
;
comment
- = cl::str_p("//") [span_start("comment", self.out)]
+ = cl::str_p("//") [span_start("comment")]
>> *( escape
| (+(cl::anychar_p - (cl::eol_p | "``")))
- [plain_char(self.out)]
+ [plain_char]
)
- >> cl::eps_p [span_end(self.out)]
- | cl::str_p("/*") [span_start("comment", self.out)]
+ >> cl::eps_p [span_end]
+ | cl::str_p("/*") [span_start("comment")]
>> *( escape
| (+(cl::anychar_p - (cl::str_p("*/") | "``")))
- [plain_char(self.out)]
+ [plain_char]
)
- >> (!cl::str_p("*/")) [span_end(self.out)]
+ >> (!cl::str_p("*/")) [span_end]
;
keyword
@@ -343,50 +352,60 @@
start() const { return program; }
};
- collector& out;
- actions& escape_actions;
+ syntax_highlight_actions& actions;
};
// Grammar for Python highlighting
// See also: The Python Reference Manual
// http://docs.python.org/ref/ref.html
- struct python_highlight
- : public cl::grammar<python_highlight>
+ struct python_highlight : public cl::grammar<python_highlight>
{
- python_highlight(collector& out, actions& escape_actions)
- : out(out), escape_actions(escape_actions) {}
+ python_highlight(syntax_highlight_actions& actions)
+ : actions(actions) {}
template <typename Scanner>
struct definition
{
definition(python_highlight const& self)
- : g(self.escape_actions.grammar())
+ : g(self.actions.escape_actions.grammar())
{
+ member_action1<syntax_highlight_actions, char const*>
+ span(self.actions, &syntax_highlight_actions::span),
+ span_start(self.actions, &syntax_highlight_actions::span_start);
+ member_action<syntax_highlight_actions>
+ span_end(self.actions, &syntax_highlight_actions::span_end),
+ unexpected_char(self.actions, &syntax_highlight_actions::unexpected_char),
+ plain_char(self.actions, &syntax_highlight_actions::plain_char),
+ pre_escape_back(self.actions, &syntax_highlight_actions::pre_escape_back),
+ post_escape_back(self.actions, &syntax_highlight_actions::post_escape_back);
+ member_action_value<syntax_highlight_actions, std::string const&>
+ do_macro(self.actions, &syntax_highlight_actions::do_macro);
+
program
=
- *( (+cl::space_p) [plain_char(self.out)]
+ *( (+cl::space_p) [plain_char]
| macro
| escape
| comment
- | keyword [span("keyword", self.out)]
- | identifier [span("identifier", self.out)]
- | special [span("special", self.out)]
- | string_ [span("string", self.out)]
- | number [span("number", self.out)]
- | cl::repeat_p(1)[cl::anychar_p]
- [unexpected_char(self.out, self.escape_actions)]
+ | keyword [span("keyword")]
+ | identifier [span("identifier")]
+ | special [span("special")]
+ | string_ [span("string")]
+ | number [span("number")]
+ | cl::repeat_p(1)[cl::anychar_p] [unexpected_char]
)
;
macro =
// must not be followed by alpha or underscore
- cl::eps_p(self.escape_actions.macro
+ cl::eps_p(self.actions.escape_actions.macro
>> (cl::eps_p - (cl::alpha_p | '_')))
- >> self.escape_actions.macro [do_macro_action(self.out, self.escape_actions)]
+ >> self.actions.escape_actions.macro
+ [do_macro]
;
escape =
- cl::str_p("``") [pre_escape_back(self.escape_actions)]
+ cl::str_p("``") [pre_escape_back]
>>
(
(
@@ -398,19 +417,19 @@
)
|
(
- cl::eps_p [self.escape_actions.error]
+ cl::eps_p [self.actions.escape_actions.error]
>> *cl::anychar_p
)
- ) [post_escape_back(self.out, self.escape_actions)]
+ ) [post_escape_back]
;
comment
- = cl::str_p("#") [span_start("comment", self.out)]
+ = cl::str_p("#") [span_start("comment")]
>> *( escape
| (+(cl::anychar_p - (cl::eol_p | "``")))
- [plain_char(self.out)]
+ [plain_char]
)
- >> cl::eps_p [span_end(self.out)]
+ >> cl::eps_p [span_end]
;
keyword
@@ -468,40 +487,46 @@
start() const { return program; }
};
- collector& out;
- actions& escape_actions;
+ syntax_highlight_actions& actions;
};
// Grammar for plain text (no actual highlighting)
- struct teletype_highlight
- : public cl::grammar<teletype_highlight>
+ struct teletype_highlight : public cl::grammar<teletype_highlight>
{
- teletype_highlight(collector& out, actions& escape_actions)
- : out(out), escape_actions(escape_actions) {}
+ teletype_highlight(syntax_highlight_actions& actions)
+ : actions(actions) {}
template <typename Scanner>
struct definition
{
definition(teletype_highlight const& self)
- : g(self.escape_actions.grammar())
+ : g(self.actions.escape_actions.grammar())
{
+ member_action<syntax_highlight_actions>
+ plain_char(self.actions, &syntax_highlight_actions::plain_char),
+ pre_escape_back(self.actions, &syntax_highlight_actions::pre_escape_back),
+ post_escape_back(self.actions, &syntax_highlight_actions::post_escape_back);
+ member_action_value<syntax_highlight_actions, std::string const&>
+ do_macro(self.actions, &syntax_highlight_actions::do_macro);
+
program
=
*( macro
| escape
- | cl::repeat_p(1)[cl::anychar_p] [plain_char(self.out)]
+ | cl::repeat_p(1)[cl::anychar_p] [plain_char]
)
;
macro =
// must not be followed by alpha or underscore
- cl::eps_p(self.escape_actions.macro
+ cl::eps_p(self.actions.escape_actions.macro
>> (cl::eps_p - (cl::alpha_p | '_')))
- >> self.escape_actions.macro [do_macro_action(self.out, self.escape_actions)]
+ >> self.actions.escape_actions.macro
+ [do_macro]
;
escape =
- cl::str_p("``") [pre_escape_back(self.escape_actions)]
+ cl::str_p("``") [pre_escape_back]
>>
(
(
@@ -513,10 +538,10 @@
)
|
(
- cl::eps_p [self.escape_actions.error]
+ cl::eps_p [self.actions.escape_actions.error]
>> *cl::anychar_p
)
- ) [post_escape_back(self.out, self.escape_actions)]
+ ) [post_escape_back]
;
}
@@ -528,8 +553,7 @@
start() const { return program; }
};
- collector& out;
- actions& escape_actions;
+ syntax_highlight_actions& actions;
};
std::string syntax_highlight(
@@ -538,22 +562,22 @@
actions& escape_actions,
std::string const& source_mode)
{
- quickbook::collector temp;
+ syntax_highlight_actions syn_actions(escape_actions);
// print the code with syntax coloring
if (source_mode == "c++")
{
- cpp_highlight cpp_p(temp, escape_actions);
+ cpp_highlight cpp_p(syn_actions);
boost::spirit::classic::parse(first, last, cpp_p);
}
else if (source_mode == "python")
{
- python_highlight python_p(temp, escape_actions);
+ python_highlight python_p(syn_actions);
boost::spirit::classic::parse(first, last, python_p);
}
else if (source_mode == "teletype")
{
- teletype_highlight teletype_p(temp, escape_actions);
+ teletype_highlight teletype_p(syn_actions);
boost::spirit::classic::parse(first, last, teletype_p);
}
else
@@ -562,7 +586,7 @@
}
std::string str;
- temp.swap(str);
+ syn_actions.out.swap(str);
return str;
}
Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk