Activate your free membership today | Log-in

Thursday, September 25th, 2008

input type=camera to give us a simple way to integrate to Webcams

Category: Browsers, Component, Firefox, HTML, Mozilla

There are a substantial number of iPhone apps that tie into the builtin native components such as the camera.

Brad Lassey has been hacking on Fennec (the Mozilla mobile browser) as well as Firefox itself to integrate with camera phones and Webcams alike:

I wrapped a video tag, image and a few buttons in xbl and bound it to <input type=”camera” />. When a user hits a website using this tag, he or she currently will see a live video preview and a “take photo” button. When the user clicks the button, the photo is grabbed from the camera and shown to the user in the image element. The image element and video element are in a deck element so only one is shown at a time. After the photo is taken, there is a button that reads “Take another photo,” in case the user doesn’t like the one they just took. Once the user is satisfied, this element works like any other form element and the file can be uploaded to a web service.

After talking to a few people this should actually be bound to <input type=”file” accept=”image/png”/>. Also, it needs some UI design both for what it looks like in content and for a configuration dialog. Finally, we’ll need to think about security and make sure no one can snap a photo of you when you’re not looking your best.

I kinda like having an input type="camera" myself, to be more explicit. It would be cool if you can get access to the image as data (e.g. the value is data:......). I love it.

Posted by Dion Almaer at 6:13 am
10 Comments

++---
2.2 rating from 74 votes

Pi.js: Simple JavaScript Library

Category: JavaScript, Library

Azer Koculu has released his Pi.js framework, which is a lightweight system that includes a minimal set of modules, and the ability to use and provide plugins.

By default you get:

  • pi.env: browser detection
  • pi.get: DOM access
  • pi.util: Extensions to JavaScript (e.g. support currying, includes, viewport config, and more)
  • pi.base: OO subsystem
  • pi.element: Create and modify the DOM
  • p.xhr: Remoting
  • Extensions to native objects such as Array, Function, Number, and String

There are then plugins to provide functionality such as Comet support, and a storage wrapper.

Pi has been used in the excellent Firebug Lite update that Azer worked on.

Posted by Dion Almaer at 6:04 am
8 Comments

+++--
3 rating from 29 votes

HTML Whitelist: Sanitize your markup

Category: HTML, Security

HTML Whitelist is the latest in the "cool little Python Web service thrown up on App Engine" by my good colleague DeWitt Clinton.

It does one thing, and it does it well. You can pass the service HTML and it will return a sanitized version.

For example:

HTML:
  1.  
  2. // original
  3. The <strong>quick</strong> brown fox <script src="http://evil.com"> jumps <kbd>over</kbd> the <em>lazy</em> dog.
  4.  
  5. // converted too
  6. The <strong>quick</strong> brown fox &lt;script src=&quot;http://evil.com&quot;&gt; jumps <kbd>over</kbd> the <em>lazy</em> dog.
  7.  

There are a bunch of options. You can pass in HTML, pass a URL to the content, using JSON and JSONP, and different encoding options.

Posted by Dion Almaer at 2:54 am
7 Comments

+++--
3.5 rating from 11 votes

Wednesday, September 24th, 2008

Ex DOM Storage gives us hope for IE 6+

Category: Browsers, IE

Toru Yamaguchi has built a very cool shim, ExDOMStorage, which implements the HTML 5 DOM Storage API for IE 6 and 7.

It does so by strapping in the functionality via an HTC behaviour:

JAVASCRIPT:
  1.  
  2. (function() {
  3.    if (window["localStorage"] && window["sessionStorage"])
  4.          return;
  5.  
  6.    with({ nodeSet: document.getElementsByTagName("script"), storages: ["localStorage", "sessionStorage"] }) {
  7.          var loader = nodeSet.item(nodeSet.length - 1);
  8.          var src = loader.getAttribute("src");
  9.          var behavior_uri = src.replace(/\/\w+\.js$/, '/exdomstorage.htc');
  10.  
  11.          for (var i in storages) with ({ storage: document.createElement('script'), name: storages[i] }) {
  12.            window[name] = storage;
  13.            loader.parentNode.appendChild(storage);
  14.            storage.addBehavior(behavior_uri + "#" + name);
  15.          }
  16.    }
  17. })();
  18.  

Posted by Dion Almaer at 7:38 am
3 Comments

+++--
3.2 rating from 26 votes

OfflineRest: One pattern for offline architecture

Category: Dojo, Offline

Kris Zyp has created OfflineRest, a new module in Dojo 1.2 that allows for a simple offline pattern to building your application.

Dojo 1.2’s new dojox.rpc.OfflineRest module automates the local storage of data and synchronization by leveraging the Dojo Data and REST abstractions. The OfflineRest module augments the JsonRest service in Dojo such that requests are cached in local storage for offline access, and modification requests (put, post, and delete) modify the cache and are recorded for delivery to the server; immediately if online, otherwise when connectivity is restored. Furthermore, JsonRest is the core engine used by JsonRestStore. Consequently, you can simply use the standard Dojo Data API with the JsonRestStore and effortlessly add offline capability with no modifications to your data interaction code. The underlying Rest service automates the handling of caching, storing data locally, and syncing changes. In addition the new OfflineRest module has no dependency on plugins, but rather progressively utilizes offline features that are available, while still operating properly on legacy browsers without offline support.

He has a demo that involves a CRUD system for hiking trails which interestingly asked me for Gears permission, even though it appears that OfflineRest doesn't abstract on top of both Gears and the emerging storage standard, which is something I would like to see, to extend the reach.

JAVASCRIPT:
  1.  
  2. dojo.require("dojox.rpc.OfflineRest");
  3. dojo.require("dojox.data.JsonRestStore");
  4.  
  5. // create a store
  6. trailStore = new dojox.data.JsonRestStore({url:"/Trail"});
  7. dojox.rpc.OfflineRest.addStore(trailStore,"");
  8.  
  9. // data
  10. var item = trailStore.newItem();
  11. trailStore.setValue(item,"foo","bar");
  12.  
  13. // manually observing download changes to force updates
  14. dojo.connect(dojox.rpc.OfflineRest, "downloadChanges", function(){
  15.         .. download changes or refresh the page ..
  16. });
  17.  

Posted by Dion Almaer at 6:19 am
1 Comment

+++--
3.8 rating from 32 votes

Detailed JavaScript and Processing.js from John Resig

Category: Canvas, Presentation

John Resig has given some great talks recently, and just posted about some of them.

First, we have his interactive learning area where the presentation is just a JavaScript application that you can play with. Double click on the code, make a change, and save away!

The talk goes into the innards of the language that we are know, love, or at least deal with:

  • Defining Functions
  • Named Functions
  • Functions as Objects
  • Context
  • Instantiation
  • Flexible Arguments
  • Closures
  • Temporary Scope
  • Function Prototypes
  • Instance Type
  • Inheritance
  • Built-in Prototypes
  • Enforcing Function Context
  • Bonus: Function Length

The goal of all of this, is that after going through the presentation you should understand the following:

JAVASCRIPT:
  1.  
  2. // The .bind method from Prototype.js
  3. Function.prototype.bind = function(){
  4.   var fn = this, args = Array.prototype.slice.call(arguments), object = args.shift();
  5.   return function() {
  6.     return fn.apply(object,
  7.       args.concat(Array.prototype.slice.call(arguments)));
  8.   };
  9. };
  10.  

Next up is his talk on Canvas, Processing and Processing.js. Everytime I see this stuff it makes me smile. Amazing visualizations are here:

Posted by Dion Almaer at 6:00 am
Comment here

+++--
3 rating from 24 votes

Ext JS Key mapping; Keyboard handling as a first class citizen

Category: Ext, Usability

I am a strong believe in making the keyboard a first class citizen for your applications, including on the Web. Thus, I was interested to read how Ext JS has keyboard handling that ties into the entire system:

Ext.KeyMap

Ext provides several components that support keyboard navigation out of the box such as GridPanel, ComboBox, and TreePanel. To implement custom keyboard handling, developers can use the Ext.KeyMap and Ext.KeyNav classes to attach keyboard bindings to any component or element they wish.

The first set of keys we wanted to handle was all of the Function keys (F1-12). While most browsers reserve some/all of these keys, with some ext-pertise, we are able to override the default function if need be for our application. The application we were working with was completely dynamic and server driven, so we really couldn’t define all of the handlers ahead of time. This led to us dynamically building an array of key handler configuration objects and passing them all through to our new Ext.KeyMap object.

JAVASCRIPT:
  1.  
  2. var keys = [];
  3. for(var i = 0;i <buttons.length;i++) {
  4.     var btn = buttons[i];
  5.     // fkey property contains a string referencing the Ext constants (ie: Ext.EventObject.F1)
  6.     var fk = eval(button.fkey);
  7.     btn.handler = this.handleKey.createDelegate(this, [fk]);
  8.  
  9.     keys.push({
  10.         key: fk,
  11.         handler: this.handleKey.createDelegate(this, [fk]),
  12.         stopEvent: true,
  13.         scope: this
  14.     });
  15. }
  16.  

Ext.KeyNav

The next set of key handling added was some additions to the grid keyboard navigation. The GridPanel has built in key navigation from the RowSelectionModel that it creates. Check out this grid example and select a row, you can then use the arrow keys to move up/down and even hold shift and press down to select a range of rows. We added a simple way to navigate through a large paged data set by extending GrindPanel. The PagingToolbar provides keyboard handling once you’ve focused within the built-in TextField, but we wanted to allow the users to just hit ‘page down’ or ‘end’ when focus was anywhere within the GridPanel and ensure it functions as expected.

JAVASCRIPT:
  1.  
  2. MyGrid = Ext.extend(Ext.grid.GridPanel,{
  3. ...
  4. afterRender : function() {
  5.    MyGrid.superclass.afterRender.call(this);
  6.  
  7.     this.nav = new Ext.KeyNav(this.getEl(),{
  8.         pageDown: this.pagingNav.createDelegate(this,['next']),
  9.         pageUp: this.pagingNav.createDelegate(this, ['prev']),
  10.         home: this.pagingNav.createDelegate(this,['first']),
  11.         end: this.pagingNav.createDelegate(this,['last']),
  12.         scope: this
  13.     });
  14. },
  15.  
  16. pagingNav: function(page) {
  17.     var pt = this.getBottomToolbar();
  18.     if (!pt[page].disabled) {
  19.         pt.onClick(page);
  20.     }
  21. },
  22. ...
  23. });
  24.  

Posted by Dion Almaer at 5:28 am
6 Comments

++++-
4.3 rating from 64 votes

Tuesday, September 23rd, 2008

BrowserHawk Lives!

Category: JavaScript

Many years ago I stumbled across the original BrowserHawk. Back then, it was primarily a way to feed information about a client's web browser to a server-side web framework. I was impressed at the time with its ability to detect display resolution, color depth, and a variety of other data not available via HTTP headers.

Richard Litofsky wrote in to tell us that BrowserHawk lives on in a new form: BrowserHawk To-Go. It sounds interesting, though not as revolutionary today as it was to me back when embraced complete ignorance of client-side browser programming:

BHTG is a complete rewrite of our classic BrowserHawk product and is
specifically designed for cross browser, JavaScript-centric programming.

By including our BHTG JS library developers can add our robust browser
sniffer that detects over 100 different properties including browser
type/version/platform, connection type and speed, latency, installed
plug-ins, blocked popups, Java settings, and more. This data can be logged
and/or used to dynamically control page behavior.

BHTG also can add an automated browser troubleshooting and self-help page to
a web site, again just by including the JS library. It also can, with one
line, monitor the *actual* page load times experienced by each user to a
site. And it reports any JavaScript errors users encounter on the site, with
customizable match rules.

BrowserHawk To-Go is a commercial product; they're going for a Software-as-a-Service model where their servers host the script (à la Omniture, etc.).

Posted by Ben Galbraith at 7:30 am
6 Comments

+++--
3.9 rating from 38 votes

Invaders from Mars: Building a JavaScript Game

Category: Games, JavaScript

As a follow-up to our recent posting of a JavaScript Pac-Man clone, we bring you a JavaScript Space Invaders clone: Invaders from Mars. Only this time, in addition to a link to the game itself, we've got a link to the author's blog (one Mark Wilcox) in which he goes into detail on the various design issues he faced whilst creating his game and discusses the lower-level framework he created to drive his game.

Invaders from Mars does it old-school, as did the Pac-Man clone: divs and images, baby. Performance is pretty good, but I can't wait to see people realize that if they go with <canvas>, they can really do some interesting stuff. What do you think on the Canvas vs. DOM rendering model for games, etc.?

Posted by Ben Galbraith at 7:00 am
10 Comments

+++--
3.6 rating from 22 votes

New Sessions at the Ajax Experience

Category: The Ajax Experience

The Ajax Experience is coming up in a week and I wanted to share some exciting last minute developments:

1. Google Chrome. Google's Ojan Vafai will be giving a keynote on their new browser. Obviously, this should be interesting. :-)

2. Opera. We've been trying to get them at the show from the beginning. Opera's Anne van Kesteran presenting on "Opera and Ajax".

3. Ext JS. We've got two great Ext JS talks! Jack Slocum is speaking on "Advanced CSS and Theming of Ext" and Aaron Conran will present "Hands-on Ext".

4. Cappuccino / Objective-J. The folks behind the framework behind the impressive 280slides.com on-line presentation site are giving a lightning talk introducing their framework as well as a full-length presentation entitled "The Road to Cappuccino."

5. Processing.js. John Resig's port of Processing to JavaScript--Processing.js--is amazing. Come hear him talk about it in detail.

6. Hacking NetFlix. Bill Scott of NetFlix talks about their new rich open Ajax APIs. Hint: it's not just about queue management and it's pretty exciting stuff.

7. Episodes. Client-side performance guru Steve Souders has added another talk to his Ajax Experience quiver discussing an entirely new way to benchmark "Web 2.0" applications.

And that's just the new stuff! We've got plenty of other goodness in the agenda. Hope you can join us!

Posted by Ben Galbraith at 6:30 am
3 Comments

+++--
3.6 rating from 9 votes

Audible Ajax Episode 30: Interview with Kris Zyp

Category: Podcasts

Dealing with data is one of those areas of software development that we haven't quite gotten right yet; anyone who tells you otherwise is selling something (or has developed an open-source framework). Whether you embed SQL in your code, map objects to data via some kind of tool, mash it all up LINQ-style, or go all sci-fi with funky XML-all-the-way-down tools, each approach has a series of trade-offs and compromises that just don't feel right.

Kris Zip, a researcher with SitePen, is throwing his hat into the ring with efforts he and others at SitePen are leading to provide Ajax developers with a fully coherent JSON stack. That is, frameworks and services that allow developers to deal entirely in JSON from the bits on the disk to the data on display.

In Audible Ajax Episode 30, Kris chats with us about the JSON work in progress, a bit on his background, and a discussion of the talks he'll be giving at the Ajax Experience next week that covers some of this material.

We have the audio directly available, or you can subscribe to the podcast.

Kris also provided some graphics to accompany his talk:

Dojo Client Model

Persevere

Posted by Ben Galbraith at 6:00 am
3 Comments

+++--
3.7 rating from 23 votes

Sphere: Spherical effect via canvas

Category: Canvas

Christian "Mr. Canvas Effects" Effenberger has shared Sphere.js another effect that allows you to add a spherical picture effect (including background gradient) to images on your web pages.

This joins the many other effects such as Slided and Filmed.

As always, you can add these effects with simple CSS classes on the images.

Posted by Dion Almaer at 4:54 am
6 Comments

++++-
4.2 rating from 33 votes

Monday, September 22nd, 2008

PhoneGap: “AIR for the iPhone”

Category: iPhone

Dave Johnson calls PhoneGap "AIR for the iPhone" because this nice little hack, first created at an iPhone BarCamp, wraps the Web view with a container. This container gives the view access to APIs available on the device, that may not be available yet via WebKit alone. AIR provides a similar container for Flash and Ajax content on the desktop.

PhoneGap is a free open source development tool and framework that allows web developers to take advantage of the powerful features in the iPhone SDK from HTML and JavaScript. We're trying to make iPhone app development easy and open. For many applications a web application is the way to but in Safari you don't get access to the native iPhone APIs, and the that's the problem we're trying to solve.

It is written in Objective-C and allows developers to embed their web app (HTML, JavaScript, CSS) in Webkit within a native iPhone app. We're big advocates of the Open Web and want JavaScript developers to be able to get access iPhone features such as a spring board icon, background processing, push, geo location, camera, local sqlLite and accelerometers without the burden of learning Objective-C and Cocoa.

PhoneGap also has a web app that allows web developers to quickly package their web app into a native iPhone app by providing a URL, a name and icon graphic the web service with automagically create a native iPhone application. We haven't open sourced that code but we're going to soon.

PhoneGap was conceived at iPhoneDevCamp II by Nitobi developer Brock Whitten, Rob Ellis, freelance designer Colin Toomey and Eric Oesterle.

There are a few APIs available now, and others pending:

JAVASCRIPT:
  1.  
  2. // Location API
  3. // Feels a little ugly compared to passing in a closure. Using a hard coded name? :)
  4.   getLocation();
  5.  
  6.   //GAP will invoke this function once it has the location
  7.   function gotLocation(lat,lon){
  8.     $('lat').innerHTML = "latitude: " + lat;
  9.     $('lon').innerHTML = "longitude: " + lon;
  10.   }
  11.  
  12. // Accelerometer API
  13.  
  14.   function updateAccel(){
  15.     $('accel').innerHTML = "accel: " + accelX + " " + accelY + " " + accelZ;   
  16.     setTimeout(updateAccel,100);
  17.   }
  18.  
  19. // Camera (pending)
  20.   function takePhoto(){
  21.     var photo = gap:takePhoto();
  22.     return photo;
  23.   }
  24.  
  25. // Vibration (pending)
  26.  
  27.   function vibrate(){
  28.     gap:vibrate();
  29.     return false;
  30.   }
  31.  

You can take a peak at the open source code on github. For example, here is the code that wraps the iPhone location service:

[c]
@implementation Location

- (id)init{
NSLog(@"Gap::Location");
locationManager = [[CLLocationManager alloc] init];
[locationManager setDelegate:self];
return self;
}

+ (void)startTracking{
NSLog(@"starting location tracker");
[locationManager startUpdatingLocation];
}

+ (void)stopTracking{
NSLog(@"stopping location tracker");
[locationManager stopUpdatingLocation];
}

- (void)location{
NSLog(@"location is");
}

- (void)log{
NSLog(@"the location is...");
}

- (void)dealloc {
[locationManager release];
[super dealloc];
}

@end
[/c]

Posted by Dion Almaer at 7:33 am
5 Comments

+++--
3.8 rating from 19 votes

OtherInbox showcases SproutCore again

Category: Showcase

SproutCore jumped onto the scene when MobileMe launched to much acclaim on the visual side (even if the back end couldn't handle the load).

It doesn't seem to be a one-hit wonder, especially in the field of e-mail. OtherInbox "provides consumers with a free email account that automatically organizes newsletters, social networking updates, coupons and receipts from online purchases", and showcases SproutCore again.

If you are looking to build desktop-looking applications, it is worth giving SproutCore a look.

Posted by Dion Almaer at 7:04 am
4 Comments

++---
2.4 rating from 24 votes

PURE JavaScript Template Library Improves

Category: JavaScript

PURE, the JavaScript template engine, has had a major new release which includes:

  • Auto-rendering: a new PURE method takes your HTML and your JSON data and merges them automatically. The class attribute is used to map the HTML and the data. (Read more about autoRender and its jQuery version on our Wiki).
  • Functions as directive are called by reference and not serialized
  • Change the id of the template root node (as any other attribute)
  • Better string value handling
  • Use of named properties in iteration “obj.prop” as well as “obj['name']“

For a feel of the library check out the documentation which takes you from the simplest render:

JAVASCRIPT:
  1.  
  2. $('#hello').autoRender({ "who": "Mary" });}
  3.  

to more advanced examples such as going back to the server to get data to fill in:

JAVASCRIPT:
  1.  
  2.   button.value = 'loading data...';
  3.   var script = (button.id == 'b4_2') ? 'js/jsonBig.js':'js/jsonSmall.js';
  4.   $.getJSON(script, function(context){
  5.  
  6.   var directive = {
  7.     'tbody tr td[onclick]':'"clickLine(this)"',
  8.     'tbody tr td[onmouseover]': '"swapStyle(this, true);"',
  9.     'tbody tr td[onmouseout]' : '"swapStyle(this, false);"',
  10.     'tbody tr td[style]':'\'cursor:pointer\'',
  11.                
  12.     'tbody tr[class]+':
  13.         function(context, items, pos){
  14.           var oddEven =  (pos % 2 == 0) ? 'even' : 'odd';
  15.           var firstLast = (pos == 0) ? 'first': (pos == items.length -1) ? 'last':'';
  16.           return oddEven + ' ' + firstLast; }}
  17.  
  18.   $('table.players.2').autoRender(context, directive);
  19.  
  20.   button.value = 'Refresh the page to render again';});}
  21.  

Posted by Dion Almaer at 6:21 am
Comment here

+++--
3 rating from 30 votes

What if we didn’t lump all “accessibility” requirements together?

Category: Accessibility, Editorial

Joe Walker was thinking about accessibility and wrote about a thought experiment that he had where he ponders 'What if we didn't lump all "accessibility" requirements together?'

What if, instead, apps are written for one audience. What could you do differently for different use cases?

Designing for Screen Readers

So you want to create a version of your site specifically for screen readers, ignoring everyone else. What might you do?

Scroll bars are generally bad for sighted people. They hide content, slow things down, and some people find them hard to use. But screen readers don't care about long pages; the scrollbars are invisible anyway. So how about packing the whole site into a single page? Since the graphics are irrelevant, we can skip those, and for many sites still have less to download. The page can then start with a description of the access keys and the user can then navigate really quickly. We could quickly summarize the access keys at each page boundary in case they've been forgotten.

Designing for Dyslexia

Dyslexia is generally less of a barrier to web use compared to blindness, however it is very common and often overlooked. In contrast to the low graphic, high text approach for Screen Readers, some dyslexics think in terms of pictures, and may prefer a layout which uses a standard set of icons to back up common concepts. Many users without this disability may find this approach distracting, and it's certainly going to be annoying to anyone with a screen reader, if the text goes on regular side-tracks reading the ALT text that is only there to back up the text anyway.

Designing for Cognitive Disability

One of the problems with the web, and computers in general is the level of distraction. Distractions are a problem for everyone whatever their abilities, but the problem is exacerbated by disability. I've noticed that as people slow down, they start to look around at their screens using their neck muscles, pointing their entire head rather than just their eyes, and I think it's all about focus. We need a way to narrow our focus to concentrate on the important questions.

It might be possible to have a site where we could "zoom in" on what was important. If you could "zoom-in" to simplify GMail, what would you throw out? Invitations would go, as would links to other services, settings, maybe labels and the 2 sets of buttons that do the same thing. I think many people use email by just seeing their inbox, and maybe search. Ultimately email could be a wizard where you see what's new and that's it. Clearly this lack of detail isn't going to be good for everyone, but having a "simplify it" function could be really useful in many cases.

Designing for Low Vision and Motor Impairment

I don't know, but I suspect that the "zoom-in" to simplify concept is going to require lots of complex layout. In comparison to which, people with low vision or motor impairment want simple layout. They also want to zoom in, but probably just to make the words/buttons bigger. People with low vision often differ in how they need the screen enhanced. Is it black/white or white/black. Have colors gone, or might a flash of yellow help? Often the OS takes care of much of this problem, but websites that use yellow-fade might be helping, or might not, depending on OS settings. Good design for low vision is probably going to let the user select the type of visual aid that helps.

Of course, this sounds interesting in theory, but we have the sliding scale:

  • How many developers build for more than one browser, let alone...
  • Old browsers, let alone...
  • Accessibility, let alone...
  • Multiple accessible sites.

Christian Heilmann talked about having a movement for accessibility, and how we need to not be flailing in the wind.

Posted by Dion Almaer at 5:56 am
1 Comment

++++-
4.4 rating from 18 votes

« Previous PageNext Page »