Bookmarklets are simple programs written in the JavaScript language, stored like regular links or bookmarks, and executed by clicking on the link or selecting the bookmark. So they only work in browsers that support JavaScript.
Their leading proponent and innovator is Steve Kangas at bookmarklets.com.
This page offers a tutorial on writing one particular kind of bookmarklet, that generates a URL based on the current date.
Normally, you copy URLs by selecting them in the little URL-field at the top of the browser window, but you can't do this with bookmarklets. Instead, you have to use the popup menu that appears on a Mac when you click on the link and hold the mouse-button down, or in Windows when you click the link with the right mouse-button, instead of the left.
And if you need a full JavaScript reference, Netscape offers this one.
Here's a very simple bookmarklet that moves your current window to the upper left corner of the screen:
Try the 'Copy This Link Location' item in the popup menu, if you've never done that before, and make sure you can paste the javascript into a word-processing document.
All of the following forms work identically (note parens and semicolons):
javascript: moveTo(4,4) javascript: (moveTo(4,4)) javascript: void moveTo(4,4) javascript: void(moveTo(4,4)) javascript: moveTo(4,4); javascript: (moveTo(4,4)); javascript: void moveTo(4,4); javascript: void(moveTo(4,4));
JavaScript will ignore the carriage returns and whitespace, generally, but the convention is to omit them for compactness.
At the same time you relocate the window, you can resize it (which comes in handy if a badly-behaved site changes your default window size):
javascript: moveTo(4,4); resizeTo(645,450)
Here the semicolon is required between the two commands.
Bookmarklets can also cause a link to open in a new window:
javascript:
open('http://www.yahoo.com/');
void 1(The final 'void 1' here keeps the original window from being overwritten like this.)
This technique gets really useful for opening several windows at once. I have one batch (of nine!) that I open first thing in the morning, another batch of weblogs for mid-morning, and this batch of three pages that occasionally offer new, sample 'first chapters':
javascript:
open('http://www.washingtonpost.com/wp-srv/style/books/front.htm');
open('http://www.usatoday.com/life/enter/books/chapter.htm');
open('http://www.cnn.com/books/beginnings/');
void 1
(The first embedded-date bookmark, for CNN EarthWeek, was written by Dan Budiac.)
The reason for embedded-date bookmarklets is that many web periodicals require you to link to a homepage with no content, and then click on a second link for the current issue's table of contents. For example, Lingua Franca's homepage is at: http://www.linguafranca.com/ but the table of contents for May 1999 is at: http://www.linguafranca.com/9905/toc.9905.html
Here's a bookmarklet that can generate the embedded-date URL:
javascript: var t=new Date(); var m=t.getMonth()+1+''; var y=t.getYear()%100+''; if(m.length==1)m='0'+m; if(y.length==1)y='0'+y; location.href='http://www.linguafranca.com/'+y+m+'/toc.'+y+m+'.html';
Looking at this line-by-line:
var t=new Date();
Creates a variable 't' and assigns it the value of the current date, in JavaScript format.
var m=t.getMonth()+1+'';
Extracts the current month from the date 't', adds '1' to it (because they perversely call January '0' not '1'), and then changes it to a string rather than a number by appending an empty string.
var y=t.getYear()%100+'';
Extracts the current year, in an odd format that counts 1900 as '0', divides by 100 and keeps the remainder (the 'modulo' operation), and converts it to a string.
if(m.length==1)m='0'+m;
Tests to see if the month is one digit or two, and pre-pends a zero if it's just one (so '5' becomes '05').
if(y.length==1)y='0'+y;
Ditto for the year.
location.href='http://www.linguafranca.com/'+y+m+'/toc.'+y+m+'.html';
Links together all the pieces to get something like:
http://www.linguafranca.com/9905/toc.9905.html
Here's a very similar one for Sun's column on scripting:
javascript: var t=new Date(); var m=t.getMonth()+1+''; var y=t.getYear()+1900+''; if(m.length==1)m='0'+m; location.href='http://www.sunworld.com/swol-'+m+'-'+y+'/swol-'+m+'-regex.html';
The big difference here is that the year has to be converted to four digits rather than two: http://www.sunworld.com/swol-05-1999/swol-05-regex.html
The next one is for NASA's daily AstroPic, and includes the day as well as the month and year. (There's a standard URL for this page as well: http://antwrp.gsfc.nasa.gov/apod/astropix.html but it's no good for linking to particular pictures, which need this format: http://antwrp.gsfc.nasa.gov/apod/ap990522.html
javascript: var t=new Date(); var d=t.getDate()+''; var m=t.getMonth()+1+''; var y=t.getYear()%100+''; if(d.length==1)d='0'+d; if(m.length==1)m='0'+m; if(y.length==1)y='0'+y; location.href='http://antwrp.gsfc.nasa.gov/apod/ap'+y+m+d+'.html';
Harper's magazine offers very little content on the Web, as yet, but they do post the previous month's 'Index' around the first of each month:
javascript: var t=new Date(); t.setMonth(t.getMonth()-1); var m=t.getMonth()+1+''; var y=t.getYear()+1900+''; if(m.length==1)m='0'+m; location.href='http://www.harpers.org/harpers-index/listing.phtml?sub_month='+m+'&sub_year='+y;
The result here is a messy search engine query: http://www.harpers.org/harpers-index/listing.phtml?sub_month=04&sub_year=1999
The only new feature is the third line:
t.setMonth(t.getMonth()-1);
The current date has both the current month and current year, but every January we'll need to roll back both the month and the year. JavaScripts 'date object' knows how to do this automatically if you use the setMonth/ getMonth format.
Dilbert holds back the daily cartoon for a week before posting it, and then after a day moves it from the undated URL: http://www.unitedmedia.com/comics/dilbert/ab.html to a dated URL (for the next month): http://www.unitedmedia.com/comics/dilbert/archive/dilbert19990529.html
For a lazy weblogger, it's easiest to just follow the eight-day-old URL: Dilbert
javascript: var t=new Date();t.setDate(t.getDate()-8); var m=t.getMonth()+1+''; var y=t.getYear()+1900+''; if(m.length==1)m='0'+m; var d=t.getDate()+'.html'; if(d.length==6)d='0'+d; location.href='http://www.unitedmedia.com/comics/dilbert/archive/dilbert'+y+m+d;
Sometimes, annoyingly, the month will be expressed as an abbreviation: http://boardwatch.internet.com/mag/99/apr/fable.html
This bookmarklet handles this by brute force:
javascript:
mn=new Array('jan','feb','mar','apr','may','jun','jul','aug','sep','oct','nov','dec');
var t=new Date();
t.setMonth(t.getMonth()-1);
var m=t.getMonth();
var y=t.getYear()%100+'';
if(y.length==1)y='0'+y;
location.href='http://boardwatch.internet.com/mag/'+y+'/'+mn[m]+'/fable.html';This line creates an array of month abbreviations:
mn=new Array('jan','feb','mar','apr','may','jun','jul','aug','sep','oct','nov','dec');
which are accessed by the form 'mn[m]' in the last line.
Weekly periodicals require a new complication depending on which day of the week they're posted. If the new issues come out on Friday, you want the bookmarklet to work right for the rest of the week:
javascript: var t=new Date(); t.setDate(t.getDate()-(t.getDay()+2)%7); var y=t.getYear()+''; var m=t.getMonth()+1+''; var d=t.getDate()+''; if(m.length==1)m='0'+m; if(d.length==1)d='0'+d; location.href='http://www.cnn.com/NATURE/'+y+m+'/'+d+'/diary.planet/index.html';
You need to rewind the date to the previous Friday, which requires a somewhat unintuitive operation on the getDay value:
getDay offset F 5 -0 S 6 -1 S 0 -2 M 1 -3 T 2 -4 W 3 -5 T 4 -6
So the offset is "(getDay + 2) modulo 7"
(t.getDay()+2)%7)
An alternate approach is via a for-loop:
for( var t=new Date(); t.getDay()!=5; t.setDate(t.getDate()-1));
which can be broken down as:
for(
which sets up the loop
var t=new Date();
which initialises the loop
t.getDay()!=5;
which tests if the day of the week is Friday (where Sunday = 0)
t.setDate(t.getDate()-1));
and keeps subtracting one day per loop, if it isn't.
The same techniques work for daily periodicals that suspend publication on weekends:
javascript: var t=new Date(); t.setDate(t.getDate()-(t.getDay()==0?2:(t.getDay()==6?1:0))); var y=t.getYear()+1900+'/'; var m=t.getMonth()+1+'/'; var d=t.getDate()+'/'; if(m.length==2)m='0'+m; if(d.length==2)d='0'+d; location.href='http://www.salon.com/ent/tv/glow/'+y+m+d+'glow/print.html';
The offsets here will be:
getDay offset M 1 -0 T 2 -0 W 3 -0 T 4 -0 F 5 -0 S 6 -1 S 0 -2
because Salon's TV column for Friday includes the Sat and Sun highlights as well.
So the offset is "if getDay==0 then 2 else (if getday==6 then 1 else 0)" where the form "if x then y else z" can be represented as 'x ? y : z':
t.getDay()==0?2:(t.getDay()==6?1:0)
Or, with the looping approach:
for( var t=new Date(); t.getDay()==(6||0); t.setDate(t.getDate()-1));
The test here uses the '||' operator to mean OR (Saturday OR Sunday).
Messier still is the case of the New Scientist, where the issue dated Saturday is posted to the Web on Wednesday:
javascript: var t=new Date(); var d=t.getDay(); t.setDate(t.getDate()-((d>2)?(d-6):(d+1))); var y=t.getYear()+1900+''; var m=t.getMonth()+1+''; var d=t.getDate()+''; if(m.length==1)m='0'+m; if(d.length==1)d='0'+d; location.href='http://www.newscientist.com/ns/'+y+m+d+'/news1.html';
On Wed, Thurs, and Fri you want to advance the date to Saturday. From Sun thru Tues you want to step back to the Sat before:
getDay offset S 0 -1 M 1 -2 T 2 -3 W 3 +3 T 4 +2 F 5 +1 S 6 0
(d > 2) ? (d - 6) : (d + 1)
Finally, the 'new Date' command automatically assumes that the date advances at midnight in your local timezone, but daily periodicals post at some arbitrary time in their own time zone. So to be accurate, we need to compensate with the 'getTimezoneOffset' operator:
javascript: var t=new Date(); t.setHours(t.getHours()-3+t.getTimezoneOffset()/60); t.setDate(t.getDate()-((t.getDay()==0)?1:0)); var y=t.getYear()+1900+'/'; var m=t.getMonth()+1+''; var d=t.getDate()+'/'; if(m.length==1)m='0'+m; if(d.length==2)d='0'+d; location.href='http://www.ireland.com/newspaper/features/'+y+m+d+'index.htm';
The Irish Times posts around 0300 GMT:
t.setHours(t.getHours()-3+t.getTimezoneOffset()/60);
(TimezoneOffset is measured in minutes, not hours, because a few locations require it.)
And they take Sunday off:
t.setDate(t.getDate()-((t.getDay()==0)?1:0));
And the London Times posts around 0100 GMT, and has a slightly different URL-format on Sundays:
javascript: var t=new Date(); t.setHours(t.getHours()-1+t.getTimezoneOffset()/60); var y=t.getYear()%100+'/'; var m=t.getMonth()+1+'/'; var d=t.getDate()+'/'; if(m.length==2)m='0'+m; if(d.length==2)d='0'+d; location.href='http://www.sunday-times.co.uk/news/pages/'+ ((t.getDay()==0)?'sti/':'tim/') +y+m+d+ ((t.getDay()==0)?'fpcontent':'timconcon01001') +'.html?1334425';
Here's the two compact tests for Sunday:
(t.getDay()==0)?'sti/':'tim/' (t.getDay()==0)?'fpcontent':'timconcon01001'
Special topics:
surfing-skills :
url-hacking :
open content :
semantics :
pagelength :
linktext :
startpages :
bookmarklets :
weblogging :
colors :
autobiographical pages :
thumbnail-graphics :
web-video :
timeline of hypertext
Anti-XML/W3C/etc:
structure-myth :
page-parsing :
firstcut-parser :
html-history :
semantic web
Design prototypes:
topical portal :
dense-content faq :
annotated lit :
random-access lit-summary :
poetry sampler :
gossipy history :
author-resources :
hyperlinked-timeline :
horizontal-timeslice :
web-dossier
Website-resource pages:
RobotWisdom.com :
Altavista.com :
1911encyclopedia.com :
Google.com :
IMDb.com :
Perseus.org :
Salon.com :
Yahoo.com
Older stuff:
design-lab :
design-checklist :
HyperTerrorist :
design-theory :
design cog-sci
Hosting provided by instinct.org. Content may be copied under Open Web Content License.