hosting LA HN and having me. A little bit about myself. My name is Jerry, and I work as a Rails developer for Intridea. We do mobile and web consulting, and also sell products like Presently, a micro-blogging platform. I heard about SproutCore while I was doing some mac development for fun. It got me interested in this new desktop/ web hybrid development paradigm I think will play a big part in the next few years. We’ll get to that later in the slides. First off...
HTML5 application framework for building responsive, desktop-caliber apps that work in any modern web browser, without plugins. That’s the official definition from the SproutCore homepage, and it crams in a lot of information. Let’s break that down and see what it really means.
apps in any modern web browser, without plugins. Monday, September 26, 11 First, let’s try to define what a desktop-caliber app is.... More and more these days, I find that I use web apps to replace desktop software because I like having my data online and available whenever I want it. But even as webapps get better, there’s still a lot of things that just work better with on the desktop.
apps in any modern web browser, without plugins. Monday, September 26, 11 I’m not a fan of iTunes, but it does make a good example of where a desktop app beats the web:
apps in any modern web browser, without plugins. Monday, September 26, 11 On the left sidebar, iTunes has these tabs called ‘smart filters’. they’re basically saved searches that stay up to date even when you add new stuff to your itunes library. So if I buy a new CD and import it, the contents will get updated automatically. As soon as you click the “Top 25 Most Played” filter...
apps in any modern web browser, without plugins. Monday, September 26, 11 ... the entire interface is updated. It doesn’t matter if you have 5 songs, or 5 million songs, it updates my song list instantaneously. If I click another smart filter, the song list is updated again. There’s no lag time so you don’t have to worry about clicking around the app. Now compare iTunes’ interface with...
apps in any modern web browser, without plugins. Monday, September 26, 11 Last.fm. This is my last.fm profile page. It also has these tabs to lets me filter through my song information, but unlike iTunes, every time I click one of these tabs, there’s an animated progress spinner. What’s really happening is this:
apps in any modern web browser, without plugins. Monday, September 26, 11 my browser sends a request across the US, under the atlantic ocean, into the last.fm stack, figures out my recent favorite artists, then carries that response back the same way and back into my browser. I’m exaggerating this request/response cycle, but if you think about it, since all my music is local, doesn’t it seem like overkill to make this request...
apps in any modern web browser, without plugins. http://www.flickr.com/photos/savaman/29693053/ Monday, September 26, 11 ...just to figure out that I play a ton of country music while I work?
apps in any modern web browser, without plugins. Monday, September 26, 11 so it’s nice sometimes to be able to do your computing locally rather than in your server backend. But it’s a lot of work to write a client for every platform out there. The web works everywhere, so it makes sense that Sproutcore uses HTML5 as a foundation to build on. Unlike other app frameworks that promises cross-platform capabilities, SproutCore doesn’t try to run a virtual machine, or cross-compile your code to different platforms. This has been tried before and the results weren’t always pretty. SproutCore’s primary language is Javascript, and it uses HTML and CSS for drawing content.
apps in any modern web browser, without plugins. Monday, September 26, 11 What this means is that your team’s awesome web developers and designers can build a mac client for your site without learning objective-c and cocoa. Or your company can build a mobile version of your site without having to hire a whole new team of mobile developers. It also lets you reuse existing skillsets that your team already has. For example...
apps in any modern web browser, without plugins. Monday, September 26, 11 You can also reuse your existing server-side stack for managing your data. It doesn’t matter what your backend technology is, you can write a custom data store layer. As long as your layer conforms to SproutCore’s small data interface, Sproutcore will be able to talk to your backend through that.
apps in any modern web browser, without plugins. Monday, September 26, 11 because sproutcore is based on web standards, it’ll run across any of today’s modern browsers.
apps in any modern web browser, without plugins. Me too? Monday, September 26, 11 Does that include our beloved Internet Explorer? I actually haven’t tested in in IE, but if you’re asking for IE support at this point, Sproutcore is probably still to early in development for you.
apps in any modern web browser, without plugins. Monday, September 26, 11 On the other hand, if you’re starting fresh, then the current browsers all do pretty well. I noticed a few minor rendering problems in some of the sproutcore projects that are up online today, but they’re mostly styling related and because of CSS differences. Functionality-wise, the major browsers all seem to work. On top of desktop browsers, we can create also custom interfaces for...
apps in any modern web browser, without plugins. Monday, September 26, 11 mobile browsers. SproutCore has an additional library called SproutCore Touch that lets you handle touch events. The best example up online now is their iPad documentation app. It’s a really simple app that looks like a native app and lets you browse their docs.
apps in any modern web browser, without plugins. Monday, September 26, 11 On top of mobile browsers and desktop browsers, it’s also possible to do a hybrid approach. This is a screenshot of the Mashable mac app that I helped build. It doesn’t use sproutcore, but the article display panel is an embedded webkit component. By mixing a desktop app with a browser, you can get a really seamless user experience.
deploy would probably be Apple’s mobile me. It lets you sync you docs and files between different apple devices. Looking at the code and architecture for sproutcore, there’s actually very deep similarities with Apple’s Cocoa frameworks. Even the terminology they use in the docs turn out to be identical sometimes.
sproutit. They’re all in behind the technology and actively contribute back to the project. They have a product called mailroom for managing customer emails and support. It looks a lot like Apple mail, but runs inside of a browser and has more organization tools.
overview and build a concrete example. I was going to build a sproutcore app on top of a pet project I made called beerpad which is like a Yelp for beer, but I ran out of time. Sorry. Instead I’ll walk through the Todo list tutorial they have on the Sproutcore wiki and highlight some of the cooler features of the framework
CSS for rendering the views, but you work in terms of widgets instead of writing everything yourself. Layouts and views are defined in javascript. Even though it’s code, it’s really a data format for describing UI’s. There is an interface builder called Greenhouse that can read these files and give you a wsywig editor for making UIs.
how this view is laid out. There’s 3 sections, a top ToolbarView with an ‘Add Task’ ButtonView, a center ListView embedded within a ScrollView, and a bottom ToolbarView to display how many tasks I have.
Button to actually do something, we use the ‘Target-Action’ pattern from Mac development. The Target is an object that will handle the click, and the Action is the method we call on the Target.
12, width: 100 }, title: "Add Task", target: "Todos.tasksController", action: "addTask" }) Monday, September 26, 11 In our view, we add the target and action properties to our buttonView. The target is an object that knows how to respond to a method named addTask. When you click the button, it calls the addTask method on the target. The target will create the record and update the backend. I’m skipping the controller code because it looks boring on the slides. If anyone’s curious, I can show it to you after.
concept ripped off from Mac development is bindings. Think of bindings as glue code that observe when your objects change and notifies your views when they need to something. The ListView in the middle for showing tasks has a Binding to a controller object to figure out what to display...
0, bottom: 32 }, hasHorizontalScroller: NO, backgroundColor: 'white', contentView: SC.ListView.design({ contentBinding: 'Todos.tasksController.arrangedObjects', selectionBinding: 'Todos.tasksController.selection', contentValueKey: "description", contentCheckboxKey: "isDone", canEditContent: YES, canDeleteContent: YES }) }), Monday, September 26, 11 To make the list view with bindings, I add some properties to the contentView. ‘contentBinding’ tells my contentview where to get it’s display values ‘selectionBinding’ tells my contentview which task is currently selected ‘contentValueKey’ means that we should use the ‘description’ field on our objects for display.
an object a view cares about, that view will know to automatically refresh itself. For example, labelview that shows the number of tasks in your list knows to redraw itself whenever you add or delete a task
can use anything as it’s external backend. It’s cool if you’re using Java, Ruby, Python, or PHP. Anything works as long as you follow the Data- Source interface. SproutCore uses your custom data source whenever it needs to grab data or when it wants to send data to your backend.
destroyRecord Monday, September 26, 11 ... To write a custom data source, you need these methods. If you’re familiar with restful programming, then these should sound pretty familiar...
destroyRecord Monday, September 26, 11 Fetches are done when you want a group of objects. For our todo app, we use fetch to grab all the tasks at once to fill the listview. A really cool feature is that you can configure your views to only fetch what’s displayable in the view. So when you have a million Tasks in your list, it only fetches the 20 tasks that you can see, and then fetches more when you start scrolling.
destroyRecord Monday, September 26, 11 retrieveRecord is for when you want to show a single Task. I didn’t use this for the todo app because I use fetch to grab them all at once. But if you wanted to have a ‘details’ view for a task, you would need retrieveRecord
destroyRecord Monday, September 26, 11 Create and update record are pretty straight forward. Whenever you make changes in your views, these will get called. Since I’m using Rails as my backend, my implementation just does a POST and PUT to Rails with json data hashes.
Heavily influenced by Cocoa on Mac • Backend agnostic Monday, September 26, 11 To wrap up, sproutcore reuses existing web technologies to for desktop and mobile development. It isn’t an addon to your existing webapp, but instead lets you reuse your data to build clients for different platforms...
Heavily influenced by Cocoa on Mac • Backend agnostic Monday, September 26, 11 When you’re coding, a lot of the terminology and patterns will be closer to mac desktop development than web development. This takes a bit of getting used to, but at least you’ll already be familiar with the web technologies.
Heavily influenced by Cocoa on Mac • Backend agnostic Monday, September 26, 11 Best of all, you can start using sproutcore with your existing app. Since you can write a custom adapter for your external data source, you can start building mobile or desktop clients alongside your webapp without having to heavily re-architect your backend.