More cleanups to HTML rewriter API: remove the InsertTag method; was too complicated

and clients can achieve a cleaner design just by inserting tags directly.  Reserve
the "html" namespace for meta-level operations (e.g., escaping text, etc.)

llvm-svn: 48524
This commit is contained in:
Ted Kremenek 2008-03-19 01:30:02 +00:00
parent 265f780c22
commit 5ddff02861
3 changed files with 31 additions and 124 deletions

View File

@ -50,22 +50,32 @@ HTMLPrinter::~HTMLPrinter() {
html::EscapeText(R, FileID);
html::AddLineNumbers(R, FileID);
html::InsertOuterTag(R, html::PRE, StartLoc, EndLoc, 0, 0, true);
html::InsertOuterTag(R, html::BODY, StartLoc, EndLoc, NULL, "\n", true);
// Generate CSS.
// Generate header
std::ostringstream css;
css << "\n <style type=\"text/css\">\n";
css << " .nums, .lines { vertical-align:top }\n";
css << " .nums { padding-right:.5em; width:2.5em }\n";
css << " </style>\n";
{
std::ostringstream os;
os << "<html>\n<head>\n"
<< " <style type=\"text/css\">\n"
<< " .nums, .lines { vertical-align:top }\n"
<< " .nums { padding-right:.5em; width:2.5em }\n"
<< " </style>\n"
<< "</head>\n"
<< "<body>\n<pre>";
// Add <head> and <html> tags.
R.InsertTextBefore(StartLoc, os.str().c_str(), os.str().size());
}
// Generate footer
{
std::ostringstream os;
os << "</pre>\n</body></html>\n";
R.InsertTextAfter(EndLoc, os.str().c_str(), os.str().size());
}
html::InsertTagBefore(R, html::HEAD, StartLoc, StartLoc, 0,css.str().c_str());
html::InsertOuterTag(R, html::HTML, StartLoc, EndLoc, 0, "\n");
// Emit the HTML.

View File

@ -23,43 +23,8 @@ class Rewriter;
namespace html {
// Basic operations.
enum Tags { BODY,
DIV,
HEAD,
HTML,
PRE,
SPAN,
STYLE };
void EscapeText(Rewriter& R, unsigned FileID, bool EscapeSpaces = false);
void InsertTag(Rewriter& R, Tags tag,
SourceLocation OpenLoc, SourceLocation CloseLoc,
const char* Attrs = NULL, const char* Content = NULL,
bool Newline = false,
bool OpenInsertBefore = true, bool CloseInsertBefore = false);
static inline
void InsertTagBefore(Rewriter& R, Tags tag,
SourceLocation OpenLoc, SourceLocation CloseLoc,
const char* Attrs = NULL, const char* Content = NULL,
bool Newline = false) {
InsertTag(R, tag, OpenLoc, CloseLoc, Attrs, Content, Newline, true, true);
}
static inline
void InsertOuterTag(Rewriter& R, Tags tag,
SourceLocation OpenLoc, SourceLocation CloseLoc,
const char* Attrs = NULL, const char* Content = NULL,
bool Newline = false) {
InsertTag(R, tag, OpenLoc, CloseLoc, Attrs, Content, Newline, true, false);
}
// High-level operations.
void AddLineNumbers(Rewriter& R, unsigned FileID);
} // end html namespace

View File

@ -20,10 +20,6 @@
using namespace clang;
//===----------------------------------------------------------------------===//
// Basic operations.
//===----------------------------------------------------------------------===//
void html::EscapeText(Rewriter& R, unsigned FileID, bool EscapeSpaces) {
const llvm::MemoryBuffer *Buf = R.getSourceMgr().getBuffer(FileID);
@ -50,83 +46,19 @@ void html::EscapeText(Rewriter& R, unsigned FileID, bool EscapeSpaces) {
}
}
static void TagOpen(Rewriter& R, const char* TagStr,
const char* Attr, const char* Content,
SourceLocation L, bool InsertBefore) {
std::ostringstream os;
os << '<' << TagStr;
if (Attr) os << ' ' << Attr;
os << '>';
if (Content) os << Content;
if (InsertBefore)
R.InsertTextBefore(L, os.str().c_str(), os.str().size());
else
R.InsertTextAfter(L, os.str().c_str(), os.str().size());
}
static void TagClose(Rewriter& R, const char* TagStr, SourceLocation L,
bool Newline, bool InsertBefore) {
std::ostringstream os;
os << "</" << TagStr << ">";
if (Newline) os << '\n';
if (InsertBefore)
R.InsertTextBefore(L, os.str().c_str(), os.str().size());
else
R.InsertTextAfter(L, os.str().c_str(), os.str().size());
}
void html::InsertTag(Rewriter& R, html::Tags tag,
SourceLocation B, SourceLocation E,
const char* Attr, const char* Content, bool Newline,
bool OpenInsertBefore, bool CloseInsertBefore) {
const char* TagStr = 0;
switch (tag) {
default: break;
case BODY: TagStr = "body"; break;
case DIV: TagStr = "div"; break;
case HEAD: TagStr = "head"; break;
case HTML: TagStr = "html"; break;
case PRE: TagStr = "pre"; break;
case SPAN: TagStr = "span"; break;
case STYLE: TagStr = "style"; break;
}
assert (TagStr && "Tag not supported.");
// Generate the opening tag. We also generate the closing
// tag of the start and end SourceLocations are the same.
if (OpenInsertBefore) {
TagClose(R, TagStr, E, Newline, CloseInsertBefore);
TagOpen(R, TagStr, Attr, Content, B, true);
}
else {
TagOpen(R, TagStr, Attr, Content, B, false);
TagClose(R, TagStr, E, Newline, true);
}
}
//===----------------------------------------------------------------------===//
// High-level operations.
//===----------------------------------------------------------------------===//
static void AddLineNumber(Rewriter& R, unsigned LineNo,
SourceLocation B, SourceLocation E) {
// Add two "div" tags: one to contain the line number, and the other
// to contain the content of the line.
// Surround the line with a span tag.
R.InsertTextBefore(E, "</span>", 7);
R.InsertTextBefore(B, "<span style=lines>", 18);
// Insert a span tag for the line number.
std::ostringstream os;
os << LineNo;
html::InsertTag(R, html::SPAN, B, E, "style=lines");
html::InsertTag(R, html::SPAN, B, B, "style=nums", os.str().c_str());
os << "<span style=nums>" << LineNo << "</span>";
R.InsertTextBefore(B, os.str().c_str(), os.str().size());
}
void html::AddLineNumbers(Rewriter& R, unsigned FileID) {