<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Funk Rock &#187; Web</title>
	<atom:link href="http://rossboucher.com/category/web/feed/" rel="self" type="application/rss+xml" />
	<link>http://rossboucher.com</link>
	<description>Blog by Ross</description>
	<lastBuildDate>Sun, 01 Mar 2009 21:31:18 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.2</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>Limitations of the WAI-ARIA</title>
		<link>http://rossboucher.com/2009/03/01/limitations-of-the-wai-aria/</link>
		<comments>http://rossboucher.com/2009/03/01/limitations-of-the-wai-aria/#comments</comments>
		<pubDate>Sun, 01 Mar 2009 19:51:43 +0000</pubDate>
		<dc:creator>Ross</dc:creator>
				<category><![CDATA[Technology]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[accessibility]]></category>
		<category><![CDATA[ARIA]]></category>
		<category><![CDATA[DOM]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[WAI-ARIA]]></category>
		<category><![CDATA[web applications]]></category>

		<guid isPermaLink="false">http://rossboucher.com/?p=44</guid>
		<description><![CDATA[As a follow up to my previous post, I wanted to learn more about the WAI-ARIA spec, so I went ahead and read it. I won&#8217;t claim to be an expert, or to have anything more than a basic understanding of the spec at this point, but I was not impressed with what I saw. [...]]]></description>
			<content:encoded><![CDATA[<p>As a follow up to my previous post, I wanted to learn more about the <a href="http://www.w3.org/TR/wai-aria/">WAI-ARIA</a> spec, so I went ahead and read it. I won&#8217;t claim to be an expert, or to have anything more than a basic understanding of the spec at this point, but I was not impressed with what I saw. </p>
<p>Unfortunately, the spec doesn&#8217;t seem particularly forward thinking. There are two main issues I have with the spec: first is that it&#8217;s a very limited extension of the DOM and of what we already have on the web; second is that there is no programmatic interface to the accessibility system. </p>
<p>The most obvious downside of assuming that the DOM will be the basic building block of future web applications is that it presumes all web apps will always be structured with DOM trees. But this already isn&#8217;t true today. Look at <a href="https://bespin.mozilla.com/">Mozilla&#8217;s Bespin editor</a>, which renders text inside a canvas element, or SUN&#8217;s <a href="http://research.sun.com/projects/lively/">Lively Kernel</a>, which implements an entire widget set in SVG. Because there is no underlying DOM structure, these two programs can not be made accessible under the WAI-ARIA spec without substantial hacks. </p>
<p>What about elements that aren&#8217;t part of the visual structure at all? For example, in <a href="http://cappuccino.org">Cappuccino</a>, every application has a CPApplication object. This object contains information that would undoubtedly be useful to the accessibility system, but because it&#8217;s an abstract object and isn&#8217;t part of the render tree in any way, it will never be visible to WAI-ARIA compliant browsers. </p>
<p>This leads us to the second problem, not having programmatic access to the accessibility system. This spec is designed to target <em>web applications</em>, but it has taken the same document based approach as HTML. Applications are defined by requiring a programming language, which in the case of the browser is usually JavaScript. It seems short sighted to develop a standard for applications that uses a fundamentally different technology than the application does.</p>
<p>Even beyond the fact that elements in your program that don&#8217;t exist in the DOM tree can&#8217;t become part of the accessibility system, not having a programmatic interface means that you can&#8217;t dynamically compute accessibility values. Imagine some user interface element that changes frequently, or perhaps is a composite of several other objects. Under the current WAI-ARIA spec, every change to this user interface element needs to be immediately reflected in the DOM. This means a potentially substantial performance hit that is unnecessary for the vast majority of users, and even for people requiring the accessibility feature if they aren&#8217;t focused on that element. </p>
<p>Lack of an actual API also limits the potential uses of ARIA. I can&#8217;t, for example, implement my own accessibility tool within the browser. It also causes issues with the event system, and doesn&#8217;t add any enhanced functionality for simulating events using accessibility APIs, which could have enabled a lot of advanced automated testing.</p>
<p>These thoughts are a result of my very brief research into ARIA so far, and if anything is technically incorrect, I&#8217;d appreciate that feedback. At this point, I&#8217;m not sure where to go with ARIA and accessibility. As far as Cappuccino implementation is concerned, there is enough in ARIA that we can significantly enhance the accessibility of Cappuccino, if not 100%. I suspect the performance implications will be minimal for most UI elements (though I am concerned about text fields), but it&#8217;s impossible to say until we actually have ARIA implemented. </p>
<p>I&#8217;m interested to hear other opinions on ARIA, especially from those who are developing modern web applications. It would be interesting to know if anyone shares my concerns, and if there is any way to actually address some of them within the current framework of ARIA or perhaps another active project I&#8217;m not aware of. I don&#8217;t claim to have any answers, just a lot of questions, so please share your thoughts.</p>
]]></content:encoded>
			<wfw:commentRss>http://rossboucher.com/2009/03/01/limitations-of-the-wai-aria/feed/</wfw:commentRss>
		<slash:comments>17</slash:comments>
		</item>
		<item>
		<title>Accessibility &amp; Degradation in Cappuccino</title>
		<link>http://rossboucher.com/2009/02/26/accessibility-degradation-in-cappuccino/</link>
		<comments>http://rossboucher.com/2009/02/26/accessibility-degradation-in-cappuccino/#comments</comments>
		<pubDate>Thu, 26 Feb 2009 09:59:47 +0000</pubDate>
		<dc:creator>Ross</dc:creator>
				<category><![CDATA[Projects]]></category>
		<category><![CDATA[Technology]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[280north]]></category>
		<category><![CDATA[accessibility]]></category>
		<category><![CDATA[atlas]]></category>
		<category><![CDATA[cappuccino]]></category>

		<guid isPermaLink="false">http://rossboucher.com/?p=41</guid>
		<description><![CDATA[On Tuesday, we announced Atlas, our new visual layout tool for Cappuccino. I&#8217;m incredibly excited about where Atlas is headed, and I&#8217;m also glad to hear all the feedback we&#8217;ve been getting just from our demo video. One of the things in particular that I&#8217;ve read several discussion on is accessibility and Cappuccino, and I [...]]]></description>
			<content:encoded><![CDATA[<p>On Tuesday, we announced <a href="http://280atlas.com">Atlas</a>, our new visual layout tool for <a href="http://cappuccino.org">Cappuccino</a>. I&#8217;m incredibly excited about where Atlas is headed, and I&#8217;m also glad to hear all the feedback we&#8217;ve been getting just from our demo video. One of the things in particular that I&#8217;ve read several discussion on is accessibility and Cappuccino, and I wanted to share some thoughts on the topic.</p>
<p>Drew McLellan wrote <a href="http://allinthehead.com/retro/337/the-cost-of-accessibility">an interesting piece</a> outlining his concerns about the subject, but I think certain things need to be clarified. First, there&#8217;s a difference between accessibility and the availability of JavaScript. Accessibility is about enabling assistive technologies like screen readers to relay information to users with disabilities like vision impairment. JavaScript availability, on the other hand, is about whether or not a user&#8217;s browser has JavaScript enabled (or supports JavaScript at all). JavaScript availability is what people are talking about when they talk about graceful degradation. Both of these issues are important, but they need to be addressed separately.</p>
<p>Let me state the obvious: JavaScript availability is a requirement for writing an application in the browser. The reason is simple, writing a program requires a programming language, which HTML and CSS are not. To be more precise, I&#8217;m talking about an application that doesn&#8217;t rely on the server for all its logic, a truly browser based application, not a website with a dynamic back end. Not all programs should be or need to be written this way, that is something we readily acknowledge. But, some applications only make sense written like this: a presentation editor can&#8217;t hit the server on every single move or update or reposition of a slide element; a word processor can&#8217;t hit the server every time you need to type a character. I don&#8217;t believe this is a controversial statement, it&#8217;s a fundamental reality of the web. And it&#8217;s something you see not just in Cappuccino, but in any complex web application, from Google&#8217;s to Apple&#8217;s and countless others.</p>
<p>The second issue is accessibility, and I do believe its important. First, to put on my contrarian hat, you have to consider that not all applications can be made accessible. Although I could be wrong, I don&#8217;t think there&#8217;s a reasonable way to make Photoshop accessible to someone who can&#8217;t see; fundamentally it&#8217;s a visual tool. 280 Slides, for the most part, is the same (and to a large extent, Atlas may be as well). They are largely visual tools, heavily relying on visual design, drag and drop, and other mouse based metaphors. Since Cappuccino development up to this point has been driven mostly by our own needs, that may help explain why this hasn&#8217;t been a top priority for us. </p>
<p>All that aside, we absolutely want Cappuccino to be an accessible platform. Until pretty recently, this just wasn&#8217;t a possibility. Browser vendors and assistive technology vendors provided absolutely no facilities for interacting with the accessibility system. We&#8217;ve been working on Cappuccino for some time now, and I think it would be a travesty if none of the things we&#8217;ve accomplished had been done simply because there wasn&#8217;t yet a way to make them accessible. Cappuccino is pushing the edges of web development right now, and understandably some things take time to catch up. Vendors need to take their share of responsibility for the problem.</p>
<p>More recently, efforts like WAI ARIA are starting to be taken seriously enough to consider as a potential avenue for Cappuccino. Like the rest of our APIs, we have a strong foundation to build upon &#8212; Mac OS X has great support for accessibility in custom UI. I am extremely excited about integrating some of these technologies into Cappuccino. At the same time, 280 North is a three person company, developing our own products to support our business, and developing Cappuccino in the open to benefit everyone. We can&#8217;t program every feature needed in Cappuccino all at once, but that&#8217;s part of why we&#8217;re embracing open source. If people feel strongly about WAI ARIA, I encourage them to get in touch with us about helping to add support to Cappuccino. It isn&#8217;t an area we have a great deal of expertise in, but we&#8217;re happy to learn new things, and this is absolutely a problem we want to work on.</p>
<p>As for Atlas, I&#8217;m looking forward to sharing more about development status, and what it can do. We&#8217;ve got a lot of ideas, but we really love hearing what fellow developers feel is important. This is just one good example of the feedback we&#8217;ve been getting, and hopefully I&#8217;ll be able to share more in the coming months.</p>
]]></content:encoded>
			<wfw:commentRss>http://rossboucher.com/2009/02/26/accessibility-degradation-in-cappuccino/feed/</wfw:commentRss>
		<slash:comments>21</slash:comments>
		</item>
		<item>
		<title>iReddit &#8211; the official reddit iPhone App</title>
		<link>http://rossboucher.com/2009/02/15/ireddit-the-official-reddit-iphone-app/</link>
		<comments>http://rossboucher.com/2009/02/15/ireddit-the-official-reddit-iphone-app/#comments</comments>
		<pubDate>Sun, 15 Feb 2009 18:47:01 +0000</pubDate>
		<dc:creator>Ross</dc:creator>
				<category><![CDATA[Projects]]></category>
		<category><![CDATA[Technology]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[iphone]]></category>
		<category><![CDATA[ireddit]]></category>
		<category><![CDATA[reddit]]></category>
		<category><![CDATA[wil wheaton]]></category>

		<guid isPermaLink="false">http://rossboucher.com/?p=35</guid>
		<description><![CDATA[An iPhone application I wrote just got posted to the app store yesterday. iReddit (cleverly named huh?) is the official reddit client for the iPhone. I may have built the iPhone app, but they built reddit, which is the really hard part, and for that we&#8217;re all thankful.

Actually, I&#8217;ve been interested in trying out the [...]]]></description>
			<content:encoded><![CDATA[<p>An iPhone application I wrote just got posted to the app store yesterday. <a href="http://itunes.com/apps/ireddit">iReddit</a> (cleverly named huh?) is the <a href="http://www.reddit.com/iphone">official reddit client for the iPhone</a>. I may have built the iPhone app, but they built reddit, which is the really hard part, and for that we&#8217;re all thankful.</p>
<div id="attachment_36" align="alignleft" style="float:left; width:200; margin-right:10px;"><a href="http://rossboucher.com/wp-content/uploads/2009/02/img_0009.png"><img src="http://rossboucher.com/wp-content/uploads/2009/02/img_0009-200x300.png" alt="iReddit Home Screen" title="iReddit" width="200" height="300" class="size-medium wp-image-36" /></a></div>
<p>Actually, I&#8217;ve been interested in trying out the iPhone dev environment for some time. I got to talking with Alexis and thought this would be a great opportunity to build something useful, and help out our startup at the same time. All in all it was a good experience, but at times the iPhone dev process may make you want to kill yourself (and not because of the programming part). Don&#8217;t say I didn&#8217;t warn you.</p>
<p>The app itself is pretty great. You can browse the combined front page, or look at individual subreddits, and even get your own customized reddit list on the phone by logging in. Commenting, voting, and saving are all there, plus &#8220;serendipity&#8221; mode, which displays a random upcoming reddit story every time you shake the iPhone. The best part of the app is probably the reddit alien getting pissed off at slow loading pages. The effect is great.</p>
<p>So, if you haven&#8217;t already, <a href="http://itunes.com/apps/ireddit">go buy the app</a>! I&#8217;ll try and write more about the dev process in future posts, and in particular about my take on the app store and some of the things people have been complaining about.</p>
<p>Alexis has a bit of a crazy side to him, and it called him to make this commercial for the app. Hand modeling by yours truly. Still waiting to hear what <a href="http://twitter.com/wilw">Wil Wheaton</a> actually thinks of it.</p>
<p><object width="425" height="344"><param name="movie" value="http://www.youtube.com/v/jjxlEodOETU&#038;color1=0xb1b1b1&#038;color2=0xcfcfcf&#038;hl=en&#038;feature=player_embedded&#038;fs=1"></param><param name="allowFullScreen" value="true"></param><embed src="http://www.youtube.com/v/jjxlEodOETU&#038;color1=0xb1b1b1&#038;color2=0xcfcfcf&#038;hl=en&#038;feature=player_embedded&#038;fs=1" type="application/x-shockwave-flash" allowfullscreen="true" width="425" height="344"></embed></object></p>
]]></content:encoded>
			<wfw:commentRss>http://rossboucher.com/2009/02/15/ireddit-the-official-reddit-iphone-app/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>JavaScript IS a High Level Language!</title>
		<link>http://rossboucher.com/2008/12/09/javascript-is-a-high-level-language/</link>
		<comments>http://rossboucher.com/2008/12/09/javascript-is-a-high-level-language/#comments</comments>
		<pubDate>Wed, 10 Dec 2008 01:30:54 +0000</pubDate>
		<dc:creator>Ross</dc:creator>
				<category><![CDATA[Technology]]></category>
		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://rossboucher.com/?p=31</guid>
		<description><![CDATA[In response to some extended discussion via JResig, Ajaxian, and Francisco, Charles Jolley said the following:
JavaScript, on the other hand, is a high level language. It has garbage collection, lambda functions, dynamic typing, object messages, and nearly every other feature you would expect in a modern high-level language.
When you wrap JavaScript in another high-level language, you don’t free yourself [...]]]></description>
			<content:encoded><![CDATA[<p>In response to some extended discussion via <a href="http://ejohn.org/blog/javascript-language-abstractions/">JResig</a>, <a href="http://ajaxian.com/archives/you-leaked-on-my-javascript#comments">Ajaxian</a>, and <a href="http://cappuccino.org/discuss/2008/12/08/on-leaky-abstractions-and-objective-j/">Francisco</a>, Charles Jolley said the <a href="http://www.okito.net/post/63990089/ajaxian-you-leaked-on-my-javascript">following</a>:</p>
<blockquote><p>JavaScript, on the other hand, <em>is</em> a high level language. It <em>has</em> garbage collection, lambda functions, dynamic typing, object messages, and nearly every other feature you would expect in a modern high-level language.</p>
<p>When you wrap JavaScript in another high-level language, you don’t free yourself from managing low-level details; you just exchange one abstraction for another.  You pay the cost of two high-level languages without gaining any benefits for your final product.</p></blockquote>
<p>The implication here is that JavaScript is the highest level language currently imaginable; in a word, it&#8217;s perfect. Actually, the next line, which I won&#8217;t quote, warns us not to interpret that as claiming JavaScript is perfect. It then goes on to reverse course and say the only way to abstract JS further is with a UI builder.</p>
<p>But is this really the case? There&#8217;s a simple test: Can I create a language on top of JavaScript that has at least one feature not present in JavaScript? Of course, the answer is yes, and the proof is Objective-J. If there is one feature that proves this point best, it&#8217;s @import. Importing is a feature that almost every high level language offers, and yet it isn&#8217;t present in JavaScript. </p>
<p>This begs the question: couldn&#8217;t I just implement this as a feature in a native library? Yes, and no. This is a complex topic, and I don&#8217;t want to get into the specifics, but to get the asynchronous/look-ahead code importing built into Objective-J, you need to preprocess code (aka, extend the language).</p>
<p>Objective-J doesn&#8217;t just add one feature, it adds many. These include dynamic message sending (which enables features like method_missing from ruby, and which is completely different from what JavaScript does have &#8212; function calls; I&#8217;m not sure why Charles called them &#8220;object messages&#8221;), importing, and classical inheritance. Many of these features use a runtime component, called the Objective-J runtime. Most of the new syntax in Objective-J is shorthand for accessing this runtime (which is built, of course, in JavaScript). You could say that the language frees yourself from managing low-level details of the runtime that you shouldn&#8217;t need to worry about.</p>
<p>And since Objective-J is a strict superset of JavaScript, you don&#8217;t pay any cost for utilizing it. You can drop down to &#8220;pure&#8221; JavaScript at any time. You don&#8217;t even need a compiler or a special build tool to use Objective-J, since the language is written in JS and preprocesses dynamically in the browser. </p>
]]></content:encoded>
			<wfw:commentRss>http://rossboucher.com/2008/12/09/javascript-is-a-high-level-language/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Google, iPhone, and Thinking Like a Programmer</title>
		<link>http://rossboucher.com/2008/11/20/google-iphone-and-thinking-like-a-programmer/</link>
		<comments>http://rossboucher.com/2008/11/20/google-iphone-and-thinking-like-a-programmer/#comments</comments>
		<pubDate>Thu, 20 Nov 2008 19:37:01 +0000</pubDate>
		<dc:creator>Ross</dc:creator>
				<category><![CDATA[Apple]]></category>
		<category><![CDATA[Projects]]></category>
		<category><![CDATA[Technology]]></category>
		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://rossboucher.com/2008/11/20/google-iphone-and-thinking-like-a-programmer/</guid>
		<description><![CDATA[Yesterday, John Gruber declared that Google Mobile uses private iPhone APIs. Since he wrote it, it must be true, which is why TechCrunch picked up on the article this morning. Nevermind the fact that the only evidence offered by Gruber was that &#8220;there is no public API in the iPhone SDK for using the proximity [...]]]></description>
			<content:encoded><![CDATA[<p>Yesterday, John Gruber declared that <a href="http://daringfireball.net/2008/11/google_mobile_uses_private_iphone_apis">Google Mobile uses private iPhone APIs</a>. Since he wrote it, it must be true, which is why TechCrunch <a href="http://www.crunchgear.com/2008/11/20/googles-mobile-app-uses-secret-proximity-sensing-system-untruthiness/">picked up</a> on the article this morning. Nevermind the fact that the only evidence offered by Gruber was that &#8220;there is no public API in the iPhone SDK for using the proximity sensor in this way.&#8221;</p>
<p>The critical mistake Gruber makes is assuming that because there&#8217;s no documented method for trivially utilizing the proximity sensor, there must be <em>no possible way</em> to do it. This is a severe lack of imagination.</p>
<p>Programming is an exercise in creative thinking, especially when working within the context of specific platform. There are always things you, the developer, want to do but don&#8217;t seem to be able to. This has always been and will always be true. It&#8217;s the reason why plenty of desktop Mac apps use private Apple APIs, and it&#8217;s the reason why plenty of iPhone apps on the store are using undocumented APIs.</p>
<p>The essential question, then, is can what Google is doing be done without using undocumented APIs on the phone? I think it can. I spent an hour this morning trying to prove it, and came up with <a href="/downloads/proximity.zip">this iPhone app</a>.</p>
<p>To be fair, this doesn&#8217;t work as well as Google&#8217;s version, or exactly the same way. For one, I didn&#8217;t bother to program in the proximity requirement for the trigger. This is well documented, so anyone could easily add it to this project. The other way in which my method underperforms Google&#8217;s is that the phone actually has to touch your ear before it will trigger. Google&#8217;s just needs to come close to your ear. But, the code does use the proximity sensor, and it only uses the available API method for that sensor, which gives you the ability to turn it on and off. The code uses no undocumented APIs.</p>
<p>How does it work? As I mentioned, it requires you actually touch the phone to your ear. Once you do, the application receives a touchBegan event, and turns on the proximity sensor. It also makes a note that the app is in the middle of a touch sequence, and finally it fires off a timer which makes this trick work. Once the proximity sensor is turned on, it is immediately engaged because the phone is so close to your face. When the proximity sensor is engaged Cocoa turns off the touch sensor, but it doesn&#8217;t send a touchEnded message to the application. Thanks to that timer we fired, we can poll for the current number of touches on the screen. If it drops to zero, but we never saw the touchEnded message, we know we&#8217;ve triggered the proximity sensor. The project I&#8217;ve included will turn the screen yellow and play a little sound, just like the Google application. Here&#8217;s all the relevant code:</p>
<div style="text-align:left;color:#000000; background-color:#ffffff; border:solid black 1px; padding:0.5em 1em 0.5em 1em; overflow:auto;font-size:small; font-family:monospace; ">- (<span style="color:#881350;">void</span>)<span style="color:#6c0540;">touchesBegan:</span>(<span style="color:#400080;">NSSet</span> *)touches <span style="color:#6c0540;">withEvent:</span>(UIEvent *)event<br />
{<br />
    [<span style="color:#881350;">self</span> <span style="color:#6c0540;">setBackgroundColor:</span>[UIColor <span style="color:#6c0540;">redColor</span>]];<br />
    [UIApplication <span style="color:#6c0540;">sharedApplication</span>].proximitySensingEnabled = <span style="color:#881350;">YES</span>;<br />
    <br />
    _inLiveTouch = <span style="color:#881350;">YES</span>;<br />
    <br />
    [<span style="color:#881350;">self</span> <span style="color:#6c0540;">performSelector:</span><span style="color:#881350;">@selector</span>(checkTouches:) <span style="color:#6c0540;">withObject:</span>event <span style="color:#6c0540;">afterDelay:</span><span style="color:#0000ff;">0</span>];<br />
}</p>
<p>- (<span style="color:#881350;">void</span>)<span style="color:#6c0540;">touchesEnded:</span>(<span style="color:#400080;">NSSet</span> *)touches <span style="color:#6c0540;">withEvent:</span>(UIEvent *)event<br />
{<br />
    [<span style="color:#881350;">self</span> <span style="color:#6c0540;">setBackgroundColor:</span>[UIColor <span style="color:#6c0540;">greenColor</span>]];<br />
    <br />
    _inLiveTouch = <span style="color:#881350;">NO</span>;<br />
    [UIApplication <span style="color:#6c0540;">sharedApplication</span>].proximitySensingEnabled = <span style="color:#881350;">NO</span>;<br />
}</p>
<p>- (<span style="color:#881350;">void</span>)<span style="color:#6c0540;">checkTouches:</span>(UIEvent *)event<br />
{   <br />
    <span style="color:#881350;">if</span><span style="color:#003369;"> </span>(_inLiveTouch &#038;&#038; [[event <span style="color:#6c0540;">allTouches</span>] <span style="color:#6c0540;">count</span>] == <span style="color:#0000ff;">0</span>)<br />
    {<br />
        [<span style="color:#881350;">self</span> <span style="color:#6c0540;">setBackgroundColor:</span>[UIColor <span style="color:#6c0540;">yellowColor</span>]];<br />
        <span style="color:#003369;">AudioServicesPlaySystemSound</span>(_sound);<br />
        <span style="color:#881350;">return</span>;<br />
    }</p>
<p>    <span style="color:#881350;">if</span><span style="color:#003369;"> </span>(_inLiveTouch)<br />
        [<span style="color:#881350;">self</span> <span style="color:#6c0540;">performSelector:</span><span style="color:#881350;">@selector</span>(checkTouches:) <span style="color:#6c0540;">withObject:</span>event <span style="color:#6c0540;">afterDelay:</span><span style="color:#0000ff;">0.5</span>];<br />
}</div>
<p>An hour of programming, and three methods get us something relatively close to what Google is doing. I&#8217;m far from an expert in the iPhone SDK, but it only took a little bit of imagination to come up with this idea. Google has perhaps a dozen or more employees working full time on the iPhone. It&#8217;s not much of a leap to believe they figured out an even smarter trick than mine to accomplish what they wanted to do. Gruber did mention later that at least <a href="http://itunes.com/app/Note2Self">one other app</a> is doing something similar without using the proximity sensor, but was quick to point out how inferior it was to the proximity based approach.</p>
<p>Now, as it turns out, Google <em>probably is</em> using private APIs to do what they&#8217;re doing. Erica Sadun, over at Ars Technica, <a href="http://arstechnica.com/journals/apple.ars/2008/11/19/ars-investigates-does-google-mobile-use-private-apis">made a more convincing case</a>.</p>
<p>The ultimate question then, is does it matter? The reality of the situation is that there are a lot of apps doing this that have already shipped. It isn&#8217;t just Google, and it isn&#8217;t just big companies, it&#8217;s everybody. Either Apple knows this and isn&#8217;t doing anything about it, or they don&#8217;t know. Either way points to indifference. If they know, it&#8217;s obvious how not taking action is indifferent towards things, but what about if  they don&#8217;t know. In that case, it means the review process they&#8217;ve built is not designed to catch these cases. To be sure, the dynamic nature of Objective-C would make it difficult to catch all instances of runtime tomfoolery, but it&#8217;s not impossible to do so, nor would it be particularly burdensome to catch <em>most</em> of the cases. As it currently works, I believe they are only checking to see which frameworks you link against statically, and denying anyone who includes private frameworks in that list.</p>
<p>Even if Apple was deeply concerned that people were using undocumented APIs, would it be a big deal if Google was granted an exception? Gruber thinks so:</p>
<blockquote><p>
Third-party iPhone development is purportedly a level playing field. If regular developers are forced to play by the rules, but Google is allowed to use private APIs just because they’re Google, the system is rigged.
</p></blockquote>
<p>Rigged? Who said the iPhone SDK was a level playing field in the first place? Apple has never been a company that stands up for level playing fields, nor should they have to be. Every business makes business deals, partnerships, exclusive rights agreements &#8212; this is common business practice, at Apple, Google, and everywhere else in the business world. Why should the iPhone be any different? If you had billions of dollars in the bank, Apple would talk to you too.</p>
<p>This isn&#8217;t only realistic, it&#8217;s also reasonable. One of the reasons to prevent people from using undocumented APIs is not wanting applications to break between upgrades. If Apple knows every single application that will break, because it has an arrangement with the developer, it can make sure to correct the problem in advance. This obviously doesn&#8217;t scale to every developer, but it makes perfect sense to do so on a limited case by case basis. In fact, this is how Apple already behaves in the desktop world. Wil Shipley gets his bugs fixed faster than Joe the Indy Developer. Why? Because his app is popular, and because he has connections at Apple. </p>
<p>TechCrunch claimed in their article this morning that &#8220;Apple wouldn’t allow Google to use an unsupported call. It’s not in their DNA.&#8221; If anything, Apple is more likely to help Google than any other company. After all, Google provided Apple with a special version of maps for the iPhone application, and now the company refuses to license Google Maps to any other iPhone developer, even the ones willing to pay the outrageous sums of money a license costs. Google gave Apple a virtual maps monopoly for the iPhone, the least Apple can do is let them use an undocumented method here and there.</p>
]]></content:encoded>
			<wfw:commentRss>http://rossboucher.com/2008/11/20/google-iphone-and-thinking-like-a-programmer/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>iPhone Touch Events in JavaScript</title>
		<link>http://rossboucher.com/2008/08/19/iphone-touch-events-in-javascript/</link>
		<comments>http://rossboucher.com/2008/08/19/iphone-touch-events-in-javascript/#comments</comments>
		<pubDate>Tue, 19 Aug 2008 18:44:40 +0000</pubDate>
		<dc:creator>Ross</dc:creator>
				<category><![CDATA[Apple]]></category>
		<category><![CDATA[Projects]]></category>
		<category><![CDATA[Technology]]></category>
		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://rossboucher.com/2008/08/19/iphone-touch-events-in-javascript/</guid>
		<description><![CDATA[Yesterday I gave a presentation at the San Francisco JavaScript Meetup about the new JavaScript touch events API in iPhone 2.0.  I thought I&#8217;d share the slides, in case people were interested in viewing them after the fact.

I owe a great deal of thanks to Neil Roberts from SitePen, who&#8217;s post on the topic [...]]]></description>
			<content:encoded><![CDATA[<p>Yesterday I gave a presentation at the <a href="http://javascript.meetup.com/4/">San Francisco JavaScript Meetup</a> about the new JavaScript touch events API in iPhone 2.0.  I thought I&#8217;d share the slides, in case people were interested in viewing them after the fact.</p>
<p><iframe width="400" height="328" src="http://280slides.com/Viewer/?user=37&#038;name=javascript%20iphone%20events" style="border: 1px solid black; margin: 0; padding: 0;"></iframe></p>
<p>I owe a great deal of thanks to Neil Roberts from SitePen, who&#8217;s <a href="http://www.sitepen.com/blog/2008/07/10/touching-and-gesturing-on-the-iphone/">post on the topic</a> was my main source of information.  My co-founder Tom Robinson was also helpful, thanks to his <a href="http://tlrobinson.net/iphone/lighttable/">iPhone light-table</a>.</p>
<p>One of the interesting things I was able to talk about was reusing existing mouse based libraries with the iPhone by using touch events to simulate mouse events.  The basic idea behind it was to address the fact that mouse events don&#8217;t work particularly well on the phone.  It&#8217;s unpredictable when you&#8217;ll get them, if at all (you won&#8217;t if you attach only to document, for example).  Mousemove in particular doesn&#8217;t work in any meaningful way.</p>
<p>In contrast, the touch events are completely predictable and reliable (excepting the existing bugs). We can use these events to simulate the existing mouse events with a fair amount of accuracy.  In particular, when one finger is down on the screen, touchstart, touchend, and touchmove correspond nicely with mousedown, mouseup, and mousemove.  There&#8217;s some difference in the way mousemove works, since we can&#8217;t get mousemove events when the finger is not touching the screen, but this is an acceptable trade off.  It doesn&#8217;t make sense on the iPhone anyway because there&#8217;s no persistent cursor.</p>
<p>I took this jQuery based <a href="http://threedubmedia.blogspot.com/2008/08/eventspecialdrop.html">drag and drop example</a> to see if I could get it working on the iPhone without modification.  Here&#8217;s the <a href="http://rossboucher.com/iphone/">working iPhone demo</a>.  The only existing code that I modified was some CSS to make the page fit nicely on the iPhone screen, and a viewport meta tag.  The added code to get drag and drop working is really simple:</p>
<div style="text-align:left;color:#000000; background-color:#ffffff; border:solid black 1px; padding:0.5em 1em 0.5em 1em; overflow:auto;font-size:small; font-family:monospace; "><span style="color:#881350;">function</span> <span style="color:#003369;">touchHandler</span>(event)<br />
{<br />
    <span style="color:#881350;">var</span> touches = event.changedTouches,<br />
        first = touches[<span style="color:#0000ff;">0</span>],<br />
        type = <span style="color:#760f15;">&#8220;&#8221;</span>;<br />
    <br />
    <span style="color:#881350;">switch</span>(event.type)<br />
    {<br />
        <span style="color:#881350;">case</span> <span style="color:#760f15;">&#8220;touchstart&#8221;</span>: type = <span style="color:#760f15;">&#8220;mousedown&#8221;</span>; <span style="color:#881350;">break</span>;<br />
        <span style="color:#881350;">case</span> <span style="color:#760f15;">&#8220;touchmove&#8221;</span>:  type=<span style="color:#760f15;">&#8220;mousemove&#8221;</span>; <span style="color:#881350;">break</span>;        <br />
        <span style="color:#881350;">case</span> <span style="color:#760f15;">&#8220;touchend&#8221;</span>:   type=<span style="color:#760f15;">&#8220;mouseup&#8221;</span>; <span style="color:#881350;">break</span>;<br />
        <span style="color:#881350;">default</span>: <span style="color:#881350;">return</span>;<br />
    }<br />
        <br />
    <span style="color:#236e25;">//initMouseEvent(type, canBubble, cancelable, view, clickCount, <br />
</span>    <span style="color:#236e25;">//           screenX, screenY, clientX, clientY, ctrlKey, <br />
</span>    <span style="color:#236e25;">//           altKey, shiftKey, metaKey, button, relatedTarget);<br />
</span>    <br />
    <span style="color:#881350;">var</span> simulatedEvent = document.<span style="color:#003369;">createEvent</span>(<span style="color:#760f15;">&#8220;MouseEvent&#8221;</span>);<br />
    simulatedEvent.<span style="color:#003369;">initMouseEvent</span>(type, <span style="color:#881350;">true</span>, <span style="color:#881350;">true</span>, window, <span style="color:#0000ff;">1</span>, <br />
                              first.screenX, first.screenY, <br />
                              first.clientX, first.clientY, <span style="color:#881350;">false</span>, <br />
                              <span style="color:#881350;">false</span>, <span style="color:#881350;">false</span>, <span style="color:#881350;">false</span>, <span style="color:#0000ff;">0</span><span style="color:#236e25;">/*left*/</span>, null);<br />
                                                                            <br />
    first.target.<span style="color:#003369;">dispatchEvent</span>(simulatedEvent);<br />
    event.<span style="color:#003369;">preventDefault</span>();<br />
}</p>
<p><span style="color:#881350;">function</span> <span style="color:#003369;">init</span>() <br />
{<br />
    document.<span style="color:#003369;">addEventListener</span>(<span style="color:#760f15;">&#8220;touchstart&#8221;</span>, touchHandler, <span style="color:#881350;">true</span>);<br />
    document.<span style="color:#003369;">addEventListener</span>(<span style="color:#760f15;">&#8220;touchmove&#8221;</span>, touchHandler, <span style="color:#881350;">true</span>);<br />
    document.<span style="color:#003369;">addEventListener</span>(<span style="color:#760f15;">&#8220;touchend&#8221;</span>, touchHandler, <span style="color:#881350;">true</span>);<br />
    document.<span style="color:#003369;">addEventListener</span>(<span style="color:#760f15;">&#8220;touchcancel&#8221;</span>, touchHandler, <span style="color:#881350;">true</span>);    <br />
}
</div>
<p>I&#8217;ve captured the touch events and then manually fired my own mouse events to match. Although the code isn&#8217;t particularly general purpose as is, it should be trivial to adapt to most existing drag and drop libraries, and probably most existing mouse event code.  Hopefully this idea will come in handy to people developing web applications for the iPhone.</p>
<p>Update: In posting this, I noticed that calling preventDefault on all touch events will prevent links from working properly.  The main reason to call preventDefault at all is to stop the phone from scrolling, and you can do that by calling it only on the touchmove callback.  The only downside to doing it this way is that the iPhone will sometimes display its hover popup over the drag origin.  If I discover a way to prevent that, I&#8217;ll update this post.</p>
<p><strong>Second Update:</strong> I&#8217;ve found the CSS property to turn off the callout, &#8220;-webkit-touch-callout&#8221;. You can read about it in Apple&#8217;s <a href="http://developer.apple.com/DOCUMENTATION/AppleApplications/Reference/SafariCSSRef/Articles/StandardCSSProperties.html#//apple_ref/doc/uid/TP30001266-UserInterface">documentation</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://rossboucher.com/2008/08/19/iphone-touch-events-in-javascript/feed/</wfw:commentRss>
		<slash:comments>9</slash:comments>
		</item>
		<item>
		<title>Resizing TextAreas</title>
		<link>http://rossboucher.com/2008/07/28/resizing-textareas/</link>
		<comments>http://rossboucher.com/2008/07/28/resizing-textareas/#comments</comments>
		<pubDate>Tue, 29 Jul 2008 00:06:30 +0000</pubDate>
		<dc:creator>Ross</dc:creator>
				<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://rossboucher.com/2008/07/28/resizing-textareas/</guid>
		<description><![CDATA[Yesterday I was working on making a textarea element automatically resize itself to fit its content without a scroll bar.  I&#8217;ve seen this done before, so it isn&#8217;t something strictly new, but I did notice that a lot of people are doing hacks with rows/columns, so I thought I&#8217;d share my own approach.
In my [...]]]></description>
			<content:encoded><![CDATA[<p>Yesterday I was working on making a textarea element automatically resize itself to fit its content without a scroll bar.  I&#8217;ve seen this done before, so it isn&#8217;t something strictly new, but I did notice that a lot of people are doing hacks with rows/columns, so I thought I&#8217;d share my own approach.</p>
<p>In my case, I wanted a fixed minimum height, and then I wanted the box to grow as the user typed additional text.  Assuming you have a reference to your textarea, and a MIN_HEIGHT variable defined somewhere, the javascript is actually very simple:<br />
<code style="white-space: pre; font-size:70%; font-family:monaco, monospaced; line-height:1em;"></p>
<div style="text-align:left;color:#000000; background-color:#ffffff; border:solid black 1px; padding:0.5em 1em 0.5em 1em; overflow:auto;font-size:small; font-family:monospace; ">textArea.style.height = MIN_HEIGHT + <span style="color:#760f15;">"px"</span>;<br />
textArea.style.height = Math.<span style="color:#003369;">max</span>(MIN_HEIGHT, textArea.scrollHeight) + <span style="color:#760f15;">"px"</span>;
</div>
<p></code><br />
We need to do the first set because otherwise Firefox and Safari will not shrink if the user deletes text.  I should note that the textarea was styled with a fixed width in pixels, which shouldn&#8217;t be strictly necessary.</p>
<p>The real reason I wanted this auto-expanding and contracting view was actually because I wanted to use it in my own <a href="http://objective-j.org">custom scroller</a>.  For the scroller to work properly, it needs to know the size of whatever its scrolling inside of it.  The other problem with putting a textarea into my custom scroller was knowing where to scroll too.  Since textarea&#8217;s have their own caret, and since most browsers will scroll the textarea to follow the caret no matter what you set overflow to, I needed a way to know where exactly the caret was in the textarea.  </p>
<p>Both Firefox and Safari have the selectionStart and selectionEnd properties on textarea elements.  When there&#8217;s no selection, these two numbers are the same; they tell you the character index of the caret.  Strictly speaking, knowing the index of the caret isn&#8217;t enough; I need to know the vertical offset.  There&#8217;s no easy way to do this, so I reused one of the hack&#8217;s I&#8217;ve been playing around with lately.</p>
<p>What I did was create a duplicate of the textarea&#8217;s text content inside another element (a div in our case).  We make sure to style the textarea and div the same so that the rendered text would look exactly the same, except one would be editable and the other wouldn&#8217;t.  The trick is, in our new element, I surround each character with it&#8217;s own span.  Then, I can use the caret index we got before as an index into the childNode array of our div element to get a reference to the specific character we&#8217;re dealing with.  Here&#8217;s a relatively simple implementation of what I&#8217;m talking about:<br />
<code style="white-space:pre; font-size:70%; font-family:monaco; line-height: 1em;"></p>
<div style="text-align:left;color:#000000; background-color:#ffffff; border:solid black 1px; padding:0.5em 1em 0.5em 1em; overflow:auto;font-size:small; font-family:monospace; "><span style="color:#1a1aa6;">var</span> start = textArea.selectionStart,<br />
    end = textArea.selectionEnd,<br />
    imposter = document.<span style="color:#003369;">createElement</span>('div'),<br />
    referenceSpan = document.<span style="color:#003369;">createElement</span>('span'),<br />
    stringValue = textArea.value;</p>
<p><span style="color:#236e25;">//You may need to copy more than just these two styles<br />
</span>imposter.style.height = textArea.style.height;<br />
imposter.style.width  = <span style="color:#003369;">getComputedStyle</span>(textArea, <span style="color:#760f15;">""</span>).<span style="color:#003369;">getPropertyValue</span>('width');</p>
<p><span style="color:#1a1aa6;">for</span>(<span style="color:#1a1aa6;">var</span> i=<span style="color:#0000ff;">0</span>; i<start; i++)<br />
{<br />
    referenceSpan.innerHTML = stringValue.<span style="color:#003369;">charAt</span>(i).<span style="color:#003369;">replace</span>(<span style="color:#760f15;">"\n"</span>, <span style="color:#760f15;">"<br />"</span>);<br />
    imposter.<span style="color:#003369;">appendChild</span>(referenceSpan.<span style="color:#003369;">cloneNode</span>(<span style="color:#1a1aa6;">true</span>));<br />
}</p>
<p>document.body.<span style="color:#003369;">appendChild</span>(imposter);</p>
<p><span style="color:#1a1aa6;">var</span> caretOffsetTop = imposter.childNodes[start - <span style="color:#003369;">1</span>].offsetTop - imposter.offsetTop,<br />
    caretHeight = imposter.childNodes[start-<span style="color:#003369;">1</span>].offsetHeight;</p>
<p>document.body.<span style="color:#003369;">removeChild</span>(imposter);
</div>
<p></code><br />
At the end of that block we have the vertical position of the caret in the textarea (or at least an incredibly good approximation).  There are a few things I&#8217;ve glossed over; the most obvious is that if you call this on every keypress you&#8217;ve turned an O(1) operation into an O(n) operation.  </p>
<p>The enterprising individual will want to cache and and keep track of the state of the textarea rather than build from scratch, but I can tell you from personal experience that it&#8217;s a real pain, and may not be worth the effort.  For most uses, and in pretty much any version of Firefox or Safari, the above code will work well enough.  The other thing to watch out for is that many browsers won&#8217;t report the size/position of whitespace characters, so you&#8217;ll need to scan for the nearest non-whitespace character.</p>
<p>Right now this doesn&#8217;t work in Internet Explorer.  IE uses a different mechanism &#8212; document.selection.createTextRange() &#8212; to return information about the position of the caret.  Unfortunately, the character index is not one of the properties of the TextRange object.  The object does have an offsetTop property, but it seems to return the offset into the whole window, and I&#8217;m having difficulty keeping that in sync with the scrolling textarea.  If anybody has any feedback on that front, or on the hack in general, I&#8217;d like to hear it.</p>
]]></content:encoded>
			<wfw:commentRss>http://rossboucher.com/2008/07/28/resizing-textareas/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Aftermath of 280 Slides</title>
		<link>http://rossboucher.com/2008/06/19/aftermath-of-280-slides/</link>
		<comments>http://rossboucher.com/2008/06/19/aftermath-of-280-slides/#comments</comments>
		<pubDate>Thu, 19 Jun 2008 23:49:48 +0000</pubDate>
		<dc:creator>Ross</dc:creator>
				<category><![CDATA[Projects]]></category>
		<category><![CDATA[Technology]]></category>
		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://rossboucher.com/2008/06/19/aftermath-of-280-slides/</guid>
		<description><![CDATA[We launched 280 Slides two weeks ago, and it&#8217;s been a great experience. After putting five months of non stop work into it, it&#8217;s a good feeling to be able to point to it and say &#8220;That&#8217;s what I&#8217;ve been doing.&#8221; It&#8217;s also fantastic to be getting all kinds of feedback from people who like [...]]]></description>
			<content:encoded><![CDATA[<p>We <a href="http://blog.280north.com/2008/06/15/on-ramp/">launched 280 Slides</a> two weeks ago, and it&#8217;s been a great experience. After putting five months of non stop work into it, it&#8217;s a good feeling to be able to point to it and say &#8220;That&#8217;s what I&#8217;ve been doing.&#8221; It&#8217;s also fantastic to be getting all kinds of feedback from people who like (and dislike) the application. It really does help you focus on what matters to people. </p>
<p>We&#8217;ve had some great press mentions too (both <a href="http://280slides.com">Slides</a> and <a href="http://objective-j.org">Cappuccino</a>):</p>
<p><a href="http://www.techcrunch.com/2008/06/05/280-north-launches-its-online-keynote-280-slides/">TechCrunch</a><br />
<a href="http://rossboucher.com/wp-admin/post.php">Ajaxian</a><br />
<a href="http://www.tuaw.com/2008/06/15/wwdc-08-280-north/">TUAW</a><br />
<a href="http://blogs.guardian.co.uk/technology/2008/06/05/want_to_use_apples_keynote_on_a_pc_you_can_via_the_web.html">Guardian.co.uk</a></p>
<p><a href="http://iamthewalr.us/blog/2008/06/05/280-slides/">And</a> <a href="http://www.xxeo.com/archives/2008/06/05/new-web-site-in-objective-c-via-javascript.html">quite</a> <a href="http://www.indezine.com/blog/2008/06/first-look-at-280-slides.html">a</a> <a href="http://www.matthewpaulmoore.com/articles/923-bringing-sexy-back-280slides">few</a> <a href="http://log.scifihifi.com/post/37541224/ajaxian-an-interview-with-280-north-on-objective-j">blogs</a><a href="http://www.shauninman.com/archive/2008/06/06/280_slides">.</a> (<a href="http://twitter.com/chockenberry/statuses/828065292">and twitter</a>)</p>
<p>There&#8217;s also been a fair amount of confusion regarding <a href="http://www.apple.com/mobileme/">MobileMe</a> and <a href="http://sproutcore.com">SproutCore</a>.  Just to clarify, MobileMe is not based on Objective-J or Cappuccino, and 280 Slides is not based on SproutCore.  280 Slides isn&#8217;t part of MobileMe, and we have no affiliation to Apple.  Oh, and there are <a href="http://tlrobinson.net">three</a> <a href="http://tolmasky.com">of</a> <a href="http://rossboucher.com">us</a>, not two.</p>
]]></content:encoded>
			<wfw:commentRss>http://rossboucher.com/2008/06/19/aftermath-of-280-slides/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Safari&#8217;s Web Inspector</title>
		<link>http://rossboucher.com/2008/04/21/safari-web-inspector/</link>
		<comments>http://rossboucher.com/2008/04/21/safari-web-inspector/#comments</comments>
		<pubDate>Mon, 21 Apr 2008 21:12:42 +0000</pubDate>
		<dc:creator>Ross</dc:creator>
				<category><![CDATA[Apple]]></category>
		<category><![CDATA[Technology]]></category>
		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://rossboucher.com/2008/04/21/safari-web-inspector/</guid>
		<description><![CDATA[The WebKit team announced the list of participants they&#8217;ll be working with on this year&#8217;s Google Summer of Code today.  Of particular interest to me was this applicant.  Anyone who does serious web work can attest to the difficulty of debugging anything in Safari, meaning that most web developers have pretty much given [...]]]></description>
			<content:encoded><![CDATA[<p>The WebKit team <a href="http://webkit.org/blog/178/webkit-gsoc-students-announced/">announced the list of participants</a> they&#8217;ll be working with on this year&#8217;s Google Summer of Code today.  Of particular interest to me was <a href="http://code.google.com/soc/2008/webkit/appinfo.html?csaid=447F2B5EA98E00A7">this applicant</a>.  Anyone who does serious web work can attest to the difficulty of debugging anything in Safari, meaning that most web developers have pretty much given up and develop in Firefox full time.  This is such a shame, since Safari is almost universally a better browser &#8212; it&#8217;s faster, it supports more of the things I care about, and for all the reasons <a href="http://daringfireball.net/2008/04/firefox_3_safari_3">Gruber listed</a> (and more), it&#8217;s the browser I use personally.</p>
<p>The thing is, the WebKit team has known for some time that they have serious issues with debugging.  In fact, I&#8217;ve been told better debugging support is the number one requested feature.  We saw some attention paid to the issue with Drosera, but it turned out to be nothing more than lip service.  Our code brings Drosera to a halt in seconds, as do most of the complicated sites we&#8217;ve tried it on.  Safari desperately needs a profiler, stack traces, and someday step through debugging.  Even beyond advanced tools like what Drosera promised and what Firebug has, WebKit fails on some of the most basic levels.  <a href="https://bugs.webkit.org/show_bug.cgi?id=17470">This bug</a> is damning.  It should be a P1.  Any callback function (read: any AJAX request, event handler, etc.) fails to report the error it encounters.  Almost every error in our code base is reported as &#8220;undefined&#8221; by Safari.</p>
<p>Keishi, you&#8217;ve got an important job ahead of you.  You&#8217;ve been tasked with doing what might be the most important thing the WebKit project has done in a long time.  Safari has been kicking ass in pretty much every other area, but it&#8217;s ignored by web developers precisely because it&#8217;s so cruel towards them.  I wish you the best of luck in doing this project, and if you&#8217;re looking for feature requests, I&#8217;ve got at least a million.  At the top of my list?  Solve the most important limitation of Firebug &#8212; not properly recognizing anonymous (eval&#8217;d) code.  I have high hopes for what this could be by the end of summer, and I&#8217;ll definitely be following the progress.</p>
]]></content:encoded>
			<wfw:commentRss>http://rossboucher.com/2008/04/21/safari-web-inspector/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Lions in a Cage</title>
		<link>http://rossboucher.com/2008/03/23/lions-in-a-cage/</link>
		<comments>http://rossboucher.com/2008/03/23/lions-in-a-cage/#comments</comments>
		<pubDate>Mon, 24 Mar 2008 01:45:08 +0000</pubDate>
		<dc:creator>Ross</dc:creator>
				<category><![CDATA[Life]]></category>
		<category><![CDATA[Technology]]></category>
		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://rossboucher.com/2008/03/23/lions-in-a-cage/</guid>
		<description><![CDATA[Paul Graham wrote an essay last week where he compared employees of big companies to lions in a cage at the zoo.  Sort of.  

I was in Africa last year and saw a lot of animals in the wild that I&#8217;d only seen in zoos before. It was remarkable how different they seemed. [...]]]></description>
			<content:encoded><![CDATA[<p>Paul Graham wrote <a href="http://paulgraham.com/boss.html">an essay</a> last week where he compared employees of big companies to lions in a cage at the zoo.  Sort of.  </p>
<blockquote><p>
I was in Africa last year and saw a lot of animals in the wild that I&#8217;d only seen in zoos before. It was remarkable how different they seemed. Particularly lions. Lions in the wild seem about ten times more alive. They&#8217;re like different animals. And seeing those guys on their scavenger hunt was like seeing lions in a zoo after spending several years watching them in the wild.
</p></blockquote>
<p>Technically, Paul is comparing the startling impact of seeing lions in a cage after seeing them in the wild to his experience seeing these employees (&#8216;those guys on their scavenger hunt&#8221;) after spending the last three years watching founders at Y Combinator.  Nevertheless, the article (and this quote in particular) caused quite the <a href="http://www.codinghorror.com/blog/archives/001080.html">controversy</a> <a href="http://www.tonywright.com/2008/reading-the-lines-not-between-them-pg-coding-horror/">around</a> <a href="http://kevin.scaldeferri.com/blog/2008/03/23/ZooVsSavannah.html">the</a> <a href="http://www.paulgraham.com/bossnotes.html">Internet</a> (or at least around the tiny subset of the Internet that reads Paul&#8217;s essays, myself included).  </p>
<p>It&#8217;s not hard to read that last sentence and interpret it as a claim that working for a big company is like being an animal in a cage.  I don&#8217;t think it was Paul&#8217;s intention to say exactly that, but even if it were, I think the point is immaterial to the essay as a whole.  It is, at its worst, an exaggeration to prove a point, something I think we can all admit to doing from time to time (indeed it&#8217;s something that great writers have always done).  </p>
<p>The central thesis of the essay is that being an employee is harmful to individual programmers, and that being a startup founder is a better way to live.  In fact, he states this explicitly:</p>
<blockquote><p>
Watching employees get transformed into founders makes it clear that the difference between the two is due mostly to environment—and in particular that the environment in big companies is toxic to programmers.
</p></blockquote>
<p>It seems to me that Jeff Atwood&#8217;s (and others) primary argument is that some employees have actually enjoyed working for big companies, himself included, and Paul is thus making a generalization that is not true.  But Paul makes no claim about employees being unhappy.  Though he doesn&#8217;t address the topic directly, he sets up the entire essay by saying that he <em>isn&#8217;t</em> talking about some special property of founders, he believes there is something missing from the life of an employee.  The absence of something you don&#8217;t even know you&#8217;re missing is hardly likely to make you unhappy on its own.</p>
<p>When I left Apple, it was not because I was unhappy.  I was working with phenomenal individuals on an interesting set of problems.  I left because I was excited about the potential of <a href="http://280north.com">our company</a>.  And despite having worked in a great environment, at an amazing company (Apple was my dream job), I feel that all the things Paul said about founders at Y Combinator ring true.  I am definitely &#8220;more worried and happier at the same time.&#8221;  So is <a href="http://daringfireball.net/linked/2008/march#fri-21-graham">John Gruber</a>.  When I had lunch with my old team on Friday, at least one person mentioned noticing the change as well. </p>
<p>I think Paul&#8217;s food analogy was a much better one to illustrate the point.  There is plenty of science to back up the claim that most of the food we eat is unhealthy (and I&#8217;m just as guilty as anyone else), however the position is still controversial.  People who avoid highly processed foods, high fructose corn syrup, refined sugar, white flour, and lots of red meat are generally healthier.  These people will tell you that they are happier, and more active, and that it&#8217;s directly related to what they eat.  Yet these people are also ridiculed by the majority as fringe environmentalists, lunatics, or hippies.  Most people will live their entire life eating what everyone else does and will be perfectly happy doing so, but until you&#8217;ve actually gone out and changed your lifestyle and started eating &#8220;like a hippy,&#8221; you can&#8217;t possibly know whether or not you would feel <em>better</em> than you already do.</p>
<p>Eating like a hippy isn&#8217;t for everyone and neither is starting a startup, but a lot more people would thrive in a startup environment than you think, just as a lot more people really would feel better eating like a hippy.  Not everyone will be convinced by Paul&#8217;s essay, and that&#8217;s okay.  There are parts I disagree with as well, in particular with respect to getting some experience at a company before starting your own.  As a whole, though, the essay is consistent with what I&#8217;ve experienced at Y Combinator, and other founders I&#8217;ve talked to agree.</p>
]]></content:encoded>
			<wfw:commentRss>http://rossboucher.com/2008/03/23/lions-in-a-cage/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>
