From e0e6bde4a5f1e4b7994937b3e385e823c24e9b3b Mon Sep 17 00:00:00 2001
From: jrandom <jrandom>
Date: Tue, 6 Sep 2005 20:05:09 +0000
Subject: [PATCH] throw css around like mad (very minimal stylesheet in place)

---
 .../java/src/net/i2p/syndie/BlogManager.java  |  43 +--
 apps/syndie/java/src/net/i2p/syndie/User.java |   4 +-
 .../i2p/syndie/sml/HTMLPreviewRenderer.java   |  70 ++--
 .../src/net/i2p/syndie/sml/HTMLRenderer.java  | 315 +++++++++++-------
 .../net/i2p/syndie/web/ArchiveViewerBean.java |  57 +---
 .../net/i2p/syndie/web/RemoteArchiveBean.java |  79 +++--
 apps/syndie/jsp/_bodyindex.jsp                |  11 +-
 apps/syndie/jsp/_topnav.jsp                   |  40 +--
 apps/syndie/jsp/addresses.jsp                 |  86 +++--
 apps/syndie/jsp/admin.jsp                     |  69 ++--
 apps/syndie/jsp/externallink.jsp              |  26 +-
 apps/syndie/jsp/import.jsp                    |  49 +--
 apps/syndie/jsp/index.jsp                     |  17 +-
 apps/syndie/jsp/post.jsp                      |  71 ++--
 apps/syndie/jsp/register.jsp                  |  41 +--
 apps/syndie/jsp/remote.jsp                    |  55 +--
 apps/syndie/jsp/style.jsp                     |   8 +-
 apps/syndie/jsp/syndie.css                    | 141 ++++----
 apps/syndie/jsp/viewmetadata.jsp              |  26 +-
 .../src/net/i2p/crypto/SHA256Generator.java   |   3 +
 core/java/src/net/i2p/util/FileUtil.java      |   5 +-
 21 files changed, 675 insertions(+), 541 deletions(-)

diff --git a/apps/syndie/java/src/net/i2p/syndie/BlogManager.java b/apps/syndie/java/src/net/i2p/syndie/BlogManager.java
index 3e696c0633..bbc0423119 100644
--- a/apps/syndie/java/src/net/i2p/syndie/BlogManager.java
+++ b/apps/syndie/java/src/net/i2p/syndie/BlogManager.java
@@ -185,7 +185,7 @@ public class BlogManager {
     }
     
     public String login(User user, String login, String pass) {
-        if ( (login == null) || (pass == null) ) return "Login not specified";
+        if ( (login == null) || (pass == null) ) return "<span class=\"b_loginMsgErr\">Login not specified</span>";
         Hash userHash = _context.sha().calculateHash(DataHelper.getUTF8(login));
         Hash passHash = _context.sha().calculateHash(DataHelper.getUTF8(pass));
         File userFile = new File(_userDir, Base64.encode(userHash.getData()));
@@ -208,10 +208,10 @@ public class BlogManager {
                 return user.login(login, pass, props);
             } catch (IOException ioe) {
                 ioe.printStackTrace();
-                return "Error logging in - corrupt userfile";
+                return "<span class=\"b_loginMsgErr\">Error logging in - corrupt userfile</span>";
             }
         } else {
-            return "User does not exist";
+            return "<span class=\"b_loginMsgErr\">User does not exist</span>";
         }
     }
     
@@ -294,17 +294,18 @@ public class BlogManager {
     }
     
     public String authorizeRemoteAccess(User user, String password) {
-        if (!user.getAuthenticated()) return "Not logged in";
+        if (!user.getAuthenticated()) return "<span class=\"b_remoteMsgErr\">Not logged in</span>";
         String remPass = getRemotePasswordHash();
         if (remPass == null)
-            return "Remote access password not configured - please specify a remote archive password in your syndie.config or on /admin.jsp";
+            return "<span class=\"b_remoteMsgErr\">Remote access password not configured - please <a href=\"admin.jsp\">specify</a> a remote " +
+                   "archive password</span>";
         
         if (authorizeRemote(password)) {
             user.setAllowAccessRemote(true);
             saveUser(user);
-            return "Remote access authorized";
+            return "<span class=\"b_remoteMsgOk\">Remote access authorized</span>";
         } else {
-            return "Remote access denied";
+            return "<span class=\"b_remoteMsgErr\">Remote access denied</span>";
         }
     }
     
@@ -329,15 +330,15 @@ public class BlogManager {
         if (hashedRegistrationPassword != null) {
             try {
                 if (!hashedRegistrationPassword.equals(Base64.encode(_context.sha().calculateHash(registrationPassword.getBytes("UTF-8")).getData())))
-                    return "Invalid registration password";
+                    return "<span class=\"b_regMsgErr\">Invalid registration password</span>";
             } catch (UnsupportedEncodingException uee) {
-                return "Error registering";
+                return "<span class=\"b_regMsgErr\">Error registering</span>";
             }
         }
         String userHash = Base64.encode(_context.sha().calculateHash(DataHelper.getUTF8(login)).getData());
         File userFile = new File(_userDir, userHash);
         if (userFile.exists()) {
-            return "Cannot register the login " + login + ": it already exists";
+            return "<span class=\"b_regMsgErr\">Cannot register the login " + login + ": it already exists</span>";
         } else {
             BlogInfo info = createBlog(blogName, blogDescription, contactURL, null);
             String hashedPassword = Base64.encode(_context.sha().calculateHash(DataHelper.getUTF8(password)).getData());
@@ -355,7 +356,7 @@ public class BlogManager {
                 bw.flush();
             } catch (IOException ioe) {
                 ioe.printStackTrace();
-                return "Internal error registering - " + ioe.getMessage();
+                return "<span class=\"b_regMsgErr\">Internal error registering - " + ioe.getMessage() + "</span>";
             } finally {
                 if (out != null) try { out.close(); } catch (IOException ioe) {}
             }
@@ -367,7 +368,7 @@ public class BlogManager {
 
     public String exportHosts(User user) {
         if (!user.getAuthenticated() || !user.getAllowAccessRemote())
-            return "Not authorized to export the hosts";
+            return "<span class=\"b_addrMsgErr\">Not authorized to export the hosts</span>";
         Map newNames = new HashMap();
         PetNameDB db = user.getPetNameDB();
         for (Iterator names = db.getNames().iterator(); names.hasNext(); ) {
@@ -395,11 +396,11 @@ public class BlogManager {
                     osw.close();
                 } catch (IOException ioe) {
                     ioe.printStackTrace();
-                    return "Error exporting the hosts: " + ioe.getMessage();
+                    return "<span class=\"b_addrMsgErr\">Error exporting the hosts: " + ioe.getMessage() + "</span>";
                 }
             }
         }
-        return "Hosts exported";
+        return "<span class=\"b_addrMsgOk\">Hosts exported</span>";
     }
     
     public BlogURI createBlogEntry(User user, String subject, String tags, String entryHeaders, String sml) {
@@ -527,25 +528,25 @@ public class BlogManager {
     }
 
     public String addAddress(User user, String name, String protocol, String location, String schema) {
-        if (!user.getAuthenticated()) return "Not logged in";
+        if (!user.getAuthenticated()) return "<span class=\"b_addrMsgErr\">Not logged in</span>";
         boolean ok = validateAddressName(name);
-        if (!ok) return "Invalid name: " + HTMLRenderer.sanitizeString(name);
+        if (!ok) return "<span class=\"b_addrMsgErr\">Invalid name: " + HTMLRenderer.sanitizeString(name) + "</span>";
         ok = validateAddressLocation(location);
-        if (!ok) return "Invalid location: " + HTMLRenderer.sanitizeString(location);
-        if (!validateAddressSchema(schema)) return "Unsupported schema: " + HTMLRenderer.sanitizeString(schema);
+        if (!ok) return "<span class=\"b_addrMsgErr\">Invalid location: " + HTMLRenderer.sanitizeString(location) + "</span>";
+        if (!validateAddressSchema(schema)) return "<span class=\"b_addrMsgErr\">Unsupported schema: " + HTMLRenderer.sanitizeString(schema) + "</span>";
         // no need to quote user/location further, as they've been sanitized
         
         PetNameDB names = user.getPetNameDB();
         if (names.exists(name))
-            return "Name is already in use";
+            return "<span class=\"b_addrMsgErr\">Name is already in use</span>";
         PetName pn = new PetName(name, schema, protocol, location);
         names.set(name, pn);
         
         try {
             names.store(user.getAddressbookLocation());
-            return "Address " + name + " written to your addressbook";
+            return "<span class=\"b_addrMsgOk\">Address " + name + " written to your addressbook</span>";
         } catch (IOException ioe) {
-            return "Error writing out the name: " + ioe.getMessage();
+            return "<span class=\"b_addrMsgErr\">Error writing out the name: " + ioe.getMessage() + "</span>";
         }
     }
     
diff --git a/apps/syndie/java/src/net/i2p/syndie/User.java b/apps/syndie/java/src/net/i2p/syndie/User.java
index 9bb1279e1a..0fe1a6c5c0 100644
--- a/apps/syndie/java/src/net/i2p/syndie/User.java
+++ b/apps/syndie/java/src/net/i2p/syndie/User.java
@@ -108,7 +108,7 @@ public class User {
         String hpass = Base64.encode(_context.sha().calculateHash(DataHelper.getUTF8(pass)).getData());
         if (!hpass.equals(expectedPass)) {
             _authenticated = false;
-            return "Incorrect password";
+            return "<span class=\"b_loginMsgErr\">Incorrect password</span>";
         }
         
         _username = login;
@@ -194,7 +194,7 @@ public class User {
         try { return Integer.parseInt(val); } catch (NumberFormatException nfe) { return -1; }
     }
     
-    public static final String LOGIN_OK = "Logged in";
+    public static final String LOGIN_OK = "<span class=\"b_loginMsgOk\">Logged in</span>";
     
     public String export() {
         StringBuffer buf = new StringBuffer(512);
diff --git a/apps/syndie/java/src/net/i2p/syndie/sml/HTMLPreviewRenderer.java b/apps/syndie/java/src/net/i2p/syndie/sml/HTMLPreviewRenderer.java
index b12db6b690..b1ecec61a3 100644
--- a/apps/syndie/java/src/net/i2p/syndie/sml/HTMLPreviewRenderer.java
+++ b/apps/syndie/java/src/net/i2p/syndie/sml/HTMLPreviewRenderer.java
@@ -37,23 +37,24 @@ public class HTMLPreviewRenderer extends HTMLRenderer {
             File f = (File)_files.get(id);
             String name = (String)_filenames.get(id);
             String type = (String)_fileTypes.get(id);
-            _bodyBuffer.append("<a href=\"").append(getAttachmentURL(id)).append("\">");
+            _bodyBuffer.append("<a ").append(getClass("attachmentView")).append(" href=\"").append(getAttachmentURL(id)).append("\">");
             _bodyBuffer.append(sanitizeString(anchorText)).append("</a>");
-            _bodyBuffer.append(" (").append(f.length()/1024).append("KB, ");
-            _bodyBuffer.append(" \"").append(sanitizeString(name)).append("\", ");
-            _bodyBuffer.append(sanitizeString(type)).append(")");
+            _bodyBuffer.append(getSpan("attachmentSummary")).append(" (");
+            _bodyBuffer.append(getSpan("attachmentSummarySize")).append(f.length()/1024).append("KB</span>, ");
+            _bodyBuffer.append(getSpan("attachmentSummaryName")).append(" \"").append(sanitizeString(name)).append("\"</span>, ");
+            _bodyBuffer.append(getSpan("attachmentSummaryType")).append(sanitizeString(type)).append("</span>)</span>");
         }
     }
     
     public void receiveEnd() { 
         _postBodyBuffer.append("</td></tr>\n");
-        _postBodyBuffer.append("<tr>\n");
+        _postBodyBuffer.append("<tr ").append(getClass("summDetail")).append(" >\n");
         _postBodyBuffer.append("<form action=\"").append(getAttachmentURLBase()).append("\">\n");
-        _postBodyBuffer.append("<td colspan=\"2\" valign=\"top\" align=\"left\" class=\"syndieEntryAttachmentsCell\"\n");
+        _postBodyBuffer.append("<td colspan=\"2\" valign=\"top\" align=\"left\" ").append(getClass("summDetail")).append("> \n");
 
         if (_files.size() > 0) {
-            _postBodyBuffer.append("<b>Attachments:</b> ");
-            _postBodyBuffer.append("<select name=\"").append(ArchiveViewerBean.PARAM_ATTACHMENT).append("\">\n");
+            _postBodyBuffer.append(getSpan("summDetailAttachment")).append("Attachments:</span> ");
+            _postBodyBuffer.append("<select ").append(getClass("summDetailAttachmentId")).append(" name=\"").append(ArchiveViewerBean.PARAM_ATTACHMENT).append("\">\n");
             for (int i = 0; i < _files.size(); i++) {
                 _postBodyBuffer.append("<option value=\"").append(i).append("\">");
                 File f = (File)_files.get(i);
@@ -64,48 +65,58 @@ public class HTMLPreviewRenderer extends HTMLRenderer {
                 _postBodyBuffer.append(", type ").append(sanitizeString(type)).append(")</option>\n");
             }
             _postBodyBuffer.append("</select>\n");
-            _postBodyBuffer.append("<input type=\"submit\" value=\"Download\" name=\"Download\" /><br />\n");
+            _postBodyBuffer.append("<input ").append(getClass("summDetailAttachmentDl")).append(" type=\"submit\" value=\"Download\" name=\"Download\" /><br />\n");
         }
 
         if (_blogs.size() > 0) {
-            _postBodyBuffer.append("<b>Blog references:</b> ");
+            _postBodyBuffer.append(getSpan("summDetailBlog")).append("Blog references:</span> ");
             for (int i = 0; i < _blogs.size(); i++) {
                 Blog b = (Blog)_blogs.get(i);
-                _postBodyBuffer.append("<a href=\"").append(getPageURL(new Hash(Base64.decode(b.hash)), b.tag, b.entryId, -1, -1, (_user != null ? _user.getShowExpanded() : false), (_user != null ? _user.getShowImages() : false)));
+                boolean expanded = (_user != null ? _user.getShowExpanded() : false);
+                boolean images = (_user != null ? _user.getShowImages() : false);
+                _postBodyBuffer.append("<a ").append(getClass("summDetailBlogLink")).append(" href=\"");
+                _postBodyBuffer.append(getPageURL(new Hash(Base64.decode(b.hash)), b.tag, b.entryId, -1, -1, expanded, images));
                 _postBodyBuffer.append("\">").append(sanitizeString(b.name)).append("</a> ");
             }
             _postBodyBuffer.append("<br />\n");
         }
 
         if (_links.size() > 0) {
-            _postBodyBuffer.append("<b>External links:</b> ");
+            _postBodyBuffer.append(getSpan("summDetailExternal")).append("External links:</span> ");
             for (int i = 0; i < _links.size(); i++) {
                 Link l = (Link)_links.get(i);
-                _postBodyBuffer.append("<a href=\"externallink.jsp?schema=");
-                _postBodyBuffer.append(sanitizeURL(l.schema)).append("&location=");
-                _postBodyBuffer.append(sanitizeURL(l.location));
+                _postBodyBuffer.append("<a ").append(getClass("summDetailExternalLink")).append(" href=\"externallink.jsp?");
+                if (l.schema != null)
+                    _postBodyBuffer.append("schema=").append(sanitizeURL(l.schema)).append('&');
+                if (l.location != null)
+                    _postBodyBuffer.append("location=").append(sanitizeURL(l.location)).append('&');
                 _postBodyBuffer.append("\">").append(sanitizeString(l.location));
-                _postBodyBuffer.append(" (").append(sanitizeString(l.schema)).append(")</a> ");
+                _postBodyBuffer.append(getSpan("summDetailExternalNet")).append(" (").append(sanitizeString(l.schema)).append(")</span></a> ");
             }
             _postBodyBuffer.append("<br />\n");
         }
 
         if (_addresses.size() > 0) {
-            _postBodyBuffer.append("<b>Addresses:</b> ");
+            _postBodyBuffer.append(getSpan("summDetailAddr")).append("Addresses:</span>");
             for (int i = 0; i < _addresses.size(); i++) {
                 Address a = (Address)_addresses.get(i);
-                
+
                 String knownName = null;
                 if (_user != null)
                     knownName = _user.getPetNameDB().getNameByLocation(a.location);
                 if (knownName != null) {
-                    _postBodyBuffer.append(' ').append(sanitizeString(knownName));
+                    _postBodyBuffer.append(' ').append(getSpan("summDetailAddrKnown"));
+                    _postBodyBuffer.append(sanitizeString(knownName)).append("</span>");
                 } else {
-                    _postBodyBuffer.append(" <a href=\"addresses.jsp?network=");
-                    _postBodyBuffer.append(sanitizeTagParam(a.schema)).append("&location=");
-                    _postBodyBuffer.append(sanitizeTagParam(a.location)).append("&name=");
-                    _postBodyBuffer.append(sanitizeTagParam(a.protocol)).append("&protocol=");
-                    _postBodyBuffer.append(sanitizeTagParam(a.name));
+                    _postBodyBuffer.append(" <a ").append(getClass("summDetailAddrLink")).append(" href=\"addresses.jsp?");
+                    if (a.schema != null)
+                        _postBodyBuffer.append("network=").append(sanitizeTagParam(a.schema)).append('&');
+                    if (a.location != null)
+                        _postBodyBuffer.append("location=").append(sanitizeTagParam(a.location)).append('&');
+                    if (a.name != null)
+                        _postBodyBuffer.append("name=").append(sanitizeTagParam(a.name)).append('&');
+                    if (a.protocol != null)
+                        _postBodyBuffer.append("protocol=").append(sanitizeTagParam(a.protocol)).append('&');
                     _postBodyBuffer.append("\">").append(sanitizeString(a.name)).append("</a>");
                 }
             }
@@ -113,13 +124,18 @@ public class HTMLPreviewRenderer extends HTMLRenderer {
         }
 
         if (_archives.size() > 0) {
-            _postBodyBuffer.append("<b>Archives:</b>");
+            _postBodyBuffer.append(getSpan("summDetailArchive")).append("Archives:</span>");
             for (int i = 0; i < _archives.size(); i++) {
                 ArchiveRef a = (ArchiveRef)_archives.get(i);
-                _postBodyBuffer.append(" <a href=\"").append(getArchiveURL(null, new SafeURL(a.locationSchema + "://" + a.location)));
+                _postBodyBuffer.append(" <a ").append(getClass("summDetailArchiveLink")).append(" href=\"").append(getArchiveURL(null, new SafeURL(a.locationSchema + "://" + a.location)));
                 _postBodyBuffer.append("\">").append(sanitizeString(a.name)).append("</a>");
                 if (a.description != null)
-                    _postBodyBuffer.append(": ").append(sanitizeString(a.description));
+                    _postBodyBuffer.append(": ").append(getSpan("summDetailArchiveDesc")).append(sanitizeString(a.description)).append("</span>");
+                if (null == _user.getPetNameDB().getNameByLocation(a.location)) {
+                    _postBodyBuffer.append(" <a ").append(getClass("summDetailArchiveBookmark")).append(" href=\"");
+                    _postBodyBuffer.append(getBookmarkURL(a.name, a.location, a.locationSchema, "syndiearchive"));
+                    _postBodyBuffer.append("\">bookmark</a>");
+                }
             }
             _postBodyBuffer.append("<br />\n");
         }
diff --git a/apps/syndie/java/src/net/i2p/syndie/sml/HTMLRenderer.java b/apps/syndie/java/src/net/i2p/syndie/sml/HTMLRenderer.java
index d6066a7d1c..d1c5b8253d 100644
--- a/apps/syndie/java/src/net/i2p/syndie/sml/HTMLRenderer.java
+++ b/apps/syndie/java/src/net/i2p/syndie/sml/HTMLRenderer.java
@@ -61,20 +61,49 @@ public class HTMLRenderer extends EventReceiverImpl {
         }
     }
     
+    /**
+     * Retrieve: class="s_summary_$element" or class="s_detail_$element ss_$style_detail_$element"
+     */
+    protected String getClass(String element) {
+        StringBuffer rv = new StringBuffer(64);
+        rv.append(" class=\"s_");
+        if (_cutBody)
+            rv.append("summary_");
+        else
+            rv.append("detail_");
+        rv.append(element);
+        if (_entry != null) {
+            String style = sanitizeStyle(_entry.getHeader(HEADER_STYLE));
+            if (style != null) {
+                rv.append(" ss_").append(style);
+                if (_cutBody)
+                    rv.append("summary_");
+                else
+                    rv.append("detail_");
+                rv.append(element);
+            }
+        }
+        rv.append("\" ");
+        return rv.toString();
+    }
+    protected String getSpan(String element) {
+        return "<span " + getClass(element) + ">";
+    }
+    
     public void renderUnknownEntry(User user, Archive archive, BlogURI uri, Writer out) throws IOException {
         BlogInfo info = archive.getBlogInfo(uri);
         if (info == null)
-            out.write("<br />The blog " + uri.getKeyHash().toBase64() + " is not known locally.  "
-                      + "Please get it from an archive and <a href=\"" 
+            out.write("<br /><span " + getClass("unknownBlog") + ">The blog <span " + getClass("blogURI") + ">" + uri.getKeyHash().toBase64() + "</span> is not known locally.  "
+                      + "Please get it from an archive and <a " + getClass("unknownRetry") + " href=\"" 
                       + getPageURL(uri.getKeyHash(), null, uri.getEntryId(), -1, -1, user.getShowExpanded(), user.getShowImages())
-                      + "\">try again</a>");
+                      + "\">try again</a></span>");
         else
-            out.write("<br />The blog <a href=\""
+            out.write("<br /><span " + getClass("unknownEntry") + ">The blog <a " + getClass("unknownRetry") + " href=\""
                       + getPageURL(uri.getKeyHash(), null, -1, -1, -1, user.getShowExpanded(), user.getShowImages())
                       + "\">" + info.getProperty(BlogInfo.NAME) + "</a> is known, but the entry " + uri.getEntryId() + " is not.  "
-                      + "Please get it from an archive and <a href=\"" 
+                      + "Please get it from an archive and <a " + getClass("unknownRetry") + " href=\"" 
                       + getPageURL(uri.getKeyHash(), null, uri.getEntryId(), -1, -1, user.getShowExpanded(), user.getShowImages())
-                      + "\">try again</a>");
+                      + "\">try again</a></span>");
     }
     
     public void render(User user, Archive archive, EntryContainer entry, Writer out, boolean cutBody, boolean showImages) throws IOException {
@@ -118,64 +147,64 @@ public class HTMLRenderer extends EventReceiverImpl {
     
     public void receiveBold(String text) { 
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<b>").append(sanitizeString(text)).append("</b>");
+        _bodyBuffer.append("<em ").append(getClass("bold")).append(" >").append(sanitizeString(text)).append("</em>");
     }
     public void receiveItalic(String text) { 
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<i>").append(sanitizeString(text)).append("</i>");
+        _bodyBuffer.append("<em ").append(getClass("italic")).append(" >").append(sanitizeString(text)).append("</em>");
     }
     public void receiveUnderline(String text) { 
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<u>").append(sanitizeString(text)).append("</u>");
+        _bodyBuffer.append("<em ").append(getClass("underline")).append(" >").append(sanitizeString(text)).append("</em>");
     }
     public void receiveHR() {
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<hr />");
+        _bodyBuffer.append(getSpan("hr")).append("<hr /></span>");
     }
     public void receiveH1(String body) {
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<h1>").append(sanitizeString(body)).append("</h1>");
+        _bodyBuffer.append("<h1 ").append(getClass("h1")).append(" >").append(sanitizeString(body)).append("</span></h1>");
     }
     public void receiveH2(String body) {
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<h2>").append(sanitizeString(body)).append("</h2>");
+        _bodyBuffer.append("<h2 ").append(getClass("h2")).append(" >").append(sanitizeString(body)).append("</span></h2>");
     }
     public void receiveH3(String body) {
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<h3>").append(sanitizeString(body)).append("</h3>");
+        _bodyBuffer.append("<h3 ").append(getClass("h3")).append(" >").append(sanitizeString(body)).append("</span></h3>");
     }
     public void receiveH4(String body) {
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<h4>").append(sanitizeString(body)).append("</h4>");
+        _bodyBuffer.append("<h4 ").append(getClass("h4")).append(" >").append(sanitizeString(body)).append("</span></h4>");
     }
     public void receiveH5(String body) {
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<h5>").append(sanitizeString(body)).append("</h5>");
+        _bodyBuffer.append("<h5 ").append(getClass("h5")).append(" >").append(sanitizeString(body)).append("</span></h5>");
     }
     public void receivePre(String body) {
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<pre>").append(sanitizeString(body)).append("</pre>");
+        _bodyBuffer.append("<pre ").append(getClass("pre")).append(" >").append(sanitizeString(body)).append("</pre>");
     }
     
     public void receiveQuote(String text, String whoQuoted, String quoteLocationSchema, String quoteLocation) {
         if (!continueBody()) { return; }
-        _bodyBuffer.append("<quote>").append(sanitizeString(text)).append("</quote>");
+        _bodyBuffer.append("<quote ").append(getClass("quote")).append(" >").append(sanitizeString(text)).append("</quote>");
     }
     public void receiveCode(String text, String codeLocationSchema, String codeLocation) { 
         if (!continueBody()) { return; }
-           _bodyBuffer.append("<code>").append(sanitizeString(text)).append("</code>");
+           _bodyBuffer.append("<code ").append(getClass("code")).append(" >").append(sanitizeString(text)).append("</code>");
     }
     public void receiveImage(String alternateText, int attachmentId) {
         if (!continueBody()) { return; }
         if (_showImages) {
-            _bodyBuffer.append("<img src=\"").append(getAttachmentURL(attachmentId)).append("\"");
+            _bodyBuffer.append("<img ").append(getClass("img")).append(" src=\"").append(getAttachmentURL(attachmentId)).append("\"");
             if (alternateText != null)
                 _bodyBuffer.append(" alt=\"").append(sanitizeTagParam(alternateText)).append("\"");
             _bodyBuffer.append(" />");
         } else {
-            _bodyBuffer.append("[image: attachment ").append(attachmentId);
-            _bodyBuffer.append(": ").append(sanitizeString(alternateText));
-            _bodyBuffer.append(" <a href=\"").append(getEntryURL(true)).append("\">view images</a>]");
+            _bodyBuffer.append(getSpan("imgSummary")).append("[image: ").append(getSpan("imgSummaryAttachment")).append(" attachment ").append(attachmentId);
+            _bodyBuffer.append(":</span> ").append(getSpan("imgSummaryAlt")).append(sanitizeString(alternateText));
+            _bodyBuffer.append("</span> <a ").append(getClass("imgSummaryLink")).append(" href=\"").append(getEntryURL(true)).append("\">view images</a>]</span>");
         }
     }
     
@@ -183,7 +212,7 @@ public class HTMLRenderer extends EventReceiverImpl {
         if (!continueBody()) { return; }
         _cutReached = true;
         if (_cutBody) {
-            _bodyBuffer.append("<a href=\"").append(getEntryURL()).append("\">");
+            _bodyBuffer.append("<a ").append(getClass("cutExplicit")).append(" href=\"").append(getEntryURL()).append("\">");
             if ( (summaryText != null) && (summaryText.length() > 0) )
                 _bodyBuffer.append(sanitizeString(summaryText));
             else
@@ -191,7 +220,7 @@ public class HTMLRenderer extends EventReceiverImpl {
             _bodyBuffer.append("</a>\n");
         } else {
             if (summaryText != null)
-                _bodyBuffer.append(sanitizeString(summaryText));
+                _bodyBuffer.append(getSpan("cutIgnore")).append(sanitizeString(summaryText)).append("</span>\n");
         }
     }
     
@@ -202,7 +231,7 @@ public class HTMLRenderer extends EventReceiverImpl {
         //    System.out.println("rv: " + rv + " Cut reached: " + _cutReached + " bodyBufferSize: " + _bodyBuffer.length() + " cutBody? " + _cutBody);
         if (!rv && !_cutReached) {
             // exceeded the allowed size
-            _bodyBuffer.append("<a href=\"").append(getEntryURL()).append("\">more inside...</a>");
+            _bodyBuffer.append("<a ").append(getClass("cutImplicit")).append(" href=\"").append(getEntryURL()).append("\">more inside...</a>\n");
             _cutReached = true;
         }
         return rv;
@@ -211,26 +240,26 @@ public class HTMLRenderer extends EventReceiverImpl {
     public void receiveNewline() { 
         if (!continueBody()) { return; }
         if (true || (_lastNewlineAt >= _bodyBuffer.length()))
-            _bodyBuffer.append("<br />\n");
+            _bodyBuffer.append(getSpan("nl")).append("<br /></span>\n");
         else
             _lastNewlineAt = _bodyBuffer.length();
     }
     public void receiveLT() { 
         if (!continueBody()) { return; }
-        _bodyBuffer.append("&lt;");
+        _bodyBuffer.append(getSpan("lt")).append("&lt;</span>");
     }
     public void receiveGT() { 
         if (!continueBody()) { return; }
-        _bodyBuffer.append("&gt;");
+        _bodyBuffer.append(getSpan("gt")).append("&gt;</span>");
     }
     public void receiveBegin() {}
     public void receiveLeftBracket() { 
         if (!continueBody()) { return; }
-        _bodyBuffer.append('[');
+        _bodyBuffer.append(getSpan("lb")).append("[</span>");
     }
     public void receiveRightBracket() { 
         if (!continueBody()) { return; }
-        _bodyBuffer.append(']');
+        _bodyBuffer.append(getSpan("rb")).append("]</span>");
     }
     
     protected static class Blog {
@@ -287,7 +316,7 @@ public class HTMLRenderer extends EventReceiverImpl {
         Hash blog = new Hash(blogData);
         if (entryId > 0) {
             String pageURL = getPageURL(blog, tag, entryId, -1, -1, true, (_user != null ? _user.getShowImages() : false));
-            _bodyBuffer.append("<a href=\"").append(pageURL).append("\">");
+            _bodyBuffer.append("<a ").append(getClass("blogEntryLink")).append(" href=\"").append(pageURL).append("\">");
             if ( (description != null) && (description.trim().length() > 0) ) {
                 _bodyBuffer.append(sanitizeString(description));
             } else if ( (name != null) && (name.trim().length() > 0) ) {
@@ -300,29 +329,30 @@ public class HTMLRenderer extends EventReceiverImpl {
         
         
         String url = getPageURL(blog, null, -1, -1, -1, (_user != null ? _user.getShowExpanded() : false), (_user != null ? _user.getShowImages() : false));
-        _bodyBuffer.append(" [<a href=\"").append(url);
+        _bodyBuffer.append(getSpan("blogEntrySummary")).append(" [<a ").append(getClass("blogLink")).append(" href=\"").append(url);
         _bodyBuffer.append("\">");
         if ( (name != null) && (name.trim().length() > 0) )
             _bodyBuffer.append(sanitizeString(name));
         else
             _bodyBuffer.append("view");
-        _bodyBuffer.append("</a> (<a href=\"").append(getMetadataURL(blog)).append("\">meta</a>)");
+        _bodyBuffer.append("</a> (<a ").append(getClass("blogMeta")).append(" href=\"").append(getMetadataURL(blog)).append("\">meta</a>)");
         if ( (tag != null) && (tag.trim().length() > 0) ) {
             url = getPageURL(blog, tag, -1, -1, -1, false, false);
-            _bodyBuffer.append(" <a href=\"").append(url);
+            _bodyBuffer.append(" <a ").append(getClass("blogTagLink")).append(" href=\"").append(url);
             _bodyBuffer.append("\">Tag: ").append(sanitizeString(tag)).append("</a>");
         }
         if ( (locations != null) && (locations.size() > 0) ) {
-            _bodyBuffer.append(" Archives: ");
+            _bodyBuffer.append(getSpan("blogArchive")).append(" Archives: ");
             for (int i = 0; i < locations.size(); i++) {
                 SafeURL surl = (SafeURL)locations.get(i);
                 if (_user.getAuthenticated() && _user.getAllowAccessRemote())
-                    _bodyBuffer.append("<a href=\"").append(getArchiveURL(blog, surl)).append("\">").append(sanitizeString(surl.toString())).append("</a> ");
+                    _bodyBuffer.append("<a ").append(getClass("blogArchiveView")).append(" href=\"").append(getArchiveURL(blog, surl)).append("\">").append(sanitizeString(surl.toString())).append("</a> ");
                 else
-                    _bodyBuffer.append(sanitizeString(surl.toString())).append(' ');
+                    _bodyBuffer.append(getSpan("blogArchiveURL")).append(sanitizeString(surl.toString())).append("</span> ");
             }
+            _bodyBuffer.append("</span>");
         }
-        _bodyBuffer.append("] ");
+        _bodyBuffer.append("]</span> ");
     }
     
     protected static class ArchiveRef {
@@ -350,18 +380,19 @@ public class HTMLRenderer extends EventReceiverImpl {
     
         if (!continueBody()) { return; }
         
-        _bodyBuffer.append(sanitizeString(anchorText)).append(" [Archive ");
+        _bodyBuffer.append(getSpan("archive")).append(sanitizeString(anchorText)).append("</span>");
+        _bodyBuffer.append(getSpan("archiveSummary")).append(" [Archive ");
         if (name != null)
-            _bodyBuffer.append(sanitizeString(name));
+            _bodyBuffer.append(getSpan("archiveSummaryName")).append(sanitizeString(name)).append("</span>");
         if (location != null) {
             _bodyBuffer.append(" at ");
             SafeURL surl = new SafeURL(locationSchema + "://" + location);
-            _bodyBuffer.append("<a href=\"").append(getArchiveURL(null, surl));
+            _bodyBuffer.append("<a ").append(getClass("archiveSummaryLink")).append(" href=\"").append(getArchiveURL(null, surl));
             _bodyBuffer.append("\">").append(sanitizeString(surl.toString())).append("</a>");
         }
         if (description != null)
-            _bodyBuffer.append(": ").append(sanitizeString(description));
-        _bodyBuffer.append("]");
+            _bodyBuffer.append(": ").append(getSpan("archiveSummaryDesc")).append(sanitizeString(description)).append("</span>");
+        _bodyBuffer.append("]</span>");
     }
     
     protected static class Link {
@@ -381,7 +412,7 @@ public class HTMLRenderer extends EventReceiverImpl {
             _links.add(l);
         if (!continueBody()) { return; }
         if ( (schema == null) || (location == null) ) return;
-        _bodyBuffer.append("<a href=\"externallink.jsp?schema=");
+        _bodyBuffer.append("<a ").append(getClass("externalLink")).append(" href=\"externallink.jsp?schema=");
         _bodyBuffer.append(sanitizeURL(schema)).append("&location=");
         _bodyBuffer.append(sanitizeURL(location)).append("&description=");
         _bodyBuffer.append(sanitizeURL(text)).append("\">").append(sanitizeString(text)).append("</a>");
@@ -412,15 +443,20 @@ public class HTMLRenderer extends EventReceiverImpl {
         if (_user != null)
             knownName = _user.getPetNameDB().getNameByLocation(location);
         if (knownName != null) {
-            _bodyBuffer.append(sanitizeString(anchorText));
-            _bodyBuffer.append(" <i>(").append(sanitizeString(knownName)).append(")</i>");
+            _bodyBuffer.append(getSpan("addr")).append(sanitizeString(anchorText)).append("</span>");
+            _bodyBuffer.append(getSpan("addrKnownName")).append("(").append(sanitizeString(knownName)).append(")</span>");
         } else {
             System.err.println("Receiving address [" + location + "]");
-            _bodyBuffer.append("<a href=\"addresses.jsp?network=");
-            _bodyBuffer.append(sanitizeTagParam(schema)).append("&name=");
-            _bodyBuffer.append(sanitizeTagParam(name)).append("&protocol=");
-            _bodyBuffer.append(sanitizeTagParam(protocol)).append("&location=");
-            _bodyBuffer.append(sanitizeTagParam(location)).append("\">").append(sanitizeString(anchorText)).append("</a>");
+            _bodyBuffer.append("<a ").append(getClass("addrAdd")).append(" href=\"addresses.jsp?");
+            if (schema != null)
+                _bodyBuffer.append("network=").append(sanitizeTagParam(schema)).append('&');
+            if (name != null)
+                _bodyBuffer.append("name=").append(sanitizeTagParam(name)).append('&');
+            if (protocol != null)
+                _bodyBuffer.append("protocol=").append(sanitizeTagParam(protocol)).append('&');
+            if (location != null)
+                _bodyBuffer.append("location=").append(sanitizeTagParam(location));
+            _bodyBuffer.append("\">").append(sanitizeString(anchorText)).append("</a>");
         }
     }
     
@@ -428,23 +464,26 @@ public class HTMLRenderer extends EventReceiverImpl {
         if (!continueBody()) { return; }
         Attachment attachments[] = _entry.getAttachments();
         if ( (id < 0) || (id >= attachments.length)) {
-            _bodyBuffer.append(sanitizeString(anchorText));
+            _bodyBuffer.append(getSpan("attachmentUnknown")).append(sanitizeString(anchorText)).append("</span>");
         } else {
-            _bodyBuffer.append("<a href=\"").append(getAttachmentURL(id)).append("\">");
+            _bodyBuffer.append("<a ").append(getClass("attachmentView")).append(" href=\"").append(getAttachmentURL(id)).append("\">");
             _bodyBuffer.append(sanitizeString(anchorText)).append("</a>");
-            _bodyBuffer.append(" (").append(attachments[id].getDataLength()/1024).append("KB, ");
-            _bodyBuffer.append(" \"").append(sanitizeString(attachments[id].getName())).append("\", ");
-            _bodyBuffer.append(sanitizeString(attachments[id].getMimeType())).append(")");
+            _bodyBuffer.append(getSpan("attachmentSummary")).append(" (");
+            _bodyBuffer.append(getSpan("attachmentSummarySize")).append(attachments[id].getDataLength()/1024).append("KB</span>, ");
+            _bodyBuffer.append(getSpan("attachmentSummaryName")).append(" \"").append(sanitizeString(attachments[id].getName())).append("\"</span>, ");
+            _bodyBuffer.append(getSpan("attachmentSummaryDesc")).append(" \"").append(sanitizeString(attachments[id].getDescription())).append("\"</span>, ");
+            _bodyBuffer.append(getSpan("attachmentSummaryType")).append(sanitizeString(attachments[id].getMimeType())).append("</span>)</span>");
         }
     }
     
     public void receiveEnd() { 
-        _postBodyBuffer.append("</td></tr>\n");
+        _postBodyBuffer.append("</td></tr>\n<!-- end of the post body -->");
         if (_cutBody) {
-            _postBodyBuffer.append("<tr class=\"syndieEntryAttachmentsCell\">\n");
-            _postBodyBuffer.append("<td colspan=\"2\" valign=\"top\" align=\"left\" class=\"syndieEntryAttachmentsCell\">");
-            _postBodyBuffer.append("<a href=\"").append(getEntryURL()).append("\">View details...</a> ");
-            
+            _postBodyBuffer.append("<!-- beginning of the post summary -->\n");
+            _postBodyBuffer.append("<tr ").append(getClass("summ")).append("\">\n");
+            _postBodyBuffer.append("<td colspan=\"2\" valign=\"top\" align=\"left\" ").append(getClass("summ")).append(" >");
+            _postBodyBuffer.append("<a ").append(getClass("summLink")).append(" href=\"").append(getEntryURL()).append("\">View details...</a> ");
+            _postBodyBuffer.append(getSpan("summ"));
             if ( (_entry != null) && (_entry.getAttachments() != null) && (_entry.getAttachments().length > 0) ) {
                 int num = _entry.getAttachments().length;
                 if (num == 1)
@@ -489,11 +528,13 @@ public class HTMLRenderer extends EventReceiverImpl {
         
             String inReplyTo = (String)_headers.get(HEADER_IN_REPLY_TO);
             if ( (inReplyTo != null) && (inReplyTo.trim().length() > 0) )
-                _postBodyBuffer.append(" <a href=\"").append(getPageURL(sanitizeTagParam(inReplyTo))).append("\">(view parent)</a>\n");
+                _postBodyBuffer.append(" <a ").append(getClass("summParent")).append(" href=\"").append(getPageURL(sanitizeTagParam(inReplyTo))).append("\">(view parent)</a>\n");
             
-            _postBodyBuffer.append("</td></tr>\n");
+            _postBodyBuffer.append("</span></td></tr>\n");
+            _postBodyBuffer.append("<!-- end of the post summary -->\n");
         } else {
-            _postBodyBuffer.append("<tr class=\"syndieEntryAttachmentsCell\">\n");
+            _postBodyBuffer.append("<!-- beginning of the post summary details -->\n");
+            _postBodyBuffer.append("<tr ").append(getClass("summDetail")).append(">\n");
             _postBodyBuffer.append("<form action=\"").append(getAttachmentURLBase()).append("\">\n");
             _postBodyBuffer.append("<input type=\"hidden\" name=\"").append(ArchiveViewerBean.PARAM_BLOG);
             _postBodyBuffer.append("\" value=\"");
@@ -509,11 +550,11 @@ public class HTMLRenderer extends EventReceiverImpl {
             else
                 _postBodyBuffer.append("unknown");
             _postBodyBuffer.append("\" />\n");
-            _postBodyBuffer.append("<td colspan=\"2\" valign=\"top\" align=\"left\" class=\"syndieEntryAttachmentsCell\">\n");
+            _postBodyBuffer.append("<td colspan=\"2\" valign=\"top\" align=\"left\" ").append(getClass("summDetail")).append(" >\n");
 
             if ( (_entry != null) && (_entry.getAttachments() != null) && (_entry.getAttachments().length > 0) ) {
-                _postBodyBuffer.append("<b>Attachments:</b> ");
-                _postBodyBuffer.append("<select name=\"").append(ArchiveViewerBean.PARAM_ATTACHMENT).append("\">\n");
+                _postBodyBuffer.append(getSpan("summDetailAttachment")).append("Attachments:</span> ");
+                _postBodyBuffer.append("<select ").append(getClass("summDetailAttachmentId")).append(" name=\"").append(ArchiveViewerBean.PARAM_ATTACHMENT).append("\">\n");
                 for (int i = 0; i < _entry.getAttachments().length; i++) {
                     _postBodyBuffer.append("<option value=\"").append(i).append("\">");
                     Attachment a = _entry.getAttachments()[i];
@@ -526,34 +567,39 @@ public class HTMLRenderer extends EventReceiverImpl {
                     _postBodyBuffer.append(", type ").append(sanitizeString(a.getMimeType())).append(")</option>\n");
                 }
                 _postBodyBuffer.append("</select>\n");
-                _postBodyBuffer.append("<input type=\"submit\" value=\"Download\" name=\"Download\" /><br />\n");
+                _postBodyBuffer.append("<input ").append(getClass("summDetailAttachmentDl")).append(" type=\"submit\" value=\"Download\" name=\"Download\" /><br />\n");
             }
 
             if (_blogs.size() > 0) {
-                _postBodyBuffer.append("<b>Blog references:</b> ");
+                _postBodyBuffer.append(getSpan("summDetailBlog")).append("Blog references:</span>");
                 for (int i = 0; i < _blogs.size(); i++) {
                     Blog b = (Blog)_blogs.get(i);
-                    _postBodyBuffer.append("<a href=\"").append(getPageURL(new Hash(Base64.decode(b.hash)), b.tag, b.entryId, -1, -1, (_user != null ? _user.getShowExpanded() : false), (_user != null ? _user.getShowImages() : false)));
+                    _postBodyBuffer.append("<a ").append(getClass("summDetailBlogLink")).append(" href=\"");
+                    boolean expanded = (_user != null ? _user.getShowExpanded() : false);
+                    boolean images = (_user != null ? _user.getShowImages() : false);
+                    _postBodyBuffer.append(getPageURL(new Hash(Base64.decode(b.hash)), b.tag, b.entryId, -1, -1, expanded, images));
                     _postBodyBuffer.append("\">").append(sanitizeString(b.name)).append("</a> ");
                 }
                 _postBodyBuffer.append("<br />\n");
             }
 
             if (_links.size() > 0) {
-                _postBodyBuffer.append("<b>External links:</b> ");
+                _postBodyBuffer.append(getSpan("summDetailExternal")).append("External links:</span> ");
                 for (int i = 0; i < _links.size(); i++) {
                     Link l = (Link)_links.get(i);
-                    _postBodyBuffer.append("<a href=\"externallink.jsp?schema=");
-                    _postBodyBuffer.append(sanitizeURL(l.schema)).append("&location=");
-                    _postBodyBuffer.append(sanitizeURL(l.location));
+                    _postBodyBuffer.append("<a ").append(getClass("summDetailExternalLink")).append(" href=\"externallink.jsp?");
+                    if (l.schema != null)
+                        _postBodyBuffer.append("schema=").append(sanitizeURL(l.schema)).append('&');
+                    if (l.location != null)
+                        _postBodyBuffer.append("location=").append(sanitizeURL(l.location)).append('&');
                     _postBodyBuffer.append("\">").append(sanitizeString(l.location));
-                    _postBodyBuffer.append(" (").append(sanitizeString(l.schema)).append(")</a> ");
+                    _postBodyBuffer.append(getSpan("summDetailExternalNet")).append(" (").append(sanitizeString(l.schema)).append(")</span></a> ");
                 }
                 _postBodyBuffer.append("<br />\n");
             }
 
             if (_addresses.size() > 0) {
-                _postBodyBuffer.append("<b>Addresses:</b>");
+                _postBodyBuffer.append(getSpan("summDetailAddr")).append("Addresses:</span>");
                 for (int i = 0; i < _addresses.size(); i++) {
                     Address a = (Address)_addresses.get(i);
                     
@@ -561,13 +607,18 @@ public class HTMLRenderer extends EventReceiverImpl {
                     if (_user != null)
                         knownName = _user.getPetNameDB().getNameByLocation(a.location);
                     if (knownName != null) {
-                        _postBodyBuffer.append(' ').append(sanitizeString(knownName));
+                        _postBodyBuffer.append(' ').append(getSpan("summDetailAddrKnown"));
+                        _postBodyBuffer.append(sanitizeString(knownName)).append("</span>");
                     } else {
-                        _postBodyBuffer.append(" <a href=\"addresses.jsp?network=");
-                        _postBodyBuffer.append(sanitizeTagParam(a.schema)).append("&location=");
-                        _postBodyBuffer.append(sanitizeTagParam(a.location)).append("&name=");
-                        _postBodyBuffer.append(sanitizeTagParam(a.name)).append("&protocol=");
-                        _postBodyBuffer.append(sanitizeTagParam(a.protocol));
+                        _postBodyBuffer.append(" <a ").append(getClass("summDetailAddrLink")).append(" href=\"addresses.jsp?");
+                        if (a.schema != null)
+                            _postBodyBuffer.append("network=").append(sanitizeTagParam(a.schema)).append('&');
+                        if (a.location != null)
+                            _postBodyBuffer.append("location=").append(sanitizeTagParam(a.location)).append('&');
+                        if (a.name != null)
+                            _postBodyBuffer.append("name=").append(sanitizeTagParam(a.name)).append('&');
+                        if (a.protocol != null)
+                            _postBodyBuffer.append("protocol=").append(sanitizeTagParam(a.protocol)).append('&');
                         _postBodyBuffer.append("\">").append(sanitizeString(a.name)).append("</a>");
                     }
                 }
@@ -575,16 +626,18 @@ public class HTMLRenderer extends EventReceiverImpl {
             }
 
             if (_archives.size() > 0) {
-                _postBodyBuffer.append("<b>Archives:</b>");
+                _postBodyBuffer.append(getSpan("summDetailArchive")).append("Archives:</span>");
                 for (int i = 0; i < _archives.size(); i++) {
                     ArchiveRef a = (ArchiveRef)_archives.get(i);
-                    _postBodyBuffer.append(" <a href=\"").append(getArchiveURL(null, new SafeURL(a.locationSchema + "://" + a.location)));
+                    _postBodyBuffer.append(" <a ").append(getClass("summDetailArchiveLink")).append(" href=\"").append(getArchiveURL(null, new SafeURL(a.locationSchema + "://" + a.location)));
                     _postBodyBuffer.append("\">").append(sanitizeString(a.name)).append("</a>");
                     if (a.description != null)
-                        _postBodyBuffer.append(": ").append(sanitizeString(a.description));
-                    _postBodyBuffer.append(" <a href=\"");
-                    _postBodyBuffer.append(getBookmarkURL(a.name, a.location, a.locationSchema, "syndiearchive"));
-                    _postBodyBuffer.append("\">bookmark</a>");
+                        _postBodyBuffer.append(": ").append(getSpan("summDetailArchiveDesc")).append(sanitizeString(a.description)).append("</span>");
+                    if (null == _user.getPetNameDB().getNameByLocation(a.location)) {
+                        _postBodyBuffer.append(" <a ").append(getClass("summDetailArchiveBookmark")).append(" href=\"");
+                        _postBodyBuffer.append(getBookmarkURL(a.name, a.location, a.locationSchema, "syndiearchive"));
+                        _postBodyBuffer.append("\">bookmark</a>");
+                    }
                 }
                 _postBodyBuffer.append("<br />\n");
             }
@@ -592,21 +645,23 @@ public class HTMLRenderer extends EventReceiverImpl {
             if (_entry != null) {
                 List replies = _archive.getIndex().getReplies(_entry.getURI());
                 if ( (replies != null) && (replies.size() > 0) ) {
-                    _postBodyBuffer.append("<b>Replies:</b> ");
+                    _postBodyBuffer.append(getSpan("summDetailReplies")).append("Replies:</span> ");
                     for (int i = 0; i < replies.size(); i++) { 
                         BlogURI reply = (BlogURI)replies.get(i);
-                        _postBodyBuffer.append("<a href=\"");
+                        _postBodyBuffer.append("<a ").append(getClass("summDetailReplyLink")).append(" href=\"");
                         _postBodyBuffer.append(getPageURL(reply.getKeyHash(), null, reply.getEntryId(), -1, -1, true, _user.getShowImages()));
                         _postBodyBuffer.append("\">");
+                        _postBodyBuffer.append(getSpan("summDetailReplyAuthor"));
                         BlogInfo replyAuthor = _archive.getBlogInfo(reply);
                         if (replyAuthor != null) {
                             _postBodyBuffer.append(sanitizeString(replyAuthor.getProperty(BlogInfo.NAME)));
                         } else {
                             _postBodyBuffer.append(reply.getKeyHash().toBase64().substring(0,16));
                         }
-                        _postBodyBuffer.append(" on ");
+                        _postBodyBuffer.append("</span> on ");
+                        _postBodyBuffer.append(getSpan("summDetailReplyDate"));
                         _postBodyBuffer.append(getEntryDate(reply.getEntryId()));
-                        _postBodyBuffer.append("</a> ");
+                        _postBodyBuffer.append("</a></span> ");
                     }
                     _postBodyBuffer.append("<br />");
                 }
@@ -614,10 +669,11 @@ public class HTMLRenderer extends EventReceiverImpl {
         
             String inReplyTo = (String)_headers.get(HEADER_IN_REPLY_TO);
             if ( (inReplyTo != null) && (inReplyTo.trim().length() > 0) ) {
-                _postBodyBuffer.append(" <a href=\"").append(getPageURL(sanitizeTagParam(inReplyTo))).append("\">(view parent)</a><br />\n");
+                _postBodyBuffer.append(" <a ").append(getClass("summDetailParent")).append(" href=\"").append(getPageURL(sanitizeTagParam(inReplyTo))).append("\">(view parent)</a><br />\n");
             }
                 
             _postBodyBuffer.append("</td>\n</form>\n</tr>\n");
+            _postBodyBuffer.append("<!-- end of the post summary details -->\n");
         }
         _postBodyBuffer.append("</table>\n");
     }
@@ -644,7 +700,7 @@ public class HTMLRenderer extends EventReceiverImpl {
     }
     
     public void receiveHeaderEnd() {
-        _preBodyBuffer.append("<table width=\"100%\" border=\"0\">\n");
+        _preBodyBuffer.append("<table ").append(getClass("overall")).append(" width=\"100%\" border=\"0\">\n");
         renderSubjectCell();
         renderMetaCell();
         renderPreBodyCell();
@@ -657,27 +713,28 @@ public class HTMLRenderer extends EventReceiverImpl {
     public static final String HEADER_PETNAME = "PetName";
     
     private void renderSubjectCell() {
-        _preBodyBuffer.append("<tr class=\"syndieEntrySubjectCell\"><td align=\"left\" valign=\"top\" class=\"syndieEntrySubjectCell\" width=\"400\"> ");
+        _preBodyBuffer.append("<form action=\"index.jsp\">");
+        _preBodyBuffer.append("<tr ").append(getClass("subject")).append(">");
+        _preBodyBuffer.append("<td ").append(getClass("subject")).append(" align=\"left\" valign=\"top\" width=\"400\"> ");
         String subject = (String)_headers.get(HEADER_SUBJECT);
         if (subject == null)
             subject = "[no subject]";
-        _preBodyBuffer.append(sanitizeString(subject));
-        _preBodyBuffer.append("</td>\n");
+        _preBodyBuffer.append(getSpan("subjectText")).append(sanitizeString(subject));
+        _preBodyBuffer.append("</span></td>\n");
     }
     
     private void renderPreBodyCell() {
+        _preBodyBuffer.append("</form>");
         String bgcolor = (String)_headers.get(HEADER_BGCOLOR);
-        if (_cutBody)
-            _preBodyBuffer.append("<tr class=\"syndieEntrySummaryCell\"><td colspan=\"2\" align=\"left\" valign=\"top\" class=\"syndieEntrySummaryCell\" " + (bgcolor != null ? "bgcolor=\"" + sanitizeTagParam(bgcolor) + "\"" : "") + "\">");
-        else
-            _preBodyBuffer.append("<tr class=\"syndieEntryBodyCell\"><td colspan=\"2\" align=\"left\" valign=\"top\" class=\"syndieEntryBodyCell\" " + (bgcolor != null ? "bgcolor=\"" + sanitizeTagParam(bgcolor) + "\"" : "") + "\">");
+        _preBodyBuffer.append("<tr ").append(getClass("body")).append(" >");
+        _preBodyBuffer.append("<td colspan=\"2\" align=\"left\" valign=\"top\" ").append(getClass("body"));
+        _preBodyBuffer.append((bgcolor != null ? " bgcolor=\"" + sanitizeTagParam(bgcolor) + "\"" : "") + ">");
     }
     
     private void renderMetaCell() {
         String tags[] = (_entry != null ? _entry.getTags() : null);
-        if ( (tags != null) && (tags.length > 0) )
-            _preBodyBuffer.append("<form action=\"index.jsp\">");
-        _preBodyBuffer.append("<td nowrap=\"true\" align=\"right\" valign=\"top\" class=\"syndieEntryMetaCell\">\n");
+        _preBodyBuffer.append("<td nowrap=\"nowrap\" align=\"right\" valign=\"top\" ");
+        _preBodyBuffer.append(getClass("meta")).append(">\n");
         
         String knownName = null;
         if ( (_entry != null) && (_user != null) )
@@ -689,30 +746,30 @@ public class HTMLRenderer extends EventReceiverImpl {
         if (_entry != null) 
             info = _archive.getBlogInfo(_entry.getURI());
         if (info != null) {
-            _preBodyBuffer.append("<a href=\"").append(getMetadataURL()).append("\">");
+            _preBodyBuffer.append("<a ").append(getClass("metaLink")).append(" href=\"").append(getMetadataURL()).append("\">");
             if (knownName != null) {
-                _preBodyBuffer.append(sanitizeString(knownName));
+                _preBodyBuffer.append(getSpan("metaKnown")).append(sanitizeString(knownName)).append("</span>");
             } else {
                 String nameStr = info.getProperty("Name");
                 if (nameStr == null)
-                    _preBodyBuffer.append("[no name]");
+                    _preBodyBuffer.append(getSpan("metaUnknown")).append("[no name]</span>");
                 else
-                    _preBodyBuffer.append(sanitizeString(nameStr));
+                    _preBodyBuffer.append(getSpan("metaUnknown")).append(sanitizeString(nameStr)).append("</span>");
             }
             _preBodyBuffer.append("</a>");
         } else {
-            _preBodyBuffer.append("[unknown blog]");
+            _preBodyBuffer.append(getSpan("metaUnknown")).append("[unknown blog]</span>");
         }
 
         
         if ( (_user != null) && (_user.getAuthenticated()) && (_entry != null) ) {
             PetName pn = _user.getPetNameDB().get(knownName);
             if ( (pn == null) || (!pn.isMember("Favorites")) )
-                _preBodyBuffer.append(" <input type=\"submit\" name=\"action\" value=\"Bookmark blog\" />");
+                _preBodyBuffer.append(" <input ").append(getClass("bookmark")).append(" type=\"submit\" name=\"action\" value=\"Bookmark blog\" />");
             if ( (pn == null) || (!pn.isMember("Ignore")) )
-                _preBodyBuffer.append(" <input type=\"submit\" name=\"action\" value=\"Ignore blog\" />");
+                _preBodyBuffer.append(" <input ").append(getClass("ignore")).append(" type=\"submit\" name=\"action\" value=\"Ignore blog\" />");
             else
-                _preBodyBuffer.append(" <input type=\"submit\" name=\"action\" value=\"Unignore blog\" />");
+                _preBodyBuffer.append(" <input ").append(getClass("unignore")).append(" type=\"submit\" name=\"action\" value=\"Unignore blog\" />");
             _preBodyBuffer.append(" <input type=\"hidden\" name=\"blog\" value=\"").append(_entry.getURI().getKeyHash().toBase64()).append("\" />");
             if (info != null)
                 _preBodyBuffer.append(" <input type=\"hidden\" name=\"name\" value=\"").append(sanitizeTagParam(info.getProperty("Name"))).append("\" />");
@@ -720,8 +777,8 @@ public class HTMLRenderer extends EventReceiverImpl {
 
         
         if ( (tags != null) && (tags.length > 0) ) {
-            _preBodyBuffer.append(" Tags: ");
-            _preBodyBuffer.append("<select name=\"selector\">");
+            _preBodyBuffer.append(getSpan("metaTags")).append(" Tags: ");
+            _preBodyBuffer.append("<select ").append(getClass("metaTagList")).append(" name=\"selector\">");
             for (int i = 0; tags != null && i < tags.length; i++) {
                 _preBodyBuffer.append("<option value=\"blogtag://");
                 _preBodyBuffer.append(_entry.getURI().getKeyHash().toBase64());
@@ -739,7 +796,7 @@ public class HTMLRenderer extends EventReceiverImpl {
                  */
             }
             _preBodyBuffer.append("</select>");
-            _preBodyBuffer.append("<input type=\"submit\" value=\"View\" />\n");
+            _preBodyBuffer.append("<input ").append(getClass("metaTagView")).append(" type=\"submit\" value=\"View\" /></span>\n");
             //_preBodyBuffer.append("</i>");
         }
         _preBodyBuffer.append(" ");
@@ -749,16 +806,18 @@ public class HTMLRenderer extends EventReceiverImpl {
             _preBodyBuffer.append(" <a href=\"").append(getPageURL(sanitizeTagParam(inReplyTo))).append("\">In reply to</a>\n");
          */
         
+        _preBodyBuffer.append(getSpan("metaDate"));
         if (_entry != null)
             _preBodyBuffer.append(getEntryDate(_entry.getURI().getEntryId()));
         else
             _preBodyBuffer.append(getEntryDate(new Date().getTime()));
+        _preBodyBuffer.append("</span>");
+        
         if ( (_user != null) && (_user.getAuthenticated()) ) {
-            _preBodyBuffer.append(" <a href=\"").append(getPostURL(_user.getBlog(), true)).append("\">Reply</a>\n");
+            _preBodyBuffer.append(" <a ").append(getClass("replyLink"));
+            _preBodyBuffer.append(" href=\"").append(getPostURL(_user.getBlog(), true)).append("\">Reply</a>\n");
         }
         _preBodyBuffer.append("\n</td>");
-        if ( (tags != null) && (tags.length > 0) )
-            _preBodyBuffer.append("</form>");
         _preBodyBuffer.append("</tr>\n");
     }
     
@@ -800,8 +859,12 @@ public class HTMLRenderer extends EventReceiverImpl {
         return str;
     }
 
-    public static final String sanitizeURL(String str) { return Base64.encode(DataHelper.getUTF8(str)); }
+    public static final String sanitizeURL(String str) { 
+        if (str == null) return "";
+        return Base64.encode(DataHelper.getUTF8(str)); 
+    }
     public static final String sanitizeTagParam(String str) {
+        if (str == null) return "";
         str = str.replace('&', '_'); // this should be &amp;
         if (str.indexOf('\"') < 0)
             return sanitizeString(str);
@@ -810,6 +873,7 @@ public class HTMLRenderer extends EventReceiverImpl {
     }
     
     public static final String sanitizeXML(String orig) {
+        if (orig == null) return "";
         if (orig.indexOf('&') < 0) return orig;
         StringBuffer rv = new StringBuffer(orig.length()+32);
         for (int i = 0; i < orig.length(); i++) {
@@ -821,6 +885,7 @@ public class HTMLRenderer extends EventReceiverImpl {
         return rv.toString();
     }
     public static final String sanitizeXML(StringBuffer orig) {
+        if (orig == null) return "";
         if (orig.indexOf("&") < 0) return orig.toString();
         for (int i = 0; i < orig.length(); i++) {
             if (orig.charAt(i) == '&') {
@@ -830,7 +895,17 @@ public class HTMLRenderer extends EventReceiverImpl {
         }
         return orig.toString();
     }
-    
+
+    private static final String STYLE_CHARS = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_";
+    public static String sanitizeStyle(String style) {
+        if ( (style == null) || (style.trim().length() <= 0) ) return null;
+        char c[] = style.toCharArray();
+        for (int i = 0; i < c.length; i++)
+            if (STYLE_CHARS.indexOf(c[i]) < 0)
+                c[i] = '_';
+        return new String(c);
+    }
+        
     protected String getEntryURL() { return getEntryURL(_user != null ? _user.getShowImages() : false); }
     protected String getEntryURL(boolean showImages) {
         if (_entry == null) return "unknown";
diff --git a/apps/syndie/java/src/net/i2p/syndie/web/ArchiveViewerBean.java b/apps/syndie/java/src/net/i2p/syndie/web/ArchiveViewerBean.java
index 93a0c2b204..59b18c2948 100644
--- a/apps/syndie/java/src/net/i2p/syndie/web/ArchiveViewerBean.java
+++ b/apps/syndie/java/src/net/i2p/syndie/web/ArchiveViewerBean.java
@@ -20,25 +20,6 @@ public class ArchiveViewerBean {
         else
             return HTMLRenderer.sanitizeString(info.getProperty("Name"));
     }
-    public static String getEntryTitle(String keyHash, long entryId) {
-        String name = getBlogName(keyHash);
-        return getEntryTitleDate(name, entryId);
-    }
-    
-    private static final SimpleDateFormat _dateFormat = new SimpleDateFormat("yyyy/MM/dd", Locale.UK);
-    public static final String getEntryTitleDate(String blogName, long when) {
-        synchronized (_dateFormat) {
-            try {
-                String str = _dateFormat.format(new Date(when));
-                long dayBegin = _dateFormat.parse(str).getTime();
-                return blogName + ":<br /> <i>" + str + "-" + (when - dayBegin) + "</i>";
-            } catch (ParseException pe) {
-                pe.printStackTrace();
-                // wtf
-                return "unknown";
-            }
-        }
-    }
     
     /** base64 encoded hash of the blog's public key, or null for no filtering by blog */
     public static final String PARAM_BLOG = "blog";
@@ -91,13 +72,12 @@ public class ArchiveViewerBean {
             BlogManager.instance().saveUser(user);
         }
         
-        out.write("<select name=\"");
+        out.write("<select class=\"b_selector\" name=\"");
         out.write(PARAM_SELECTOR);
         out.write("\">");
         out.write("<option value=\"");
         out.write(getDefaultSelector(user, parameters));
         out.write("\">Default blog filter</option>\n");
-        out.write("\">");
         out.write("<option value=\"");
         out.write(SEL_ALL);
         out.write("\">All posts from all blogs</option>\n");
@@ -421,7 +401,6 @@ public class ArchiveViewerBean {
                 pages = entries.size() / numPerPage;
                 if (numPerPage * pages < entries.size())
                     pages++;
-                out.write("<i>");
                 if (pageNum > 0) {
                     String prevURL = null;
                     if ( (selector == null) || (selector.trim().length() <= 0) )
@@ -429,11 +408,11 @@ public class ArchiveViewerBean {
                     else
                         prevURL = HTMLRenderer.getPageURL(user, selector, numPerPage, pageNum-1);
                     System.out.println("prevURL: " + prevURL);
-                    out.write(" <a href=\"" + prevURL + "\">&lt;&lt;</a>");
+                    out.write(" <a class=\"b_selectorPrevMore\" href=\"" + prevURL + "\">&lt;&lt;</a>");
                 } else {
-                    out.write(" &lt;&lt; ");
+                    out.write(" <span class=\"b_selectorPrevNone\">&lt;&lt;</span> ");
                 }
-                out.write("Page " + (pageNum+1) + " of " + pages);
+                out.write("<span class=\"b_selectorPage\">Page " + (pageNum+1) + " of " + pages + "</span>");
                 if (pageNum + 1 < pages) {
                     String nextURL = null;
                     if ( (selector == null) || (selector.trim().length() <= 0) )
@@ -441,11 +420,10 @@ public class ArchiveViewerBean {
                     else
                         nextURL = HTMLRenderer.getPageURL(user, selector, numPerPage, pageNum+1);
                     System.out.println("nextURL: " + nextURL);
-                    out.write(" <a href=\"" + nextURL + "\">&gt;&gt;</a>");
+                    out.write(" <a class=\"b_selectorNextMore\" href=\"" + nextURL + "\">&gt;&gt;</a>");
                 } else {
-                    out.write(" &gt;&gt;");
+                    out.write(" <span class=\"b_selectorNextNone\">&gt;&gt;</span>");
                 }
-                out.write("</i>");
             }
         }
         
@@ -670,7 +648,7 @@ public class ArchiveViewerBean {
     }
     
     private static void renderInvalidAttachment(Map parameters, OutputStream out) throws IOException {
-        out.write(DataHelper.getUTF8("<b>No such entry, or no such attachment</b>"));
+        out.write(DataHelper.getUTF8("<span class=\"b_msgErr\">No such entry, or no such attachment</span>"));
     }
     
     public static void renderMetadata(Map parameters, Writer out) throws IOException {
@@ -684,43 +662,44 @@ public class ArchiveViewerBean {
                 return;
             }
             String props[] = info.getProperties();
-            out.write("<table border=\"0\">");
+            out.write("<table class=\"b_meta\" border=\"0\">");
             for (int i = 0; i < props.length; i++) {
                 if (props[i].equals(BlogInfo.OWNER_KEY)) {
-                    out.write("<tr><td><b>Blog:</b></td><td>");
+                    out.write("<tr class=\"b_metaBlog\"><td class=\"b_metaBlog\"><span class=\"b_metaBlog\">Blog:</span></td>");
                     String blogURL = HTMLRenderer.getPageURL(blog, null, -1, -1, -1, false, false);
-                    out.write("<a href=\"" + blogURL + "\">" + Base64.encode(blog.getData()) + "</td></tr>\n");
+                    out.write("<td class=\"b_metaBlog\"><a class=\"b_metaBlog\" href=\"" + blogURL + "\">" + Base64.encode(blog.getData()) + "</td></tr>\n");
                 } else if (props[i].equals(BlogInfo.SIGNATURE)) {
                     continue;
                 } else if (props[i].equals(BlogInfo.POSTERS)) {
                     SigningPublicKey keys[] = info.getPosters();
                     if ( (keys != null) && (keys.length > 0) ) {
-                        out.write("<tr><td><b>Allowed authors:</b></td><td>");
+                        out.write("<tr class=\"b_metaAuthor\"><td class=\"b_metaAuthor\"><span class=\"b_metaAuthor\">Allowed authors:</span></td>");
+                        out.write("<td class=\"b_metaAuthor\">");
                         for (int j = 0; j < keys.length; j++) {
-                            out.write(keys[j].calculateHash().toBase64());
+                            out.write("<span class=\"b_metaAuthor\">" + keys[j].calculateHash().toBase64() + "</span>");
                             if (j + 1 < keys.length)
                                 out.write("<br />\n");
                         }
                         out.write("</td></tr>\n");
                     }
                 } else {
-                    out.write("<tr><td>" + HTMLRenderer.sanitizeString(props[i]) + ":</td><td>" +
-                              HTMLRenderer.sanitizeString(info.getProperty(props[i])) + "</td></tr>\n");
+                    out.write("<tr class=\"b_metaField\"><td class=\"b_metaField\"><span class=\"b_metaField\">" + HTMLRenderer.sanitizeString(props[i]) 
+                              + ":</span></td><td class=\"b_metaValue\"><span class=\"b_metaValue\">" + HTMLRenderer.sanitizeString(info.getProperty(props[i])) + "</span></td></tr>\n");
                 }
             }
             List tags = BlogManager.instance().getArchive().getIndex().getBlogTags(blog);
             if ( (tags != null) && (tags.size() > 0) ) {
-                out.write("<tr><td>Known tags:</td><td>");
+                out.write("<tr class=\"b_metaTags\"><td class=\"b_metaTags\"><span class=\"b_metaTags\">Known tags:</span></td><td class=\"b_metaTags\">");
                 for (int i = 0; i < tags.size(); i++) {
                     String tag = (String)tags.get(i);
-                    out.write("<a href=\"" + HTMLRenderer.getPageURL(blog, tag, -1, -1, -1, false, false) + "\">" +
+                    out.write("<a class=\"b_metaTag\" href=\"" + HTMLRenderer.getPageURL(blog, tag, -1, -1, -1, false, false) + "\">" +
                               HTMLRenderer.sanitizeString(tag) + "</a> ");
                 }
                 out.write("</td></tr>");
             }
             out.write("</table>");
         } else {
-            out.write("Blog not specified");
+            out.write("<span class=\"b_metaMsgErr\">Blog not specified</span>");
         }
     }
 }
diff --git a/apps/syndie/java/src/net/i2p/syndie/web/RemoteArchiveBean.java b/apps/syndie/java/src/net/i2p/syndie/web/RemoteArchiveBean.java
index 81c97ce661..1a435a258c 100644
--- a/apps/syndie/java/src/net/i2p/syndie/web/RemoteArchiveBean.java
+++ b/apps/syndie/java/src/net/i2p/syndie/web/RemoteArchiveBean.java
@@ -558,7 +558,7 @@ public class RemoteArchiveBean {
     public void renderDeltaForm(User user, ArchiveIndex localIndex, Writer out) throws IOException {
         Archive archive = BlogManager.instance().getArchive();
         StringBuffer buf = new StringBuffer(512);
-        buf.append("<b>New blogs:</b> <select name=\"blog\"><option value=\"ALL\">All</option>\n");
+        buf.append("<em class=\"b_remMeta\">New blogs:</em> <select class=\"b_remMeta\"name=\"blog\"><option value=\"ALL\">All</option>\n");
         Set localBlogs = archive.getIndex().getUniqueBlogs();
         Set remoteBlogs = _remoteIndex.getUniqueBlogs();
         int newBlogs = 0;
@@ -573,12 +573,12 @@ public class RemoteArchiveBean {
         }
         if (newBlogs > 0) {
             out.write(buf.toString());
-            out.write("</select> <input type=\"submit\" name=\"action\" value=\"Fetch metadata\" /><br />\n");
+            out.write("</select> <input class=\"b_remMetaFetch\" type=\"submit\" name=\"action\" value=\"Fetch metadata\" /><br />\n");
         }
         
         int newEntries = 0;
         int localNew = 0;
-        out.write("<table border=\"1\" width=\"100%\">\n");
+        out.write("<table class=\"b_remDelta\" border=\"1\" width=\"100%\">\n");
         List entries = new ArrayList();
         for (Iterator iter = remoteBlogs.iterator(); iter.hasNext(); ) {
             Hash blog = (Hash)iter.next();
@@ -586,37 +586,44 @@ public class RemoteArchiveBean {
                 continue;
             buf.setLength(0);
             int shownEntries = 0;
-            buf.append("<tr><td colspan=\"5\" align=\"left\" valign=\"top\">\n");
+            buf.append("<tr class=\"b_remBlog\"><td class=\"b_remBlog\" colspan=\"5\" align=\"left\" valign=\"top\">\n");
             BlogInfo info = archive.getBlogInfo(blog);
             if (info != null) {
-                buf.append("<a href=\"" + HTMLRenderer.getPageURL(blog, null, -1, -1, -1, user.getShowExpanded(), user.getShowImages()) + "\"><b>" + HTMLRenderer.sanitizeString(info.getProperty(BlogInfo.NAME)) + "</b></a>: " +
-                HTMLRenderer.sanitizeString(info.getProperty(BlogInfo.DESCRIPTION)) + "\n");
+                buf.append("<a class=\"b_remBlog\" href=\"");
+                buf.append(HTMLRenderer.getPageURL(blog, null, -1, -1, -1, user.getShowExpanded(), user.getShowImages()));
+                buf.append("\">").append(HTMLRenderer.sanitizeString(info.getProperty(BlogInfo.NAME))).append("</a>: ");
+                buf.append("<span class=\"b_remBlogDesc\">").append(HTMLRenderer.sanitizeString(info.getProperty(BlogInfo.DESCRIPTION)));
+                buf.append("</span>\n");
             } else {
-                buf.append("<b>" + blog.toBase64() + "</b>\n");
+                buf.append("<span class=\"b_remBlog\">" + blog.toBase64() + "</span>\n");
             }
             buf.append("</td></tr>\n");
-            buf.append("<tr><td>&nbsp;</td><td nowrap=\"true\"><b>Posted on</b></td><td nowrap=\"true\"><b>#</b></td><td nowrap=\"true\"><b>Size</b></td><td width=\"90%\" nowrap=\"true\"><b>Tags</b></td></tr>\n");
+            buf.append("<tr class=\"b_remHeader\"><td class=\"b_remHeader\">&nbsp;</td><td class=\"b_remHeader\" nowrap=\"nowrap\">");
+            buf.append("<em class=\"b_remHeader\">Posted on</em></td>");
+            buf.append("<td class=\"b_remHeader\" nowrap=\"nowrap\"><em class=\"b_remHeader\">#</em></td>");
+            buf.append("<td class=\"b_remHeader\" nowrap=\"nowrap\"><em class=\"b_remHeader\">Size</em></td>");
+            buf.append("<td class=\"b_remHeader\" width=\"90%\" nowrap=\"true\"><em class=\"b_remHeader\">Tags</em></td></tr>\n");
             entries.clear();
             _remoteIndex.selectMatchesOrderByEntryId(entries, blog, null);
             for (int i = 0; i < entries.size(); i++) {
                 BlogURI uri = (BlogURI)entries.get(i);
-                buf.append("<tr>\n");
+                buf.append("<tr class=\"b_remDetail\">\n");
                 if (!archive.getIndex().getEntryIsKnown(uri)) {
-                    buf.append("<td><input type=\"checkbox\" name=\"entry\" value=\"" + uri.toString() + "\" /></td>\n");
+                    buf.append("<td class=\"b_remDetail\"><input class=\"b_remSelect\" type=\"checkbox\" name=\"entry\" value=\"" + uri.toString() + "\" /></td>\n");
                     newEntries++;
                     shownEntries++;
                 } else {
                     String page = HTMLRenderer.getPageURL(blog, null, uri.getEntryId(), -1, -1,
                     user.getShowExpanded(), user.getShowImages());
-                    buf.append("<td><a href=\"" + page + "\">(local)</a></td>\n");
+                    buf.append("<td class=\"b_remDetail\"><a class=\"b_remLocal\" href=\"" + page + "\">(local)</a></td>\n");
                 }
-                buf.append("<td>" + getDate(uri.getEntryId()) + "</td>\n");
-                buf.append("<td>" + getId(uri.getEntryId()) + "</td>\n");
-                buf.append("<td>" + _remoteIndex.getBlogEntrySizeKB(uri) + "KB</td>\n");
-                buf.append("<td>");
+                buf.append("<td class=\"b_remDetail\"><span class=\"b_remDate\">" + getDate(uri.getEntryId()) + "</span></td>\n");
+                buf.append("<td class=\"b_remDetail\"><span class=\"b_remNum\">" + getId(uri.getEntryId()) + "</span></td>\n");
+                buf.append("<td class=\"b_remDetail\"><span class=\"b_remSize\">" + _remoteIndex.getBlogEntrySizeKB(uri) + "KB</span></td>\n");
+                buf.append("<td class=\"b_remDetail\">");
                 for (Iterator titer = new TreeSet(_remoteIndex.getBlogEntryTags(uri)).iterator(); titer.hasNext(); ) {
                     String tag = (String)titer.next();
-                    buf.append("<a href=\"" + HTMLRenderer.getPageURL(blog, tag, -1, -1, -1, user.getShowExpanded(), user.getShowImages()) + "\">" + tag + "</a> \n");
+                    buf.append("<a class=\"b_remTag\" href=\"" + HTMLRenderer.getPageURL(blog, tag, -1, -1, -1, user.getShowExpanded(), user.getShowImages()) + "\">" + tag + "</a> \n");
                 }
                 buf.append("</td>\n");
                 buf.append("</tr>\n");
@@ -630,22 +637,22 @@ public class RemoteArchiveBean {
             // now for posts in known blogs that we have and they don't
             entries.clear();
             localIndex.selectMatchesOrderByEntryId(entries, blog, null);
-            buf.append("<tr><td colspan=\"5\">Entries we have, but the remote Syndie doesn't:</td></tr>\n");
+            buf.append("<tr class=\"b_remLocalHeader\"><td class=\"b_remLocalHeader\" colspan=\"5\"><span class=\"b_remLocalHeader\">Entries we have, but the remote Syndie doesn't:</span></td></tr>\n");
             for (int i = 0; i < entries.size(); i++) {
                 BlogURI uri = (BlogURI)entries.get(i);
                 if (!_remoteIndex.getEntryIsKnown(uri)) {
-                    buf.append("<tr>\n");
-                    buf.append("<td><input type=\"checkbox\" name=\"localentry\" value=\"" + uri.toString() + "\" /></td>\n");
+                    buf.append("<tr class=\"b_remLocalDetail\">\n");
+                    buf.append("<td class=\"b_remLocalDetail\"><input class=\"b_remLocalSend\" type=\"checkbox\" name=\"localentry\" value=\"" + uri.toString() + "\" /></td>\n");
                     shownEntries++;
                     newEntries++;
                     localNew++;
-                    buf.append("<td>" + getDate(uri.getEntryId()) + "</td>\n");
-                    buf.append("<td>" + getId(uri.getEntryId()) + "</td>\n");
-                    buf.append("<td>" + localIndex.getBlogEntrySizeKB(uri) + "KB</td>\n");
-                    buf.append("<td>");
+                    buf.append("<td class=\"b_remLocalDate\"><span class=\"b_remLocalDate\">" + getDate(uri.getEntryId()) + "</span></td>\n");
+                    buf.append("<td class=\"b_remLocalNum\"><span class=\"b_remLocalNum\">" + getId(uri.getEntryId()) + "</span></td>\n");
+                    buf.append("<td class=\"b_remLocalSize\"><span class=\"b_remLocalSize\">" + localIndex.getBlogEntrySizeKB(uri) + "KB</span></td>\n");
+                    buf.append("<td class=\"b_remLocalTags\">");
                     for (Iterator titer = new TreeSet(localIndex.getBlogEntryTags(uri)).iterator(); titer.hasNext(); ) {
                         String tag = (String)titer.next();
-                        buf.append("<a href=\"" + HTMLRenderer.getPageURL(blog, tag, -1, -1, -1, user.getShowExpanded(), user.getShowImages()) + "\">" + tag + "</a> \n");
+                        buf.append("<a class=\"b_remLocalTag\" href=\"" + HTMLRenderer.getPageURL(blog, tag, -1, -1, -1, user.getShowExpanded(), user.getShowImages()) + "\">" + tag + "</a> \n");
                     }
                     buf.append("</td>\n");
                     buf.append("</tr>\n");
@@ -659,7 +666,7 @@ public class RemoteArchiveBean {
         // now for posts in blogs we have and they don't
         int newBefore = localNew;
         buf.setLength(0);
-        buf.append("<tr><td colspan=\"5\">Blogs the remote Syndie doesn't have</td></tr>\n");
+        buf.append("<tr class=\"b_remLocalHeader\"><td class=\"b_remLocalHeader\" colspan=\"5\"><span class=\"b_remLocalHeader\">Blogs the remote Syndie doesn't have</span></td></tr>\n");
         for (Iterator iter = localBlogs.iterator(); iter.hasNext(); ) {
             Hash blog = (Hash)iter.next();
             if (remoteBlogs.contains(blog)) {
@@ -672,15 +679,15 @@ public class RemoteArchiveBean {
             
             for (int i = 0; i < entries.size(); i++) {
                 BlogURI uri = (BlogURI)entries.get(i);
-                buf.append("<tr>\n");
-                buf.append("<td><input type=\"checkbox\" name=\"localentry\" value=\"" + uri.toString() + "\" /></td>\n");
-                buf.append("<td>" + getDate(uri.getEntryId()) + "</td>\n");
-                buf.append("<td>" + getId(uri.getEntryId()) + "</td>\n");
-                buf.append("<td>" + localIndex.getBlogEntrySizeKB(uri) + "KB</td>\n");
-                buf.append("<td>");
+                buf.append("<tr class=\"b_remLocalDetail\">\n");
+                buf.append("<td class=\"b_remLocalDetail\"><input class=\"b_remLocalSend\" type=\"checkbox\" name=\"localentry\" value=\"" + uri.toString() + "\" /></td>\n");
+                buf.append("<td class=\"b_remLocalDate\"><span class=\"b_remLocalDate\">" + getDate(uri.getEntryId()) + "</span></td>\n");
+                buf.append("<td class=\"b_remLocalNum\"><span class=\"b_remLocalNum\">" + getId(uri.getEntryId()) + "</span></td>\n");
+                buf.append("<td class=\"b_remLocalSize\"><span class=\"b_remLocalSize\">" + localIndex.getBlogEntrySizeKB(uri) + "KB</span></td>\n");
+                buf.append("<td class=\"b_remLocalTags\">");
                 for (Iterator titer = new TreeSet(localIndex.getBlogEntryTags(uri)).iterator(); titer.hasNext(); ) {
                     String tag = (String)titer.next();
-                    buf.append("<a href=\"" + HTMLRenderer.getPageURL(blog, tag, -1, -1, -1, user.getShowExpanded(), user.getShowImages()) + "\">" + tag + "</a> \n");
+                    buf.append("<a class=\"b_remLocalTag\" href=\"" + HTMLRenderer.getPageURL(blog, tag, -1, -1, -1, user.getShowExpanded(), user.getShowImages()) + "\">" + tag + "</a> \n");
                 }
                 buf.append("</td>\n");
                 buf.append("</tr>\n");
@@ -692,13 +699,13 @@ public class RemoteArchiveBean {
         
         out.write("</table>\n");
         if (newEntries > 0) {
-            out.write("<input type=\"submit\" name=\"action\" value=\"Fetch selected entries\" /> \n");
-            out.write("<input type=\"submit\" name=\"action\" value=\"Fetch all new entries\" /> \n");
+            out.write("<input class=\"b_remFetchSelected\" type=\"submit\" name=\"action\" value=\"Fetch selected entries\" /> \n");
+            out.write("<input class=\"b_remFetchAll\" type=\"submit\" name=\"action\" value=\"Fetch all new entries\" /> \n");
         } else {
-            out.write(HTMLRenderer.sanitizeString(_remoteLocation) + " has no new posts to offer us\n");
+            out.write("<span class=\"b_remNoRemotePosts\">" + HTMLRenderer.sanitizeString(_remoteLocation) + " has no new posts to offer us</span>\n");
         }
         if (localNew > 0) {
-            out.write("<input type=\"submit\" name=\"action\" value=\"Post selected entries\" /> \n");
+            out.write("<input class=\"b_remPostSelected\" type=\"submit\" name=\"action\" value=\"Post selected entries\" /> \n");
         }
         out.write("<hr />\n");
     }
diff --git a/apps/syndie/jsp/_bodyindex.jsp b/apps/syndie/jsp/_bodyindex.jsp
index e31810486b..ebb41702bf 100644
--- a/apps/syndie/jsp/_bodyindex.jsp
+++ b/apps/syndie/jsp/_bodyindex.jsp
@@ -31,10 +31,9 @@ if (user.getAuthenticated() && (null != request.getParameter("action")) ) {
     BlogManager.instance().saveUser(user);
   }
 }
-%><table border="0" width="100%">
-<tr><form action="index.jsp"><td nowrap="true">
-<b>Blogs:</b> <%ArchiveViewerBean.renderBlogSelector(user, request.getParameterMap(), out);%>
-<input type="submit" value="Refresh" />
-<input type="submit" name="action" value="<%=ArchiveViewerBean.SEL_ACTION_SET_AS_DEFAULT%>" />
-<!-- char encoding: [<%=response.getCharacterEncoding()%>] content type [<%=response.getContentType()%>] Locale [<%=response.getLocale()%>] -->
+%><table border="0" width="100%" class="b_content">
+<tr class="b_content"><form action="index.jsp"><td nowrap="true">
+<em class="b_selectorTitle">Blogs:</em> <span class="b_selector"><%ArchiveViewerBean.renderBlogSelector(user, request.getParameterMap(), out);%></span>
+<input type="submit" value="Refresh" class="b_selectorRefresh" />
+<input type="submit" name="action" value="<%=ArchiveViewerBean.SEL_ACTION_SET_AS_DEFAULT%>" class="b_selectorDefault" />
 <%ArchiveViewerBean.renderBlogs(user, request.getParameterMap(), out, "</td></form></tr><tr><td align=\"left\" valign=\"top\">");%></td></tr></table>
\ No newline at end of file
diff --git a/apps/syndie/jsp/_topnav.jsp b/apps/syndie/jsp/_topnav.jsp
index db26180d8e..921a1bd4cd 100644
--- a/apps/syndie/jsp/_topnav.jsp
+++ b/apps/syndie/jsp/_topnav.jsp
@@ -1,15 +1,18 @@
 <%@page import="net.i2p.syndie.*, net.i2p.syndie.sml.*, net.i2p.syndie.web.*" %>
 <jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" />
-<td valign="top" align="left" class="syndieTopNavBlogsCell" height="10"><a href="index.jsp">Home</a></td>
-<td valign="top" align="left" class="syndieTopNavRemoteCell" height="10">
-<a href="admin.jsp">Syndie admin</a>
-<a href="remote.jsp">Remote archives</a>
-<a href="import.jsp">Import</a>
-</td>
 <form action="<%=request.getRequestURI() + "?" + (request.getQueryString() != null ? request.getQueryString() : "")%>">
-<td nowrap="true" valign="top" align="right" class="syndieTopNavManageCell" height="10"><%
+<td nowrap="true" colspan="2" height="10" class="b_topnav">
+<span class="b_topnavHome"><a href="index.jsp" class="b_topnavHome">Home</a></span>
+<a href="admin.jsp" class="b_topnavAdmin">Syndie admin</a>
+<a href="remote.jsp" class="b_topnavRemote">Remote archives</a>
+<a href="import.jsp" class="b_topnavImport">Import</a>
+</td><td nowrap="true" height="10" class="b_topnavUser"><%
 if ("true".equals(request.getParameter("logout"))) {
   user.invalidate();
+  RemoteArchiveBean rem = (RemoteArchiveBean)session.getAttribute("remote");
+  if (rem != null) rem.reinitialize();
+  PostBean post = (PostBean)session.getAttribute("post");
+  if (post != null) post.reinitialize();
 }
 String login = request.getParameter("login");
 String pass = request.getParameter("password");
@@ -17,28 +20,27 @@ String loginSubmit = request.getParameter("Login");
 if ( (login != null) && (pass != null) && (loginSubmit != null) && (loginSubmit.equals("Login")) ) {
   String loginResult = BlogManager.instance().login(user, login, pass);
   if (!user.getAuthenticated())
-    out.write("<b>" + loginResult + "</b>");
+    out.write("<b class=\"b_topnavLoginResult\">" + loginResult + "</b>");
 }
 %>
 <% if (user.getAuthenticated()) { %>
-Logged in as: <b><jsp:getProperty property="username" name="user" />:</b>
-<a href="<%=HTMLRenderer.getPageURL(user.getBlog(), null, -1, -1, -1, user.getShowExpanded(), user.getShowImages())%>"><%=HTMLRenderer.sanitizeString(ArchiveViewerBean.getBlogName(user.getBlogStr()))%></a>
-<a href="<%=HTMLRenderer.getPostURL(user.getBlog())%>">Post</a>
-<a href="<%=HTMLRenderer.getMetadataURL(user.getBlog())%>">Metadata</a>
-<a href="addresses.jsp">Addressbook</a>
-<a href="index.jsp?logout=true">Logout</a><br />
+<span class="b_topnavUsername">Logged in as:</span> <em class="b_topnavUsername"><jsp:getProperty property="username" name="user" />:</em>
+<a class="b_topnavBlog" href="<%=HTMLRenderer.getPageURL(user.getBlog(), null, -1, -1, -1, user.getShowExpanded(), user.getShowImages())%>"><%=HTMLRenderer.sanitizeString(ArchiveViewerBean.getBlogName(user.getBlogStr()))%></a>
+<a class="b_topnavPost" href="<%=HTMLRenderer.getPostURL(user.getBlog())%>">Post</a>
+<a class="b_topnavMeta" href="<%=HTMLRenderer.getMetadataURL(user.getBlog())%>">Metadata</a>
+<a class="b_topnavAddr" href="addresses.jsp">Addressbook</a>
+<a class="b_topnavLogout" href="index.jsp?logout=true">Logout</a>
 <%} else {%>
-Login: <input type="text" name="login" size="8" />
-Pass: <input type="password" name="password" size="8" /><%
+<span class="b_topnavLogin">Login:</span> <input class="b_topnavLogin" type="text" name="login" size="8" />
+<span class="b_topnavPass">Pass:</span> <input class="b_topnavPass" type="password" name="password" size="8" /><%
 java.util.Enumeration params = request.getParameterNames();
 while (params.hasMoreElements()) {
  String p = (String)params.nextElement();
  String val = request.getParameter(p); 
  %><input type="hidden" name="<%=p%>" value="<%=val%>" /><%
 }%>
-<input type="submit" name="Login" value="Login" />
-<a href="register.jsp">Register</a>
+<input class="b_topnavLoginSubmit" type="submit" name="Login" value="Login" />
+<a class="b_topnavRegister" href="register.jsp">Register</a>
 <% } %>
-
 </td>
 </form> 
\ No newline at end of file
diff --git a/apps/syndie/jsp/addresses.jsp b/apps/syndie/jsp/addresses.jsp
index d5e067ddf5..f420346343 100644
--- a/apps/syndie/jsp/addresses.jsp
+++ b/apps/syndie/jsp/addresses.jsp
@@ -1,20 +1,20 @@
-<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.Base64, net.i2p.syndie.web.*, net.i2p.syndie.sml.*, net.i2p.syndie.data.*, net.i2p.syndie.*, org.mortbay.servlet.MultiPartRequest, java.util.*, java.io.*" %>
-<% request.setCharacterEncoding("UTF-8"); %>
-<jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" />
+<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.Base64, net.i2p.syndie.web.*, net.i2p.syndie.sml.*, net.i2p.syndie.data.*, net.i2p.syndie.*, org.mortbay.servlet.MultiPartRequest, java.util.*, java.io.*" %><%
+ request.setCharacterEncoding("UTF-8"); %><jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" 
+/><!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 TRANSITIONAL//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd">
 <html>
 <head>
 <title>SyndieMedia addressbook</title>
-<link href="style.jsp" rel="stylesheet" type="text/css" />
+<link href="style.jsp" rel="stylesheet" type="text/css" >
 </head>
 <body>
 <table border="1" cellpadding="0" cellspacing="0" width="100%">
-<tr><td colspan="5" valign="top" align="left"><jsp:include page="_toplogo.jsp" /></td></tr>
-<tr><td valign="top" align="left" rowspan="2"><jsp:include page="_leftnav.jsp" /></td>
+<tr class="b_toplogo"><td colspan="5" valign="top" align="left" class="b_toplogo"><jsp:include page="_toplogo.jsp" /></td></tr>
+<tr><td valign="top" align="left" rowspan="2" class="b_leftnav"><jsp:include page="_leftnav.jsp" /></td>
     <jsp:include page="_topnav.jsp" />
-    <td valign="top" align="left" rowspan="2"><jsp:include page="_rightnav.jsp" /></td></tr>
-<tr><td valign="top" align="left" colspan="3"><%
+    <td valign="top" align="left" rowspan="2" class="b_rightnav"><jsp:include page="_rightnav.jsp" /></td></tr>
+<tr class="b_content"><td valign="top" align="left" colspan="3" class="b_content"><%
 if (!user.getAuthenticated()) { 
-    %>You must log in to view your addressbook<% 
+    %><span class="b_addrMsgErr">You must log in to view your addressbook</span><% 
 } else {
     PetNameDB names = user.getPetNameDB();
     String action = request.getParameter("action");
@@ -31,11 +31,11 @@ if (!user.getAuthenticated()) {
           names.remove(oldPetname);
           names.set(cur.getName(), cur);
           names.store(user.getAddressbookLocation());
-          %><b>Address updated</b><%
+          %><span class="b_addrMsgOk">Address updated</span><%
         }
     } else if ( (action != null) && ("Add".equals(action)) ) {
         PetName cur = names.get(request.getParameter("name"));
-        if (cur != null) { %><b>Address already exists</b><% } else {
+        if (cur != null) { %><span class="b_addrMsgErr">Address already exists</span><% } else {
           cur = new PetName();
           cur.setName(request.getParameter("name"));
           cur.setNetwork(request.getParameter("network"));
@@ -45,29 +45,36 @@ if (!user.getAuthenticated()) {
           cur.setGroups(request.getParameter("groups"));
           names.set(cur.getName(), cur);
           names.store(user.getAddressbookLocation());
-          %><b>Address added</b><%
+          %><span class="b_addrMsgOk">Address added</span><%
         }
     } else if ( (action != null) && ("Delete".equals(action)) ) {
         PetName cur = names.get(request.getParameter("name"));
         if (cur != null) { 
           names.remove(cur.getName());
           names.store(user.getAddressbookLocation());
-          %><b>Address removed</b><%
+          %><span class="b_addrMsgOk">Address removed</span><%
         }
     } else if ( (action != null) && ("Export".equals(action)) ) {
       %><%=BlogManager.instance().exportHosts(user)%><%
     }
     TreeSet sorted = new TreeSet(names.getNames());
-    %><table border="0" width="100%">
-<tr><td><b>Name</b></td><td><b>Network</b></td><td><b>Protocol</b></td><td><b>Location</b></td><td><b>Public?</b></td><td><b>Groups</b><td>&nbsp;</td></tr>
+    %><table border="0" width="100%" class="b_addr">
+<tr class="b_addrHeader">
+ <td class="b_addrHeader"><em class="b_addrHeader">Name</em></td>
+ <td class="b_addrHeader"><em class="b_addrHeader">Network</em></td>
+ <td class="b_addrHeader"><em class="b_addrHeader">Protocol</em></td>
+ <td class="b_addrHeader"><em class="b_addrHeader">Location</em></td>
+ <td class="b_addrHeader"><em class="b_addrHeader">Public?</em></td>
+ <td class="b_addrHeader"><em class="b_addrHeader">Groups</em></td> 
+ <td class="b_addrHeader">&nbsp;</td></tr>
 <%
     StringBuffer buf = new StringBuffer(128);
     for (Iterator iter = sorted.iterator(); iter.hasNext(); ) {
         PetName name = names.get((String)iter.next());
-        buf.append("<tr><form action=\"addresses.jsp\" method=\"POST\">");
+        buf.append("<tr class=\"b_addrDetail\"><form action=\"addresses.jsp\" method=\"POST\">");
         buf.append("<input type=\"hidden\" name=\"petname\" value=\"").append(name.getName()).append("\" />");
-        buf.append("<td><input type=\"text\" size=\"20\" name=\"name\" value=\"").append(name.getName()).append("\" /></td><td>");
-        buf.append("<select name=\"network\">");
+        buf.append("<td class=\"b_addrName\"><input class=\"b_addrName\" type=\"text\" size=\"20\" name=\"name\" value=\"").append(name.getName()).append("\" /></td>");
+        buf.append("<td class=\"b_addrNet\"><select class=\"b_addrNet\" name=\"network\">");
         String net = name.getNetwork();
         if (net == null) net = "";
         buf.append("<option value=\"i2p\" ");
@@ -95,7 +102,9 @@ if (!user.getAuthenticated()) {
             buf.append("selected=\"true\" ");
         buf.append("/>Internet</option>");
 
-        buf.append("</select></td><td><select name=\"protocol\">");
+        buf.append("</select></td>");
+
+        buf.append("<td class=\"b_addrProto\"><select class=\"b_addrProto\" name=\"protocol\">");
         String proto = name.getProtocol();
         if (proto == null) proto = "";
 
@@ -124,23 +133,27 @@ if (!user.getAuthenticated()) {
             buf.append("selected=\"true\" ");
         buf.append("/>Syndie blog</option>");
 
-        buf.append("</select></td><td>");
+        buf.append("</select></td>");
+
+        buf.append("<td class=\"b_addrLoc\">");
         if (name.getLocation() != null)
-            buf.append("<input name=\"location\" size=\"50\" value=\"").append(name.getLocation()).append("\" />");
+            buf.append("<input class=\"b_addrLoc\" name=\"location\" size=\"50\" value=\"").append(name.getLocation()).append("\" />");
         else
-            buf.append("<input name=\"location\" size=\"50\" value=\"\" />");
+            buf.append("<input class=\"b_addrLoc\" name=\"location\" size=\"50\" value=\"\" />");
 
-        buf.append("</td><td><input type=\"checkbox\" name=\"isPublic\" ");
+        buf.append("</td>");
+        buf.append("<td class=\"b_addrPublic\"><input class=\"b_addrPublic\" type=\"checkbox\" name=\"isPublic\" ");
         if (name.getIsPublic())
             buf.append("checked=\"true\" ");
-        buf.append(" /></td><td><input type=\"text\" name=\"groups\" size=\"10\" value=\"");
+        buf.append(" /></td>");
+        buf.append("<td class=\"b_addrGroup\"><input class=\"b_addrGroup\" type=\"text\" name=\"groups\" size=\"10\" value=\"");
         for (int j = 0; j < name.getGroupCount(); j++) {
             buf.append(HTMLRenderer.sanitizeTagParam(name.getGroup(j)));
             if (j + 1 < name.getGroupCount()) 
                 buf.append(',');
         }
-        buf.append("\" /></td><td nowrap=\"true\">");
-        buf.append("<input type=\"submit\" name=\"action\" value=\"Change\" /> <input type=\"submit\" name=\"action\" value=\"Delete\" />");
+        buf.append("\" /></td><td class=\"b_addrDetail\" nowrap=\"true\">");
+        buf.append("<input class=\"b_addrChange\" type=\"submit\" name=\"action\" value=\"Change\" /> <input class=\"b_addrDelete\" type=\"submit\" name=\"action\" value=\"Delete\" />");
         buf.append("</td></form></tr>");
         out.write(buf.toString());
         buf.setLength(0);
@@ -156,26 +169,29 @@ if (!user.getAuthenticated()) {
     if (name == null || active) name = "";
     if (loc == null || active) loc= "";
     %>
-    <tr><form action="addresses.jsp" method="POST"><td><input type="text" name="name" size="20" value="<%=name%>" /></td>
-        <td><select name="network">
+    <tr class="b_addrDetail"><form action="addresses.jsp" method="POST">
+        <td class="b_addrName"><input class="b_addrName" type="text" name="name" size="20" value="<%=name%>" /></td>
+        <td class="b_addrNet"><select class="b_addrNet" name="network">
             <option value="i2p" <%="i2p".equalsIgnoreCase(net) ? " selected=\"true\" " : ""%>>I2P</option>
             <option value="syndie" <%="syndie".equalsIgnoreCase(net) ? " selected=\"true\" " : ""%>>Syndie</option>
             <option value="tor" <%="tor".equalsIgnoreCase(net) ? " selected=\"true\" " : ""%>>Tor</option>
             <option value="freenet" <%="freenet".equalsIgnoreCase(net) ? " selected=\"true\" " : ""%>>Freenet</option>
             <option value="internet" <%="internet".equalsIgnoreCase(net) ? " selected=\"true\" " : ""%>>Internet</option></select></td>
-        <td><select name="protocol">
+        <td class="b_addrProto"><select class="b_addrProto" name="protocol">
             <option value="http" <%="http".equalsIgnoreCase(proto) ? " selected=\"true\" " : ""%>>HTTP</option>
             <option value="irc" <%="irc".equalsIgnoreCase(proto) ? " selected=\"true\" " : ""%>>IRC</option>
             <option value="i2phex" <%="i2phex".equalsIgnoreCase(proto) ? " selected=\"true\" " : ""%>>I2Phex</option>
             <option value="syndiearchive" <%="syndiearchive".equalsIgnoreCase(proto) ? " selected=\"true\" " : ""%>>Syndie archive</option>
             <option value="syndieblog" <%="syndieblog".equalsIgnoreCase(proto) ? " selected=\"true\" " : ""%>>Syndie blog</option></select></td>
-        <td><input type="text" size="50" name="location" value="<%=loc%>" /></td>
-        <td><input type="checkbox" name="isPublic" /></td>
-        <td><input type="text" name="groups" size="10" /></td>
-        <td><input type="submit" name="action" value="Add" /></td>
+        <td class="b_addrLoc"><input class="b_addrLoc" type="text" size="50" name="location" value="<%=loc%>" /></td>
+        <td class="b_addrPublic"><input class="b_addrPublic" type="checkbox" name="isPublic" /></td>
+        <td class="b_addrGroup"><input class="b_addrGroup" type="text" name="groups" size="10" /></td>
+        <td class="b_addrDetail"><input class="b_addrAdd" type="submit" name="action" value="Add" /></td>
     </form></tr>
-    <tr><form action="addresses.jsp" method="POST">
-        <td colspan="7">Export the eepsites to your router's userhosts.txt: <input type="submit" name="action" value="Export" /></td>
+    <tr class="b_addrExport"><form action="addresses.jsp" method="POST">
+        <td class="b_addrExport" colspan="7">
+          <span class="b_addrExport">Export the eepsites to your router's userhosts.txt:</span>
+          <input class="b_addrExportSubmit" type="submit" name="action" value="Export" /></td>
         </form></tr>
     </table>
     <%
diff --git a/apps/syndie/jsp/admin.jsp b/apps/syndie/jsp/admin.jsp
index 61b3d77163..59eb76dd02 100644
--- a/apps/syndie/jsp/admin.jsp
+++ b/apps/syndie/jsp/admin.jsp
@@ -1,20 +1,20 @@
-<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.Base64, net.i2p.syndie.web.*, net.i2p.syndie.sml.*, net.i2p.syndie.data.*, net.i2p.syndie.*, org.mortbay.servlet.MultiPartRequest, java.util.*, java.io.*" %>
-<% request.setCharacterEncoding("UTF-8"); %>
-<jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" />
-<html>
+<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.Base64, net.i2p.syndie.web.*, net.i2p.syndie.sml.*, net.i2p.syndie.data.*, net.i2p.syndie.*, org.mortbay.servlet.MultiPartRequest, java.util.*, java.io.*" %><% 
+request.setCharacterEncoding("UTF-8"); 
+%><jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" 
+/><!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 TRANSITIONAL//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd"><html>
 <head>
 <title>SyndieMedia admin</title>
-<link href="style.jsp" rel="stylesheet" type="text/css" />
+<link href="style.jsp" rel="stylesheet" type="text/css" >
 </head>
 <body>
 <table border="1" cellpadding="0" cellspacing="0" width="100%">
-<tr><td colspan="5" valign="top" align="left"><jsp:include page="_toplogo.jsp" /></td></tr>
-<tr><td valign="top" align="left" rowspan="2"><jsp:include page="_leftnav.jsp" /></td>
+<tr class="b_toplogo"><td colspan="5" valign="top" align="left" class="b_toplogo"><jsp:include page="_toplogo.jsp" /></td></tr>
+<tr><td valign="top" align="left" rowspan="2" class="b_leftnav"><jsp:include page="_leftnav.jsp" /></td>
     <jsp:include page="_topnav.jsp" />
-    <td valign="top" align="left" rowspan="2"><jsp:include page="_rightnav.jsp" /></td></tr>
-<tr><td valign="top" align="left" colspan="3"><%
+    <td valign="top" align="left" rowspan="2" class="b_rightnav"><jsp:include page="_rightnav.jsp" /></td></tr>
+<tr class="b_content"><td valign="top" align="left" colspan="3" class="b_content"><%
 if (!user.getAuthenticated()) { 
-  %>You must be logged in to configure your Syndie instance!<% 
+  %><span class="b_adminMsgErr">You must be logged in to configure your Syndie instance!</span><% 
 } else {
   String action = request.getParameter("action");
   if ( (action != null) && ("Save".equals(action)) ) {
@@ -30,50 +30,51 @@ if (!user.getAuthenticated()) {
         int port = -1;
         try { port = Integer.parseInt(proxyPort); } catch (NumberFormatException nfe) { port = 4444; }
         BlogManager.instance().configure(regPass, remotePass, adminPass, selector, proxyHost, port, null);
-        %>Configuration updated<%
+        %><span class="b_adminMsgOk">Configuration updated</span><%
       } else {
-        %>Invalid admin password.  If you lost it, please update your syndie.config.<%
+        %><span class="b_adminMsgErr">Invalid admin password.  If you lost it, please update your syndie.config.</span><%
       }
     } else {
       int port = -1;
       try { port = Integer.parseInt(proxyPort); } catch (NumberFormatException nfe) { port = 4444; }
       BlogManager.instance().configure(regPass, remotePass, adminPass, selector, proxyHost, port, null);
-      %>Configuration saved<%
+      %><span class="b_adminMsgOk">Configuration saved</span><%
     }
   } else {
 %><form action="admin.jsp" method="POST">
-<b>Registration password:</b> <input type="text" name="regpass" size="10" /><br />
-Users must specify this password on the registration form to proceed.  If this is
-blank, anyone can register.<br />
-<b>Remote password:</b> <input type="text" name="remotepass" size="10" /><br />
-To access remote archives, users must first provide this password on their 
+<em class="b_adminField">Registration password:</em> <input class="b_adminField" type="text" name="regpass" size="10" /><br />
+<span class="b_adminDescr">Users must specify this password on the registration form to proceed.  If this is
+blank, anyone can register.</span><br />
+<em class="b_adminField">Remote password:</em> <input class="b_adminField" type="text" name="remotepass" size="10" /><br />
+<span class="b_adminDescr">To access remote archives, users must first provide this password on their 
 metadata page.  Remote access is 'dangerous', as it allows the user to instruct
 this Syndie instance to establish HTTP connections with arbitrary locations.  If
-this field is not specified, no one can use remote archives.<br />
-<b>Default remote proxy host:</b> <input type="text" name="proxyhost" size="20" value="localhost" /><br />
-<b>Default remote proxy port:</b> <input type="text" name="proxyport" size="5" value="4444" /><br />
-This is the default HTTP proxy shown on the remote archive page.<br />
-<b>Default blog selector:</b> <input type="text" name="selector" size="40" value="ALL" /><br />
-The selector lets you choose what blog (or blogs) are shown on the front page for
-new, unregistered users.  Valid values include:<ul>
- <li><code>ALL<code>: all blogs</li>
- <li><code>blog://$blogHash</code>: all posts in the blog identified by $blogHash</li>
- <li><code>blogtag://$blogHash/$tagBase64</code>: all posts in the blog identified by $blogHash 
+this field is not specified, no one can use remote archives.</span><br />
+<em class="b_adminField">Default remote proxy host:</em> <input class="b_adminField" type="text" name="proxyhost" size="20" value="localhost" /><br />
+<em class="b_adminField">Default remote proxy port:</em> <input class="b_adminField" type="text" name="proxyport" size="5" value="4444" /><br />
+<span class="b_adminDescr">This is the default HTTP proxy shown on the remote archive page.</span><br />
+<em class="b_adminField">Default blog selector:</em> <input class="b_adminField" type="text" name="selector" size="40" value="ALL" /><br />
+<span class="b_adminDescr">The selector lets you choose what blog (or blogs) are shown on the front page for
+new, unregistered users.  Valid values include:<ul class="b_adminDescr">
+ <li class="b_adminDescr"><code class="b_adminDescr">ALL</code>: all blogs</li>
+ <li class="b_adminDescr"><code class="b_adminDescr">blog://$blogHash</code>: all posts in the blog identified by $blogHash</li>
+ <li class="b_adminDescr"><code class="b_adminDescr">blogtag://$blogHash/$tagBase64</code>: all posts in the blog identified by $blogHash 
            tagged by the tag whose modified base64 encoding is $tagBase64</li>
- <li><code>tag://$tagBase64</code>: all posts in any blog tagged by the tag whose 
+ <li class="b_adminDescr"><code class="b_adminDescr">tag://$tagBase64</code>: all posts in any blog tagged by the tag whose 
            modified base64 encoding is $tagBase64</li>
 </ul>
+</span>
 <hr />
 <% if (!BlogManager.instance().isConfigured()) { 
 long passNum = new Random().nextLong(); %>
-<b>Administrative password:</b> <input type="password" name="adminpass" size="10" value="<%=passNum%>" /> <br />
-Since this Syndie instance is not already configured, you can specify a new 
+<em class="b_adminField">Administrative password:</em> <input class="b_adminField" type="password" name="adminpass" size="10" value="<%=passNum%>" /> <br />
+<span class="b_adminDescr b_adminDescrFirstRun">Since this Syndie instance is not already configured, you can specify a new 
 administrative password which must be presented whenever you update this configuration.
-The default value filled in there is <code><%=passNum%></code><br />
+The default value filled in there is <code class="b_adminDescr b_adminDescrFirstRun"><%=passNum%></code></span><br />
 <% } else { %>
-<b>Administrative password:</b> <input type="password" name="adminpass" size="10" value="" /> <br />
+<em class="b_adminField">Administrative password:</em> <input class="b_adminField" type="password" name="adminpass" size="10" value="" /> <br />
 <% } %>
-<input type="submit" name="action" value="Save" />
+<input class="b_adminSave" type="submit" name="action" value="Save" />
 <% } 
 } %>
 </td></tr>
diff --git a/apps/syndie/jsp/externallink.jsp b/apps/syndie/jsp/externallink.jsp
index 43c8ba0e28..f5744e8474 100644
--- a/apps/syndie/jsp/externallink.jsp
+++ b/apps/syndie/jsp/externallink.jsp
@@ -1,17 +1,19 @@
-<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.*, net.i2p.syndie.web.*, net.i2p.syndie.sml.*" %>
-<% request.setCharacterEncoding("UTF-8"); %>
+<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.*, net.i2p.syndie.web.*, net.i2p.syndie.sml.*" %><% 
+request.setCharacterEncoding("UTF-8"); 
+%><!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 TRANSITIONAL//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd">
 <html>
 <head>
 <title>SyndieMedia</title>
-<link href="style.jsp" rel="stylesheet" type="text/css" />
+<link href="style.jsp" rel="stylesheet" type="text/css" >
 </head>
 <body>
 <table border="1" cellpadding="0" cellspacing="0" width="100%">
-<tr><td colspan="5" valign="top" align="left"><jsp:include page="_toplogo.jsp" /></td></tr>
-<tr><td valign="top" align="left" rowspan="2"><jsp:include page="_leftnav.jsp" /></td>
+<tr class="b_toplogo"><td colspan="5" valign="top" align="left" class="b_toplogo"><jsp:include page="_toplogo.jsp" /></td></tr>
+<tr><td valign="top" align="left" rowspan="2" class="b_leftnav"><jsp:include page="_leftnav.jsp" /></td>
     <jsp:include page="_topnav.jsp" />
-    <td valign="top" align="left" rowspan="2"><jsp:include page="_rightnav.jsp" /></td></tr>
-<tr><td valign="top" align="left" colspan="3">Are you sure you really want to go to 
+    <td valign="top" align="left" rowspan="2" class="b_rightnav"><jsp:include page="_rightnav.jsp" /></td></tr>
+<tr class="b_content"><td valign="top" align="left" colspan="3" class="b_content">
+<span class="b_externalWarning">Are you sure you really want to go to 
 <%
 String loc = request.getParameter("location");
 String schema = request.getParameter("schema");
@@ -21,14 +23,14 @@ if (schema != null) schema = HTMLRenderer.sanitizeString(DataHelper.getUTF8(Base
 if (desc != null) desc = HTMLRenderer.sanitizeString(DataHelper.getUTF8(Base64.decode(desc)));
 
 if ( (loc != null) && (schema != null) ) { 
-  out.write(loc + " (" + schema + ")"); 
+  out.write("<span class=\"b_externalLoc\">" + loc + "</span> <span class=\"b_externalNet\"(" + schema + ")</span>"); 
   if (desc != null)
-    out.write(": " + desc);
+    out.write(": <span class=\"b_externalDesc\"" + desc + "\"</span>");
   out.write("? ");
-  out.write("<a href=\"" + loc + "\">yes</a>");
+  out.write("<a class=\"b_external\" href=\"" + loc + "\">yes</a>");
 } else {
-  out.write("(some unspecified location...)");
+  out.write("<span class=\"b_externalUnknown\">(some unspecified location...)</span>");
 }
-%></td></tr>
+%></span></td></tr>
 </table>
 </body>
\ No newline at end of file
diff --git a/apps/syndie/jsp/import.jsp b/apps/syndie/jsp/import.jsp
index 2827367121..652fcf0eeb 100644
--- a/apps/syndie/jsp/import.jsp
+++ b/apps/syndie/jsp/import.jsp
@@ -1,18 +1,19 @@
-<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.Base64, net.i2p.syndie.web.*, net.i2p.syndie.sml.*, net.i2p.syndie.data.*, net.i2p.syndie.*, org.mortbay.servlet.MultiPartRequest, java.util.*, java.io.*" %>
-<% request.setCharacterEncoding("UTF-8"); %>
-<jsp:useBean scope="session" class="net.i2p.syndie.data.TransparentArchiveIndex" id="archive" />
+<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.Base64, net.i2p.syndie.web.*, net.i2p.syndie.sml.*, net.i2p.syndie.data.*, net.i2p.syndie.*, org.mortbay.servlet.MultiPartRequest, java.util.*, java.io.*" %><%
+request.setCharacterEncoding("UTF-8"); 
+%><jsp:useBean scope="session" class="net.i2p.syndie.data.TransparentArchiveIndex" id="archive" 
+/><!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 TRANSITIONAL//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd">
 <html>
 <head>
 <title>SyndieMedia import</title>
-<link href="style.jsp" rel="stylesheet" type="text/css" />
+<link href="style.jsp" rel="stylesheet" type="text/css" >
 </head>
 <body>
 <table border="1" cellpadding="0" cellspacing="0" width="100%">
-<tr><td colspan="5" valign="top" align="left"><jsp:include page="_toplogo.jsp" /></td></tr>
-<tr><td valign="top" align="left" rowspan="2"><jsp:include page="_leftnav.jsp" /></td>
+<tr class="b_toplogo"><td colspan="5" valign="top" align="left" class="b_toplogo"><jsp:include page="_toplogo.jsp" /></td></tr>
+<tr><td valign="top" align="left" rowspan="2" class="b_leftnav"><jsp:include page="_leftnav.jsp" /></td>
     <jsp:include page="_topnav.jsp" />
-    <td valign="top" align="left" rowspan="2"><jsp:include page="_rightnav.jsp" /></td></tr>
-<tr><td valign="top" align="left" colspan="3"><%
+    <td valign="top" align="left" rowspan="2" class="b_rightnav"><jsp:include page="_rightnav.jsp" /></td></tr>
+<tr class="b_content"><td valign="top" align="left" colspan="3" class="b_content"><%
 
 String contentType = request.getContentType();
 if ((contentType != null) && (contentType.indexOf("boundary=") != -1) ) {
@@ -23,7 +24,7 @@ if ((contentType != null) && (contentType.indexOf("boundary=") != -1) ) {
       if (meta == null)
         break;
       if (!BlogManager.instance().importBlogMetadata(meta)) {
-        System.err.println("blog meta " + metaId + " failed to be imported");
+        %><span class="b_importMsgErr">Metadata <%=metaId%> failed to be imported</span><br /><%
         break;
        }
       metaId++;
@@ -34,7 +35,7 @@ if ((contentType != null) && (contentType.indexOf("boundary=") != -1) ) {
       if (entry == null)
         break;
       if (!BlogManager.instance().importBlogEntry(entry)) {
-        System.err.println("blog entry " + entryId + " failed to be imported");
+        %><span class="b_importMsgErr">Entry <%=entryId%> failed to be imported</span><br /><%
         break;
       }
       entryId++;
@@ -44,23 +45,23 @@ if ((contentType != null) && (contentType.indexOf("boundary=") != -1) ) {
       BlogManager.instance().getArchive().regenerateIndex();
       session.setAttribute("index", BlogManager.instance().getArchive().getIndex());
     }
-%>Imported <%=entryId%> posts and <%=metaId%> blog metadata files.
+%><span class="b_importMsgOk">Imported <%=entryId%> posts and <%=metaId%> blog metadata files.</span>
 <% 
 } else { %><form action="import.jsp" method="POST" enctype="multipart/form-data"> 
-Blog metadata 0: <input type="file" name="blogmeta0" /><br />
-Blog metadata 1: <input type="file" name="blogmeta1" /><br />
-Post 0: <input type="file" name="blogpost0" /><br />
-Post 1: <input type="file" name="blogpost1" /><br />
-Post 2: <input type="file" name="blogpost2" /><br />
-Post 3: <input type="file" name="blogpost3" /><br />
-Post 4: <input type="file" name="blogpost4" /><br />
-Post 5: <input type="file" name="blogpost5" /><br />
-Post 6: <input type="file" name="blogpost6" /><br />
-Post 7: <input type="file" name="blogpost7" /><br />
-Post 8: <input type="file" name="blogpost8" /><br />
-Post 9: <input type="file" name="blogpost9" /><br />
+<span class="b_importField">Blog metadata 0:</span> <input class="b_importField" type="file" name="blogmeta0" /><br />
+<span class="b_importField">Blog metadata 1:</span> <input class="b_importField" type="file" name="blogmeta1" /><br />
+<span class="b_importField">Post 0:</span> <input class="b_importField" type="file" name="blogpost0" /><br />
+<span class="b_importField">Post 1:</span> <input class="b_importField" type="file" name="blogpost1" /><br />
+<span class="b_importField">Post 2:</span> <input class="b_importField" type="file" name="blogpost2" /><br />
+<span class="b_importField">Post 3:</span> <input class="b_importField" type="file" name="blogpost3" /><br />
+<span class="b_importField">Post 4:</span> <input class="b_importField" type="file" name="blogpost4" /><br />
+<span class="b_importField">Post 5:</span> <input class="b_importField" type="file" name="blogpost5" /><br />
+<span class="b_importField">Post 6:</span> <input class="b_importField" type="file" name="blogpost6" /><br />
+<span class="b_importField">Post 7:</span> <input class="b_importField" type="file" name="blogpost7" /><br />
+<span class="b_importField">Post 8:</span> <input class="b_importField" type="file" name="blogpost8" /><br />
+<span class="b_importField">Post 9:</span> <input class="b_importField" type="file" name="blogpost9" /><br />
 <hr />
-<input type="submit" name="Post" value="Post entry" /> <input type="reset" value="Cancel" />
+<input class="b_importSubmit" type="submit" name="Post" value="Post entry" /> <input class="b_importCancel" type="reset" value="Cancel" />
 <% } %>
 </td></tr>
 </table>
diff --git a/apps/syndie/jsp/index.jsp b/apps/syndie/jsp/index.jsp
index b7a7aa1ef1..3fbbe7dc27 100644
--- a/apps/syndie/jsp/index.jsp
+++ b/apps/syndie/jsp/index.jsp
@@ -1,9 +1,10 @@
-<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.syndie.web.*" %>
-<% request.setCharacterEncoding("UTF-8"); %>
+<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.syndie.web.*" %><% 
+request.setCharacterEncoding("UTF-8"); 
+%><!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 TRANSITIONAL//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd">
 <html>
 <head>
 <title>SyndieMedia</title>
-<link href="style.jsp" rel="stylesheet" type="text/css" />
+<link href="style.jsp" rel="stylesheet" type="text/css" >
 <link href="rss.jsp?<%
 if (request.getParameter("blog") != null)
   out.write("blog=" + request.getParameter("blog") + "&");
@@ -13,14 +14,14 @@ if (request.getParameter("tag") != null)
   out.write("tag=" + request.getParameter("tag") + "&");
 if (request.getParameter("selector") != null)
   out.write("selector=" + request.getParameter("selector") + "&");
-%>" rel="alternate" type="application/rss+xml" />
+%>" rel="alternate" type="application/rss+xml" >
 </head>
 <body>
 <table border="1" cellpadding="0" cellspacing="0" width="100%">
-<tr><td colspan="5" valign="top" align="left"><jsp:include page="_toplogo.jsp" /></td></tr>
-<tr><td valign="top" align="left" rowspan="2"><jsp:include page="_leftnav.jsp" /></td>
+<tr class="b_toplogo"><td colspan="5" valign="top" align="left" class="b_toplogo"><jsp:include page="_toplogo.jsp" /></td></tr>
+<tr><td valign="top" align="left" rowspan="2" class="b_leftnav"><jsp:include page="_leftnav.jsp" /></td>
     <jsp:include page="_topnav.jsp" />
-    <td valign="top" align="left" rowspan="2"><jsp:include page="_rightnav.jsp" /></td></tr>
-<tr><td valign="top" align="left" colspan="3"><jsp:include page="_bodyindex.jsp" /></td></tr>
+    <td valign="top" align="left" rowspan="2" class="b_rightnav"><jsp:include page="_rightnav.jsp" /></td></tr>
+<tr class="b_content"><td valign="top" align="left" colspan="3" class="b_content"><jsp:include page="_bodyindex.jsp" /></td></tr>
 </table>
 </body>
\ No newline at end of file
diff --git a/apps/syndie/jsp/post.jsp b/apps/syndie/jsp/post.jsp
index 08020b445f..f92a7716dd 100644
--- a/apps/syndie/jsp/post.jsp
+++ b/apps/syndie/jsp/post.jsp
@@ -1,22 +1,23 @@
-<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.Base64, net.i2p.syndie.web.*, net.i2p.syndie.sml.*, net.i2p.syndie.data.*, net.i2p.syndie.*, org.mortbay.servlet.MultiPartRequest, java.util.*" %>
-<% request.setCharacterEncoding("UTF-8"); %>
-<jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" />
-<jsp:useBean scope="session" class="net.i2p.syndie.web.PostBean" id="post" />
+<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.Base64, net.i2p.syndie.web.*, net.i2p.syndie.sml.*, net.i2p.syndie.data.*, net.i2p.syndie.*, org.mortbay.servlet.MultiPartRequest, java.util.*" %><% 
+request.setCharacterEncoding("UTF-8"); 
+%><jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" 
+/><jsp:useBean scope="session" class="net.i2p.syndie.web.PostBean" id="post" 
+/><!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 TRANSITIONAL//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd">
 <html>
 <head>
-<title>SyndieMedia</title>
-<link href="style.jsp" rel="stylesheet" type="text/css" />
+<title>SyndieMedia post</title>
+<link href="style.jsp" rel="stylesheet" type="text/css" >
 </head>
 <body>
 <table border="1" cellpadding="0" cellspacing="0" width="100%">
-<tr><td colspan="5" valign="top" align="left"><jsp:include page="_toplogo.jsp" /></td></tr>
-<tr><td valign="top" align="left" rowspan="2"><jsp:include page="_leftnav.jsp" /></td>
+<tr class="b_toplogo"><td colspan="5" valign="top" align="left" class="b_toplogo"><jsp:include page="_toplogo.jsp" /></td></tr>
+<tr><td valign="top" align="left" rowspan="2" class="b_leftnav"><jsp:include page="_leftnav.jsp" /></td>
     <jsp:include page="_topnav.jsp" />
-    <td valign="top" align="left" rowspan="2"><jsp:include page="_rightnav.jsp" /></td></tr>
-<tr><td valign="top" align="left" colspan="3"><%
+    <td valign="top" align="left" rowspan="2" class="b_rightnav"><jsp:include page="_rightnav.jsp" /></td></tr>
+<tr class="b_content"><td valign="top" align="left" colspan="3" class="b_content"><%
 
 if (!user.getAuthenticated()) { 
-  %>You must be logged in to post<%
+  %><span class="b_postMsgErr">You must be logged in to post</span><%
 } else {
   String confirm = request.getParameter("action");
   if ( (confirm != null) && (confirm.equalsIgnoreCase("confirm")) ) {
@@ -24,10 +25,10 @@ if (!user.getAuthenticated()) {
     post.setArchive(archive);
     BlogURI uri = post.postEntry(); 
     if (uri != null) {
-      %>Blog entry <a href="<%=HTMLRenderer.getPageURL(user.getBlog(), null, uri.getEntryId(), -1, -1, 
-                                                        user.getShowExpanded(), user.getShowImages())%>">posted</a>!<%
+      %><span class="b_postMsgOk">Blog entry <a class="b_postOkLink" href="<%=HTMLRenderer.getPageURL(user.getBlog(), null, uri.getEntryId(), -1, -1, 
+                                                        user.getShowExpanded(), user.getShowImages())%>">posted</a>!</span><%
     } else {
-      %>There was an unknown error posting the entry...<%
+      %><span class="b_postMsgErro">There was an unknown error posting the entry...</span><%
     }
     post.reinitialize();
     post.setUser(user);
@@ -95,11 +96,11 @@ if (!user.getAuthenticated()) {
         }
 
         post.renderPreview(out);
-        %><hr /><form action="post.jsp" method="POST">
+        %><hr /><span class="b_postConfirm"><form action="post.jsp" method="POST">
 Please confirm that the above is ok<% if (user.getAllowAccessRemote()) { %>, and select what additional archives you 
 want the post transmitted to.  Otherwise, just hit your browser's back arrow and
 make changes. 
-<select name="archive">
+<select class="b_postConfirm" name="archive">
 <option name="">-None-</option>
 <% 
 PetNameDB db = user.getPetNameDB();
@@ -115,22 +116,22 @@ for (Iterator iter = names.iterator(); iter.hasNext(); ) {
   out.write("<option value=\"" + HTMLRenderer.sanitizeTagParam(name) + "\">" + HTMLRenderer.sanitizeString(name) + "</option>\n");
 }
 %>
-</select><br /><% } %>
-<input type="submit" name="action" value="Confirm" /><%
+</select><br /><% } %></span>
+<input class="b_postConfirm" type="submit" name="action" value="Confirm" /><%
     } else {
       // logged in and not confirmed because they didn't send us anything!  
       // give 'em a new form
 %><form action="post.jsp" method="POST" enctype="multipart/form-data"> 
-Post subject: <input type="text" size="80" name="entrysubject" value="<%=post.getSubject()%>" /><br />
-Post tags: <input type="text" size="20" name="entrytags" value="<%=post.getTags()%>" /><br />
-Post style: <select name="style">
+<span class="b_postField">Post subject:</span> <input class="b_postSubject" type="text" size="80" name="entrysubject" value="<%=post.getSubject()%>" /><br />
+<span class="b_postField">Post tags:</span> <input class="b_postTags" type="text" size="20" name="entrytags" value="<%=post.getTags()%>" /><br />
+<span class="b_postField">Post style:</span> <select class="b_postStyle" name="style">
  <option value="default" selected="true">Default</option>
  <option value="meta">Meta (hide everything but the metadata)</option>
 </select><br />
-Include public names? <input type="checkbox" name="includenames" value="true" /><br />
-Post content (in raw SML, no headers):<br />
-<textarea rows="6" cols="80" name="entrytext"><%=post.getText()%></textarea><br />
-<b>SML cheatsheet:</b><br /><textarea rows="6" cols="80" readonly="true">
+<span class="b_postField">Include public names?</span> <input class="b_postNames" type="checkbox" name="includenames" value="true" /><br />
+<span class="b_postField">Post content (in raw SML, no headers):</span><br />
+<textarea class="b_postText" rows="6" cols="80" name="entrytext"><%=post.getText()%></textarea><br />
+<span class="b_postField">SML cheatsheet:</span><br /><textarea class="b_postCheatsheet" rows="6" cols="80" readonly="true">
 * newlines are newlines are newlines. 
 * all &lt; and &gt; are replaced with their &amp;symbol;
 * [b][/b] = <b>bold</b>
@@ -150,24 +151,18 @@ SML headers are newline delimited key=value pairs.  Example keys are:
 * bgimage = attachment number to place as the background image for the post (only shown if images are enabled) (e.g. bgimage=1)
 * textfont = font to put most text into
 </textarea><br />
-SML post headers:<br />
-<textarea rows="3" cols="80" name="entryheaders"><%=post.getHeaders()%></textarea><br /><%
+<span class="b_postField">SML post headers:</span><br />
+<textarea class="b_postHeaders" rows="3" cols="80" name="entryheaders"><%=post.getHeaders()%></textarea><br /><%
 String s = request.getParameter(ArchiveViewerBean.PARAM_IN_REPLY_TO);
 if ( (s != null) && (s.trim().length() > 0) ) {%>
 <input type="hidden" name="<%=ArchiveViewerBean.PARAM_IN_REPLY_TO%>" value="<%=request.getParameter(ArchiveViewerBean.PARAM_IN_REPLY_TO)%>" />
 <% } %>
-Attachment 0: <input type="file" name="entryfile0" /><br />
-Attachment 1: <input type="file" name="entryfile1" /><br />
-Attachment 2: <input type="file" name="entryfile2" /><br />
-Attachment 3: <input type="file" name="entryfile3" /><br /><!--
-Attachment 4: <input type="file" name="entryfile4" /><br />
-Attachment 5: <input type="file" name="entryfile5" /><br />
-Attachment 6: <input type="file" name="entryfile6" /><br />
-Attachment 7: <input type="file" name="entryfile7" /><br />
-Attachment 8: <input type="file" name="entryfile8" /><br />
-Attachment 9: <input type="file" name="entryfile9" /><br />-->
+<span class="b_postField">Attachment 0:</span> <input class="b_postField" type="file" name="entryfile0" /><br />
+<span class="b_postField">Attachment 1:</span> <input class="b_postField" type="file" name="entryfile1" /><br />
+<span class="b_postField">Attachment 2:</span> <input class="b_postField" type="file" name="entryfile2" /><br />
+<span class="b_postField">Attachment 3:</span> <input class="b_postField" type="file" name="entryfile3" /><br />
 <hr />
-<input type="submit" name="Post" value="Preview..." /> <input type="reset" value="Cancel" />
+<input class="b_postPreview" type="submit" name="Post" value="Preview..." /> <input class="b_postReset" type="reset" value="Cancel" />
 <%
     } // end of the 'logged in, not confirmed, nothing posted' section
   } // end of the 'logged in, not confirmed' section
diff --git a/apps/syndie/jsp/register.jsp b/apps/syndie/jsp/register.jsp
index 2288e98024..660735ed43 100644
--- a/apps/syndie/jsp/register.jsp
+++ b/apps/syndie/jsp/register.jsp
@@ -1,18 +1,19 @@
-<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.Base64, net.i2p.syndie.web.*, net.i2p.syndie.sml.*, net.i2p.syndie.*" %>
-<% request.setCharacterEncoding("UTF-8"); %>
-<jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" />
+<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.data.Base64, net.i2p.syndie.web.*, net.i2p.syndie.sml.*, net.i2p.syndie.*" %><% 
+request.setCharacterEncoding("UTF-8"); 
+%><jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" 
+/><!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 TRANSITIONAL//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd">
 <html>
 <head>
 <title>SyndieMedia</title>
-<link href="style.jsp" rel="stylesheet" type="text/css" />
+<link href="style.jsp" rel="stylesheet" type="text/css" >
 </head>
 <body>
 <table border="1" cellpadding="0" cellspacing="0" width="100%">
-<tr><td colspan="5" valign="top" align="left"><jsp:include page="_toplogo.jsp" /></td></tr>
-<tr><td valign="top" align="left" rowspan="2"><jsp:include page="_leftnav.jsp" /></td>
+<tr class="b_toplogo"><td colspan="5" valign="top" align="left" class="b_toplogo"><jsp:include page="_toplogo.jsp" /></td></tr>
+<tr><td valign="top" align="left" rowspan="2" class="b_leftnav"><jsp:include page="_leftnav.jsp" /></td>
     <jsp:include page="_topnav.jsp" />
-    <td valign="top" align="left" rowspan="2"><jsp:include page="_rightnav.jsp" /></td></tr>
-<tr><td valign="top" align="left" colspan="3"><%
+    <td valign="top" align="left" rowspan="2" class="b_rightnav"><jsp:include page="_rightnav.jsp" /></td></tr>
+<tr class="b_content"><td valign="top" align="left" colspan="3" class="b_content"><%
 String regLogin = request.getParameter("login");
 boolean showForm = true;
 if ( (regLogin != null) && ("Register".equals(request.getParameter("Register"))) ) {
@@ -23,25 +24,25 @@ if ( (regLogin != null) && ("Register".equals(request.getParameter("Register")))
   String url = request.getParameter("contacturl");
   String regResult = BlogManager.instance().register(user, regLogin, regUserPass, regPass, blogName, desc, url);
   if (User.LOGIN_OK.equals(regResult)) {
-    out.print("<b>Registration successful.</b>  <a href=\"index.jsp\">Continue...</a>\n");
-    showForm = false;
+    %><span class="b_regMsgOk">Registration successful.</span> <a class="b_reg" href="index.jsp">Continue...</a>
+<%  showForm = false;
   } else {
-    out.print("<b>" + regResult + "</b>");
+    %><span class="b_regMsgErr"><%=regResult%></span><%
   }
 } 
 if (showForm) {%><form action="register.jsp" method="POST">
-<p>To create a new blog (and Syndie user account), please fill out the following form.  
+<p class="b_reg">To create a new blog (and Syndie user account), please fill out the following form.  
 You may need to enter a registration password given to you by this Syndie instance's
 operator, or there may be no registration password in place (in which case you can
 leave that field blank).</p>
-<p>
-<b>Syndie login:</b> <input type="text" size="8" name="login" /><br />
-<b>New password:</b> <input type="password" size="8" name="password" /><br />
-<b>Registration password:</b> <input type="password" size="8" name="registrationpassword" /><br />
-<b>Blog name:</b> <input type="text" size="32" name="blogname" /><br />
-<b>Brief description:</b> <input type="text" size="60" name="description" /><br />
-<b>Contact URL:</b> <input type="text" size="20" name="contacturl" /> <i>(e.g. mailto://user@mail.i2p, http://foo.i2p/, etc)</i><br />
-<input type="submit" name="Register" value="Register" />
+<p class="b_reg">
+<em class="b_regField">Syndie login:</em> <input class="b_regField" type="text" size="8" name="login" /><br />
+<em class="b_regField">New password:</em> <input class="b_regField" type="password" size="8" name="password" /><br />
+<em class="b_regField">Registration password:</em> <input class="b_regField" type="password" size="8" name="registrationpassword" /><br />
+<em class="b_regField">Blog name:</em> <input class="b_regField" type="text" size="32" name="blogname" /><br />
+<em class="b_regField">Brief description:</em> <input class="b_regField" type="text" size="60" name="description" /><br />
+<em class="b_regField">Contact URL:</em> <input class="b_regField" type="text" size="20" name="contacturl" /> <span class="b_reg">(e.g. mailto://user@mail.i2p, http://foo.i2p/, etc)</span><br />
+<input class="b_regSubmit" type="submit" name="Register" value="Register" />
 </p>
 </form><% } %>
 </td></tr>
diff --git a/apps/syndie/jsp/remote.jsp b/apps/syndie/jsp/remote.jsp
index b207bb7cc0..506280606a 100644
--- a/apps/syndie/jsp/remote.jsp
+++ b/apps/syndie/jsp/remote.jsp
@@ -1,32 +1,34 @@
-<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.syndie.web.*, net.i2p.syndie.*, net.i2p.syndie.sml.*, java.util.*" %>
-<% request.setCharacterEncoding("UTF-8"); %>
-<jsp:useBean scope="session" class="net.i2p.syndie.web.RemoteArchiveBean" id="remote" />
-<jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" />
-<jsp:useBean scope="session" class="net.i2p.syndie.data.TransparentArchiveIndex" id="archive" />
+<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.syndie.web.*, net.i2p.syndie.*, net.i2p.syndie.sml.*, java.util.*" %><% 
+request.setCharacterEncoding("UTF-8"); 
+%><jsp:useBean scope="session" class="net.i2p.syndie.web.RemoteArchiveBean" id="remote" 
+/><jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" 
+/><jsp:useBean scope="session" class="net.i2p.syndie.data.TransparentArchiveIndex" id="archive" 
+/><!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 TRANSITIONAL//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd">
 <html>
 <head>
-<title>SyndieMedia</title>
-<link href="style.jsp" rel="stylesheet" type="text/css" />
+<title>SyndieMedia remote</title>
+<link href="style.jsp" rel="stylesheet" type="text/css" >
 </head>
 <body>
 <table border="1" cellpadding="0" cellspacing="0" width="100%">
-<tr><td colspan="5" valign="top" align="left"><jsp:include page="_toplogo.jsp" /></td></tr>
-<tr><td valign="top" align="left" rowspan="2"><jsp:include page="_leftnav.jsp" /></td>
+<tr class="b_toplogo"><td colspan="5" valign="top" align="left" class="b_toplogo"><jsp:include page="_toplogo.jsp" /></td></tr>
+<tr><td valign="top" align="left" rowspan="2" class="b_leftnav"><jsp:include page="_leftnav.jsp" /></td>
     <jsp:include page="_topnav.jsp" />
-    <td valign="top" align="left" rowspan="2"><jsp:include page="_rightnav.jsp" /></td></tr>
-<tr><form action="remote.jsp" method="POST"><td valign="top" align="left" colspan="3">
-<%
+    <td valign="top" align="left" rowspan="2" class="b_rightnav"><jsp:include page="_rightnav.jsp" /></td></tr>
+<tr class="b_content"><td valign="top" align="left" colspan="3" class="b_content"><%
 if (!user.getAuthenticated() || !user.getAllowAccessRemote()) { 
-%>Sorry, you are not allowed to access remote archives from here.  Perhaps you should install Syndie yourself?<%
-} else { %>Import from: 
-<select name="schema">
+%><span class="b_remoteMsgErr">Sorry, you are not allowed to access remote archives from here.  Perhaps you should install Syndie yourself?</span><%
+} else { %><form action="remote.jsp" method="POST"><span class="b_remoteChooser"><span class="b_remoteChooserField">Import from:</span>
+<select class="b_remoteChooserNet" name="schema">
  <option value="web" <%=("web".equals(request.getParameter("schema")) ? "selected=\"true\"" : "")%>>I2P/TOR/Freenet</option>
  <option value="mnet" <%=("mnet".equals(request.getParameter("schema")) ? "selected=\"true\"" : "")%>>MNet</option>
  <option value="feedspace" <%=("feedspace".equals(request.getParameter("schema")) ? "selected=\"true\"" : "")%>>Feedspace</option>
  <option value="usenet" <%=("usenet".equals(request.getParameter("schema")) ? "selected=\"true\"" : "")%>>Usenet</option>
 </select> 
-Proxy <input type="text" size="10" name="proxyhost" value="<%=BlogManager.instance().getDefaultProxyHost()%>" />:<input type="text" size="4" name="proxyport" value="<%=BlogManager.instance().getDefaultProxyPort()%>" /><br />
-Bookmarked archives: <select name="archivepetname"><option value="">Custom location</option><%
+<span class="b_remoteChooserField">Proxy</span> 
+  <input class="b_remoteChooserHost" type="text" size="10" name="proxyhost" value="<%=BlogManager.instance().getDefaultProxyHost()%>" />
+  <input class="b_remoteChooserPort" type="text" size="4" name="proxyport" value="<%=BlogManager.instance().getDefaultProxyPort()%>" /><br />
+<span class="b_remoteChooserField">Bookmarked archives:</span> <select class="b_remoteChooserPN" name="archivepetname"><option value="">Custom location</option><%
 for (Iterator iter = user.getPetNameDB().getNames().iterator(); iter.hasNext(); ) {
   PetName pn = user.getPetNameDB().get((String)iter.next());
   if ("syndiearchive".equals(pn.getProtocol())) {
@@ -34,8 +36,9 @@ for (Iterator iter = user.getPetNameDB().getNames().iterator(); iter.hasNext();
   }
 }
 %></select> or 
-<input name="location" size="30" value="<%=(request.getParameter("location") != null ? request.getParameter("location") : "")%>" /> 
-<input type="submit" name="action" value="Continue..." /><br />
+<input class="b_remoteChooserLocation" name="location" size="30" value="<%=(request.getParameter("location") != null ? request.getParameter("location") : "")%>" /> 
+<input class="b_remoteChooserContinue" type="submit" name="action" value="Continue..." /><br />
+</span>
 <%
   String action = request.getParameter("action");
   if ("Continue...".equals(action)) {
@@ -58,20 +61,20 @@ for (Iterator iter = user.getPetNameDB().getNames().iterator(); iter.hasNext();
     remote.postSelectedEntries(user, request.getParameterMap());
   }
   String msgs = remote.getStatus();
-  if ( (msgs != null) && (msgs.length() > 0) ) { %><pre><%=msgs%>
-<a href="remote.jsp">Refresh</a></pre><br /><% 
+  if ( (msgs != null) && (msgs.length() > 0) ) { %><pre class="b_remoteProgress"><%=msgs%>
+<a class="b_remoteProgress" href="remote.jsp">Refresh</a></pre><br /><% 
   }
-  if (remote.getFetchIndexInProgress()) { %><b>Please wait while the index is being fetched 
-from <%=remote.getRemoteLocation()%></b>. <%
+  if (remote.getFetchIndexInProgress()) { %><span class="b_remoteProgress">Please wait while the index is being fetched 
+from <%=remote.getRemoteLocation()%>.</span><%
   } else if (remote.getRemoteIndex() != null) {
     // remote index is NOT null!
-   %><b><%=remote.getRemoteLocation()%></b>
-<a href="remote.jsp?schema=<%=remote.getRemoteSchema()%>&location=<%=remote.getRemoteLocation()%><%
+   %><span class="b_remoteLocation"><%=remote.getRemoteLocation()%></span>
+<a class="b_remoteRefetch" href="remote.jsp?schema=<%=remote.getRemoteSchema()%>&location=<%=remote.getRemoteLocation()%><%
 if (remote.getProxyHost() != null && remote.getProxyPort() > 0) { 
   %>&proxyhost=<%=remote.getProxyHost()%>&proxyport=<%=remote.getProxyPort()%><%
 } %>&action=Continue...">(refetch)</a>:<br />
 <%remote.renderDeltaForm(user, archive, out);%>
-<textarea style="font-size:8pt" rows="5" cols="120"><%=remote.getRemoteIndex()%></textarea><%
+<textarea class="b_remoteIndex" rows="5" cols="120"><%=remote.getRemoteIndex()%></textarea><%
   }
 }
 %>
diff --git a/apps/syndie/jsp/style.jsp b/apps/syndie/jsp/style.jsp
index b6c8550f76..c1b37f3ee4 100644
--- a/apps/syndie/jsp/style.jsp
+++ b/apps/syndie/jsp/style.jsp
@@ -1,3 +1,7 @@
-<%@page contentType="text/css; charset=UTF-8" pageEncoding="UTF-8"  %>
+<%@page contentType="text/css; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.util.FileUtil" %>
 <% request.setCharacterEncoding("UTF-8"); %>
-<%@include file="syndie.css" %>
\ No newline at end of file
+<%@include file="syndie.css" %>
+<% 
+String content = FileUtil.readTextFile("./docs/syndie_standard.css", -1, true); 
+if (content != null) out.write(content);
+%>
\ No newline at end of file
diff --git a/apps/syndie/jsp/syndie.css b/apps/syndie/jsp/syndie.css
index b35a5d4a4c..e0d1f02c48 100644
--- a/apps/syndie/jsp/syndie.css
+++ b/apps/syndie/jsp/syndie.css
@@ -1,67 +1,92 @@
-.syndieEntrySubjectCell {
-    background-color: #999999;
-    font-size: 12px;
-    font-weight: bold;
-    margin: 0px 0px 0px 0px;
-    padding: 0px 0px 0px 0px;
-    border: 0px;
+body {
+	margin : 0px;
+	padding : 0px;
+	font-family: Arial, Helvetica, sans-serif;
+	background-color : #EEEEEE;
+	color: #000000;
+	font-size: 12px;
 }
-.syndieEntryMetaCell {
-    background-color: #888888;
-    font-size: 10px;
-    margin: 0px 0px 0px 0px;
-    padding: 0px 0px 0px 0px;
-    border: 0px;
+.b_topnavUser {
+	text-align: right;
+	background-color: #CCCCDD;
+	border-spacing: 0px;
+	margin: 0px;
+	padding: 0px;
+	border-width: 0px;
+	border: 0px;
 }
-.syndieEntryAttachmentsCell {
-    background-color: #aaaaaa;
-    font-size: 12px;
-    margin: 0px 0px 0px 0px;
-    padding: 0px 0px 0px 0px;
-    border: 0px;
+.b_topnavHome {
+	background-color: #CCCCDD;
+	color: #000000;
+	width: 50px;
+	text-align: left;
 }
-.syndieEntrySummaryCell {
-    background-color: #eeeeee;
-    font-size: 12px;
-    margin: 0px 0px 0px 0px;
-    padding: 0px 0px 0px 0px;
-    border: 0px;
+.b_topnav {
+	background-color: #CCCCDD;
+	border-spacing: 0px;
+	margin: 0px;
+	padding: 0px;
+	border-width: 0px;
+	border: 0px;
 }
-.syndieEntryBodyCell {
-    background-color: #eeeeee;
-    font-size: 12px;
-    margin: 0px 0px 0px 0px;
-    padding: 0px 0px 0px 0px;
-    border: 0px;
+.s_detail_subject {
+	font-size: 10px;
+	text-align: left;
+	background-color: #BBBBFF;
+	border-spacing: 0px;
+	margin: 0px;
+	padding: 0px;
+	border-width: 0px;
+	border: 0px;
+	border-style: none;
 }
-.syndieTopNavBlogsCell {
-    background-color: #888888;
-    font-size: 14px;
-    margin: 0px 0px 0px 0px;
-    padding: 0px 0px 0px 0px;
-    border: 0px;
+.s_detail_meta {
+	font-size: 10px;
+	text-align: right:
+	background-color: #BBBBFF;
+	border-spacing: 0px;
+	margin: 0px;
+	padding: 0px;
+	border-width: 0px;
+	border: 0px;
+	border-style: none;
 }
-.syndieTopNavRemoteCell {
-    background-color: #888888;
-    font-size: 14px;
-    margin: 0px 0px 0px 0px;
-    padding: 0px 0px 0px 0px;
-    border: 0px;
+
+.s_summary_subject {
+	font-size: 10px;
+	text-align: left;
+	background-color: #BBBBFF;
+	border-spacing: 0px;
+	margin: 0px;
+	padding: 0px;
+	border-width: 0px;
+	border: 0px;
+	border-style: none;
 }
-.syndieTopNavManageCell {
-    background-color: #888888;
-    font-size: 14px;
-    margin: 0px 0px 0px 0px;
-    padding: 0px 0px 0px 0px;
-    border: 0px;
+.s_summary_meta {
+	font-size: 10px;
+	text-align: right:
+	background-color: #BBBBFF;
+	border-spacing: 0px;
+	margin: 0px;
+	padding: 0px;
+	border-width: 0px;
+	border: 0px;
+	border-style: none;
 }
-
-body {
-	margin : 0px;
-	padding : 0px;
-	text-align : center;
-	font-family: Arial, Helvetica, sans-serif;
-	background-color : #FFFFFF;
-	color: #000000;
-    font-size: 12px;
+.s_summary_summDetail {
+	font-size: 10px;
+}
+.s_detail_summDetail {
+}
+.s_detail_summDetailBlog {
+}
+.s_detail_summDetailBlogLink {
+}
+td.s_detail_summDetail {
+	background-color: #DDDDFF;
+}
+td.s_summary_summ {
+	font-size: 10px;
+	background-color: #DDDDFF;
 }
diff --git a/apps/syndie/jsp/viewmetadata.jsp b/apps/syndie/jsp/viewmetadata.jsp
index 750b46ff81..06005d0515 100644
--- a/apps/syndie/jsp/viewmetadata.jsp
+++ b/apps/syndie/jsp/viewmetadata.jsp
@@ -1,29 +1,31 @@
-<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.syndie.web.*, net.i2p.syndie.*" %>
-<% request.setCharacterEncoding("UTF-8"); %>
-<jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" />
+<%@page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" import="net.i2p.syndie.web.*, net.i2p.syndie.*" %><% 
+request.setCharacterEncoding("UTF-8"); 
+%><jsp:useBean scope="session" class="net.i2p.syndie.User" id="user" 
+/><!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 TRANSITIONAL//EN" "http://www.w3c.org/TR/1999/REC-html401-19991224/loose.dtd">
 <html>
 <head>
-<title>SyndieMedia</title>
-<link href="style.jsp" rel="stylesheet" type="text/css" />
+<title>SyndieMedia metadata</title>
+<link href="style.jsp" rel="stylesheet" type="text/css" >
 </head>
 <body>
 <table border="1" cellpadding="0" cellspacing="0" width="100%">
-<tr><td colspan="5" valign="top" align="left"><jsp:include page="_toplogo.jsp" /></td></tr>
-<tr><td valign="top" align="left" rowspan="2"><jsp:include page="_leftnav.jsp" /></td>
+<tr class="b_toplogo"><td colspan="5" valign="top" align="left" class="b_toplogo"><jsp:include page="_toplogo.jsp" /></td></tr>
+<tr><td valign="top" align="left" rowspan="2" class="b_leftnav"><jsp:include page="_leftnav.jsp" /></td>
     <jsp:include page="_topnav.jsp" />
-    <td valign="top" align="left" rowspan="2"><jsp:include page="_rightnav.jsp" /></td></tr>
-<tr><td valign="top" align="left" colspan="3"><%
+    <td valign="top" align="left" rowspan="2" class="b_rightnav"><jsp:include page="_rightnav.jsp" /></td></tr>
+<tr class="b_content"><td valign="top" align="left" colspan="3" class="b_content"><%
 ArchiveViewerBean.renderMetadata(request.getParameterMap(), out); 
 if (user.getAuthenticated()) {
   if ("Authorize".equals(request.getParameter("action"))) {
-    %><b><%=BlogManager.instance().authorizeRemoteAccess(user, request.getParameter("password"))%></b><%
+    %><span class="b_metaStatus"><%=BlogManager.instance().authorizeRemoteAccess(user, request.getParameter("password"))%></span><%
   }
   if (!user.getAllowAccessRemote()) { 
     if (user.getBlog().toBase64().equals(request.getParameter("blog"))) {
   %><hr /><form action="viewmetadata.jsp" method="POST">
 <input type="hidden" name="blog" value="<%=request.getParameter("blog")%>" />
-To access remote instances from this instance, please supply the Syndie administration password: <input type="password" name="password" />
-<input type="submit" name="action" value="Authorize" />
+<span class="b_metaAuthorize">To access remote instances from this instance, please supply the Syndie administration password:</span> 
+<input class="b_metaAuthorize" type="password" name="password" />
+<input class="b_metaAuthorizeSubmit" type="submit" name="action" value="Authorize" />
 </form><%
     }
   }
diff --git a/core/java/src/net/i2p/crypto/SHA256Generator.java b/core/java/src/net/i2p/crypto/SHA256Generator.java
index 22880a2394..acffc75695 100644
--- a/core/java/src/net/i2p/crypto/SHA256Generator.java
+++ b/core/java/src/net/i2p/crypto/SHA256Generator.java
@@ -4,6 +4,7 @@ import java.util.Arrays;
 import java.util.ArrayList;
 import java.util.List;
 import net.i2p.I2PAppContext;
+import net.i2p.data.Base64;
 import net.i2p.data.Hash;
 
 import org.bouncycastle.crypto.digests.SHA256Digest;
@@ -72,5 +73,7 @@ public final class SHA256Generator {
         byte out[] = new byte[Hash.HASH_LENGTH];
         d.doFinal(out, 0);
         System.out.println("eq? " + net.i2p.data.DataHelper.eq(out, old.getData()));
+        for (int i = 0; i < args.length; i++)
+            System.out.println("SHA256 [" + args[i] + "] = [" + Base64.encode(ctx.sha().calculateHash(args[i].getBytes()).getData()) + "]");
     }
 }
\ No newline at end of file
diff --git a/core/java/src/net/i2p/util/FileUtil.java b/core/java/src/net/i2p/util/FileUtil.java
index 6cb8088526..0c54250f0e 100644
--- a/core/java/src/net/i2p/util/FileUtil.java
+++ b/core/java/src/net/i2p/util/FileUtil.java
@@ -131,6 +131,7 @@ public class FileUtil {
      *
      * @param startAtBeginning if true, read the first maxNumLines, otherwise read
      *                         the last maxNumLines
+     * @param maxNumLines max number of lines (or -1 for unlimited)
      *
      */
     public static String readTextFile(String filename, int maxNumLines, boolean startAtBeginning) {
@@ -140,11 +141,11 @@ public class FileUtil {
         try {
             fis = new FileInputStream(f);
             BufferedReader in = new BufferedReader(new InputStreamReader(fis));
-            List lines = new ArrayList(maxNumLines);
+            List lines = new ArrayList(maxNumLines > 0 ? maxNumLines : 64);
             String line = null;
             while ( (line = in.readLine()) != null) {
                 lines.add(line);
-                if (lines.size() >= maxNumLines) {
+                if ( (maxNumLines > 0) && (lines.size() >= maxNumLines) ) {
                     if (startAtBeginning)
                         break;
                     else
-- 
GitLab