Java Source Code Presenter
by Roedy Green ©1996-2008 Canadian Mind Products
This essay is about a suggested
student project in
Java programming. This essay gives a rough overview of how it might work. It
does not describe an actual complete program. I have
no source, object,
specifications, file layouts or anything else useful to implementing this
project. Everything I have to say to help you with this project is written below.
I am
not prepared to help you implement it; I have too many other
projects of my own.
I do contract work for a living, which could include writing a program such as
this. However, I don’t do people’s homework
for them. That just robs them of an education.
You have my full permission to implement this project any way you please.
The JDisplay Java Applet displays the large program listings on this web page.
JDisplay requires Java version 1.5 or later, preferably 1.6.0_11. If you can’t
see the listings, of you if just want to learn more about JDisplay, click
here
for help.
This converts Java source into HTML for public presentation, much like Jonathan
Revusky’s JavaToHTML. It would colour various syntatic elements. It would
use bold on a variable in the place it is defined. It would use variable sized ()
and {} depending on how deeply nested they are. You can see some examples of the
sort of output I’m after by looking at the sample. It might use special
markings to delimit methods and classes. Here is the output of a crude version I
use now that generated HTML with style tags, that than the be use to control the
fonts, coulours, sizes etc of each component of the listing. I have chosen a
rather conservative colour scheme with only subtle variations.
If, jdisplay, the above Source code display Java Applet does not work…
- This Java Applet needs Java 1.1 or later, version 1.6.0_11 recommended and a recent browser.
- You should see the Applet above looking much like the screenshot. If you don’t, the following should help you get it working:
- If you are using Microsoft Internet Explorer, try another browser. Seriously. Microsoft has taken great pains, over and over, to screw up Java and every other multi-platform standardisation.
- If you are using Internet Explorer 7 or 8, you must allow blocked content permission for Active X to run. This also gives permission to Java to run. Click the Information bar, and then click Allow blocked content. Unfortunately, this also allows dangerous ActiveX code to run. However, you must do this in order to get access to perfectly-safe Java Applets running in a sandbox. This is part of Microsoft’s war on Java. Don’t put up with it! Use a different browser.
- Especially if this Applet has worked before, try clearing the browser cache and rebooting.
- To ensure your Java is up to date, check with Wassup. First, download it and run it as an application independent of your browser, then run it online as an Applet to add the complication of your browser.
- If the above Applet does not work, check the Java console for error messages.
- If the above Applet does not work, you might have better luck with the downloadable version.
- If you still can’t get the program working click HELP for more detail.
- If you can’t get the above Applet working after trying the advice above and from the HELP button below, have bugs to report or ideas to improve the program or its documentation, please send me an email at
.
Get New Java Get New Browser
Help
It would render the HTML inside the Javadoc comments (e.g <b>length</b>
must be < 100) in human form (e.g. length
must be < 100) rather than displaying it literally as it appeared in
the orginal source.
For importing ordinary Java source code, a parser such as JavaCC or ANTLR might
be useful.
The tricky part is figuring out how to do decent variable left indenting in HTML.
I know of five techniques:
- Use a dummy gif and stretch its width. This is slow, verbose, and does not look
all that good in all browsers. Remember to use border="0"
to avoid a line around the dummy gif.The advantage is you can also control
vertical spacing by stretching the gif height.
- Use <ul> to indent and </ul>
to unindent. This has the unwanted side effect of extra blank lines. This is
technically invalid, and will set HTMLValidator
screaming, However, it works in all the browsers I have tried. I get rude public
postings about my use of it from purists though.
- Use <td colspan="n"></td> <td
colspan="max-n">real stuff</td>. You can’t
control the indentation column widths with <TABLE
CELLSPACING="30", because it affects vertical spacing as well.
You hide the tableness of the whole thing by using <TABLE
BORDER="0". This technique has the added advantage of properly
indenting wrapped long lines that don’t quite fit on the screen in some
browsers. See the HTML used to create the waterfall
entry.
- Use the margin control in CSS, e.g. with a <div class="group">
and a style div.group { margin-left : 10px;}
- Use <pre>. The advantage of this is you don’t
interfere at all with the original indenting or line breaks. You just do what
the programmer did originally. You can’t screw it up or do it a different
way from the way he likes. The problem with <pre>
stuff is that the tiniest jostle and it is turned to mush, with all the lines
wrapped.
Ideally whatever you generate is pure CSS, so the look can be changed at whim
with just the style sheet.
You might run this as a batch utility to prepare HTML. You might also create it
as an Applet that provides a scrolling display. You
pass the name of a *.java file in the Applet
tag or provide the source code text snippet inline. The end user can click a
button to download the raw *.java file.
The problem with generating HTML and embedding it in your HTML pages is you can’t
edit it. It just looks like gibberish. Further, if I change my mind on how the
rendering should be done, I have to manually regenerate all the HTML from the
orgininal Java (perhaps now lost) and replace the HTML. I think it would be
better to post the plain Java files, and then have an Applet
render them on the fly. Then people could download the pristine source without
any HTML contamination effects, such an unwanted line breaks.
The other problem with generating HTML is html beautifiers break lines
introducing improper white space into the program. Another problem is with <DIV>
tags you can’t exactly match the indentation of the original. You must
deduce the nesting depth. This gets complicated. You could do it by generating
HTML with <PRE> tags or with an Applet that
drew on a Canvas. To make cut and paste work, is
very tricky since it would be just a bit image you are displaying. If you
generated HTML and displayed it internally with Swing, at least cut and paste
would come out in the wash so people could take copies of snippets of the
program without fuss. The advantage of an Applet is
it need not render the entire listing. The disadvantage is the browser search
and search engines would not see the rendered text.
The HTML you generate can be done with <font or
with <span class="operator"> type tags.
The second form lets you tune the rendering just by changing the style sheet.
The first type will work in Swing components, whereas the second will not.
So most likely you will want to render from plain *.java
files on the fly in the Applet and give the user the
option to download the plain *.java file. Render using
Swing components and old-fashioned <pre> and <font
tags.
JDisplay Implementation
I have implemented this project in a quite different fashion than described
above. I have convert my website to use it. I still have not got around to
bundling it up for distribution. Here is the JApplet
that displays predigested source code.
Here is the main drawing class:
Upsides
- I can display code snippets, code with syntax errors, and code in languages
similar to Java.
- I can post large listings that scroll. I don’t need a window big enough
for the whole program.
- I recreate the indenting and white space exactly as on the original.
- The Applet itself is very small, and loads quickly
because it does not do any parsing.
- Rendering is extremely fast, much faster than HTML rendering.
- Parsing is extremely fast.
- You can copy/paste from the display.
- Note the variable size {} () and []. Note the bolded return
to make them stand out. Note how variable, class and method definitions are
bolded to make them stand out. Note the colour and font differences between
classes, interfaces, variable, methods, comments etc.
Downsides
- It requires Java to work, and requires loading a small Applet
for each code snippet. Applets can’t simply read the files they need. They
must be bundled in resources.
- HTML in the Javadoc is rendered as-is, not interpreted.
- To change the colour scheme, you have to change the Applet
code. You can’t change it just by changing a CSS style sheet.
- Snippets have to be preprocessed before use to parse them into arrays of
serialised objects.
- If the user prints the entire page, the Applet windows just show up as gray
squares.
How It Works
I did not use a standard Java 1.5 parser. I first cooked up a simple-minded
tokenizer and parser that breaks the text into chunks called tokens
and identifies what sort of thing each token is, e.g. a method name, a method
definition, a class, an interface, an operator, a keyword, a { etc.
Then I write out each snippet as a serialized array of objects, each of which
knows how to render itself.
The Applet then just reads the array of objects and
uses drawString to render each token in the
appropriate colour, font, style and size.
The problem is you can’t copy/paste from my colourful bitmap, so when you
click the display turns into a black and white TextField
rendering that you can copy from.
I use the Graphics.getClipBounds to only bother
rendering parts of the Java source program that are scrolled on-screen.
Rectangle r = g.getClipBounds();
I use a macro to generate the Applet tags, and a
download button for those who do not have Java to see the snippet as raw text.
Torture Test
Here is a torture test of my Java parser and presenter, a particularly difficult
document to render since it contains syntax errors. I check that it renders
precisely the same the same text I feed it. Here is the Java test program
rendered by the JDisplay Applet:
Here is the Java test program rendered in HTML:
Here is a torture test of my bat parser as rendered by the JDisplay Applet:
Here is the bat test program rendered in HTML:
Summary
To summarise, if you use the HTML-generation-the-embed approach, you don’t
have to get it perfect. You can always manually tune the results afterward, as I
do for jtoh. On the other hand, your HTML editors will inappropriately tidy your
HTHL inserting unwanted white space and removing it improperly in its desire to
get all the lines the same length. For shorter programs this will be faster
since you don’t have to fire up Java and an Applet.
If you go the dynamic generation Applet route, you
can’t use style sheets, your program must be 100% bug free, and your end
users must have recent working Java Plug-Ins with Swing. In turn you have very
little work to do to prepare each new program for display. Your editors won’t
be able to see, much less mess with your generated HTML. For very long programs
this may be faster, since you don’t have to download all the style tags.
What are the colour-size-font-bold-coding classes? keywords, operators, packages,
classes, methods, variables, class definitions (the class name in the place
where the class is defined, e.g. right after public class),
method definitions. variable definitions, constants, literals, string literals,
assignment (=), dot (.), parentheses () with size and colour coding for nest
depth, brackets [] with size and colour coding for nest depth, braces {} with
size and colour coding for nest depth, operators (+ - ++ == !=… perhaps
in shades to indicate 14 levels of priority lightest computed first, darkest and
biggest last). I also encode a name where it is defined in bold and plain where
it is referenced.
There is a such a program part of the SwingSet2 demo that comes in the demos
directory of the JDK, under Progress Bar, though I have not yet figured out what
classes it uses or how to work it. It tends to create displays in type too small.
For inspiration: