CSS Generation With JavaScript - An Underutilized Content Management Tool

There are some interesting new things going on the world of web site layouts with CSS and JavaScript all the time. Tricks and tools to add to a client side developer’s arsenal for making flexible, content accommodating navigation, layouts and presentations. Though I wouldn’t give away any of our progress, I can’t help but wonder if sometimes the amount of work we ask a visitor’s browser to do is overkill. One way to shift this workload off the browser — without placing undo burden onto the site management staff or its budget by requiring a high level of technical expertise with each site update — is to move the it to an offline or backend CMS tool creating static code for publication. This is particularly useful when doing multiple site deployments with a similar theme or building different localized site versions where the need for flexibility in type doesn’t change from user to user, but from content update to content update or deployment to deployment.

Through the use of fairly simple to create build tools we can create ‘static’ CSS for deployment and consumption and trim the amount and complexity of layout code sent with each page.

Example – Sizing Large Headings

On a site I worked on last summer I had the following scenario: Sectional headings on the web site should by default be a large fixed size, allowing for 8 or 10 characters to fill the given horizontal space. This worked 80% of the time when the site was in English, but as the site sections got translated it was clear that the default font size was too large.

What were our options at that point? We could guess at the smallest font size needed to fit the longest probable section name and then set all section headers to that resulting in a smallish feeling most of the time. We could write some client side JavaScript code to send to every visitor and resize the type on the fly [or use a tool like sIFR which does this type of thing as part of its text replacement]. Or we could create a tool that is used once as part of the deployment process or CMS to set the various heading sizes.

Defining the Rules and Constraints

Whether you’re putting the logic on the public web server for download, the CMS, or in some developer or designers brain you need to determine the contraints and parameters for setting the type size. For this section header example lets work as follows:

  • Headers fill a 600px wide column and in a 120px high block
  • 100px Georgia, Bold is the base font spec
  • When a header doesn’t fit it should be the largest font size possible but still fit inside the box

screenshot of sample header sizes

Applied to the phrases our site uses for each section we see that the base font size works in most cases, but for the one outlier ‘Privacy Policy’ we need to drop the size down to 82px or so.

Deciding on the Desired CSS

If we did the above exercise to a static site that would never get updated or translated we’d probably use some type of page or header ID to apply the one exception as well as other header style changes like color or background. Even though this isn’t the case we still need to plan what the static CSS we will generate looks like and what the HTML ‘hooks’ will be.

HTML
<div class="headerBox" id="hdr-blog">
    <h2>Blog</h2>
</div>
<div class="headerBox" id="hdr-archives">
    <h2>Archives</h2>
</div>
<div class="headerBox" id="hdr-calendar">
    <h2>Calendar</h2>
</div>
<div class="headerBox" id="hdr-privacy">
    <h2>Privacy Policy</h2>
</div>
CSS
.headerBox {
    width: 600px;
    height: 120px;
    border: 1px dashed #444;
}
.headerBox h2 {
    margin: 0;
    font-family: Georgia;
    font-weight: bold;
    font-size: 100px;
    white-space: nowrap;
}
/* section specific color themes */
#hdr-blog h2 {
	color: #f0f;
}
/* deployment specific font sizes */
#hdr-privacy h2 {
	font-size: 82px;
}

It is that last section — ‘deployment specific font sizes’ — that we need to generate once for each deployment based on the length of the varied text.

Developing the Custom Editor

I had arrived at the 82 pixel font size for ‘Privacy Policy’ by trial and error and editing the CSS manually. It took about 30 seconds to land on the right size, but that task doesn’t scale well. It gets boring and tedious over the span of a single site, and requires someone manually editing CSS code over the life of the various site deployments, translations and updates. By writing a highly site specific admin tool to do this task we can move this maintenance work out of the coder’s hands and into that of a designer, content manager or translator. With great scripting libraries out there this shouldn’t take very long to do either. For our example I’m going to grab jQuery and jQuery UI to build a static & offline tool to generate the desired CSS that can then be copied to a file in our project by anyone on the team with access.

screenshot of header tool

The resulting tool is made up of three parts:

  1. Display of the content you’re adjusting or adding
  2. Interface for adjusting content parameters
  3. Generation of CSS code based on customizations

jQuery UI sliders were initialized based on the outlined parameters above [default to 100px, move inside a reasonable range] and adjustments are seen on the fly.

CSS is then generated in kind of a brute force fashion going through the hidden fields set by the sliders:

JavaScript
$("fieldset.headerWidget").each(function(i) {
	var hdr = $(this).attr("id");
	var css = "";
	// First Line
	css += "#hdr-";
	css += hdr;
	css += " h2 {\n";
	// font size
	if ($(this).find(".hdrsize").val()) {
		css += "font-size: ";
		css += $(this).find(".hdrsize").val();
		css += "px;\n";
	}
	css += "}\n";
	css += "\n";
	output.css += css;
});
CSS Output:
#hdr-blog h2 {
}
#hdr-archives h2 {
}
#hdr-calendar h2 {
}
#hdr-privacy h2 {
font-size: 82px;
}

Even including whitespace and comments the JavaScript written to make the tool work is under 50 lines. If the changes were more complex or more parameters were set the CSS could alternately be generated based on the current appearance of the item, however this may result in more verbose CSS code to publish.

Manual Sliders vs. Automatic Adjustments

In this example I’ve used manual sliders for resizing the text. The same could have been done automatically by resizing the text with JS until it measured to fit the constraints. Which way you build a depends on the project and who is doing the content management or setting up the deployment and a balance between automation and intervention. For the example I pulled from we wanted to give the manager a little room to play and use their own judgement.

Expanding on the Idea

For simplicity I’ve shown build a standalone offline editor here, this works if you have other manual tasks as part of a deployment or site build process, but sometimes you’ll need more. It would be quite easy to build a tool like this into a CMS project and have the CSS generated then saved to the proper location. Given the common markup patterns the list of headers could also be generated based on server side content. It all could flipped on its side and rather then edit all section headers at once this this could be part of a record editor where the font size [or other specs] are saved with the individual record. While that might take more infrastructure work it may be what best fits your project.

These custom tools are not limited to the font size example here either. Anything that needs some finessing when text changes, items get added, deactivated, etc can be a candidate for content management tools rather then complex client side code. For the same site referred to earlier each deployment or localized version also had a top navigation bar that varied — both in length of text of each section but also some site features [read; nav items] were optional. To take the tedious task of re-spacing the navigation for each version of the site out by hand &the need for the coder to do it we instead took 2 days to create a custom tool to space the navigation and position the submenus according to the length of the translated section names and which of the optional elements were activated.

At the end of the day where these build tools fit into your site’s deployment process will vary, but creating custom or one off tools can be an interesting and quick problem for a web developer to solve and the time spent doing so can pay great dividends over the life of a web site or product.

Geotagging Photos With The Apple iPhone 3GS

Meadowlands Flickr Map

A while back I posted instructions on geotagging photos with any GPS capable cell phone or device. Prompted by a question from one of my students (oh hey, I should talk about my new gig sometime!) and the fact the post is one of the more popular around here I thought the post deserved revisiting.

Since 2008 I’ve updated my camera body, gotten an iPhone, and streamlined both the number of devices I carry and the workflow for getting geographic data into my photos. Still, the premise of the old post hasn’t changed — you can encode any photo you take from any digital camera you have by syncing the photos timestamp with your saved GPS information.

Here’s how I’m currently tagging photos from my Nikon D90 with information saved on my iPhone using the RunKeeper Pro app.

Tracking everything with RunKeeper for iPhone 3GS

In an effort to consolidate the number of gadgets I carry everywhere I broke down and got an Apple iPhone 3gs with built in GPS support. There are a few good GPS tracking apps in the app store but I’ve settled on RunKeeper Pro to track my bike rides, hikes and photowalks. If you want a free app that /just/ records location info to create tracks I hear that Instamapper is nice (and has apps for other phones as well).

RunKeeper Download Screenshot

As a side effect of tracking and publishing (even privately) this workout data to the RunKeeper service I have easy access to download GPX formatted tracks for each outing from their website. Whichever app you settle on the goal is to get a standard GPX file containing the tracks pointing to where you’ve been that outing. This combination retires the Sony device I had been using and kills the needed step of manually converting the data file outlined in my previous article.

Still syncing tracks with GPSPhotoLinker

Not everything is new. Once I have downloaded the GPX tracks file and the photos to my computer I’m still using GPSPhotoLinker to batch sync the GPS info to the photo metadata before importing those images into Adobe Lightroom.

The Whole Workflow

Without recapping each step of the process here’s a quick and dirty diagram of the updated workflow of getting geodata onto photos I take as I prep to import them into Lightroom.

Workflow Diagram with RunKeeper

Lightroom Plugin by Jeffrey Friedl

Though I haven’t change when in my workflow I sync the images with the geodata out of habit, Lightroom 2 users will be happy to know there’s a plugin to sync geodata with items already in your library so you don’t have to change your existing import from card (or device) process. Jeffrey Friedl’s GPS-Support Geoencoding Plugin does a graceful job of handling some of the various metadata issues that had driven me to my habit of adding this data before Lightroom imported the files. Instructions on his blog.

iPhone GPS Hints

The first few outings with the iPhone I was worried about battery life, keeping the signal, the lack of ability to run the GPS app in the “background”, etc.

  • You don’t need your iPhone out & “on” while you record for it to hold a signal. Just click the sleep button while the GPS app is the open app and stick it in your pocket.
  • Usually when I’m out taking photographs I’m not taking breaks to check mail or use the web so the lack of multitasking isn’t a big issue.
  • Don’t fret much if you need to make a call. You’re not moving much as you shoot and talk [unless you’re doing so out your car window, in which case I hope you’re not driving too!] so you’ll only miss a beat and can easily resume recording when you resume shooting.
  • Check the RunKeeper Forums which has a lot of people discussing best ways to track activity, hold onto signals, and use the many other app features.

Another Apple iPad Take

Went though a draft of this in my head as a funny Q&A with myself — 19 questions asking if I’d need the newly announced device to help me get existing work done better or if I could expect to jump in tomorrow helping clients create content for a newly introduced publishing model all answered with a simple “NO”. Followed by question 20 “will I still preorder it?” answered with a “Probably”. What I realized as I typed it up was that it all came down to work value vs. consumer value. As someone who is a somewhat recent iPhone owner and a long time Apple laptop user there was no solid work value I could find in this new type of 3G computing device but there is still plenty of consumer value as a consolidation and update of devices we’ve seen before.

Falls flat on my “Work Use” criteria

I’m a web developer working with middle to large size development and design teams. I’m not a middle manager or department lead, I don’t do a ton of presentations to clients and as a freelancer don’t attend daily conference room based meetings. I used the iPhone features I already have to stay connected while on the go, and when I need more then email, web and online tools I need a lot more and need to carry the laptop. Text editing, source control, multiple web browser installs and extensions, fully featured Photoshop are where my bread is buttered and a device that grew up from the iPhone instead of down from the laptop [like the MacBook Air] just will always fall short there.

As a photographer shooting purely for fun this doesn’t really help me for the same reason. I wouldn’t be using it for sales, but photo management and editing. Until there are more 3rd party apps that follow the new iWork or iPhoto model we saw demo’d today [I’m looking at you Adobe — bring me iPad Lightroom or Bridge] this just doesn’t do enough. The first thing I’d want to do with this is sit down with a cup of coffee or a beer after a shoot and get a head start on my workflow by integrating with my existing library, tagging and rating that turns 300 photos into 10 or 20 I want to process further. Slideshows are great if I’m meeting with clients, but the iPhone is “good enough” for for me on the go and I don’t have cause to carry this /just/ to show some photos off.

If your work involves communication more then or as much as content creation this may very well be a great device in the workplace, but for me, until it becomes something more or something I’m helping clients create content for it [more smaller publishing outlets in the future?] it just doesn’t help me out.

Still a great consumer device

Take “getting work done” out of the equation and what are you left with? A device for consumption of media by consumers. So what’s the iPad offer to that market?

A full color eBook reader that matches the Kindle DX in size, and (may) do a better job with the PDFs I randomly pick up here or there [like David Duchemin’s Craft & Vision series for photographers]. The market already puts a value on this type of device at $489.

A WiFi enabled photo frame when not in use. Though prices have come down in the last year or so, good size & quality screens w/ wifi updating will still run you $200-$300+.

A nice extra screen for watching video, video podcasts, or other content throughout the day, freeing some existing monitor space or making me more mobile around the house [someone get netflix or hulu running on this thing and you really get me charged here]. Thus removing any desire for another monitor or a netbook I may have had.

Add a few favorite games or [another] device running iTunes remote to control my music from one room to another to polish it off and you have something I can really see myself using around the house and for a price that can fit an established marketplace and a tech geeks budget.

Desire fits the pricing model

At the end of this day of lots of news, commentary and discussions I’m left with the following conclusion — at the entry point of $499 for the 16GB WiFi only model there’s a LOT to like about it and I see a good market for it [stealing sales from Kindle DX and Apple’s own iPod Touch]. At $829 + $30/month for the 64GB model with unlimited 3G data usage it just doesn’t do enough to carve out a new space between an iPhone and a laptop + wireless card for many people to justify the cost & it becomes a niche device like other existing tablets [or even the MacBook Air].

We didn’t get a magical new device made from unicorns and rainbows today. It isn’t going to change the way I work. Won’t [yet] change the publishing industry. But that’s all ok. What I do see is a solid offering by Apple and a solid start for a new device type at a good entry price point. And for the much smaller % of people that will find use in the 3G features or iWork & email on the go they can get all that, too.