«
 * C / C++ to HTML converter
 *
 * Converts C and C++ code to HTML with syntax hilighting
 * and folding by use of embedded comments.
 *
 * If you are viewing this file on a web page, it has already been
 * processed using itself, so you can click on the darker colored comments
 * to unfold the source code behind them.  Click on the comment again
 * (or the following source code) to re-fold it to the summary text.
 *
 * This comment is a fold, and clicking here will display an extended
 * comment section.
 »
/* This display style was inspired by a combination of Inmos's folding * editor for OCCAM, plus a web page from Tim Wakeham which did something * similar but at a file rather than block level. Tim tells me some current * IDEs such as SCITE have support for folded editing. There are also * editors available such as 'fe'. ( http://www.moria.de/~michael/fe/ ) * * The underlying HTML formatter is derived from an original by Brad Broerman. * (at http://www.bbroerman.net/ctohtml.html ) * * The folding convention is that "/" "*" "<" starts a fold, and the contents * of the comment are displayed as the fold's link to be clicked on. * A fold is terminated by a comment starting "/" "*" ">" and the content * of that comment is only displayed when the fold is expanded. If that * comment is completely empty (no whitespace) then it is not displayed * at all. * * Fold-comments are *not* escaped for HTML like other comments and can * therefore include HTML which will be displayed as formatted text/ * * I plan an extension so that comments between "/" "*" "<" and ">" "*" "/" * will not generate a fold but will allow HTML, simply as a way to embed * formatted text and diagrams in a source file. * * I am also considering adding a "+" (eg "/" "*" "<" "+") to a fold start * to signify that the default state for that fold should be 'unfolded', * thus allowing us to post files on the web which already show the * critical code areas ready for viewing. * * I may change the syntax of this system later to match the more common * convention of "{{{" and "}}}". */
« Declaration section »
« Support procedure section »
« Symbol table management »
« I/O support »
void PrintHeader (void) « Output Javascript and CSS to the header section »
{ « First the Javascript - comes from http://www.netlobo.com/div_hiding.html »
fprintf (stdout, "<script type=\"text/javascript\">\n"); fprintf (stdout, "<!--\n"); fprintf (stdout, "function toggleLayer( whichLayer, summary )\n"); fprintf (stdout, "{\n"); fprintf (stdout, " var elem, vis;\n"); fprintf (stdout, " if( document.getElementById ) // this is the way the standards work\n"); fprintf (stdout, " elem = document.getElementById( whichLayer );\n"); fprintf (stdout, " else if( document.all ) // this is the way old msie versions work\n"); fprintf (stdout, " elem = document.all[whichLayer];\n"); fprintf (stdout, " else if( document.layers ) // this is the way nn4 works\n"); fprintf (stdout, " elem = document.layers[whichLayer];\n"); fprintf (stdout, " vis = elem.style;\n"); fprintf (stdout, " // if the style.display value is blank we try to figure it out here\n"); fprintf (stdout, " if(vis.display==''&&elem.offsetWidth!=undefined&&elem.offsetHeight!=undefined)\n"); fprintf (stdout, " vis.display = (elem.offsetWidth!=0&&elem.offsetHeight!=0)?'block':'none';\n"); fprintf (stdout, " vis.display = (vis.display==''||vis.display=='block')?'none':'block';\n"); fprintf (stdout, "\n"); fprintf (stdout, " if( document.getElementById ) // this is the way the standards work\n"); fprintf (stdout, " elem = document.getElementById( summary );\n"); fprintf (stdout, " else if( document.all ) // this is the way old msie versions work\n"); fprintf (stdout, " elem = document.all[summary];\n"); fprintf (stdout, " else if( document.layers ) // this is the way nn4 works\n"); fprintf (stdout, " elem = document.layers[summary];\n"); fprintf (stdout, " vis = elem.style;\n"); fprintf (stdout, " // if the style.display value is blank we try to figure it out here\n"); fprintf (stdout, " if(vis.display==''&&elem.offsetWidth!=undefined&&elem.offsetHeight!=undefined)\n"); fprintf (stdout, " vis.display = (elem.offsetWidth!=0&&elem.offsetHeight!=0)?'block':'none';\n"); fprintf (stdout, " vis.display = (vis.display==''||vis.display=='block')?'none':'block';\n"); fprintf (stdout, "}\n"); fprintf (stdout, "// -->\n"); fprintf (stdout, "</script>\n"); fprintf (stdout, "\n");
« And then the CSS - derived from Tim Wakeham's page »
fprintf (stdout, "<style>\n"); fprintf (stdout, ".hidecode {\n"); fprintf (stdout, " z-index:99;\n"); fprintf (stdout, " visibility:hidden;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".file {\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".file div {\n"); fprintf (stdout, " margin: auto;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, "div p {\n"); fprintf (stdout, " margin-left: 15px;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, "body {\n"); fprintf (stdout, " font-family: Calibri, Arial, Georgia, \"Times New Roman\", Times, serif;\n"); fprintf (stdout, " color: #000000;\n"); fprintf (stdout, "}\n\n"); fprintf (stdout, "h2, h3 {\n"); fprintf (stdout, " margin-bottom: 0px;\n color: #000000;\n"); fprintf (stdout, " }\n"); fprintf (stdout, "\n"); fprintf (stdout, "p {\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, "h2 {\n color: #000000;\n"); fprintf (stdout, " }\n"); fprintf (stdout, "\n"); fprintf (stdout, "h2 .link {\n"); fprintf (stdout, " font-size: small;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".link a {\n"); fprintf (stdout, " text-decoration: none;\n outline: none;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, "h2 .link a:hover {\n"); fprintf (stdout, " text-decoration: none;\n"); fprintf (stdout, " }\n"); fprintf (stdout, "\n"); fprintf (stdout, ".data {\n"); fprintf (stdout, " display: none;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".data pre {\n"); fprintf (stdout, " overflow: auto;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".data p {\n"); fprintf (stdout, " margin-top: 0px;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".summary {\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".summary pre {\n"); fprintf (stdout, " overflow: auto;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".summary p {\n"); fprintf (stdout, " margin-top: 0px;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".summary a {\n"); /* not sure... */ fprintf (stdout, " text-decoration: none;\n outline: none;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".show {\n"); fprintf (stdout, " text-decoration: none;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".show:hover {\n"); fprintf (stdout, " text-decoration: none;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".flinks {\n"); fprintf (stdout, " text-decoration: none;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, ".flinks:hover {\n"); fprintf (stdout, " text-decoration: none;\n color: #000000;\n"); fprintf (stdout, "}\n"); fprintf (stdout, "\n"); fprintf (stdout, "\n"); fprintf (stdout, "\n"); fprintf (stdout, "</style>\n");
}
« Four procedures to output DHTML <div>s to hide/display the nested layers »
int Print_HTML (FILE * fstream, char *Title) « This is the main filter which loops over input C source and outputs HTML »
{ FILE *InFile; static int peekchar = -1; int inchar, i, newline = 1, WordIdx = 0, savecol; char word[280]; word[0] = '\0'; « Print out the HTML header. »
« Open the file for reading in text mode. »
/* Start reading it in, character by character. */ inchar = freadchar (InFile); peekchar = fpeek (InFile); while (!feof (InFile)) { « Check for keywords (& print in bold), and simple tags (not bold) »
if (inchar == '\n') { newline = 1; } if (!isspace (inchar)) { savecol = col; /* note column position. this is to re-indent <div>s which seem to be forced to start on the next line */ « Handle all '#' preprocessor directives. »
« Handle single line C++ style comments ('//'), and continue »
« Handle traditional C-style comments and folding directives, and continue »
else if ((inchar == '/') && (peekchar == '*')) { inchar = freadchar (InFile); peekchar = fpeek (InFile); if (peekchar == '<') { « start of a fold »
suppress_newline_hack = TRUE; } else if (peekchar == '>') { « end of a fold »
} else { « regular comment »
} continue; /* Now process next char */ }
« Handle double-quotes, and continue »
« Handle single-quotes, and continue »
/* Any other characters drop through */ newline = 0; } /* Including white space. I think I made an exception for it as a quick hack to remove initial spaces before a #define etc */ printchar (inchar, fstream); // print normal text here. // move on to next character inchar = freadchar (InFile); peekchar = fpeek (InFile); } fprintf (fstream, "\n</pre></BODY></HTML>\n"); fclose (InFile); return 1; }
int main (int argc, char *argv[]) { if (argc < 2) { printf ("Usage: %s [Filename]\n\n", argv[0]); return -1; } Print_HTML (stdout, argv[1]); return 0; }