<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/atom10full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><feed xmlns="http://www.w3.org/2005/Atom" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0">
	<title>Kevin McMahon</title>
	
	<link href="http://www.kevfoo.com/" />
	<updated>2013-05-22T19:41:44-05:00</updated>
	<id>http://www.kevfoo.com</id>
	<author>
		<name>Kevin McMahon</name>
		<email>kevin@kevfoo.com</email>
	</author>
	
	<atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/atom+xml" href="http://feeds.feedburner.com/kevfoo" /><feedburner:info uri="kevfoo" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><link rel="license" type="text/html" href="http://creativecommons.org/licenses/by-nc-sa/3.0/" /><entry>
		<title>#holoyolo</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/VHI8uerMxqI/" />
		<updated>2013-05-22T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2013/05/#holoyolo</id>
		<category term="google" />
		<category term="androiddev" />
		<category term="androiddesign" />
		<category term="android" />
		<category term="holo" />
		<content type="html">&lt;p&gt;&lt;a href="http://teespring.com/holoyolo"&gt;&lt;img src="http://cache.kevfoo.com/2013/05/holoyolo_tshirt.jpg" title="#holoyolo T-Shirt" alt="holoyolo_tshirt" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;What started as a tongue-in-cheek reference to the wave of apps finally being updated to align with Android's Holo design guidelines became a rallying cry at Google I/O this year. The &lt;a href="https://plus.google.com/s/%23holoyolo"&gt;#holoyolo&lt;/a&gt; hashtag made its way onto more than a few slides during the sessions last week and now it has found its way onto a &lt;a href="http://teespring.com/holoyolo"&gt;t-shirt&lt;/a&gt;. So any of you Android developers or designers out there looking for a cheeky way to induce a conversation about getting your Android app to adhere to the Holo guidelines look no further. This is the t-shirt for you.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;&lt;a href="http://teespring.com/holoyolo"&gt;Order at Teespring.com, $15&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/VHI8uerMxqI" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2013/05/%23holoyolo/</feedburner:origLink></entry>
	
	<entry>
		<title>Google I/O 2013 Recap</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/8LA9rQBlpzA/" />
		<updated>2013-05-21T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2013/05/Google-IO-2013-Recap</id>
		<category term="google" />
		<category term="io" />
		<category term="io13" />
		<category term="android" />
		<category term="conference" />
		<content type="html">&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2013/05/google_io_640_480.jpg"&gt;&lt;img src="http://cache.kevfoo.com/2013/05/google_io_640_480.jpg" title="Google I/O 2013 Logo" alt="google_io_640_480" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Last week I had the pleasure of attending this year's Google I/O. Before I got too far removed from the conference I thought I would try to capture my impressions and thoughts about last week.&lt;/p&gt;

&lt;h1&gt;Keynote&lt;/h1&gt;

&lt;p&gt;The keynote clearly wasn't as tight as WWDC keynotes and frankly not as cohesive as past I/O conferences. Lots of bits were spilled last week in the aftermath, and I will spare you a retread of the common complaints. I do think though that a majority of the problems stemmed from the lack of a unifying theme or major tent-pole announcement. It is tough to build a substantive keynote around the smaller, more strategic moves Google announced. That being said, I cannot argue with the complaints about the "blocking and tackling" problems Google had during the keynote especially at a conference this big.&lt;/p&gt;

&lt;h1&gt;Android Announcements&lt;/h1&gt;

&lt;p&gt;When the keynote came and went without an official Android bump to the API level, many took that as Google wavering on their commitment to the platform. Watching the keynote live I had the opposite impression, and the subsequent Android sessions during the week reaffirmed that.&lt;/p&gt;

&lt;p&gt;The &lt;a href="http://developer.android.com/google/play-services/index.html"&gt;Google Play Services&lt;/a&gt; and the r13 &lt;a href="http://developer.android.com/tools/extras/support-library.html"&gt;Android Support Library&lt;/a&gt; UI enhancements showed us how Google plans to curb the fragmentation issues which have plagued the platform. By packaging these enhancements in libraries that are compatible back to Froyo and immediately available for integration, Google enabled developers to get these new features and services into the hands of users immediately. This eliminates the dependency Google had previously on hand-set manufactures to integrate new Android releases on their current and older devices.&lt;/p&gt;

&lt;p&gt;Many have questioned the long term viability of the Android platform for Google as companies like Amazon and Samsung seek ways to circumvent or minimize Google's influenence on their products. The approach that Google adopted has provided a way forward that serves their needs as well as developers. That is a big deal.&lt;/p&gt;

&lt;h1&gt;Comparison to WWDC&lt;/h1&gt;

&lt;p&gt;The content and variety of sessions at both conferences is excellent. On the whole, WWDC's sessions appeared to be more polished and rehearsed when compared to the I/O sessions. I found the I/O sessions tended to be a little more light-hearted and included more variety in the session structure (fireside chats, interactive labs) which added to the enjoyment of the sessions and kept the sessions from becoming monotonous. Both conferences provide a tremendous amount of access to the engineering teams directly working on the frameworks and services developers interact with on a daily basis. These opportunities for interaction are easily the most valuable parts of each conference. While the Apple labs at WWDC predominantly allowed for one-on-one interaction with their engineers, Google made their engineers available in an Office Hours setting that had the engineers holding court for small groups around white boarded areas in the conference hall. If you had very specific questions, the WWDC labs could not be beat for access and personal attention. If you were interested in picking up some tips and inside scoop about your favorite Google developer topics, then the I/O office hours are great.&lt;/p&gt;

&lt;p&gt;My biggest gripes about I/O are mainly with the logistics and the infrastructure at the conference. The most popular talks were being held in rooms that could have easily been filled if they were four times the size. The bigger tracks like Android and Chrome could have benefitted from being clustered on one floor near each other instead of being spread over two. That would've made bouncing between sessions easier and eased up the congestion around the escalators and the other traffic hotspots on the floors. The session rooms themselves were stuffy and hot during the talks and especially so in the popular sessions which typically had crowds sitting along the walls and in the aisles. While the range of these complaints range from the minor (too crowded at times) to major (uncomfortably hot rooms) annoyancess they still detract from an otherwise great conference experience. The best thing about these issues are that they fixable. Hopefully Google will make some changes to eliminate these issues from future conferences.&lt;/p&gt;

&lt;h1&gt;External Conference Activities&lt;/h1&gt;

&lt;p&gt;The best parts of conferences are social interactions and Google I/O was no different. I kicked off the week at the &lt;a href="http://meatup.io"&gt;Meatup.io&lt;/a&gt;, made my way out to Twitter for their Mobile Showcase lightning talks and capped the week off by going to a meetup-style talk on Android testing at a local startup. It was great to meet so many great developers and engineers at these events and it was nice to be able to thank so many of the project creators and maintainers in person for their contributions to Android's open-source community.&lt;/p&gt;

&lt;h1&gt;Summary&lt;/h1&gt;

&lt;p&gt;I had a fantastic time at Google I/O. I'm still chewing on and trying to process all the great content, conversations, and code that I was exposed to last week. I highly recommend Google I/O, and if you are fortunate to get an opportunity to attend a future event, I strongly urge you to go. Being around 6,000 passionate and excited developers is an amazing way to spend a week learning and exploring new technologies and services.&lt;/p&gt;

&lt;h1&gt;Favorite Sessions&lt;/h1&gt;

&lt;h2&gt;Android&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.youtube.com/watch?v=yhv8l9F44qo"&gt;Volley: Easy, Fast Networking for Android&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.youtube.com/watch?v=XpqyiBR0lJ4"&gt;Structure in Android App Design&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.youtube.com/watch?v=qlrKh-L4bqU"&gt;Taking Advantage of Android Platform Features&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.youtube.com/watch?v=LCJAgPkpmR0"&gt;The New Android SDK Build System&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h2&gt;Non Android&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://youtu.be/r-VL7NKJqcs"&gt;The Freebase APIs: Tapping into Google's Knowledge Graph&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;Gamestorming&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.youtube.com/watch?v=z2exxj4COhU"&gt;Cognitive Science and Design&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/8LA9rQBlpzA" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2013/05/Google-IO-2013-Recap/</feedburner:origLink></entry>
	
	<entry>
		<title>That Conference 2013</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/hOxG6wMuxrg/" />
		<updated>2013-05-09T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2013/05/That-Conference-2013</id>
		<category term="android" />
		<category term="mobile" />
		<category term="apps" />
		<category term="code" />
		<category term="thatconference" />
		<category term="redpoint" />
		<category term="conference" />
		<category term="speaking" />
		<content type="html">&lt;p&gt;&lt;a href="http://www.thatconference.com/?s=badge"&gt;&lt;img alt="That Conference" border="0" src="http://www.thatconference.com/Images/SiteBadges/440w.jpg?s=badge" width="440" height="300" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I am excited and honored to be speaking at &lt;a href="http://www.thatconference.com/Sessions/session_1064"&gt;That Conference&lt;/a&gt; again this August in the Wisconsin Dells. That Conference will have multiple tracks for &lt;a href="http://www.thatconference.com/sessions#mobile"&gt;mobile&lt;/a&gt;, &lt;a href="http://www.thatconference.com/sessions#web"&gt;web&lt;/a&gt; and &lt;a href="http://www.thatconference.com/sessions#cloud"&gt;cloud&lt;/a&gt; developers as well as an interesting &lt;a href="http://www.thatconference.com/sessions#other"&gt;other&lt;/a&gt; track this year.&lt;/p&gt;

&lt;p&gt;I'll be sharing some of the hard-won Android tips and best-practices that I have collected over the past few years while building and shipping apps for clients. Hope to see you there in August!&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/hOxG6wMuxrg" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2013/05/That-Conference-2013/</feedburner:origLink></entry>
	
	<entry>
		<title>Setting Up Motorola ET1 for Android Development</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/WfBRv9SHagc/" />
		<updated>2012-10-12T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/10/setting-up-motorola-et1-for-android-development</id>
		<category term="android" />
		<category term="mobile" />
		<category term="motorola" />
		<category term="et1" />
		<category term="development" />
		<category term="osx" />
		<category term="adb" />
		<content type="html">&lt;p&gt;Getting ADB to recognize the &lt;a href="http://www.motorola.com/Business/US-EN/Business+Product+and+Services/Tablets/ET1+Enterprise+Tablet_US-EN"&gt;Motorola ET1&lt;/a&gt; took longer than I'd like so I'm posting this with the hope that it'll help others who find themselves in a similar spot.&lt;/p&gt;

&lt;p&gt;Like most Android-based devices, developers need to enable USB debugging on the device by toggling a setting in the developer section of the settings app. However, with the ET1, developers also need to add the device's vendor id (0x05E0) to the &lt;em&gt;~/.android/adb_usb.ini&lt;/em&gt; file or else the device won't be detected or visible to ADB.&lt;/p&gt;

&lt;p&gt;Once the vendor id has been added, kill and restart the ADB server. After ADB starts back up, the ET1 should now be listed in the ADB device list and able to be deployed to.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/WfBRv9SHagc" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/10/setting-up-motorola-et1-for-android-development/</feedburner:origLink></entry>
	
	<entry>
		<title>Favorites from August 2012</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/hmyjMD8MlR0/" />
		<updated>2012-08-31T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/08/Favorites-from-August-2012</id>
		<category term="links" />
		<category term="2012" />
		<content type="html">&lt;p&gt;A collection of some of my favorite links, tweets and quotes from August. While these aren't a comprehensive look at or summary of August 2012, they do capture the things that I found interesting, thought provoking, and/or cool over the past month.&lt;/p&gt;

&lt;h1&gt;Favorite Links&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.360cities.net/image/curiosity-rover-martian-solar-day-2#172.65,10.74,61.5"&gt;Mars Curiosity Panorama Photo&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.theatlantic.com/technology/archive/2012/07/the-speed-of-sound-is-too-slow-for-olympic-athletes/260413/#.UBlbWYJWZ5c.twitter"&gt;The Speed of Sound is Too Slow For Olympic Athletes&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://animatedpizzagifs.com/"&gt;Animated Pizza Gifs&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.economist.com/blogs/democracyinamerica/2012/08/infrastructure?fsrc=scn/tw/te/bl/comingapart"&gt;Infrastructure -
Coming apart at the seams&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://blog.grammarly.com/"&gt;Grammarly&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.theverge.com/gaming/2012/8/21/3258225/nintendo-power-magazine-to-cease-publication-after-24-years"&gt;RIP Nintendo Power&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://kottke.org/12/08/feynman-diagram-sculptures-by-edward-tufte"&gt;Feynman diagram sculptures by Edward Tufte&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://reason.com/archives/2012/08/20/the-wrong-side-absolutely-must-not-win"&gt;The wrong side must absolutely not win&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://therapboard.com/"&gt;The Rap Board&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.jest.com/video/186274/if-movies-had-crappy-fonts"&gt;If Movies Had Crappy Fonts&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://mapbox.com/blog/2012-08-26-mapping-mars/"&gt;Mapping Mars with Open Planetary Data&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://99u.com/videos/7185/Tony-Fadell-On-Setting-Constraints-Ignoring-Experts-Embracing-Self-Doubt"&gt;Tony Fadell: On Setting Constraints, Ignoring Experts &amp;amp; Embracing Self-Doubt&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;Favorite Quotes&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;When you say "I seen," I assume you won't finish that sentence with "the inside of a book." -- &lt;a href="http://24.media.tumblr.com/tumblr_m8hi2xcquD1r5j6uso1_500.png"&gt;someecards&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/hmyjMD8MlR0" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/08/Favorites-from-August-2012/</feedburner:origLink></entry>
	
	<entry>
		<title>Favorites from July 2012</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/vpj0OUNDxUw/" />
		<updated>2012-07-31T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/07/Favorites-from-July-2012</id>
		<category term="links" />
		<category term="2012" />
		<content type="html">&lt;p&gt;A collection of some of my favorite links, tweets and quotes from July. While these aren't a comprehensive look at or summary of July 2012, they do capture the things that I found interesting, thought provoking, and/or cool over the past month.&lt;/p&gt;

&lt;h1&gt;Favorite Links&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.youtube.com/watch?v=AXUiyK1olZ8"&gt;Amazing Tiny Wings 2 Trailer&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://drunks-and-lampposts.com/2012/06/13/graphing-the-history-of-philosophy/"&gt;Graphing the History of Philosopy&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.getkempt.com/the-code/the-phone-stack.php"&gt;The Phone Stack&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.businessweek.com/articles/2012-07-05/just-shazam-it"&gt;Just Shazam It&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.openculture.com/2012/07/alan_watts_and_his_zen_wisdom_animated_by_creators_of_south_park.html"&gt;Alan Watts and His Zen Wisdom Animated by Creators of South Park&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://allentucker.com/pay-too-much/"&gt;Pay too much&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.thisiscolossal.com/2012/07/animal-sculptures-made-from-reclaimed-household-objects/"&gt;Animal sculptures made from reclaimed household objects&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.pushing-pixels.org/2012/07/25/the-usability-of-radial-menus.html"&gt;The Usability of Radial Menus&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;Favorite Quotes&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;"No SciFi author foresaw this: we are building clans around languages we speak to the Machine.” -- &lt;a href="https://twitter.com/mraleph/status/225587192427327488"&gt;@mraleph&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;"It's important to take a moment to reflect on how fortunate we are that those alien spaceships were compatible with Jeff Goldblum's laptop." -- &lt;em&gt;&lt;a href="https://twitter.com/gavinspeiller/status/220526998437638147"&gt;@gavinspeiller&lt;/a&gt; on July 4th&lt;/em&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/vpj0OUNDxUw" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/07/Favorites-from-July-2012/</feedburner:origLink></entry>
	
	<entry>
		<title>Nexus 7 Quick Thoughts</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/KV2Ajylj32g/" />
		<updated>2012-07-17T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/07/Nexus-7-Quick-Thoughts</id>
		<category term="android" />
		<category term="nexus 7" />
		<category term="nexus" />
		<category term="google" />
		<category term="tablet" />
		<category term="review" />
		<content type="html">&lt;p&gt;A few quick initial impressions of the &lt;a href="https://play.google.com/store/devices/details?id=nexus_7_8gb"&gt;Nexus 7&lt;/a&gt;.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;A legitimate Android tablet has finally been released. It is the best Android tablet on the market.&lt;/li&gt;
&lt;li&gt;Jelly Bean is definitely "buttery".&lt;/li&gt;
&lt;li&gt;Touch is very responsive in Jelly Bean. &lt;em&gt;Big&lt;/em&gt; improvement over previous Android devices/versions.&lt;/li&gt;
&lt;li&gt;The Kindle Fire is comically bad and outdated compared to it.&lt;/li&gt;
&lt;li&gt;The build quality is ok. Doesn't feel plastic-y like the Samsung products. Not a fan of the faux leather back.&lt;/li&gt;
&lt;li&gt;Feels like a big phone.&lt;/li&gt;
&lt;li&gt;Seems like resolution/size will require better fluidity from apps. Devs will definitely have to account for more screen real estate.&lt;/li&gt;
&lt;li&gt;Not sold on the 7" form factor but I think I'll be in the minority.&lt;/li&gt;
&lt;/ol&gt;


&lt;p&gt;Overall I'm pretty impressed with the Nexus 7. Seems like the software finally caught up with the hardware and, judging by the buzz around the product, the affordable price will make this a popular choice for those consumers looking for a tablet.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/KV2Ajylj32g" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/07/Nexus-7-Quick-Thoughts/</feedburner:origLink></entry>
	
	<entry>
		<title>Core Location : The Missing Details</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/1DSbuZQfDMo/" />
		<updated>2012-07-05T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/07/Core-Location-The-Missing-Details</id>
		<category term="ios" />
		<category term="core location" />
		<category term="mapkit" />
		<category term="wwdc" />
		<category term="apple" />
		<category term="location services" />
		<category term="geofencing" />
		<category term="region monitoring" />
		<content type="html">&lt;p&gt;My primary objective at WWDC this year was to find answers to Core Location questions I had and develop some intuition about how the framework works underneath the hood. Armed with some questions and a small sample app illustrating some of the bugs I found, I set out for the one Core Location lab being run during the week. These "office hour" style labs offer developers an opportunity to talk directly with the Apple engineers who work on these frameworks, and after getting paired up with one of the more senior Core Location guys, I was blown away by how valuable these sessions can be. I was able to resolve several  issues and had  a bunch of questions answered while also picking up a few tips and tricks to use in future apps. The amount of knowledge and insight shared during my relatively short session was invaluable.&lt;/p&gt;

&lt;p&gt;While I can't share everything I learned in the lab due to the NDA covering iOS 6 updates and features, I did collect non- iOS 6 specific concepts which I can share with you. Much of the information isn't documented even though it helps paint a fuller picture of how Core Location works. During my time in the lab, two things became clear: quality of the location services can be significantly impacted by variations in environment and hardware and that Apple engineers are still actively iterating and improving Core Location. I didn't get a straight answer as to why they are reluctant to publicly share or document some of this information, but I would not be surprised if these types of things were a factor.&lt;/p&gt;

&lt;p&gt;Finally, this information was collected from some notes scribbled on paper during my lab session and a brain dump I did into nvAlt immediately following the meeting to get whatever didn't make it on the page. I am reasonably confident that what I captured in my notes is legit and valid information, but it is entirely likely that I misheard, misinterpreted, or misunderstood something. Caveat Emptor.&lt;/p&gt;

&lt;h2&gt;Region Monitoring Information:&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;The &lt;strong&gt;minimum region radius size is 100m&lt;/strong&gt;. Core Location will allow you to set a radius value smaller than 100m for a CLRegion, but internally the framework will treat the region as if its radius was 100m.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The &lt;strong&gt;maximum number of regions that can be monitored at one time is 20&lt;/strong&gt;. This is not documented anywhere, but if you try to register for more than 20 regions, you will get an error indicating that you can't add any more regions. One technique that is used to get around this cap is to load and unload regions based on your current location and using significant location change notifications to evaluate when old regions need to be removed and updated with regions closer to the user's current location. Keep in mind that adding and removing regions does take some power, so it is something that you want to do judiciously.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Regions fall into three categories&lt;/strong&gt;. Depending on what category the registered region falls into affects the time it takes for Core Location to trigger the delegate callbacks.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Fine Region (&lt;strong&gt;0 - 150m&lt;/strong&gt;)

&lt;ul&gt;
&lt;li&gt;With the floor of 100m this category's range is effectively 100-150m.&lt;/li&gt;
&lt;li&gt;For regions this size &lt;strong&gt;performance is heavily dependent on the location-related hardware&lt;/strong&gt; in the devices. The iPhone 4S, unsurprisingly, has the best hardware. Some iPads and all iPod Touches don't have cellular radios. All these types of scenarios should be considered during development.&lt;/li&gt;
&lt;li&gt;The amount of time that it takes Core Location to detect and call the appropriate delegate method is roughly &lt;strong&gt;2-3 minutes&lt;/strong&gt; on average after the region boundary has been crossed.&lt;/li&gt;
&lt;li&gt;Some developers have figured out independently that smaller regions would see quicker callbacks and would cluster smaller regions to cover one large area to improve region crossing notifications. This was frowned upon by the Apple engineer as this type of solution uses more resources/power than monitoring just the single large region, but it is a viable alternative if you need the quickest possible updates. Apple is aware of this, and they are continually trying to minimize the time that elapses until Core Location invokes the delegate methods.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;"Normal" Region (&lt;strong&gt;150m - 7km&lt;/strong&gt;)

&lt;ul&gt;
&lt;li&gt;Core Location &lt;strong&gt;can take as long as 15 minutes&lt;/strong&gt; to invoke the delegate methods, but it is usually less.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Response time improves significantly with increased user interaction&lt;/strong&gt; with the device. Core Location tries to minimize power consumption, so it doesn't accelerate battery drain and  tries to piggyback on other activities to check location. A device that is actively being used to browse the web or send text messages is more likely to have Core Location checking for updates than a device that is idle in standby mode.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;"Huge" Region (&lt;strong&gt;7km+&lt;/strong&gt;)

&lt;ul&gt;
&lt;li&gt;This was referred to as the "1/3 of the earth" region. Outside of its mention and confirmation that category of region exists, not much else was said about it.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Regions are not registered for instantaneously&lt;/strong&gt;. If you register for a region and then immediately enter/exit the region, then it won't get registered properly. The recommended suggested wait time was 10s which is helpful to know when testing.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Bugs prevented the start/stop watching region callbacks from being invoked in iOS 5. The callbacks do not work properly in the simulator and only work correctly on some hardware devices. This appears to be fixed in iOS 6.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h2&gt;Other Core Location Tidbits&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Significant location change&lt;/strong&gt; (SLC) updates will not fire unless &lt;strong&gt;5 minutes&lt;/strong&gt; elapsed and a change of &lt;strong&gt;500m&lt;/strong&gt; occurred since the last update.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;If you &lt;strong&gt;stop and then start registering for SLC notifications, there are no guarantees that it will fire immediately&lt;/strong&gt;. Apparently enough people thought this worked and/or tried this that Apple changed how Core Location behaves and now a cached value (if Core Location has one) will be returned on the subsequent firing.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;You can tell the source of your location information by observing the blue location dot used by MapKit. A &lt;strong&gt;pulsing dot means GPS&lt;/strong&gt; (&lt;a href="http://cache.kevfoo.com/2012/07/bluedot_gps.png"&gt;example&lt;/a&gt;) and a &lt;strong&gt;static dot means cell/wifi&lt;/strong&gt; (&lt;a href="http://cache.kevfoo.com/2012/07/bluedot_cellwifi.png"&gt;example&lt;/a&gt;). This is not documented anywhere officially and apparently a lot of Apple engineers don't recognize/notice the difference.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Core Location quality/performance varies substantially based on where you are&lt;/strong&gt;. In a high density area like a city, the device will pull less data and use less resources than if you're in a sparsely populated area.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;Core Location piggy backs on other user interactions&lt;/strong&gt; to do most of its updating. The more opportunities it has to check / update location, the better the response time.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;The mocked location data that is provided to the &lt;strong&gt;simulator always appears to be coming from GPS&lt;/strong&gt;. You can't simulate the behavior that the cellular or wifi sources provide or simulate what happens when the GPS source is sketchy. In prior iOS releases, region monitoring relied heavily (exclusively?) on the location data provided by cell towers to operate, but improvements to both the algorithms and simulator should mitigate any of these issues.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/1DSbuZQfDMo" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/07/Core-Location-The-Missing-Details/</feedburner:origLink></entry>
	
	<entry>
		<title>Chicago Alt.Net Amazon Web Services</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/1AatNyn8Pt8/" />
		<updated>2012-07-04T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/07/chicago-alt-net-amazon-web-services-talk</id>
		<category term="presentation" />
		<category term="slides" />
		<category term="amazon" />
		<category term="web services" />
		<category term="aws" />
		<category term="amazon web services" />
		<category term="alt.net" />
		<category term="cloud" />
		<category term="saas" />
		<category term="paas" />
		<category term="iaas" />
		<category term="ec2" />
		<category term="s3" />
		<category term="dotnet" />
		<content type="html">&lt;p&gt;In June I had the pleasure to speak at the &lt;a href="http://chicagoalt.net"&gt;Chicago Alt.Net&lt;/a&gt; meetup about &lt;a href="http://aws.amazon.com"&gt;Amazon Web Services&lt;/a&gt;. The talk covered the basics of cloud services, provided a high-level overview of how Amazon's web services work and showed how easy it was to integrate AWS into a project via the .Net SDK that Amazon provides. For some of the attendees it was their first technical look at the platform. I hope that they found the talk informative and piqued their interest enough to explore the platform further.&lt;/p&gt;

&lt;script async class="speakerdeck-embed" data-id="4ff41794a4fa25001f004724" data-ratio="1.3333333333333333" src="//speakerdeck.com/assets/embed.js"&gt;&lt;/script&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/1AatNyn8Pt8" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/07/chicago-alt-net-amazon-web-services-talk/</feedburner:origLink></entry>
	
	<entry>
		<title>Favorites from June 2012</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/j0bjgf-9DbY/" />
		<updated>2012-06-30T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/06/Favorites-from-June-2012</id>
		<category term="links" />
		<category term="2012" />
		<content type="html">&lt;p&gt;A collection of some of my favorite links, tweets and quotes from June. While these aren't a comprehensive look at or summary of June 2012, they do capture the things that I found interesting, thought provoking, and/or cool over the past month.&lt;/p&gt;

&lt;h1&gt;Favorite Links&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.lettersofnote.com/2011/10/dejobbed-bewifed-and-much-childrenised.html"&gt;Dejobbed, bewifed and much childrenised&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://designtaxi.com/news/352664/Simplistic-Illustrations-Of-Negative-Space/"&gt;Simplistic Illustrations of Negative Space&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.fastcoexist.com/1679873/a-cheap-accurate-cancer-sensor-created-by-a-15-year-old?accept-encoding=none"&gt;A cheap and accurate cancer sensor created by a 15 year old.&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://kottke.org/12/06/frida-kahlo-rocking-daft-punk"&gt;Frida Kahlo Rocking Daft Punk&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.happyplace.com/16428/newspaper-describes-nickelback-concert-and-hilarious-alternatives-funny"&gt;Newspaper artfully describes upcoming Nickelback concert and hilarious alternatives to it.&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.quickmeme.com/meme/3prrs3/"&gt;Scumbag Steve describes the Ricketts Family&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://coderwall.com/p/euwpig?i=3&amp;amp;p=1&amp;amp;t=git"&gt;A better git log&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://visual.ly/10-artists-10-years-color-palettes"&gt;10 Artists, 10 Years : Color Palettes&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://grist.org/list/gza-and-neil-degrasse-tyson-team-up-on-a-hip-hop-record-about-science/"&gt;GZA and Neil de Grasse Tyson to team up on a hip-hop science album&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.visionmobile.com/product/developer-economics-2012/"&gt;Developer Economics 2012 : The New Mobile App Economy&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.lettersofnote.com/2012/06/my-mother-declared-my-bedroom-disaster.html"&gt;My mother declared my bedroom a disaster area.&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.boston.com/bigpicture/2012/06/national_geographic_traveler_m.html"&gt;2011 National Geographic Traveler Photo Contest Winners&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.thisiscolossal.com/2012/06/digitally-assembled-paintings-by-russ-mills/"&gt;Digitally Assembled Paintings&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://twitpic.com/a1miep"&gt;Great moments in tech support history&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.buzzfeed.com/gavon/the-internet-responds-to-supreme-court-ruling-on-o?sub=1644827_399363"&gt;Chief Justice John Roberts #YOLO&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://people.csail.mit.edu/mrub/vidmag/"&gt;Eulerian Video Magnification framework that can visualize the human pulse.&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.niemanlab.org/2012/06/theres-no-such-thing-as-an-objective-filter/"&gt;There’s no such thing as an objective filter: Why designing algorithms that tell us the news is hard&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;Favorite Quotes&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;"&lt;a href="http://news.ycombinator.com/item?id=4178401"&gt;EC2 comes with a free Chaos Monkey service. It's called EC2.&lt;/a&gt;" -- &lt;em&gt;pjscott via Hacker News&lt;/em&gt;&lt;/li&gt;
&lt;li&gt;"Never attribute to stupidity that which is adequately explained by process." -- &lt;a href="https://twitter.com/ftrain/status/213341347883651072"&gt;Paul Ford&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;"We are cups, constantly and quietly being filled. The trick is, knowing how to tip ourselves over and let the beautiful stuff out." -- Ray Bradbury &lt;em&gt;RIP&lt;/em&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/j0bjgf-9DbY" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/06/Favorites-from-June-2012/</feedburner:origLink></entry>
	
	<entry>
		<title>Android Crash Course</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/G0Nbj_mSOjc/" />
		<updated>2012-06-22T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/06/Android-Crash-Course</id>
		<category term="android" />
		<category term="development" />
		<category term="crash course" />
		<category term="apps" />
		<content type="html">&lt;p&gt;One the main goals of my current client engagement was to help a team of talented developers come up to speed and become proficient with the Android platform. A key component of the approach I employed was to hold a weekly "tech talk" session that focused on basic Android topics. The topics ranged from how do views work to understanding the development tools available and were intended to fill in some of the fundamentals of the platform as the team was starting to develop the project. The scope and the depth of the sessions varied depending on the topic and the relative familiarity that the team already had with it, but ultimately they focused on building solid fundamentals.&lt;/p&gt;

&lt;p&gt;After being asked recently by another developer for some tips on getting up to speed with Android, I thought it might be useful to aggregate and cleanup the notes I had from the tech talks with the hope that they might prove useful for someone looking for a crash course in Android development.&lt;/p&gt;

&lt;p&gt;The outline is still very rough and definitely needs further refinement, but in the spirit of releasing early and often, I'm making it available today &lt;a href="http://kevfoo.com/androidcrashcourse/"&gt;here&lt;/a&gt; and in &lt;a href="http://cache.kevfoo.com/acc/AndroidCrashCourse.pdf"&gt;pdf form&lt;/a&gt;. I'd love to get feedback or suggestions on this and how it could be more helpful so please feel free to reach out.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/G0Nbj_mSOjc" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/06/Android-Crash-Course/</feedburner:origLink></entry>
	
	<entry>
		<title>Favorites from May 2012</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/VKrjrE205zU/" />
		<updated>2012-05-31T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/05/Favorites-from-May-2012</id>
		<category term="links" />
		<category term="2012" />
		<content type="html">&lt;p&gt;A collection of some of my favorite links, tweets and quotes from May. While these aren't a comprehensive look at or summary of May 2012, they do capture the things that I found interesting, thought provoking, and/or cool over the past month.&lt;/p&gt;

&lt;h1&gt;Favorite Links&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://sigpwned.com/content/complication-what-happens-when-you-try-solve-problem-you-dont-understand"&gt;Complication is What Happens When You Try to Solve a Problem You Don't Understand&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.theparisreview.org/interviews/4825/the-art-of-fiction-no-21-ernest-hemingway"&gt;Ernest Hemingway, The Art of Fiction No. 21&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.lettersofnote.com/2009/11/youre-nothing-but-pimp.html"&gt;Frank Sinatra's letter to Royko&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.thisiscolossal.com/2012/04/a-bathroom-situated-atop-a-15-story-elevator-shaft/"&gt;Bathroom on top of a 15 story elevator shaft&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.carmichaelcollective.com/Pinata-Anatomy"&gt;Pinata Anatomy&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.theatlantic.com/politics/archive/2012/05/democracy-is-for-amateurs-why-we-need-more-citizen-citizens/256818/"&gt;Democracy is for amateurs&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.smithsonianmag.com/arts-culture/Where-Did-the-Taco-Come-From.html?c=y&amp;amp;story=fullstory"&gt;Where did the taco come from?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.thisiscolossal.com/2012/05/high-speed-liquid-flowers-photographed-by-jack-long/"&gt;High speed liquid flowers&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://open.spotify.com/track/59yzZJSFso9CMcIzrEvhtL"&gt;Golden Age&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://cdixon.org/2012/05/26/the-experience-economy/"&gt;The Experience Economy&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;Favorite Quotes&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;"The world is a book and those who do not travel only read one page." --  &lt;a href="http://icanread.tumblr.com/post/23548675140"&gt;St. Augustine&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;"Lighting one candle with another candle-- spring evening" -- &lt;a href="https://kindle.amazon.com/post/PB4VB0UTRF5G"&gt;Haiku from Buson&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/VKrjrE205zU" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/05/Favorites-from-May-2012/</feedburner:origLink></entry>
	
	<entry>
		<title>That Conference - Summer Camp for Geeks</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/gWJ6JT5d8sc/" />
		<updated>2012-05-22T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/05/That-Conference-Summer-Camp-for-Geeks</id>
		<category term="ios" />
		<category term="geofencing" />
		<category term="corelocation" />
		<category term="mobile" />
		<category term="apps" />
		<category term="code" />
		<category term="thatconference" />
		<category term="redpoint" />
		<content type="html">&lt;p&gt;&lt;a href="http://www.thatconference.com/?s=badge"&gt;&lt;img alt="That Conference" border="0" src="http://www.thatconference.com/Images/SiteBadges/440w.jpg?s=badge" width="440" height="300" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I am excited and honored to be speaking at &lt;a href="http://thatconference.com"&gt;That Conference&lt;/a&gt; this August in the Wisconsin Dells. That Conference is going to have tracks for mobile, web and the cloud and the sessions look outstanding. I'll be doing a session on Core Location which, according to the iOS 6 rumors, may be a hot topic at WWDC this year. Hope to see you there!&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/gWJ6JT5d8sc" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/05/That-Conference-Summer-Camp-for-Geeks/</feedburner:origLink></entry>
	
	<entry>
		<title>Geofencing in iOS - Chicago Code Camp 2012</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/MqeniuW5UaE/" />
		<updated>2012-05-20T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/05/Geofencing-in-iOS-Talk</id>
		<category term="ios" />
		<category term="geofencing" />
		<category term="corelocation" />
		<category term="mobile" />
		<category term="apps" />
		<category term="code" />
		<category term="chicagocodecamp" />
		<category term="redpoint" />
		<content type="html">&lt;p&gt;Yesterday I had the pleasure of doing a talk exploring Core Location at the 4th annual &lt;a href="http://www.chicagocodecamp.com"&gt;Chicago Code Camp&lt;/a&gt;. Really enjoyed the audience participation and hopefully everyone left with a better understanding of Core Location.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/kevinmcmahon/LocationDemo"&gt;Code on Github&lt;/a&gt;&lt;/p&gt;

&lt;script async class="speakerdeck-embed" data-id="4fb7ab70d1170e00220208b0" data-ratio="1.299492385786802" src="//speakerdeck.com/assets/embed.js"&gt;&lt;/script&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/MqeniuW5UaE" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/05/Geofencing-in-iOS-Talk/</feedburner:origLink></entry>
	
	<entry>
		<title>Favorites from April 2012</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/SHy3Q5h8N78/" />
		<updated>2012-04-30T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/04/Favorites-from-April-2012</id>
		<category term="links" />
		<category term="2012" />
		<content type="html">&lt;p&gt;A collection of some of my favorite links, tweets and quotes from April. While these aren't a comprehensive look at or summary of April 2012, they do capture the things that I found interesting, thought provoking, and/or cool over the past month.&lt;/p&gt;

&lt;h1&gt;Favorite Links&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://startupsthisishowdesignworks.com/"&gt;Startups, this is how design works.&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://blog.getprismatic.com/blog/2012/4/18/content-focused-design-type-edition.html"&gt;Content Focused Design : Type Edition&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.vitsoe.com/en/gb/about/dieterrams/gooddesign"&gt;Dieter Rams: ten priniciples of good design&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.nytimes.com/2012/04/05/opinion/kristof-arsenic-in-our-chicken.html?_r=1&amp;amp;pagewanted=all"&gt;Arsenic in Our Chicken?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://textsfromhillaryclinton.tumblr.com/"&gt;Texts from Hillary&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.swiss-miss.com/2012/04/helvettaca.html"&gt;Helvettaca - Swiss Miss&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://theoatmeal.com/comics/facebook_likes"&gt;Facebook Likes - The Oatmeal&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.thisiscolossal.com/2012/04/figurative-willow-branch-sculpture-by-olga-ziemska/"&gt;Figurative Willow Branch Sculpture - Colossal&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.architizer.com/en_us/blog/dyn/41732/nasa-determines-average-color-of-the-universe/"&gt;Nasa determins the average color of the universe&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://design.org/blog/difference-between-ux-and-ui-subtleties-explained-cereal"&gt;The Difference Between UX and UI: Subtleties Explained in Cereal&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://twistedsifter.com/2012/04/adding-monsters-to-thrift-store-paintings/"&gt;Adding monsters to thrift store paintings.&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;Favorite Quotes&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.fastcodesign.com/1669503/user-experience-is-the-heart-of-any-company-how-do-you-make-it-top-priority"&gt;"If you start with “useful” as a first principle, then you automatically place customer need and experience first."&lt;/a&gt; -- Mary Ellen Muckerman&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/SHy3Q5h8N78" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/04/Favorites-from-April-2012/</feedburner:origLink></entry>
	
	<entry>
		<title>Favorites from March 2012</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/HNU7t_pgNZw/" />
		<updated>2012-03-31T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2012/03/Favorites-from-March-2012</id>
		<category term="links" />
		<category term="2012" />
		<content type="html">&lt;p&gt;A collection of some of my favorite links, tweets and quotes from March. While these aren't a comprehensive look at or summary of March 2012, they do capture the things that I found interesting, thought provoking, and/or cool over the past month.&lt;/p&gt;

&lt;h1&gt;Favorite Links&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://boingboing.net/2012/03/02/individual-dolphins-identify-t.html"&gt;Individual dolphins identify themselves to new dolphins they meet&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://worrydream.com/oatmeal/unexpectedly.png"&gt;Your youth has ended unexpectedly.&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://nowsourcing.com/blog/wp-content/uploads/2012/01/louisville-painter.html"&gt;The Psychology of Color&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://hiddentruths.northwestern.edu/home.html"&gt;Hidden Truths: The Chicago City Cemetery and Lincoln Park&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://blog.blprnt.com/blog/blprnt/tedxvancouver-the-weight-of-data"&gt;The Weight of Data - Nice talk about bringing a human element to data.&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.dezeen.com/2012/03/07/recreational-island-house-by-2by4-architects/"&gt;Recreation Island House&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.pbs.org/wgbh/nova/physics/fabric-of-cosmos.html"&gt;The Fabric of the Cosmos&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://propublica.github.com/stateface/"&gt;StateFace&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.coolhunting.com/design/100-ideas-that-changed-graphic-design.php"&gt;100 Ideas That Changed Graphic Design&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://maps.stamen.com/#watercolor/12/37.7706/-122.3782"&gt;Stamen Maps - Amazing map tiles&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.thehecklerstore.com/keep-calm-caray-on-t-shirt/"&gt;Keep Calm, Caray on.&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;Favorite Quotes&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;"Papyrus is a classy comic sans." -- &lt;a href="http://www.twitter.com/#!/rands"&gt;@rands&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;"Time is a created thing. To say "I don't have time" is to say "I don't want to"" - Lao Tzu&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/HNU7t_pgNZw" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/03/Favorites-from-March-2012/</feedburner:origLink></entry>
	
	<entry>
		<title>Favorites from February 2012</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/YmpUu1bBKOQ/" />
		<updated>2012-02-29T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2012/02/Favorites-from-February-2012</id>
		<category term="links" />
		<category term="2012" />
		<content type="html">&lt;p&gt;A collection of some of my favorite links, tweets and quotes from February. While these aren't a comprehensive look at or summary of February 2012, they do capture the things that I found interesting, thought provoking, and/or cool over the past month.&lt;/p&gt;

&lt;h1&gt;Favorite Links&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.listsofnote.com/2012/02/wartime-golf-rules.html"&gt;War Time Golf Rules&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.roughtype.com/archives/2012/01/why_publishers.php"&gt;Why Publishers Should Give Away - eBooks&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://t.co/pHkrvHWb"&gt;Mapresent, a new mapping presentation tool for the iPad&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://t.co/ZiVYpFqd"&gt;Yale Discovers a Fungus That Eats Plastic&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.youtube.com/watch?v=cGMCmbLq2qs&amp;amp;feature=youtu.be"&gt;Edible Balloon from Alinea&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://t.co/Deyz4qfr"&gt;How Target Figured Out A Teen Girl Was Pregnant Before Her Father Did&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://t.co/UJoaScer"&gt;L.E.D. Surfer&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.shorpy.com/node/12442"&gt;Mardi Gras 1907&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://chicagopast.com/"&gt;Chicago Past photoblog&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.dezeen.com/2012/02/23/starbucks-coffee-at-dazaifu-tenman-gu-by-kengo-kuma-and-associates/"&gt;An amazing Starbucks store on the approach to a Shinto shrine in Dazaifu, - Japan&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://blog.unitedheroes.net/archives/p/4396/"&gt;Welcome to the Internet - Advice to a 13 year old.&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://blog.frankchimero.com/post/17763077976"&gt;"This text and the one beside it are equal."&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;Favorite Quotes&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;“Chaos was the law of nature, order was the dream of man.” – Henry Adams&lt;/li&gt;
&lt;li&gt;"All men will benefit, if we can invoke the wonders of science instead of its terrors." – &lt;a href="http://www.jfklink.com/speeches/jfk/publicpapers/1962/jfk59_62.html"&gt;JFK&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/YmpUu1bBKOQ" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/02/Favorites-from-February-2012/</feedburner:origLink></entry>
	
	<entry>
		<title>Favorites from January 2012</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/0V8O3768jeM/" />
		<updated>2012-01-31T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2012/01/Favorites-from-January-2012</id>
		<category term="links" />
		<category term="2012" />
		<content type="html">&lt;p&gt;A collection of some of my favorite links, tweets and quotes from January. While these aren't a comprehensive look at or summary of January 2012, they do capture the things that I found interesting, thought provoking, and/or cool over the past month.&lt;/p&gt;

&lt;h1&gt;Favorite Links&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.youtube.com/watch?&amp;amp;v=2WmlUXsjSv8"&gt;Wilco, Nick Lowe &amp;amp; Mavis Staples rehearse The Weight&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.ted.com/talks/sheena_iyengar_choosing_what_to_choose.html"&gt;TED Talk: How To Make Choosing Easier&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.youtube.com/watch?v=e-P5RGdjICo"&gt;× as the visual symbol for multiply&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.youtube.com/watch?v=PNpVURAgG5g"&gt;Wes Anderson from above&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.flickr.com/photos/gsfc/6760135001"&gt;Blue Marble: NASA's Incredible New High Resolution Photograph of Earth&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://i3.kym-cdn.com/photos/images/newsfeed/000/234/765/b7e.jpg"&gt;MEME PIC: I have no idea what I am doing&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://t.co/hQzUMEj3"&gt;Amazing sleuth work done to determine Ice Cube's 'Good Day'&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.fastcompany.com/1810522/mits-math-breakthrough-could-transform-your-phone-tablet-pc-tv-mri-scans"&gt;New FFT calculation could be 10x faster&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.youtube.com/watch?v=D4k3bX0ydJg"&gt;Now &lt;em&gt;THIS&lt;/em&gt; is a firework&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://maxogden.com/#blog/gut-hosted-open-data-filets"&gt;Gut: HTTP Unix pipes for Open Data&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://typographica.org/2012/features/our-favorite-typefaces-of-2011/"&gt;Typographica's Favorite Typefaces for 2011&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.buzzfeed.com/mattcherette/beavis-and-butthead-in-real-life"&gt;Beavis and Butthead, as sculpted by a special FX makeup artist.&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;Favorite Tweets&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://twitter.com/#!/dansinker/status/161997962803810305"&gt;@dansinker&lt;/a&gt;:"The first rule of John Kerry fight club…" contains at least 75 subclauses."&lt;/li&gt;
&lt;li&gt;&lt;a href="https://twitter.com/#!/citizenparker/status/164060055862382592"&gt;@citizenparker&lt;/a&gt;: MUTABILITY! From hell’s heart I stab at thee (until another operation inadvertently changes my state to “not stabbing”)&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;Quotes&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://plus.google.com/u/0/107980702132412632948/posts/ikswxSskaUc"&gt;"Data is the new raw material of the 21st century"&lt;/a&gt; - Tim Berners Lee &amp;amp; Nigel Shadbolt&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/0V8O3768jeM" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/01/Favorites-from-January-2012/</feedburner:origLink></entry>
	
	<entry>
		<title>Importing CSV data with location information into PostGIS</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/Uj1MIBL1yAQ/" />
		<updated>2012-01-09T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2012/01/Importing-CSV-to-PostGIS</id>
		<category term="gis" />
		<category term="csv" />
		<category term="postgis" />
		<category term="postgresql" />
		<category term="gdal" />
		<category term="opendata" />
		<category term="gov" />
		<category term="opengov" />
		<category term="gov20" />
		<category term="chicago" />
		<content type="html">&lt;p&gt;Sometimes location data isn't neatly packaged in a SHP file, and it requires some massaging before it can be used in spatial queries. In this post I'll take a look at importing latitude and longitude data from a CSV file into our PostGIS database and transforming those coordinates into geometry data that can be spatially queried against.&lt;/p&gt;

&lt;h1&gt;Step 0 - Initial Starting Point&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Get a CSV dataset. For this example I'll be using the &lt;a href="http://data.cityofchicago.org/Historic-Preservation/Individual-Landmarks/tdab-kixi"&gt;Individual Landmarks&lt;/a&gt; dataset exported as CSV. You can get a copy of the CSV file that I am using for the example &lt;a href="http://cache.kevfoo.com/data/Individual_Landmarks.csv"&gt;here&lt;/a&gt;.
We already have the latitude and longitude and the extra location field isn't something that we'll use so I removed the location column prior to exporting the dataset. You can hide the column by selecting the arrows on the column heading in the table (&lt;a href="http://cache.kevfoo.com/2012/01/hide_column_via_header.png"&gt;shown here&lt;/a&gt;) or via the manage screen and deselecting the location column from the list of available columns (&lt;a href="http://cache.kevfoo.com/2012/01/hide_column_via_manage.png"&gt;shown here&lt;/a&gt;).&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;A PostgreSQL database with PostGIS installed.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;Step 1 - Create the table in the database&lt;/h1&gt;

&lt;p&gt;  Use the following SQL to create a table to hold the landmark data.&lt;/p&gt;

&lt;script src="https://gist.github.com/1584721.js?file=gistfile1.sql"&gt;&lt;/script&gt;


&lt;h1&gt;Step 2 - Copy the CSV data into the database&lt;/h1&gt;

&lt;p&gt;  To run the copy command, login to the database and execute the following command :&lt;/p&gt;

&lt;script src="https://gist.github.com/1584983.js?file=gistfile1.sh"&gt;&lt;/script&gt;


&lt;p&gt;There are a couple of things to note with the copy command:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;The first argument passed to the copy command specifies the tablename (&lt;em&gt;landmarks&lt;/em&gt;) and the columns which the CSV files map to. Our table includes a column &lt;em&gt;gid&lt;/em&gt; that is an auto-incremented id which is used as a primary key as well as &lt;em&gt;the_geom&lt;/em&gt; geometry column. The CSV does not include either of these columns in the data we are copying. If we don't specify the specific columns that the fields in the CSV map to, errors will occur when attempting to copy the data.&lt;/li&gt;
&lt;li&gt;The DELIMITERS argument specifies your delimiter.&lt;/li&gt;
&lt;li&gt;The CSV argument at the end lets PostgreSQL know that the file is CSV.&lt;/li&gt;
&lt;li&gt;The HEADER argument lets PostgreSQL know that the file includes the headers on the first line.&lt;/li&gt;
&lt;/ol&gt;


&lt;p&gt;Here is a look at our data after the import. Note that the_geom has no data. We'll take care of that in the next step.&lt;/p&gt;

&lt;p&gt;&lt;img src="http://cache.kevfoo.com/2012/01/imported_landmark_data.png" alt="A look at the newly imported landmark data sans geometry." /&gt;&lt;/p&gt;

&lt;h1&gt;Step 3 - Translate latitude and longitude into POINT geometry&lt;/h1&gt;

&lt;p&gt;Now that we have the data imported, we need to convert the latitude and longitude columns to a PostGIS POINT geometry. The following SQL will update &lt;em&gt;the_geom&lt;/em&gt; column in the landmarks table with a POINT geometry created from the row's latitude and longitude columns. In order to create the POINT, the ST_GeomFromText method is used. This method allows us to create a POINT, which is a PostGIS geometry type, textually with the latitude and longitude values being specified in the construction of the type.&lt;/p&gt;

&lt;script src="https://gist.github.com/1584998.js?file=gistfile1.sql"&gt;&lt;/script&gt;


&lt;p&gt;Here is a look at the data with the the_geom column populated with POINT data.&lt;/p&gt;

&lt;p&gt;&lt;img src="http://cache.kevfoo.com/2012/01/landmark_data_with_geometry.png" alt="Geometry populated landmarks table" /&gt;&lt;/p&gt;

&lt;h1&gt;Step 4 - Run some queries&lt;/h1&gt;

&lt;p&gt;Now that all the POINT geometries have been created for our landmark rows we can write some spatial queries against our data. Here are just a few of the types of queries we can run.&lt;/p&gt;

&lt;p&gt;Using the ward geometry we have from a &lt;a href="http://www.kevfoo.com/2011/12/Importing-Shapefiles-to-PostGIS-Consuming-Chicago-Open-Data/"&gt;previous example&lt;/a&gt;, we can run a query that returns all the landmarks in the 43rd Ward.&lt;/p&gt;

&lt;script src="https://gist.github.com/1585171.js?file=gistfile1.sql"&gt;&lt;/script&gt;


&lt;p&gt;This query returns the 5 closest landmarks to a given latitude and longitude :&lt;/p&gt;

&lt;script src="https://gist.github.com/1585140.js?file=gistfile1.sql"&gt;&lt;/script&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/Uj1MIBL1yAQ" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/01/Importing-CSV-to-PostGIS/</feedburner:origLink></entry>
	
	<entry>
		<title>Favorite Links and Quotes of 2011</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/8VLBgswTo18/" />
		<updated>2012-01-02T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2012/01/Favorite-Links-and-Quotes-2011</id>
		<category term="retrospective" />
		<category term="links" />
		<category term="quotes" />
		<category term="2011" />
		<content type="html">&lt;p&gt;A quest to find the name and url of a &lt;a href="http://www.thewirecutter.com"&gt;gadget review site&lt;/a&gt; that I had tweeted about a few months ago led me to the &lt;a href="http://www.twimemachine.com/"&gt;TwimeMachine&lt;/a&gt; web app. TwimeMachine lets you read your old tweets and, while I was looking for the gadget website, I got a chance to take a stroll down memory lane and revisit some of my favorite links and quotes from the past year. I pulled out some of my favorites and have shared them below. While these lists aren't a comprehensive look at or summary of 2011, they do capture the things that I found interesting, thought provoking, and/or cool over the past year.&lt;/p&gt;

&lt;h1&gt;My Favorite Links from 2011&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://kottke.org/x/4pra"&gt;No more fish in the sea&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://bit.ly/j2KLrn"&gt;"The correct use of a semicolon is a big red flag for me"&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://j.mp/jW23Op"&gt;Canada's new money is pretty amazing, eh?&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://pinchzoom.com/posts/oh-dear-how-to-seo-for-the-itunes-app-store/"&gt;How to SEO for the iTunes App Store&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://youtu.be/Q1ZeXnmDZMQ"&gt;The Tragedy of Suburbia&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://bit.ly/rjvFOi"&gt;Dean Martin makes a burger.&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/Uax2F2M"&gt;Vitamin String Quartet – The Suburbs&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://bit.ly/lWR2ho"&gt;Imaginative, provocative video from students on the need for (r)evolution in teaching and learning&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://www.nosh.com/404"&gt;404&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://bit.ly/poIjmp"&gt;10 Unmissable TED Videos For Designers&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://j.mp/mQt3lm"&gt;How does one become a brogrammer?&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/NncsHbq"&gt;Preschool: The Best Job-Training Program&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://j.mp/ogu721"&gt;Internet High Five&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/XxOz0H7r"&gt;Shifting the Suburban Paradigm&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/83CBFI5F"&gt;The Wirecutter&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://www.lettersofnote.com/2011/07/persist.html"&gt;Persist - Letters of Note&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;German designer David Hanauer creates &lt;a href="http://t.co/KmGuvewI"&gt;dizzying carpets from aerial Google Earth images&lt;/a&gt;.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/ruhzylRf"&gt;Tufte's Data Analysis for Politics and Policy&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/CkAtnPIL"&gt;Apple's Three Laws of Developers&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/BSalHGD4"&gt;"A Brief Rant on the Future of Interaction Design"&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://www.foreignpolicy.com/articles/2011/10/28/black_market_global_economy?page=full&amp;amp;t=1320868571"&gt;The Shadow Superpower&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/rWofhyNp"&gt;Chicago Type&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/gfsvMNEK"&gt;Weapons of Mass Creation&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/RSVE5Koz"&gt;Woody Gutherie's "New Years Rulin's"&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://iamadriansbrain.posterous.com/andy-swan-ok-but-there-are-two-rules"&gt;“OK, but there are two rules:  1. You can’t change the recipe.   2.  You can’t do anything that anyone else has done before.”&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://sivers.org/restrictions-will-set-you-free"&gt;Restrictions will set you free.&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://www.cnn.com/2011/OPINION/02/13/greene.gracious.gesture/index.html"&gt;4 Star General, 5 Star Grace&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://bit.ly/hH6MV0"&gt;Possibilians vs Agnostics by Dave Eagleman.&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://bit.ly/gR4Ui6"&gt;Sir Ken Robinson on passion&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://t.co/Kzw3vsc"&gt;How to write faster&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://webtypography.net/"&gt;The Elements of Typography Style Applied to the Web&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a href="http://www.fontshop.com/blog/newsletters/april10c/indexEMAIL.html"&gt;Combining Type with Helvetica&lt;/a&gt;&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;My Favorite Quotes from 2011&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;"I’m impressed with the people from Chicago. Hollywood is hype. New York is talk. Chicago is work." -Michael Douglas&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;"The arts are not a way to make a living. They are a very human way of making life more bearable." -- Kurt Vonnegut&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;"Another flaw in the human character is that everybody wants to build and nobody wants to do maintenance." -- Kurt Vonnegut&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;@zachklein: Just told to me: "Schools are the coal-fired power plants of education."&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;h1&gt;My Favorite Funny Tweets from 2011&lt;/h1&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;@jonlech "Next year HTML5 will replace native apps" is the new "Next year will be the year of Linux on the desktop".&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;@hubs: What doesn't kill you makes you smaller. ~Super Mario&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;@dcurtis: The Container Store is like a strip club for people with OCD.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;@larrybraverman: GUYS IF EGYPT CAN TAKE DOWN MUBARAK WE CAN TAKE DOWN TICKETMASTER&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/8VLBgswTo18" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/01/Favorite-Links-and-Quotes-2011/</feedburner:origLink></entry>
	
	<entry>
		<title>2011 by the Numbers</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/sXdRMwWUG5c/" />
		<updated>2012-01-01T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2012/01/2011-by-the-numbers</id>
		<category term="retrospective" />
		<category term="personal" />
		<category term="2011" />
		<content type="html">&lt;h2&gt;Apps Shipped : 7&lt;/h2&gt;

&lt;p&gt;4 Android apps with one in the can set for release in a few weeks. 3 iOS apps. Not 100% sure what I can and can't disclose due to client agreements, but I am very proud and happy with the apps that I helped produce last year. Lots more mobile work on the agenda for 2012.&lt;/p&gt;

&lt;h2&gt;High School Programming Courses Taught: 1&lt;/h2&gt;

&lt;p&gt;In early 2011 I taught Android development to high schoolers participating in a pilot program for the 21st Century Youth Project. It was an amazing experience and I hope to work with them again in the future as the program matures.&lt;/p&gt;

&lt;h2&gt;Speaking Engagements : 4&lt;/h2&gt;

&lt;p&gt;I had the honor of being selected to speak at &lt;a href="http://windycitygo.org/videos2011/#5"&gt;WindyCityGo&lt;/a&gt; and &lt;a href="http://www.chicagocodecamp.org"&gt;Chicago Code Camp&lt;/a&gt; last spring as well as speaking to user groups in Rockford and Milwaukee.&lt;/p&gt;

&lt;h2&gt;Jobs Changed : 1&lt;/h2&gt;

&lt;p&gt;In July I joined Redpoint Technologies and became a consultant for the first time in my career. While consulting isn't for everyone, I have enjoyed the diversity of the projects/clients I had the privilege of working on/with.&lt;/p&gt;

&lt;h2&gt;Side Hustles : Numerous&lt;/h2&gt;

&lt;p&gt;Along with maintaining a few sets of &lt;a href="http://www.github.com/kevinmcmahon"&gt;MonoTouch bindings&lt;/a&gt;, I put together a &lt;a href="http://www.appdevwiki.com"&gt;wiki for mobile app developers&lt;/a&gt; and started working with &lt;a href="http://www.hoodiechicago.com"&gt;some of the data&lt;/a&gt; that the City of Chicago is publishing. I was able to help out some friends working on some stealth startups by offering technical advice and mentoring and have a few more tricks up my sleeve for the upcoming year.&lt;/p&gt;

&lt;h2&gt;Trips : 7&lt;/h2&gt;

&lt;p&gt;In addition to usual trips to Minneapolis to visit the in-laws and the guys trip out to Phoenix for the PGA event, I was able to squeeze in a "business" trip to Las Vegas, a vacation to southern California, and attend an amazing wedding in Greece.&lt;/p&gt;

&lt;h2&gt;Lucky Guy: 1&lt;/h2&gt;

&lt;p&gt;In reflecting back over the last year I am left feeling a tremendous amount of gratitude and appreciation for the amazing people, places and opportunities that I encountered over the past year. I am truly blessed.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/sXdRMwWUG5c" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2012/01/2011-by-the-numbers/</feedburner:origLink></entry>
	
	<entry>
		<title>Importing Shapefiles to PostGIS - Consuming Chicago Open Data</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/z3gmU15PSKY/" />
		<updated>2011-12-29T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2011/12/Importing-Shapefiles-to-PostGIS-Consuming-Chicago-Open-Data</id>
		<category term="gis" />
		<category term="opendata" />
		<category term="postgis" />
		<category term="postgresql" />
		<category term="hoodie" />
		<category term="gdal" />
		<category term="chicago" />
		<category term="opendata" />
		<category term="gov" />
		<category term="opengov" />
		<category term="gov20" />
		<category term="shp2pgsql" />
		<content type="html">&lt;p&gt;The most common spatial format that geographic data is distributed in is ESRI shapefiles. The geographic datasets provided at the City of Chicago's &lt;a href="http://data.cityofchicago.org"&gt;open data portal&lt;/a&gt; are no different. In this post, I'm going to walk through converting an ESRI shapefile into SQL, importing that SQL into a PostGIS enabled PostgreSQL database, and querying the geographic data.&lt;/p&gt;

&lt;h1&gt;Prerequisites&lt;/h1&gt;

&lt;p&gt;Before we get started you will need to download and/or install the following data and software:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;a href="http://postgis.org/"&gt;PostGIS/PostgreSQL database&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.gdal.org/index.html"&gt;The GDAL libraries&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;A dataset from the &lt;a href="http://data.cityofchicago.org"&gt;City of Chicago Data Portal&lt;/a&gt;. For this example I am going to use the &lt;a href="http://data.cityofchicago.org/Facilities-Geographic-Boundaries/Boundaries-Wards/bhcv-wqkf"&gt;Ward data&lt;/a&gt; provided by the city.&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.pgadmin.org/download/"&gt;pgAdminIII&lt;/a&gt; - A PostgreSQL admin and management tool that is optional but &lt;em&gt;highly&lt;/em&gt; recommended.&lt;/li&gt;
&lt;/ol&gt;


&lt;h1&gt;Step 1: SHP file to SQL file&lt;/h1&gt;

&lt;p&gt;The data published by the city uses a spacial reference system (SRS) called &lt;em&gt;&lt;a href="http://spatialreference.org/ref/esri/102671/"&gt;NAD 1983 StatePlane Illinois East FIPS 1201 Feet&lt;/a&gt;&lt;/em&gt; to store data. This SRS falls into the &lt;em&gt;State Plane&lt;/em&gt; category which is typically great for measurement and maps covering a limited geographic area like a state or city. For most contexts this is perfect but, if you want to use this spatial data with mapping layers or geocoding services from Google or Bing, it will cause problems. Mapping providers like Google and Microsoft Bing expect data to be stored using the WGS 84 (EPSG code 4326) SRS. This means that if we want to use latitude and longitude coordinates from these services or utilize their mapping layers we will have to convert our data from State Plane to WGS 84. Thankfully the GDAL tools provide a utility to transform the data.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;ogr2ogr -f "ESRI Shapefile" -s_srs "EPSG:102671" -t_srs "EPSG:4326" Wards4326.shp Wards.shp
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Once the shapefile has been converted from State Plane to WGS 84, we can then use the shp2pgsql tool to generate the SQL statements necessary to add the geography data to our database.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;shp2pgsql -s 4326  -I -c -W UTF-8 Wards4326.shp wards &amp;gt; wards.sql
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Here is a sample of one of the insert statements generated by the shp2pgsql with geometry column (the_geom) abbreviated:&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre&gt;&lt;code class="sql"&gt;&lt;span class="k"&gt;INSERT&lt;/span&gt; &lt;span class="k"&gt;INTO&lt;/span&gt; &lt;span class="ss"&gt;&amp;quot;wards&amp;quot;&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;data_admin&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;perimeter&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;ward&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;alderman&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;class&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;ward_phone&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;hall_phone&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;hall_offic&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;address&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;edit_date1&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;shape_area&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="ss"&gt;&amp;quot;shape_len&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="n"&gt;the_geom&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;VALUES&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;111078823.37393899&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;98206.78600274&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;20&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;WILLIE COCHRAN&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;1&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;773-955-5610&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;312-744-6840&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;121 N LASALLE ST, RM 300 OFFICE 19, 60602&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;6357 S COTTAGE GROVE&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;20030527&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;111200062.771999999&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;98166.05290559999&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;0106000020E6100...&amp;#39;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;


&lt;h1&gt;Step 2: Insert Data into DB&lt;/h1&gt;

&lt;p&gt;Now that the dataset has been transformed and the SQL has been generated, it is time to add it to the database. You can do so by running the following command. (NOTE: you will have to swap in your own database name and user for the $DB_NAME and $DB_USER arguments).&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;psql -d $DB_NAME $DB_USER &amp;lt; wards.sql
&lt;/code&gt;&lt;/pre&gt;

&lt;h1&gt;Step 3: Write Queries&lt;/h1&gt;

&lt;p&gt;With the data entered into the database we can now write queries against it. Here is a query that returns information about the ward that contains the point specified by latitude and longitude arguments.&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre&gt;&lt;code class="sql"&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;ward&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;alderman&lt;/span&gt; 
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;wards&lt;/span&gt; 
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;ST_Contains&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;the_geom&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ST_GeomFromText&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;&amp;#39;POINT(41.927064 87.645658)&amp;#39;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;4326&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;


&lt;p&gt;The WHERE clause is calling the spatial relationship function ST_Contains. Spatial relationship functions in PostGIS take two input geometries and return either a boolean or another geometry. In our case, ST_Contains returns a boolean indicating if the point geometry passed as the second argument is contained in the geometry stored in the the_geom column of the wards table. The point geometry is constructed from another spatial function ST_GeomFromText. This function takes a textual representation of the geometry along with a spatial reference id (SRID) specifying the SRS that the geometry should be created in. In our case, we are using latitude and longitude values obtained from Google so we are creating the point geometry in the EPSG 4326 SRS.&lt;/p&gt;

&lt;h1&gt;Additional Resources&lt;/h1&gt;

&lt;p&gt;I found the following links useful as I started learning about PostGIS.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.bostongis.com/PrinterFriendly.aspx?content_name=postgis_tut01"&gt;Boston GIS's - Getting Started With PostGIS: An almost Idiot's Guide&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.kyngchaos.com/software/postgres"&gt;Kyng Chaos' PostgreSQL, PostGIS, and pgRouting installers for Mac OS X&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.postgis.us/page_buy_book"&gt;PostGIS in Action&lt;/a&gt; book&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/z3gmU15PSKY" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2011/12/Importing-Shapefiles-to-PostGIS-Consuming-Chicago-Open-Data/</feedburner:origLink></entry>
	
	<entry>
		<title>Announcing the App Dev Wiki</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/BHXVi1Aulm8/" />
		<updated>2011-10-08T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2011/10/app-dev-wiki</id>
		<category term="mobile" />
		<category term="wiki" />
		<category term="android" />
		<category term="ios" />
		<category term="wp7" />
		<category term="development" />
		<category term="monotouch" />
		<category term="monodroid" />
		<category term="phonegap" />
		<content type="html">&lt;p&gt;&lt;a href="http://www.appdevwiki.com/?utm_source=blog&amp;amp;utm_medium=post&amp;amp;utm_campaign=wiki"&gt;AppDevWiki&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Earlier this week I put together a wiki to centralize the links, libraries and miscellania that I have been collecting regarding mobile development. I did this mainly for personal use and to provide a reference for coworkers and colleagues getting into mobile dev but hopefully others will find it useful. Check it out and feel free to add your favorite tools, libraries and links to it.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/BHXVi1Aulm8" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2011/10/app-dev-wiki/</feedburner:origLink></entry>
	
	<entry>
		<title>MonoTouch Bindings</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/qU7yvCu3o5Q/" />
		<updated>2011-09-14T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2011/09/monotouch_bindings</id>
		<category term="monotouch" />
		<category term="bindings" />
		<category term="howto" />
		<category term="guide" />
		<category term="objective-c" />
		<content type="html">&lt;p&gt;Creating bindings for native, Objective-C based libraries can be somewhat confusing when first starting out. To help smooth the learning curve for those looking to create bindings (and hopefully share them) I have put together some links and an overview of the steps that I use.&lt;/p&gt;

&lt;p&gt;As MonoTouch development is picking up steam again after the Novell/Xamarin deal I've noticed more and more people looking for help and information about just how to consume native libraries. Most of this information and the utility that auto-generates the code was gleaned from the #monotouch IRC channel, looking at other MonoTouch bindings and experimentation.&lt;/p&gt;

&lt;p&gt;The core of this post was written in May 2011 when I was helping out a few folks with some binding issues. The general gist of the process still applies but somethings may have changed. Please let me know via comments or email if I am missing anything or if there are some corrections needed.&lt;/p&gt;

&lt;h3&gt;Useful Links&lt;/h3&gt;

&lt;p&gt;&lt;a href="http://ios.xamarin.com/Documentation/Binding_New_Objective-C_Types"&gt;Binding Objective-C Types - MonoTouch Docs&lt;/a&gt;&lt;br/&gt;
&lt;a href="http://ios.xamarin.com/Documentation/Binding_New_Objective-C_Types/Binding_Details"&gt;Binding Details - MonoTouch Docs&lt;/a&gt;&lt;br/&gt;
&lt;a href="https://github.com/kevinmcmahon/monotouch-localytics"&gt;An Example Project&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;Binding Steps&lt;/h3&gt;

&lt;h4&gt;Step 1: Create the Binding Code&lt;/h4&gt;

&lt;p&gt;The binding that you are going to call from your C#/MonoTouch code you will need to create a C# version You can manually write the bindings by hand or use a utility to help automate the process. There is a tool you can compile from the source found in this &lt;a href="https://gist.github.com/512356"&gt;gist&lt;/a&gt; that can help save some time.  You will need to compile the tool using mcs and invoke it to generate the bindings like so :&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;mono ObjCParser.exe &amp;lt;FILENAME&amp;gt;.h
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;You can pass multiple header files associated with the Objective-C library that you are trying to bind. The tool generates three different .cs files which contain the C# bindings you can use. You will need to update the namespaces and the using statements as the files generated by the utility are using the MonoMac namespaces.&lt;/p&gt;

&lt;p&gt;The tool isn't perfect and there are known issues. Cleaning this tool up is on my todo list but extremely low since I know the quirks and it is just faster for me to generate and fix it up than to polish it.&lt;/p&gt;

&lt;p&gt;These are the biggest issues that those using the tool should be aware of:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt; Methods are included correctly in their corresponding C# classes but properties aren't. You'll need to grab the properties and stick them in the right classes.&lt;/li&gt;
&lt;li&gt; If a method specified in a .h file spans multiple lines the tool can't recognize that. When you go to compile you'll get some errors.&lt;/li&gt;
&lt;li&gt; Delegates can be tricky. When creating delegate mappings need to update and figure out how to handle the delegates. Due to the brute force nature of the generator tool, the delegates are typed as IntPtr's when in reality they should be typed so it requires so hand updating to straighten the delegates out.&lt;/li&gt;
&lt;li&gt; NSURLRequest in Objective-CObjective-C is NSUrlRequest in MonoTouch. There are a few places where the Objective-C classes don't map exactly into MonoTouch classes due to naming convention issues.&lt;/li&gt;
&lt;/ol&gt;


&lt;h4&gt;Step 2: Make the DLL&lt;/h4&gt;

&lt;p&gt;Generate the bindings by invoking btouch and providing the relevant arguments for your files. The invocation looks something like this:&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;/Developer/MonoTouch/usr/bin/btouch -out=&amp;lt;YOURNAMEHERE&amp;gt;.dll &amp;lt;YOUR_BINDING_CODE&amp;gt;.cs  
&lt;/code&gt;&lt;/pre&gt;

&lt;h4&gt;Step 3: Reference the DLL&lt;/h4&gt;

&lt;p&gt;Include a reference to the newly generated dll in your MonoTouch project. You will also need to include the static library in the project. For some reason it isn't enough to just link to the path. You actually &lt;em&gt;need&lt;/em&gt; to have the .a file included in the .csproj file. You can set the build action to None.&lt;/p&gt;

&lt;h4&gt;Step 4: Update the Additional Arguments.&lt;/h4&gt;

&lt;p&gt;Finally, the MonoTouch project settings need to be updated so the Objective-C library is linked against during compile time. Update the Extra Arguments field in the iPhone Build settings under the Project Options. I've taken &lt;a href="http://grab.by/8PtI"&gt;a screen grab&lt;/a&gt; showing the field.&lt;/p&gt;

&lt;p&gt;You can read more in the official docs under the "Linking the Dependencies" section &lt;a href="http://monotouch.net/Documentation/Binding_New_Objective-C_Types"&gt;here&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;These are the basic steps.  It isn't hard but it isn't exactly straight forward. My best recommendation is to take a look at my fork of the &lt;a href="https://github.com/kevinmcmahon/monotouch-localytics"&gt;Localytics project on github&lt;/a&gt; and try and reproduce the bindings on your own.&lt;/p&gt;

&lt;h3&gt;Notes&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;There is a linker bug that Apple introduced in XCode 3.x that causes problems at compile time when trying to link in static libraries with THUMB enabled. You can run a command via the shell to check the dumped output (&lt;a href="http://monotouch.pastebin.com/4Kq52f9D"&gt;here is an example&lt;/a&gt;. Make sure to look at line 5, second column. The two byte address is the give away that the library is THUMB) but I don't have the command off the top of my head.  The best way to handle this is to get the full Objective-C source and uncheck the THUMB code option. If you are still using XCode 3.2 then you &lt;em&gt;HAVE&lt;/em&gt; to use a static library that has been compiled without THUMB code. The linker bug apparently has been fixed in XCode 4 and you should be able to link against both THUMB and non-THUMB libraries.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;You also might want to look into making a fat static library. I do this for most of the bindings I publish so that there is only one static library to link against and you don't have to hassle with using one library which has been compiled for use with the simulator and one that has been compiled for the device. Checkout this &lt;a href="http://stackoverflow.com/questions/3520977/build-fat-static-library-device-simulator-using-xcode-and-sdk-4"&gt;Stack Overflow question&lt;/a&gt; for more details on how to make a fat static library.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;p&gt;&lt;em&gt;Updated Decemeber 28, 2011&lt;/em&gt; : Added link to fat static library instructions.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/qU7yvCu3o5Q" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2011/09/monotouch_bindings/</feedburner:origLink></entry>
	
	<entry>
		<title>Mono for Android talk at WindyCityGo</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/L4CoqDQTQ68/" />
		<updated>2011-05-08T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2011/05/windy-city-go-mono-for-android</id>
		<category term="mono for android" />
		<category term="mobile" />
		<category term="conference" />
		<category term="android" />
		<category term="windycitygo" />
		<content type="html">&lt;p&gt;Here is the video and the slides from the &lt;a href="http://mono-android.net/"&gt;Mono for Android&lt;/a&gt; talk I gave last month at &lt;a href="http://windycitygo.org/"&gt;WindyCityGo&lt;/a&gt;.&lt;/p&gt;

&lt;iframe src="http://player.vimeo.com/video/22402266?title=0&amp;amp;byline=0&amp;amp;portrait=0&amp;amp;color=007ECE" frameborder="0"&gt;&lt;/iframe&gt;


&lt;p&gt;&lt;a href="http://vimeo.com/22402266"&gt;.NET on Android? MonoDroid Does by Kevin McMahon&lt;/a&gt; from &lt;a href="http://vimeo.com/chicagoruby"&gt;ChicagoRuby&lt;/a&gt; on &lt;a href="http://vimeo.com"&gt;Vimeo&lt;/a&gt;.&lt;/p&gt;




&lt;div style="width:425px" id="__ss_7578318"&gt; &lt;strong style="display:block;margin:12px 0 4px"&gt;&lt;a href="http://www.slideshare.net/klmcmahon/mono-for-android" title="Mono for Android?"&gt;Mono for Android?&lt;/a&gt;&lt;/strong&gt; &lt;iframe src="http://www.slideshare.net/slideshow/embed_code/7578318" frameborder="0" marginwidth="0" marginheight="0" scrolling="no"&gt;&lt;/iframe&gt; &lt;div style="padding:5px 0 12px"&gt; View more &lt;a href="http://www.slideshare.net/"&gt;presentations&lt;/a&gt; from &lt;a href="http://www.slideshare.net/klmcmahon"&gt;Kevin McMahon&lt;/a&gt; &lt;/div&gt; &lt;/div&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/L4CoqDQTQ68" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2011/05/windy-city-go-mono-for-android/</feedburner:origLink></entry>
	
	<entry>
		<title>Quick Primer: Cocoa and Cocoa Touch for .Net Developers</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/GlAgQQbj9bY/" />
		<updated>2011-05-04T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2011/05/quick-primer-cocoa-and-cocoa-touch</id>
		<category term="ios" />
		<category term="application classes" />
		<category term="cocoa" />
		<category term="objective-c" />
		<category term="cocoa touch" />
		<content type="html">&lt;h2&gt;Cocoa and Cocoa Touch&lt;/h2&gt;

&lt;p&gt;At their core Cocoa and Cocoa Touch are composed of two frameworks. The Foundation Kit provides the core, non-UI classes and, depending on whether you're developing apps for OS X or iOS, AppKit or UIKit respectively provides the core UI classes. For data the Core Data framework is available.&lt;/p&gt;

&lt;h2&gt;Foundation&lt;/h2&gt;

&lt;p&gt;The Foundation framework provides the core, non-UI classes that all Cocoa and Cocoa Touch applications are built upon. Basic object behavior, memory management, object mutability, and notifications are all defined among the 80 classes that comprise the framework.&lt;/p&gt;

&lt;p&gt;This is the framework that provides the root class NSObject. Much like System.Object, NSObject is the class that all other classes are derived from. NSObject provides the nuts and bolts which enable object-oriented functionality and behaviors in Objective-C. You will also find in Foundation classes like NSString, NSArray, and NSThread or data types, collections, and operating system abstractions respectively.&lt;/p&gt;

&lt;h2&gt;AppKit (OS X) / UIKit (iOS)&lt;/h2&gt;

&lt;p&gt;AppKit for Cocoa and its sister framework UIKit for Cocoa Touch provide the windows, dialogs, buttons, menus, scrollers, textfields and all the other UI elements available to developers. The AppKit framework is used for desktop applications and the UIKit for iOS applications.&lt;/p&gt;

&lt;p&gt;The Window, View, and Application classes provided in the AppKit and UIKit framework define the core functionality of app. Each class plays a crucial role in displaying the user interface and responding to the various user events generated while the program is executing. These three classes, constitute what is considered to be the core program framework since all apps derive their functionality and behaviors from them.&lt;/p&gt;

&lt;p&gt;While both frameworks share many of the same types and perform similar tasks, having separate frameworks does provide some benefit. Having two, specific frameworks makes it easier to provide device implementations for UI controls when called for (e.g. handling motion or touch gestures) but remain conceptually similar when it comes to behavior (e.g. window, view, and application class relationship), and it eliminates an unnecessary dependency that would be created by lumping desktop and iOS specific code together into a single framework.&lt;/p&gt;

&lt;p&gt;It is easy to tell the difference between Cocoa and Cocoa Touch classes. Classes that are found in Cocoa are prefixed with an NS (e.g. NSWindow, NSView), and Cocoa Touch classes are prefixed with UI (e.g. UIWindow, UIView).&lt;/p&gt;

&lt;h2&gt;Delegates&lt;/h2&gt;

&lt;p&gt;The Cocoa framework leverages the delegate pattern to allow an object's behavior to be modified without having to resort to subclassing. Unlike C#, which includes a delegate language element, the concept of delegates come to Cocoa purely via the implementation of the delegate design pattern and not a mix language features and pattern.&lt;/p&gt;

&lt;p&gt;A delegate in Cocoa is an object that implements some or all of a protocol (interface in Objective-C speak) and is assigned to another object to handle events. Classes using delegates typically define a contract via a protocol which provides the level of indirection needed to decouple the caller object and the delegate object. It is common practice in Cocoa to define all the methods in a delegate protocol as optional. This allows the selective implementation of event handlers for the events needing custom behaviors.&lt;/p&gt;

&lt;h2&gt;Notifications&lt;/h2&gt;

&lt;p&gt;Notifications in Cocoa provide a mechanism for decoupled message passing. Communication between objects is done by passing messages to and from objects. In order for the communication to take place, the sender must know about the receiver, and this knowledge of the other object introduces tight coupling between the two. Notifications remove the coupling by providing a one-to-many broadcast mechanism which allows objects to register with a notification center as notifications posters, observers, or both. When a notification is posted by an object, the notification center acts as a dispatcher and invokes any callback methods registered with the notification center for that particular notification.&lt;/p&gt;

&lt;p&gt;Notifications sound very similar to delegates, but they differ in three key areas. First, there is no limit to the number of objects that can receive notifications. In a delegate scenario, only the delegate object associated with the host object can respond to events. Second, an object can register for any number of notification from the notification center and not just the methods defined by the delegate protocol. Finally, an object posting a notification does not require another object to invoke methods. It can simply fire the notification and not worry about whether there is an observer on the other end to respond.&lt;/p&gt;

&lt;h2&gt;Model-View-Controller&lt;/h2&gt;

&lt;p&gt;You will find many different design patterns being employed in the Cocoa framework but none are as pervasive as the Model-View-Controller (MVC) pattern. In this pattern there are three possible stereotypes that an object can take on. Model objects encapsulate data and behaviors; view objects handle display and user interaction; and controller objects bind the data and the objects together.&lt;/p&gt;

&lt;p&gt;The benefits realized from the pattern come from the separation of concerns imposed on applications. Interactions between layers occur via well-defined interfaces, which provides the abstraction necessary to limit the impact of code changes, and the code is easier to reuse since the interfaces and API are well-defined.&lt;/p&gt;

&lt;p&gt;It is important to note that Cocoa does bleed the line between some of the layers in the framework. The concept of the view-controller is prevalent in both Cocoa and Cocoa Touch, and there are some instances in Cocoa where there are model-controllers. When these roles are combined into a single class, the controller takes on the responsibilities that come with owning the second role and still provides the bridge to the third role. So in the case of a UITableViewController, the controller is responsible not only for its traditional role of tying the model with the view but also for how that data looks in the table which is typically the view's role.&lt;/p&gt;

&lt;h2&gt;Links&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://developer.apple.com/library/mac/#documentation/Cocoa/Conceptual/CocoaFundamentals"&gt;Cocoa Fundamentals Guide from Apple&lt;/a&gt; [Apple]&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.amazon.com/gp/product/0321695003?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=0321695003"&gt;Cocoa Programming Developer's Handbook&lt;/a&gt; [Amazon]&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.amazon.com/gp/product/0321535022?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=0321535022"&gt;Cocoa Design Patterns&lt;/a&gt; [Amazon]&lt;/li&gt;
&lt;/ul&gt;

&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/GlAgQQbj9bY" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2011/05/quick-primer-cocoa-and-cocoa-touch/</feedburner:origLink></entry>
	
	<entry>
		<title>Monotouch: Facebook Binding Updates</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/5gQgt1ExMv0/" />
		<updated>2010-12-12T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2010/12/monotouch-facebook-binding-updates</id>
		<category term="monotouch" />
		<category term="facebook" />
		<category term="binding" />
		<category term="ios" />
		<category term="iphone" />
		<category term="wiki" />
		<category term="architecture" />
		<category term="thumb code" />
		<content type="html">&lt;p&gt;UPDATE (12/30/2011) : Facebook Connect bindings are being maintained by the &lt;a href="https://github.com/mono/monotouch-bindings/tree/master/FacebookConnect"&gt;Mono Project &lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I pushed some updates to the &lt;a href="https://github.com/kevinmcmahon/monotouch-facebook/"&gt;monotouch-facebook&lt;/a&gt; project recently to eliminate potential linking problems that could come up. Apple introduced a bug in their linker that causes problems when linking non-Thumb MonoTouch code with Thumb code. The default settings for the &lt;a href="https://github.com/facebook/facebook-ios-sdk"&gt;Facebook iOS SDK&lt;/a&gt; project will produce a static library with Thumb code so I forked the project and turned off Thumb code generation.&lt;/p&gt;

&lt;p&gt;I also made the fat static Facebook library a little fatter by linking the simulator version of the library (i386 architecture) in along with the iPhone and iPad library (armv6 and armv7 architectures). This fatter library doesn't require managing and maintaining two versions of the library for the different architectures.&lt;/p&gt;

&lt;p&gt;The bindings have been refreshed due to the Facebook iOS SDK being updated recently. You can see the changes reflected in the example app. The biggest change introduced by the update is the app's Info.plist now needs to be modified to register a custom URL Scheme that will enable the example app to be called back after the user authenticates with Facebook. You can see what the Info.plist should look like in the picture below. You will need to replace &lt;em&gt;&lt;em&gt;&amp;lt;&amp;lt;&amp;lt;YOURAPPIDHERE&amp;gt;&amp;gt;&amp;gt;&lt;/em&gt;&lt;/em&gt; with your real app id.&lt;/p&gt;

&lt;p&gt;&lt;img src="http://cache.kevfoo.com/images/mtfb_plist.png" alt="" /&gt;&lt;/p&gt;

&lt;p&gt;I hope to get this info up on the monotouch-facebook project's wiki page soon. If you find any issues please open them on the project's issue tracker. Enjoy.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/5gQgt1ExMv0" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/12/monotouch-facebook-binding-updates/</feedburner:origLink></entry>
	
	<entry>
		<title>MonoTouch: Dropbox via DropNet, JSON.Net and RestSharp</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/2vfvVer6pQg/" />
		<updated>2010-11-19T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2010/11/monotouch-dropbox-via-dropnet-json-net-and-restsharp</id>
		<category term="dropbox" />
		<category term="open source" />
		<category term="libraries" />
		<category term="monotouch" />
		<category term="bindings" />
		<category term="mobile" />
		<category term="restsharp" />
		<category term="monotouch" />
		<category term="iphone" />
		<category term="c#" />
		<category term="dotnet" />
		<category term="ios" />
		<category term="json" />
		<content type="html">&lt;p&gt;&lt;em&gt;MonoTouch-ified code on github: &lt;a href="https://github.com/kevinmcmahon/DropNet"&gt;DropNet&lt;/a&gt;&lt;/em&gt;, &lt;em&gt;&lt;a href="https://github.com/kevinmcmahon/RestSharp"&gt;RestSharp&lt;/a&gt;&lt;/em&gt;, &lt;em&gt;&lt;a href="https://github.com/chrisntr/Newtonsoft.Json"&gt;JSON.Net&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Recently I wanted to add Dropbox access to a MonoTouch app that I am working on and came across the &lt;a href="https://github.com/dkarzon/DropNet"&gt;DropNet&lt;/a&gt; project. DropNet abstracts away all the plumbing involved to interact with Dropbox via their REST-based API and provides an easy-to-use C# API.In order to be able to use DropNet in a MonoTouch app, a few of the libraries that DropNet depends on, RestSharp and JSON.Net, had to be ported so that they too would build and run on MonoTouch. Thankfully, the process of getting the DropNet dependencies ported didn't require a lot of work. Chris Hardy had already done the &lt;a href="https://github.com/chrisntr/Newtonsoft.Json"&gt;JSON.Net&lt;/a&gt; port and John Sheehan, the maintainer of &lt;a href="http://www.restsharp.org/"&gt;RestSharp&lt;/a&gt;, had already begun the process of porting RestSharp. After making a few changes to get RestSharp to compile and adding a MonoTouch-specific project to DropNet, I was able to access my Dropbox via my MonoTouch app. Very cool and very easy thanks to the open source contributions made by the C# and MonoTouch communities.I hope to post a DropNet demo app soon. In the mean time, you can grab the libraries I used from these repositories: &lt;a href="https://github.com/kevinmcmahon/DropNet"&gt;DropNet&lt;/a&gt;, &lt;a href="https://github.com/kevinmcmahon/RestSharp"&gt;RestSharp&lt;/a&gt;, and &lt;a href="https://github.com/chrisntr/Newtonsoft.Json"&gt;JSON.Net&lt;/a&gt;. If you're interested in just DropNet for MonoTouch, pre-compiled binaries of RestSharp and JSON.Net are already included in the repository. Enjoy!&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/2vfvVer6pQg" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/11/monotouch-dropbox-via-dropnet-json-net-and-restsharp/</feedburner:origLink></entry>
	
	<entry>
		<title>Chicago Alt.Net MonoDroid Talk</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/vpWJ_ygSWnY/" />
		<updated>2010-11-11T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2010/11/chicago-alt-net-monodroid-talk</id>
		<category term="presentation" />
		<category term="tools" />
		<category term="slides" />
		<category term="novell" />
		<category term="apps" />
		<category term="developers" />
		<category term="alt.net" />
		<category term="monodroid" />
		<category term="mono for android" />
		<category term="android" />
		<category term="dotnet" />
		<category term="mobile" />
		<category term="c#" />
		<content type="html">&lt;div id="__ss_5722575" style="width: 425px"&gt;&lt;object id="__sse5722575" height="355" width="425"&gt;&lt;param name="movie" value="http://static.slidesharecdn.com/swf/ssplayer2.swf?doc=monodroid101-101109223452-phpapp02&amp;amp;stripped_title=net-monodroid-does&amp;amp;userName=klmcmahon" /&gt;&lt;param name="allowFullScreen" value="true" /&gt;&lt;param name="allowScriptAccess" value="always" /&gt;&lt;embed name="__sse5722575" allowfullscreen="true" src="http://static.slidesharecdn.com/swf/ssplayer2.swf?doc=monodroid101-101109223452-phpapp02&amp;amp;stripped_title=net-monodroid-does&amp;amp;userName=klmcmahon" allowscriptaccess="always" type="application/x-shockwave-flash" height="355" width="425"&gt;&lt;/embed&gt;&lt;/object&gt;    &lt;div style="padding-bottom: 12px; padding-left: 0px; padding-right: 0px; padding-top: 5px"&gt;
 View this &lt;a href="http://www.slideshare.net/klmcmahon/net-monodroid-does"&gt;presentation&lt;/a&gt; and &lt;a href="http://www.slideshare.net/klmcmahon"&gt;others&lt;/a&gt; on Slideshare.&lt;/div&gt; &lt;/div&gt;


&lt;p&gt;&lt;/p&gt;

&lt;p&gt;Wednesday I had the pleasure of introducing MonoDroid to the developers at the &lt;a href="http://chicagoalt.net"&gt;Chicago Alt.Net&lt;/a&gt; meetup. We had a great turn out at the meeting and there was a lot of interest both the Android platform and the MonoDroid tools. The talk consisted of the slides above and some code examples (both &lt;a href="https://github.com/kevinmcmahon/MonoDroid101"&gt;available on github&lt;/a&gt;) and was intended to show off the awesome work that the MonoDroid team at Novell has done in bringing C# to Android.&lt;/p&gt;

&lt;p&gt;If anyone is interested in learning more about Android and developing apps in C# for Android, I strongly recommend you head over to the &lt;a href="http://monodroid.net"&gt;project website&lt;/a&gt; and sign-up for a preview invite. The MonoDroid team is inviting more developers to participate in the preview with each new release so now is as good a time as any to get signed up.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/vpWJ_ygSWnY" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/11/chicago-alt-net-monodroid-talk/</feedburner:origLink></entry>
	
	<entry>
		<title>Ubuntu Tip : Broadcom 43xx Wireless Setup</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/J5ZN1uea_qM/" />
		<updated>2010-11-03T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2010/11/ubuntu-tip-broadcom-43xx-wireless-setup</id>
		<category term="ethernet cable" />
		<category term="laptop adapter" />
		<category term="wlan" />
		<category term="broadcom 43xx" />
		<category term="wireless" />
		<category term="wifi" />
		<category term="modprobe" />
		<category term="b43" />
		<category term="wireless access point" />
		<category term="kernel source" />
		<category term="dell xps" />
		<category term="wubi" />
		<category term="linux" />
		<category term="ubuntu" />
		<category term="configuration" />
		<content type="html">&lt;p&gt;Recently I installed Ubuntu on my windows machine using the latest &lt;a href="http://www.ubuntu.com/desktop/get-ubuntu/windows-installer"&gt;Wubi&lt;/a&gt; installer and ran into an issue getting my Dell XPS M1530 laptop's wireless adapter up and operational. My particular flavor of the M1530 uses the &lt;em&gt;Dell Wireless 1505 Draft 802.11n WLAN Mini-Card&lt;/em&gt; wireless adapter. This adapter is built on the the Broadcom 43xx series of chips (in my case the Broadcom 4328) and unfortunately these devices don't work with Ubuntu 10.10 out-of-the-box.&lt;/p&gt;

&lt;p&gt;To fix this, grab an ethernet cable and get on the your network the wired way. Pop open a terminal window and run:&lt;/p&gt;

&lt;pre&gt;~$ sudo apt-get install bcmwl-kernel-source&lt;br /&gt;~$ sudo modprobe -r b43 ssb wl&lt;br /&gt;~$ sudo modprobe wl&lt;/pre&gt;


&lt;p&gt;&lt;/p&gt;

&lt;p&gt;This should get the wireless adapter up and running and now you can use &lt;a href="http://ubuntuforums.org/showthread.php?t=1425727"&gt;these instructions&lt;/a&gt; from the Ubuntu forums to connect to a wireless access point.&lt;/p&gt;

&lt;p&gt;Hope this helps.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/J5ZN1uea_qM" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/11/ubuntu-tip-broadcom-43xx-wireless-setup/</feedburner:origLink></entry>
	
	<entry>
		<title>Monotouch: Flurry Demo App</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/EE9K1XRKwXE/" />
		<updated>2010-10-12T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2010/10/monotouch-flurry-demo-app</id>
		<category term="apps" />
		<category term="api" />
		<category term="objective-c" />
		<category term="c#" />
		<category term="monotouch" />
		<category term="ios" />
		<category term="analytics" />
		<category term="flurry" />
		<category term="mobile" />
		<content type="html">&lt;p&gt;&lt;em&gt;Github repository can be found here: &lt;a href="http://github.com/kevinmcmahon/FlurryTestApp"&gt;Flurry Test App&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Recently a request was made for a working example of a Monotouch app that uses the &lt;a href="http://blog.kevfoo.com/index.php/2010/08/monotouch-flurry-analytics-bindings/"&gt;Flurry bindings&lt;/a&gt; so I put one together. The example, while trivial in its nature, shows the basics required to incorporate the Flurry SDK Objective-C libraries and their bindings into a Monotouch app and provide an example call pattern that shows how to use the Flurry API.&lt;/p&gt;

&lt;p&gt;There are a couple things to note about this demo app. You'll need to register with Flurry and get a unique application key to use with the test app. In the example code you will see that I have some comments about providing a real debug and release application key. A best practice is to have two separate keys so you can keep your production analytics separate from your test analytics. So while you are testing your app use the testing application key and switch it out for the release application key when submitting your app to the App Store.&lt;/p&gt;

&lt;p&gt;The latest Flurry SDK is designed to work with iOS version 4.1. If you are looking to have your app run on devices still running iOS 3.x, you can either add a couple extra linker flags as extra arguments or use an older version (2.6) of the Flurry SDK. I plan on updating the demo example to include the linker flags needed to get 3.x support with the latest Flurry SDK.&lt;/p&gt;

&lt;p&gt;Finally, I have included a line of code in the example that appears extraneous and out of place. This is to make sure that Monotouch doesn't strip out code that Flurry has an implicit dependency on. Monotouch aggressively prunes unused code from assemblies to shrink the size of apps and this trivial demo app doesn't make explicit use of anything from a part of the CoreGraphics library that Flurry needs (something which almost all non-trivial iOS apps will do by necessity) so it gets excised during compilation.&lt;/p&gt;

&lt;p&gt;I hope this helps get people started. The Flurry analytics are really easy to use and provide a lot of valuable data. Please let me know if you have any questions or comments on the example.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/EE9K1XRKwXE" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/10/monotouch-flurry-demo-app/</feedburner:origLink></entry>
	
	<entry>
		<title>Book Review: Tapworthy</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/CyHA4ExhgHc/" />
		<updated>2010-08-27T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2010/08/book-review-tapworthy-2</id>
		<category term="book" />
		<category term="review" />
		<category term="mobile applications" />
		<category term="iphone apps" />
		<category term="mobile context" />
		<category term="iphone" />
		<category term="design" />
		<category term="ux" />
		<category term="app design" />
		<category term="design" />
		<category term="review" />
		<category term="ios" />
		<category term="ui" />
		<content type="html">&lt;h2&gt;The Book&lt;/h2&gt;

&lt;p&gt;&lt;a href="http://www.amazon.com/gp/product/1449381650?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=1449381650"&gt;Tapworthy: Designing Great iPhone Apps&lt;/a&gt; by Josh Clark&lt;/p&gt;

&lt;blockquote&gt;"Designing a tapworthy app means designing for an economy of time, attention, and space."&lt;/blockquote&gt;


&lt;p&gt;&lt;/p&gt;

&lt;h2&gt;The Review&lt;/h2&gt;

&lt;p&gt;Tapworthy is an indispensable resource for developers trying to make quality mobile applications for all platforms. While the book uses iPhone apps and user interface elements to illustrate the concepts discussed, many of the observations made about the mechanics, human interactions, and the psychology of what makes great applications are applicable to all mobile applications.The book does a good job of exploring the user interface elements found in iOS apps and provides a good summary of how and why you would use the elements in your designs. The coverage of this material is quite good but pales in comparison to the exploration of what goes into making a tapworthy app. It is in this exploration of what makes a tapworthy app that I got my two main takeaways from the book.The first is to be ruthless when cutting scope and narrowing the focus of your app. To help developers and designers do this, a series of questions are provided and discussed.&lt;/p&gt;

&lt;p&gt;It is amazing how quickly issues with your design arise when your ideas are subjected to simple questions like:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;What does your app do and &lt;em&gt;why&lt;/em&gt;?&lt;/li&gt;
&lt;li&gt;What specific problem does your app uniquely solve for users?&lt;/li&gt;
&lt;li&gt;What makes this app mobile?&lt;/li&gt;
&lt;li&gt;What mobile context are you designing for?&lt;/li&gt;
&lt;li&gt;Why would you use this app when you are away from your computer?&lt;/li&gt;
&lt;/ul&gt;


&lt;p&gt;These questions are straightforward and may seem somewhat obvious, but they are an easy way to vet ideas. If you can't quickly provide a compelling answers for these questions, then you might not have a best selling app idea. Conversely, the questions can be used to identify weaknesses that might need more attention and potentially turn a good idea into a great one.The second takeaway was to recognize the three mobile contexts: microtasking, local, and boredom. To make a good app, you need to tightly wrap the answers to the 5Ws (who is the user, what are they doing, why are they doing it on a mobile, where are they, and when are they doing it) around one or more of these. Something common among the most successful apps is how easy it is to identify the answers to the 5W questions plus which mobile context it applies to. When the scope of an app is perfectly tailored to a specific scenario or use case, users will find that every tap has a payoff and accomplishing tasks within the app will seem effortless. Efficiency becomes a feature.&lt;/p&gt;

&lt;h2&gt;The Summary&lt;/h2&gt;

&lt;p&gt;There is so much to like about this book. Tapworthy forces us to ask the right questions in designing mobile apps and provides invaluable tips and insights about maximizing your app's user experience. If you are serious about making good apps, do yourself a favor and pick this book up. You won't regret it.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/CyHA4ExhgHc" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/08/book-review-tapworthy-2/</feedburner:origLink></entry>
	
	<entry>
		<title>Monotouch: Facebook iOS SDK Bindings</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/qeqC4iPSgpw/" />
		<updated>2010-08-18T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2010/08/monotouch-facebook-ios-sdk-bindings</id>
		<category term="facebook" />
		<category term="monotouch" />
		<category term="ios" />
		<category term="development" />
		<category term="bindings" />
		<content type="html">&lt;p&gt;UPDATE (12/30/2011) : Facebook Connect bindings are being maintained by the &lt;a href="https://github.com/mono/monotouch-bindings/tree/master/FacebookConnect"&gt;Mono Project &lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;The MonoTouch libraries can be &lt;a href="http://github.com/kevinmcmahon/monotouch-facebook"&gt;found on github&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;It's late and I am tired so I'll be brief. I just pushed the binding of official &lt;a href="http://github.com/facebook/facebook-ios-sdk"&gt;Facebook iOS SDK&lt;/a&gt; to github. In addition to the bindings, the DemoApp, which was included along side the SDK, has been ported to MonoTouch. The code is straightforward and does a good job of getting you up to speed with the important elements of the SDK. &lt;/p&gt;

&lt;p&gt;If you want to run the demo application, you will have to create a Facebook application on Facebook and grab the app id. You need the app id to pass back to Facebook during the login process and you can find out where to put it by looking through the comments of the DemoAppViewController class.&lt;/p&gt;

&lt;p&gt;Please let me know if you have any issues with this library. Enjoy.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/qeqC4iPSgpw" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/08/monotouch-facebook-ios-sdk-bindings/</feedburner:origLink></entry>
	
	<entry>
		<title>Monotouch: Flurry Analytics Bindings</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/mlSKV_1EEag/" />
		<updated>2010-08-06T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2010/08/monotouch-flurry-analytics-bindings</id>
		<category term="analytics" />
		<category term="libs" />
		<category term="sdk" />
		<category term="iphone" />
		<category term="google" />
		<category term="objective-c" />
		<category term="monotouch" />
		<category term="binding" />
		<category term="mobile" />
		<content type="html">&lt;p&gt;&lt;em&gt;The MonoTouch libraries can be found on my &lt;a href="http://github.com/kevinmcmahon/monotouch-libs"&gt;fork of monotuch-libs on GitHub&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;&lt;strong&gt;For an example of how to build and use the binding check out this &lt;a href="https://github.com/kevinmcmahon/FlurryTestApp"&gt;example project on github&lt;/a&gt;.&lt;/strong&gt;&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;For my &lt;a href="http://www.tribeguides.com"&gt;latest app&lt;/a&gt; I wanted to collect some analytics to see which screens and content included in the app are the most useful to users. In evaluating my mobile analytics options, Flurry's free of charge service and easy to use API made the decision to go with them over Google Analytics and Mixpanel an easy one.Integrating Flurry analytics into your app is pretty easy but there is a small amount of setup to be done prior. You will need to grab the iPhone SDK from Flurry and also register your application with them to get an API key. The API key is unique to your application and provides Flurry a way to know who is sending events and notifications back to them to log. The SDK includes a couple header files and the Objective-C libraries you'll need to include and link against in your MonoTouch projects. Once the Flurry libraries and the &lt;a href="http://github.com/kevinmcmahon/monotouch-libs"&gt;MonoTouch bindings&lt;/a&gt; have been obtained and an API key has been generated, we can integrate them into MonoTouch application and start collecting data.Initiating data collection is as simple as calling the StartSession method with the application's API key. That is all it takes to start collecting basic information about your app like the amount of times it has been launched, the number of different users using it, and other bits of info like hardware version and service provider.Here is some code showing how to turn analytics on.&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre&gt;&lt;code class="csharp"&gt;&lt;span class="k"&gt;using&lt;/span&gt; &lt;span class="nn"&gt;System&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;using&lt;/span&gt; &lt;span class="nn"&gt;MonoTouch.Foundation&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;using&lt;/span&gt; &lt;span class="nn"&gt;MonoTouch.UIKit&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;using&lt;/span&gt; &lt;span class="nn"&gt;Flurry&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="c1"&gt;// include the MonoTouch binding lib&lt;/span&gt;

&lt;span class="k"&gt;namespace&lt;/span&gt; &lt;span class="nn"&gt;Foo&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="na"&gt;    [Register (&amp;quot;AppDelegate&amp;quot;)]&lt;/span&gt;
    &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;AppDelegate&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;UIApplicationDelegate&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;const&lt;/span&gt; &lt;span class="kt"&gt;string&lt;/span&gt; &lt;span class="n"&gt;FlurryApiKey&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;&amp;quot;...&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;override&lt;/span&gt; &lt;span class="kt"&gt;bool&lt;/span&gt; &lt;span class="nf"&gt;FinishedLaunching&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;UIApplication&lt;/span&gt; &lt;span class="n"&gt;app&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;NSDictionary&lt;/span&gt; &lt;span class="n"&gt;options&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="c1"&gt;// 1 liner to kick the session off&lt;/span&gt;
            &lt;span class="n"&gt;Flurry&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FlurryAPI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;StartSession&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;FlurryApiKey&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

            &lt;span class="c1"&gt;// Do you app thing here...&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;


&lt;p&gt;If more detailed analytics are desired, there are additional methods available to help you glean whatever meaningful information you need from your application. The example below shows how you can automatically track the changes in navigation within a tab bar. When you pass a UINavigationController or a UITabBarController to the CurrentPageViews method, each navigation action as you move from one view or tab to another gets tracked. This is ideal for seeing which parts of your app users are interacting with the most.&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre&gt;&lt;code class="csharp"&gt;&lt;span class="k"&gt;using&lt;/span&gt; &lt;span class="nn"&gt;System&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;using&lt;/span&gt; &lt;span class="nn"&gt;MonoTouch.Foundation&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;using&lt;/span&gt; &lt;span class="nn"&gt;MonoTouch.UIKit&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;using&lt;/span&gt; &lt;span class="nn"&gt;Flurry&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="c1"&gt;// include the MonoTouch binding lib&lt;/span&gt;

&lt;span class="k"&gt;namespace&lt;/span&gt; &lt;span class="nn"&gt;Foo&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt;
&lt;span class="na"&gt;    [Register (&amp;quot;AppDelegate&amp;quot;)]&lt;/span&gt;
    &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;AppDelegate&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;UIApplicationDelegate&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;const&lt;/span&gt; &lt;span class="kt"&gt;string&lt;/span&gt; &lt;span class="n"&gt;FlurryApiKey&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;&amp;quot;...&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;public&lt;/span&gt; &lt;span class="k"&gt;override&lt;/span&gt; &lt;span class="kt"&gt;bool&lt;/span&gt; &lt;span class="nf"&gt;FinishedLaunching&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;UIApplication&lt;/span&gt; &lt;span class="n"&gt;app&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;NSDictionary&lt;/span&gt; &lt;span class="n"&gt;options&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="c1"&gt;// 1 liner to kick the session off&lt;/span&gt;
            &lt;span class="n"&gt;FlurryAPI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;StartSession&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;FlurryApiKey&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

            &lt;span class="c1"&gt;// create a navigatable controller to watch...&lt;/span&gt;
            &lt;span class="n"&gt;UITabBarController&lt;/span&gt; &lt;span class="n"&gt;tabBarController&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="n"&gt;UITabBarController&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

            &lt;span class="c1"&gt;// ...and pass it to CurrentPageViews.&lt;/span&gt;
            &lt;span class="n"&gt;FlurryAPI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;CurrentPageViews&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;tabBarController&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

            &lt;span class="c1"&gt;// Do you app thing here...&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;


&lt;p&gt;I am touching on just a few things that you can do with Flurry. The SDK docs describe a number of other things you can do like creating and logging custom events and tracking how much time is spent performing activities. I'd recommend checking them out after you download the libraries.I've just started collecting analytics during beta testing and things appear to working smoothly.&lt;/p&gt;

&lt;p&gt;If you find any issues with the MonoTouch bindings please let me know. Enjoy!&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/mlSKV_1EEag" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/08/monotouch-flurry-analytics-bindings/</feedburner:origLink></entry>
	
	<entry>
		<title>Book Review: Professional Android 2 Application Development</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/t69VCdkMUac/" />
		<updated>2010-05-26T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2010/05/book-review-professional-android-2-application-development</id>
		<category term="android" />
		<category term="programming" />
		<category term="book" />
		<category term="application development" />
		<category term="development" />
		<category term="app" />
		<category term="review" />
		<content type="html">&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2010/05/pa2ad.jpg"&gt;&lt;img src="http://cache.kevfoo.com/2010/05/pa2ad_thumb.jpg" title="pa2ad" alt="pa2ad" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Reto Meier's &lt;a href="http://www.amazon.com/gp/product/0470565527?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=0470565527"&gt;Professional Android 2 Application Development&lt;/a&gt; does a great job of educating the reader on what is necessary for developing Android applications. Core application fundamentals and advanced Android features are presented to the reader via a series of real-life application examples. Readers who work the examples and leverage the breadth of coverage provided on the Android 2 framework will be well on their way towards establishing an excellent foundation for building compelling Android applications.&lt;/p&gt;

&lt;p&gt;After giving the customary history lesson and tour of the toolsets and development environment, the first half of the book deals with the components that make up an application. Chapters are devoted to activities and life cycle, UI views, data and file access, and key Android concepts like intents (message-passing mechanisms) and content providers (ability to expose data to other apps).&lt;/p&gt;

&lt;p&gt;Once the fundamentals have been covered, the remainder of the book is spent exploring the advanced and optional features available in the SDK. Android-centric concepts like background services, notifications and widgets are given the same in depth treatment given to the fundamentals so you get a lot of the "why" along with the how. Features and functionality that naturally lend them to being abstracted away via an API like media playback, GPS and Bluetooth are given adequate coverage of what is available via the framework and, where pertinent, the Android-specific behaviors are highlighted.&lt;/p&gt;

&lt;p&gt;While the book is divided into fundamentals and advanced topics, continuity is maintained throughout via the example applications used to emphasize the concepts presented. By building the to-do list, compass, and earthquake monitoring service applications while reading through the book, passive learning is transformed into active, directed learning. Unlike some programming books I've read in the past, these examples do real work, accomplish specific real-life tasks, and provide some utility once completed. Readers are not just extending these applications one feature at a time, they are also adding one key concept to their proverbial tool belt while doing it.&lt;/p&gt;

&lt;p&gt;The speed at which the Android platform is being evolved and improved upon is staggering. Since April 2009 there has been 4 major releases of the Android OS with a 5th release rumored for this fall. While the breadth of coverage provided for the APIs and framework is nice while it is still relevant, the real strength of this book comes building an understanding of the core Android fundamentals. Readers looking for a solid introduction to Android development need to look no further than &lt;a href="http://www.amazon.com/gp/product/0470565527?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=0470565527"&gt;Professional Android 2 Application Development&lt;/a&gt;.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/t69VCdkMUac" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/05/book-review-professional-android-2-application-development/</feedburner:origLink></entry>
	
	<entry>
		<title>Retargeting Visual Studio project files with PowerShell</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/-3s2H4vnM7k/" />
		<updated>2010-05-06T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2010/05/retargeting-visual-studio-project-files-with-powershell</id>
		<category term="powershell" />
		<category term="linq" />
		<category term="gist" />
		<category term="development" />
		<category term="legacy code" />
		<category term="visual studio" />
		<category term="build" />
		<category term="script" />
		<category term="dotnet" />
		<category term="powershell" />
		<content type="html">&lt;p&gt;I originally set out to write this post a little over a year ago. Back then I threw together a script to retarget all the project files from .Net 2.0 to .Net 3.5 for my previous company and recently I found myself having to a similar upgrade from .Net 3.5 to  4.0. I ended up using the same script again so I figured I'd go ahead and publish it.&lt;/p&gt;

&lt;p&gt;The upgrade process done by Visual Studio on your current projects and solutions will only migrate the file format to the newest schema and will not retarget the framework to the latest version. That is where the script I've included below comes in. It will retarget all the C# project files found under the path provided to version 4.0 of the .Net framework.&lt;/p&gt;

&lt;p&gt;C# project files are XML based and navigating the DOM with Linq to XML is a cinch but there are a couple small but important steps that the script needed to include. First, you need to append the namespace to the individual element names or else the elements will not be able to be found. Second, when saving the modified XDocument, a XmlWriterSetting instance needs to be instantiated and the OmitXmlDeclaration property set to true. Setting this property to true will make sure the XML that we save will be considered a valid project file by Visual Studio.&lt;/p&gt;

&lt;p&gt;I've included the full script below as well as created a gist that can be found &lt;a href="http://gist.github.com/391885"&gt;here&lt;/a&gt;. It is important to note that this script will edit all the csproj files found under the directory specified in the path variable. Make sure you backup these files or have them under source control prior to running the script. Enjoy.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;UPDATE: Added change suggested in comments by Jeffery Snover&lt;/em&gt;&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre&gt;&lt;code class="c#"&gt;&lt;span class="na"&gt;[Reflection.Assembly]&lt;/span&gt;&lt;span class="p"&gt;::&lt;/span&gt;&lt;span class="n"&gt;LoadWithPartialName&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;&amp;quot;System.Xml.Linq&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;|&lt;/span&gt; &lt;span class="n"&gt;Out&lt;/span&gt;&lt;span class="p"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Null&lt;/span&gt;&lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="n"&gt;specify&lt;/span&gt; &lt;span class="n"&gt;the&lt;/span&gt; &lt;span class="n"&gt;root&lt;/span&gt; &lt;span class="n"&gt;of&lt;/span&gt; &lt;span class="n"&gt;your&lt;/span&gt; &lt;span class="n"&gt;source&lt;/span&gt; &lt;span class="n"&gt;tree&lt;/span&gt; &lt;span class="n"&gt;below&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;path&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;&amp;quot;C:\Code\chatsworth&amp;quot;&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;ns&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;&amp;quot;http://schemas.microsoft.com/developer/msbuild/2003&amp;quot;&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xname&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;System&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Xml&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Linq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;XName&lt;/span&gt;&lt;span class="p"&gt;]::&lt;/span&gt;&lt;span class="n"&gt;Get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;&amp;quot;PropertyGroup&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;ns&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;tfname&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;System&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Xml&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Linq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;XName&lt;/span&gt;&lt;span class="p"&gt;]::&lt;/span&gt;&lt;span class="n"&gt;Get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;&amp;quot;TargetFrameworkVersion&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;ns&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;    &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xws&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="n"&gt;New&lt;/span&gt;&lt;span class="p"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Object&lt;/span&gt; &lt;span class="n"&gt;System&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Xml&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;XmlWriterSettings&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xws&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;OmitXmlDeclaration&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xws&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Indent&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;truefunction&lt;/span&gt; &lt;span class="n"&gt;updatefx&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;filename&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;    &lt;span class="err"&gt;#&lt;/span&gt;&lt;span class="n"&gt;Write&lt;/span&gt;&lt;span class="p"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Host&lt;/span&gt; &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;filename&lt;/span&gt;    &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;System&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Xml&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Linq&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;XDocument&lt;/span&gt;&lt;span class="p"&gt;]::&lt;/span&gt;&lt;span class="n"&gt;Load&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;filename&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;         &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Descendants&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xname&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;        &lt;span class="k"&gt;foreach&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="k"&gt;in&lt;/span&gt; &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;result&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;    &lt;span class="p"&gt;{&lt;/span&gt;        &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;fxelem&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Element&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;tfname&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;        &lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;fxelem&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;        &lt;span class="p"&gt;{&lt;/span&gt;            &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SetElementValue&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;tfname&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s"&gt;&amp;quot;v4.0&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;        &lt;span class="p"&gt;}&lt;/span&gt;    &lt;span class="p"&gt;}&lt;/span&gt;    &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xw&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;System&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Xml&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;XmlWriter&lt;/span&gt;&lt;span class="p"&gt;]::&lt;/span&gt;&lt;span class="n"&gt;Create&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;filename&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xws&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;    &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xml&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Save&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xw&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;    &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;xw&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()}&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;csprojs&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="n"&gt;Get&lt;/span&gt;&lt;span class="p"&gt;-&lt;/span&gt;&lt;span class="n"&gt;ChildItem&lt;/span&gt; &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;path&lt;/span&gt; &lt;span class="p"&gt;*.&lt;/span&gt;&lt;span class="n"&gt;csproj&lt;/span&gt; &lt;span class="p"&gt;-&lt;/span&gt;&lt;span class="n"&gt;Recurseforeach&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;file&lt;/span&gt; &lt;span class="k"&gt;in&lt;/span&gt; &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;csprojs&lt;/span&gt;&lt;span class="p"&gt;){&lt;/span&gt;    &lt;span class="n"&gt;updatefx&lt;/span&gt; &lt;span class="err"&gt;$&lt;/span&gt;&lt;span class="n"&gt;file&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FullName&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/-3s2H4vnM7k" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/05/retargeting-visual-studio-project-files-with-powershell/</feedburner:origLink></entry>
	
	<entry>
		<title>6 Thoughts about Evernote's App Design</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/-2kBBPUwtAM/" />
		<updated>2010-04-14T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2010/04/6-thoughts-about-evernotes-app-design</id>
		<category term="iphone" />
		<category term="android" />
		<category term="ipad" />
		<category term="app design" />
		<category term="mobile" />
		<category term="apps" />
		<category term="evernote" />
		<category term="design" />
		<category term="ux" />
		<content type="html">&lt;p&gt;Evernote is one of my favorite and most frequently used applications. The ubiquity of the service via all the devices in my life (laptop, desktop, iPhone, Nexus One, web, and iPad) and the ease in which I can capture and recall notes made adopting it into my daily workflow extremely easy. By taking a closer look at the clients, it became clear that the user experience, and the design decisions behind them, wasn't a happy accident.&lt;/p&gt;

&lt;p&gt;Lately I have been thinking about user design and experience as I prep my app for the App Store. Here are six things that stood out most about the Evernote iPhone app and the take-away ideas I got from looking closer at the app.&lt;/p&gt;

&lt;h3&gt;1. The mobile apps immediately present 4 distinct actions for note acquisition.&lt;/h3&gt;

&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2010/03/IMG_0448.png"&gt;&lt;img src="http://cache.kevfoo.com/2010/03/IMG_0448_thumb.png" title="IMG_0448" alt="IMG_0448" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Evernote breaks down into two key activities: note acquisition and note retrieval. Given the detached nature of the mobile device and the sluggishness still experienced with cellular networks, the note browsing and searching experience is not ideal. The constraints of the device and the unpredictable nature of the network, I believe, led to a focus on what a mobile device is good for (note capturing) and make that the key action in the mobile versions of its application.&lt;/p&gt;

&lt;p&gt;Having the app launch into the note acquisition screen implicitly signals to the user that this is the type of activity that you should be doing on the device. It seems counterintuitive to restrict features to simply not port them directly from the desktop or web offering. But by limiting the scope of the application, it actually maximizes the experience for the user. In Evernote's case they cannot completely focus on note capture at the expense of cutting out the other actions. These additional activities are included, but they are relegated to the tab bar on the iPhone and the sub menus on Android devices.&lt;/p&gt;

&lt;h3&gt;2. Smart layout and design can make sub-optimal experience tolerable&lt;/h3&gt;

&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2010/03/IMG_0450.png"&gt;&lt;img src="http://cache.kevfoo.com/2010/03/IMG_0450_thumb.png" title="IMG_0450" alt="IMG_0450" /&gt;&lt;/a&gt; &lt;a href="http://cache.kevfoo.com/2010/04/IMG_0466.png"&gt;&lt;img src="http://cache.kevfoo.com/2010/04/IMG_0466_thumb.png" title="IMG_0466" alt="IMG_0466" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Given the limited real estate available on mobile devices, it is unsurprising that note browsing is a sub-optimal experience. That being said, I think that Evernote does an excellent job making due with what little space it has. Visually we are given two options, depending on the orientation of the phone, in which we can browse our catalog of notes. While holding the phone in portrait mode, each note's metadata is visible and allows the user to see titles and tags in addition to a thumbnail image of the note. While holding the phone in landscape mode, the note browser is transformed into a tiled-thumbnail view which shows more notes in the visible frame. If you can recognize the note by the rough appearance or layout of the text, you can pretty rapidly find what you are looking for.&lt;/p&gt;

&lt;p&gt;Most people hold the phone in portrait mode so it follows that the default view is the easier of the two to quickly grasp. The two views provide the user with choices and trade offs: lower information density with a greater amount of detail or higher information density with less detail. By giving the user options, Evernote overcomes the inherent limitations of the mobile device and improves the user experience.&lt;/p&gt;

&lt;h3&gt;3. Search function is a key but clunky feature in the mobile app.&lt;/h3&gt;

&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2010/03/IMG_0449.png"&gt;&lt;img src="http://cache.kevfoo.com/2010/03/IMG_0449_thumb.png" title="IMG_0449" alt="IMG_0449" /&gt;&lt;/a&gt;&lt;a href="http://cache.kevfoo.com/2010/03/IMG_0452.png"&gt;&lt;img src="http://cache.kevfoo.com/2010/03/IMG_0452_thumb.png" title="IMG_0452" alt="IMG_0452" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Evernote has outstanding OCR software that makes everything searchable. Given that search is the killer feature of Evernote, it is surprising that search on mobile devices seems like a second-class citizen. The typical standard search box is visible on most of the non-note capturing screens, and the text search works as expected. Search does have some enhanced features like map view and search near here offered as options to help refine your search, but I am not a fan of either. The actual search queries appear to be executed on the server side and, as a result, the processing time can vary depending on your network connection. In order to do a location based search the app has to make network requests for the search results and get the map coordinates, and this typically translates to a noticeable wait when these types of searches are performed. I feel like search could cut out the location-based search filter entirely and be no worse off.&lt;/p&gt;

&lt;h3&gt;4. Sync Button is a "kitchen drawer" tab on the iPhone App&lt;/h3&gt;

&lt;p&gt;The sync tab is mislabeled, and the label masks all the other functions that are exposed on that tab. Contextually, account information and device-specific settings aren't readily associated to sync even though the sync process in Evernote synchronizes everything associated to your account. The action of synchronizing your notes could be integrated into the note screen, and the settings, account information, and about information could all be separate tabs managed by the tab controller already being utilized in the iPhone application. In fairness the move to limit the tabs is consistent with the less-is-more type of attitude, and the combination of the multiple actions into the single tab is most likely a compromise to simplify the interface.&lt;/p&gt;

&lt;h3&gt;5. The tips UX on the iPhone is well executed and non-obtrusive&lt;/h3&gt;

&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2010/04/evernotetips.jpg"&gt;&lt;img src="http://cache.kevfoo.com/2010/04/evernotetips_thumb.jpg" title="evernotetips" alt="evernotetips" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The tips screen, integrated into the main view of the Evernote iPhone app, is an excellent way of sharing information about features and activities without being pushy and obtrusive. With a smooth animation that peels back the main view to show the tips view, the user can get a quick suggestion on a feature and then be back capturing or browsing notes. This is a small but well executed design element that adds to the experience.&lt;/p&gt;

&lt;h3&gt;6. Sharp branding&lt;/h3&gt;

&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2010/03/IMG_0447.png"&gt;&lt;img src="http://cache.kevfoo.com/2010/03/IMG_0447_thumb.png" title="IMG_0447" alt="IMG_0447" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;As far as the aesthetics go, I like the Evernote logo. A combination of an elephant and piece of paper plays off the "memory like an elephant" saying and the note-based nature of the application. The logo, paired nicely with a soft green color and a nice font, is the focal point of the splash screen welcoming you into the application. The other platforms do not utilize a splash screen since the application load times aren't as great as the iPhone, but the same basic logo/font/color scheme is consistent in the icons used on all platforms.&lt;/p&gt;

&lt;h3&gt;Lessons learned from the Evernote app:&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Instead of frustrating users with clunky interfaces and hacks to enable certain features of your service or app, only port features or activities that enhance the service and take advantage of the features of mobile devices rather than expose the limitations of them.&lt;/li&gt;
&lt;li&gt;Focus on the activities that can capitalize on the advantages of a mobile device instead of fighting the platform.&lt;/li&gt;
&lt;li&gt;Optimize for those specific use cases that make sense that you want to capitalize on.&lt;/li&gt;
&lt;li&gt;Be ruthless in what you cut out or be stingy in what you put into the mobile version&lt;/li&gt;
&lt;li&gt;Be consistent in your branding, color scheme, and feel of your applications.&lt;/li&gt;
&lt;li&gt;Good design can always speak louder than any type of instruction.&amp;#160; Help users fall into the pit of success.&lt;/li&gt;
&lt;/ul&gt;


&lt;p&gt;&lt;em&gt;You can get the iPhone app in the &lt;a href="http://itunes.apple.com/WebObjects/MZStore.woa/wa/viewSoftware?id=281796108&amp;amp;mt=8"&gt;iTunes App Store&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/-2kBBPUwtAM" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/04/6-thoughts-about-evernotes-app-design/</feedburner:origLink></entry>
	
	<entry>
		<title>Monotouch Quickie: Network Indicator Tip</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/FqumA3B8V0o/" />
		<updated>2010-04-05T00:00:00-05:00</updated>
		<id>http://www.kevfoo.com/2010/04/monotouch-quickie-network-indicator-tip</id>
		<category term="iphone" />
		<category term="monotouch" />
		<category term="apps" />
		<category term="gc" />
		<category term="c#" />
		<category term="tips" />
		<category term="network" />
		<content type="html">&lt;p&gt;I've used this simple technique below many times in WinForms apps to toggle the wait cursor (hourglass) during long running operations and it is applicable for the situations that call for toggling the network activity indicator in Monotouch.When used with a using statement, the indicator is turned on when the object is constructed and turned off when the code within the using statement has finished executing and the object's Dispose method is called.&lt;/p&gt;

&lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:63442f2e-f2c9-436f-ae14-0a99c8efc4e1" style="margin: 0px; display: inline; float: none; padding: 0px;"&gt;&lt;pre style="background-color: #ffffff; white-space: pre-wrap; word-wrap: break-word; overflow: auto; font-family: Consolas; font-size: 11.25;"&gt;&lt;span style="color: #0000ff;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; NetworkIndicator : IDisposable{   &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; NetworkIndicator ()   {      UIApplication.SharedApplication.NetworkActivityIndicatorVisible &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;true&lt;/span&gt;&lt;span style="color: #000000;"&gt;;   }   &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;void&lt;/span&gt;&lt;span style="color: #000000;"&gt; Dispose ()   {      UIApplication.SharedApplication.NetworkActivityIndicatorVisible &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000ff;"&gt;false&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;/span&gt;&lt;span style="color: #000000;"&gt;            GC.SuppressFinalize(this);   }}&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;


&lt;p&gt;Usage:&lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:b22771bd-ad3c-4b68-a5ee-b2dcd3af7d42" style="margin: 0px; display: inline; float: none; padding: 0px;"&gt;&lt;pre style="background-color: #ffffff; white-space: pre-wrap; word-wrap: break-word; overflow: auto;"&gt;&lt;span style="color: #0000ff;"&gt;using&lt;/span&gt;&lt;span style="color: #000000;"&gt;(&lt;/span&gt;&lt;span style="color: #0000ff;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; NetworkIndicator()){    &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;Make network call here&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;}&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;&lt;/p&gt;

&lt;p&gt;You wouldn't want to wrap this around a UIWebView (add the toggling of the indicator to the LoadStarted and LoadFinished events) but anytime your app is making calls out the network you can wrap the using statement around the method invocation and get the user friendly network activity notification.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/FqumA3B8V0o" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/04/monotouch-quickie-network-indicator-tip/</feedburner:origLink></entry>
	
	<entry>
		<title>Thoughts on the Day of Mobile conference</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/12qOcpXTbXM/" />
		<updated>2010-03-08T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2010/03/thoughts-on-the-day-of-mobile-conference</id>
		<category term="iphone" />
		<category term="android" />
		<category term="mobile web" />
		<category term="conference" />
		<category term="dayofmobile" />
		<category term="mobile" />
		<content type="html">&lt;p&gt;Here is a collection of thoughts that I had about the &lt;a href="http://www.techinthemiddle.com/DayOfMobile/"&gt;Day of Mobile&lt;/a&gt; conference held at IIT last Saturday. This was the inaugural conference put together by the &lt;a href="http://www.techinthemiddle.com"&gt;Tech in the Middle&lt;/a&gt; guys, and I thought that they did a great job. I look forward to seeing what they do next.&lt;/p&gt;

&lt;h3&gt;Overall Themes&lt;/h3&gt;

&lt;p&gt;Two main themes that emerged during the sessions: the future of mobile is web-based apps rather than device specific apps, and the road to mobile riches probably doesn't run through an app store.&lt;/p&gt;

&lt;h3&gt;Multi-platform development is hard&lt;/h3&gt;

&lt;p&gt;Certainly scenarios exist where multi-platform apps make sense, but it is imperative that the risk/reward ratio be in your favor to have a chance to be successful. Don't underestimate the amount of effort and headaches that developing and supporting multi-platform apps will create. Going the mobile web app route has it's limitations, but it is the closest thing to "write once, run anywhere" that mobile has.&lt;/p&gt;

&lt;h3&gt;Cool Tools&lt;/h3&gt;

&lt;p&gt;Really cool tools like &lt;a href="http://www.phonegap.com"&gt;PhoneGap&lt;/a&gt; and &lt;a href="http://www.jqtouch.com"&gt;jQTouch&lt;/a&gt; are out there that help lower the barriers to making apps and, in the case of PhoneGap, multi-platform apps. Both tools have been released under MIT licenses and are free to use.&lt;/p&gt;

&lt;h3&gt;One Man's Secret Sauce for Success&lt;/h3&gt;

&lt;p&gt;David Whatley gave a funny presentation that provided a lot of laughs and some great insights into how the iPhone app store works. Even better was his ability to back up what he was saying with some real sales data and numbers. His secret sauce for success: PR, code re-use, and playing to your strengths.&lt;/p&gt;

&lt;h3&gt;App stores are glorified catalogs&lt;/h3&gt;

&lt;p&gt;Standing out or even being noticed amongst all the other apps is extremely difficult. Relying only on the app catalog to drive sales is effectively a "post and pray" strategy akin to trying to win the lottery. Try to find a niche and solve a problem. Focus on creating value for markets not just an app for it. Mark Murphy described many ways to &lt;a href="http://www.slideshare.net/commonsguy/making-money-at-mobile"&gt;make money in mobile&lt;/a&gt; other than direct app sales during his talk and in a series of blog posts about &lt;a href="http://www.androidguys.com/2010/03/04/android-business-models/"&gt;Android Business Models&lt;/a&gt;.&lt;/p&gt;

&lt;h3&gt;Links&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.phonegap.com"&gt;PhoneGap&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.jqtouch.com"&gt;jQTouch&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.iphonedevdepot.com"&gt;iPhone Dev Depot&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.slideshare.net/jschwan/mobile-web-development-tips-and-tricks"&gt;Mobile Web Development Tips and Tricks (Slides)&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.slideshare.net/commonsguy/making-money-at-mobile"&gt;Making Money at Mobile (Slides)&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://github.com/mikelaurence/CoreResource" title="http://github.com/mikelaurence/CoreResource"&gt;http://github.com/mikelaurence/CoreResource&lt;/a&gt; (Cool iPhone library)&lt;/li&gt;
&lt;/ul&gt;


&lt;h3&gt;Books Recommended During the Conference&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.amazon.com/gp/product/093849743X?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=093849743X"&gt;Aiming at Amazon&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.amazon.com/gp/product/1591841666?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=1591841666"&gt;The Dip&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.amazon.com/gp/product/0307409503?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=0307409503"&gt;The Whuffie Factor&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;p&gt;Overall, the signal-to-noise ratio at the conference was good but not great. I did manage to glean at least one or two new ideas from most of the sessions I attended, and it was great to see the enthusiasm that the Chicago tech community has for events like this.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/12qOcpXTbXM" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/03/thoughts-on-the-day-of-mobile-conference/</feedburner:origLink></entry>
	
	<entry>
		<title>Monotouch Binding Gotcha</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/EJ_d3hGy6mU/" />
		<updated>2010-02-15T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2010/02/monotouch-binding-gotcha</id>
		<category term="documentation" />
		<category term="gotcha" />
		<category term="objective-c" />
		<category term="api" />
		<category term="binding" />
		<category term="monotouch" />
		<content type="html">&lt;p&gt;I stumbled across a subtle gotcha while exploring binding Objective-C types in &lt;a href="http://monotouch.net/"&gt;MonoTouch&lt;/a&gt;. As luck would have it, someone else did also and posted a question about it on the &lt;a href="http://monotouch.net/Chat"&gt;MonoTouch IRC channel&lt;/a&gt;. The poster of the question eventually came across the answer and shared it there, and I am going to post it here in case anyone else makes the same mistake and is looking for some answers.&lt;/p&gt;

&lt;p&gt;I was following along with the documentation for &lt;a href="http://monotouch.net/Documentation/Binding_New_Objective-C_Types"&gt;binding new Objective-C types&lt;/a&gt; on the MonoTouch site, and as a way to ease into the binding process, I chose a class to define from the CloudMade SDK that I am looking to expose in MonoTouch. The class selected was the BBox class (&lt;a href="http://developers.cloudmade.com/repositories/entry/iphone-api/iphone-api/trunk/inc/CloudMade/bbox.h"&gt;bbox.h&lt;/a&gt;) and I went about creating the following API definition shown below:
  &lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:32446696-877b-4dce-94d1-62a9f74add99" style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px"&gt;&lt;pre style="background-color:#FFFFFF;white-space:-moz-pre-wrap; white-space: -pre-wrap; white-space: -o-pre-wrap; white-space: pre-wrap; word-wrap: break-word;overflow: auto;"&gt;&lt;span style="color: #0000FF;"&gt;using&lt;/span&gt;&lt;span style="color: #000000;"&gt; System;&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;using&lt;/span&gt;&lt;span style="color: #000000;"&gt; MonoTouch.Foundation;&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;using&lt;/span&gt;&lt;span style="color: #000000;"&gt; MonoTouch.ObjCRuntime;&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;namespace&lt;/span&gt;&lt;span style="color: #000000;"&gt; CloudMade{    [BaseType(&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;typeof&lt;/span&gt;&lt;span style="color: #000000;"&gt; (NSObject))]      &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;interface&lt;/span&gt;&lt;span style="color: #000000;"&gt; BBox    {        [Export(&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;westernLongitude&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;)]        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;float&lt;/span&gt;&lt;span style="color: #000000;"&gt; WesternLongitude {&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;get&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;set&lt;/span&gt;&lt;span style="color: #000000;"&gt;;}                [Export(&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;southernLatitude&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;)]        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;float&lt;/span&gt;&lt;span style="color: #000000;"&gt; SouthernLatitude {&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;get&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;set&lt;/span&gt;&lt;span style="color: #000000;"&gt;;}                [Export(&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;easternLongitude&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;)]        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;float&lt;/span&gt;&lt;span style="color: #000000;"&gt; EasternLongitude {&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;get&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;set&lt;/span&gt;&lt;span style="color: #000000;"&gt;;}                [Export(&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;northerLatitude&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;)]        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;float&lt;/span&gt;&lt;span style="color: #000000;"&gt; NorthernLatitude {&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;get&lt;/span&gt;&lt;span style="color: #000000;"&gt;;&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;set&lt;/span&gt;&lt;span style="color: #000000;"&gt;;}                [Export(&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;asString&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;)]        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;string&lt;/span&gt;&lt;span style="color: #000000;"&gt; AsString();    }}&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;&lt;div&gt;&lt;br/&gt;
  Once completed, I saved it as BBox.cs and attempted to generate the bindings by invoking btouch on the file.&amp;#160; You can see below the unsuccessful message I received. &lt;/div&gt;&lt;div&gt;&amp;#160;&lt;/div&gt;&lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:ded3f3e2-df9d-45b8-84f8-1be4953cd47a" style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px"&gt;&lt;pre style="background-color:#FFFFFF;white-space:-moz-pre-wrap; white-space: -pre-wrap; white-space: -o-pre-wrap; white-space: pre-wrap; word-wrap: break-word;overflow: auto;"&gt;&lt;span style="color: #000000;"&gt;$&lt;/span&gt;&lt;span style="color: #000000;"&gt; btouch BBox&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;cs &lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;var&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;folders&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;E4&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;E44PAZnZGKGpVrmseo2N3&lt;/span&gt;&lt;span style="color: #000000;"&gt;++++&lt;/span&gt;&lt;span style="color: #000000;"&gt;TI&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;-Tmp-&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;9qgrm9nm&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;lnv&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;CloudMade&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;BBox&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;g&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;cs&lt;/span&gt;&lt;span style="color: #000000;"&gt;(&lt;/span&gt;&lt;span style="color: #000000;"&gt;46&lt;/span&gt;&lt;span style="color: #000000;"&gt;,&lt;/span&gt;&lt;span style="color: #000000;"&gt;71&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;/span&gt;&lt;span style="color: #000000;"&gt;: error CS0117: &lt;code&gt;CloudMade&amp;lt;/span&amp;gt;&amp;lt;span style="color: #000000;"&amp;gt;.&amp;lt;/span&amp;gt;&amp;lt;span style="color: #000000;"&amp;gt;BBox' does &amp;lt;/span&amp;gt;&amp;lt;span style="color: #0000FF;"&amp;gt;not&amp;lt;/span&amp;gt;&amp;lt;span style="color: #000000;"&amp;gt; contain a definition &amp;lt;/span&amp;gt;&amp;lt;span style="color: #0000FF;"&amp;gt;for&amp;lt;/span&amp;gt;&amp;lt;span style="color: #000000;"&amp;gt;&lt;/code&gt;Messaging'&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;var&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;folders&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;E4&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;E44PAZnZGKGpVrmseo2N3&lt;/span&gt;&lt;span style="color: #000000;"&gt;++++&lt;/span&gt;&lt;span style="color: #000000;"&gt;TI&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;-Tmp-&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;9qgrm9nm&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;lnv&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;CloudMade&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;BBox&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;g&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;cs&lt;/span&gt;&lt;span style="color: #000000;"&gt;(&lt;/span&gt;&lt;span style="color: #000000;"&gt;28&lt;/span&gt;&lt;span style="color: #000000;"&gt;,&lt;/span&gt;&lt;span style="color: #000000;"&gt;30&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;/span&gt;&lt;span style="color: #000000;"&gt;: &lt;/span&gt;&lt;span style="color: #000000;"&gt;(&lt;/span&gt;&lt;span style="color: #000000;"&gt;Location of the symbol related to previous error&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;/span&gt;&lt;span style="color: #000000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;var&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;folders&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;E4&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;E44PAZnZGKGpVrmseo2N3&lt;/span&gt;&lt;span style="color: #000000;"&gt;++++&lt;/span&gt;&lt;span style="color: #000000;"&gt;TI&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;-Tmp-&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;9qgrm9nm&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;lnv&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;CloudMade&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;BBox&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;g&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;cs&lt;/span&gt;&lt;span style="color: #000000;"&gt;(&lt;/span&gt;&lt;span style="color: #000000;"&gt;57&lt;/span&gt;&lt;span style="color: #000000;"&gt;,&lt;/span&gt;&lt;span style="color: #000000;"&gt;71&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;/span&gt;&lt;span style="color: #000000;"&gt;: error CS0117: &lt;code&gt;CloudMade&amp;lt;/span&amp;gt;&amp;lt;span style="color: #000000;"&amp;gt;.&amp;lt;/span&amp;gt;&amp;lt;span style="color: #000000;"&amp;gt;BBox' does &amp;lt;/span&amp;gt;&amp;lt;span style="color: #0000FF;"&amp;gt;not&amp;lt;/span&amp;gt;&amp;lt;span style="color: #000000;"&amp;gt; contain a definition &amp;lt;/span&amp;gt;&amp;lt;span style="color: #0000FF;"&amp;gt;for&amp;lt;/span&amp;gt;&amp;lt;span style="color: #000000;"&amp;gt;&lt;/code&gt;Messaging'&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;var&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;folders&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;E4&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;E44PAZnZGKGpVrmseo2N3&lt;/span&gt;&lt;span style="color: #000000;"&gt;++++&lt;/span&gt;&lt;span style="color: #000000;"&gt;TI&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;-Tmp-&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;9qgrm9nm&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;lnv&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;CloudMade&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt;BBox&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;g&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;cs&lt;/span&gt;&lt;span style="color: #000000;"&gt;(&lt;/span&gt;&lt;span style="color: #000000;"&gt;28&lt;/span&gt;&lt;span style="color: #000000;"&gt;,&lt;/span&gt;&lt;span style="color: #000000;"&gt;30&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;/span&gt;&lt;span style="color: #000000;"&gt;: &lt;/span&gt;&lt;span style="color: #000000;"&gt;(&lt;/span&gt;&lt;span style="color: #000000;"&gt;Location of the symbol related to previous error&lt;/span&gt;&lt;span style="color: #000000;"&gt;)&lt;/span&gt;&lt;span style="color: #000000;"&gt;Compilation failed: &lt;/span&gt;&lt;span style="color: #000000;"&gt;2&lt;/span&gt;&lt;span style="color: #000000;"&gt; error&lt;/span&gt;&lt;span style="color: #000000;"&gt;(&lt;/span&gt;&lt;span style="color: #000000;"&gt;s&lt;/span&gt;&lt;span style="color: #000000;"&gt;),&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #000000;"&gt;0&lt;/span&gt;&lt;span style="color: #000000;"&gt; warningsbtouch: API binding contains errors&lt;/span&gt;&lt;span style="color: #000000;"&gt;.&lt;/span&gt;&lt;span style="color: #000000;"&gt;&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;&lt;div&gt;&lt;/p&gt;

&lt;p&gt;After looking at the errors and seeing the&lt;strong&gt;&lt;em&gt; &lt;code&gt;CloudMade.BBox' does not contain a definition for&lt;/code&gt;Messaging'&lt;/em&gt;&lt;/strong&gt; message, it looked as if I was missing a using statement.&amp;#160; However, this was not the case as &lt;em&gt;Messaging&lt;/em&gt; is a class in the MonoTouch.ObjCRuntime namespace and that namespace was already included in the using statements.&amp;#160; The problem actually turned out to be that the interface had the same name as the file and that had caused the issues shown above as the temporary classes generated during the process caused conflicts.&amp;#160; The solution to this issue was as simple as renaming the file to something other than whatever the interfaces you are defining are named.&lt;/div&gt;&lt;div&gt;&amp;#160;&lt;/div&gt;&lt;div&gt;So the moral of the story is:&lt;/div&gt;
&lt;strong&gt;&lt;em&gt;Do not give the file that the API definition is being saved in the same name as one of the interfaces that you are defining.&lt;/em&gt;&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Steer clear of that and you'll be binding Objective-C types with ease.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/EJ_d3hGy6mU" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/02/monotouch-binding-gotcha/</feedburner:origLink></entry>
	
	<entry>
		<title>Nexus One - First Impressions</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/yWen7hNS1bY/" />
		<updated>2010-02-09T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2010/02/nexus-one-first-impressions</id>
		<category term="iphone" />
		<category term="active desktop" />
		<category term="nexus one" />
		<category term="ux" />
		<category term="ui" />
		<category term="3gs" />
		<category term="review" />
		<content type="html">&lt;p&gt;My thoughts on the &lt;a href="http://www.google.com/phone"&gt;Nexus One&lt;/a&gt; and the Android OS? I like it. A lot.&lt;/p&gt;

&lt;h3&gt;Likes&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Speed. I have the older iPhone 3G hardware and from a user experience perspective it was not that bad. When compared to the Nexus One, however, it is down right sluggish. This probably isn't as big of a factor when comparing a 3GS versus Nexus One, but for someone coming from a 3G iPhone, it is a huge plus.&lt;/li&gt;
&lt;li&gt;Being able to run apps in the background. Browsing the web while streaming Pandora and downloading an app in the background works flawlessly and shows no noticeable signs of lag or sluggishness.&lt;/li&gt;
&lt;li&gt;The OLED screen is really nice. Higher resolution and OLED screen looks great in low-light situations and is supposed to save precious battery by not drawing less power than normal LCD screens.&lt;/li&gt;
&lt;li&gt;The Android OS is pretty sweet. It has a lot of nice features like the status bar, an active "desktop" that you can put interactive widgets on as well as app icons, and an easy way to get music and files on and off the device.&lt;/li&gt;
&lt;li&gt;Integration with Google Apps is fantastic as expected. I love getting mail and talk updates in the status bar and the overall experience with the apps on the Nexus One is better than on the iPhone.&lt;/li&gt;
&lt;/ul&gt;


&lt;h3&gt;Dislikes&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Cut and Paste is clunky.&amp;#160; I can see why Apple needed to spend awhile working out the UX issues before rolling it out.&lt;/li&gt;
&lt;li&gt;The touch interaction with the device has not been as good as the iPhone in my experience.&amp;#160; I am not sure where the blame lies (hardware or software), but I sometimes find it difficult to select elements in the UI.&amp;#160; This is not something that occurs frequently, but in the short time I've owned the device, it has occurred enough to be noticeable.&lt;/li&gt;
&lt;li&gt;4GB of storage out of the box is lacking.&amp;#160; It is an easy upgrade but given the amount of money that Google is charging for the device, this seems like they are skimping here.&lt;/li&gt;
&lt;li&gt;The &lt;a href="http://www.android.com/market/"&gt;Android Market&lt;/a&gt; place experience is integrated nicely but isn't as tightly integrated as the iTunes App Store.&amp;#160; This is arguably a good or a bad thing depending on how you look at it.&amp;#160; As a user this is a bad thing since it makes finding and buying apps more difficult than just popping open iTunes.&amp;#160; I've found the Android Marketplace, both on the phone and the web, hard to browse.&lt;/li&gt;
&lt;/ul&gt;


&lt;p&gt;There are a few negatives that I can't pin exclusively on the device but are still worth noting. I have been using my AT&amp;amp;T SIM with the Nexus One and most likely will do so until my contract is up in a few months. With that caveat out of the way, the talk quality seemed poor and the phone gets really hot when talking for periods greater than 10 minutes. I hesitate to even mention these issues since I am not using the phone on the network it was intended, but I know there probably are others considering doing what I did, and this feedback might help if someone is on the fence.&lt;/p&gt;

&lt;p&gt;The Nexus One is exactly the kind of phone and competition that was needed to push Apple. I strongly recommend anyone looking for a smartphone to give it serious consideration before running out and getting an iPhone.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/yWen7hNS1bY" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/02/nexus-one-first-impressions/</feedburner:origLink></entry>
	
	<entry>
		<title>iPhone Wireframes</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/0Wfdc38o728/" />
		<updated>2010-02-01T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2010/02/iphone-wireframes</id>
		<category term="notecards" />
		<category term="wireframes" />
		<category term="ui" />
		<category term="iphone" />
		<category term="design" />
		<content type="html">&lt;p&gt;I stumbled across a great collection of &lt;a href="http://www.geekchix.org/blog/2010/01/03/a-collection-of-printable-sketch-templates-and-sketch-books-for-wireframing/#mobi"&gt;iPhone wireframe templates&lt;/a&gt; tonight while going through my feeds. It got me thinking about the process I've been using to layout and design the app I am working on.&lt;/p&gt;

&lt;p&gt;I've been using regular 3 x 5' notecards to sketch out different screens for the iPhone app I am working on. On the ruled side I'll scribble notes and call out must/should/wish components of the screens to help prioritize features. On the blank side I've been sketching out wireframes of the screens to help get a feel for the UI and flow of the app.&lt;/p&gt;

&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2010/02/cards_laid_out.jpg"&gt;&lt;img src="http://cache.kevfoo.com/2010/02/cards_laid_out_thumb.jpg" title="cards_laid_out" alt="cards_laid_out" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I've played around with &lt;a href="http://www.balsamiq.com/"&gt;Balsamiq&lt;/a&gt; and, while the tool is fantastic, I find myself still partial to the notecards. With the same rough dimensions of the iPhone and the flexibility of being able to quickly rearrange and reorder the screens, the cards suit my preferences as a visual-spatial learner well. &lt;/p&gt;

&lt;p&gt;As with most tools and techniques, personal preference plays a large role in how and when they're employed. I always enjoy checking out how other people work and try and steal glean ideas from them. I've found the following blogs pretty useful for design, usability, and UX. I hope they help inspire you to create something cool.&lt;/p&gt;

&lt;p&gt;&lt;a href="http://wireframes.tumblr.com/"&gt;I (heart) wireframes&lt;/a&gt;&lt;br/&gt;
&lt;a href="http://infosthetics.com/"&gt;information aesthetics&lt;/a&gt;&lt;br/&gt;
&lt;a href="http://www.everydayux.com/"&gt;everydayUX&lt;/a&gt;&lt;br/&gt;
&lt;a href="http://sender11.typepad.com/sender11/"&gt;Sender 11&lt;/a&gt;&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/0Wfdc38o728" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/02/iphone-wireframes/</feedburner:origLink></entry>
	
	<entry>
		<title>MonoTouch Quickie : UIPasteboard Snippet</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/3tRWdtNzEqk/" />
		<updated>2010-01-26T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2010/01/monotouch-quickie-uipasteboard-snippet</id>
		<category term="apple" />
		<category term="iphone" />
		<category term="monotouch" />
		<category term="development" />
		<category term="uipasteboard" />
		<content type="html">&lt;p&gt;Came across the need to plop a string onto the clipboard (aka &lt;a href="http://go-mono.com/docs/monodoc.ashx?link=T%3aMonoTouch.UIKit.UIPasteboard"&gt;UIPasteboard&lt;/a&gt;) programatically last night and hit up the MonoTouch docs to see what was involved. It wasn't readily apparent what would work for the string expected to be passed as the SetValue method pasteboardType argument. Turns out, after digging into the official Apple docs, the string you need to provide is the Uniform Type Identifier (UTI) that corresponds to the data type being passed (in my case "public.utf8-plain-text"). For my future reference (always seems to take longer to find things at the iPhone doc site) here is a table of the relevant UTIs that might come in handy in the future.&lt;/p&gt;

&lt;table cellspacing="0" border="0" width="400" cellpadding="2"&gt;&lt;tbody&gt;     &lt;tr&gt;       &lt;td valign="top" width="200"&gt;string&lt;/td&gt;        &lt;td valign="top" width="200"&gt;public.utf8-plain-text&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td valign="top" width="200"&gt;JPEG&lt;/td&gt;        &lt;td valign="top" width="200"&gt;public.jpeg&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td valign="top" width="200"&gt;PNG&lt;/td&gt;        &lt;td valign="top" width="200"&gt;public.png&lt;/td&gt;     &lt;/tr&gt;      &lt;tr&gt;       &lt;td valign="top" width="200"&gt;Url&lt;/td&gt;        &lt;td valign="top" width="200"&gt;public.url&lt;/td&gt;     &lt;/tr&gt;   &lt;/tbody&gt;&lt;/table&gt;


&lt;p&gt;&lt;/p&gt;

&lt;p&gt;And for good measure here is a snippet that shows putting a string on the general clipboard and reading it off.&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre&gt;&lt;code class="csharp"&gt;&lt;span class="kt"&gt;string&lt;/span&gt; &lt;span class="n"&gt;clipboardText&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;&amp;quot;Copy and Paste Me!&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="n"&gt;UIPasteboard&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;General&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SetValue&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="n"&gt;NSString&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;clipboardText&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;&lt;span class="s"&gt;&amp;quot;public.utf8-plain-text&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="kt"&gt;string&lt;/span&gt; &lt;span class="n"&gt;actualClipboardText&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="n"&gt;UIPasteboard&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;General&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GetValue&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;&amp;quot;public.utf8-plain-text&amp;quot;&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="n"&gt;Assert&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;AreSame&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt; &lt;span class="n"&gt;clipboardText&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;actualClipboardText&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ToString&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;


&lt;p&gt;Enjoy.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Updated 1/30/2010: Replaced NSStrings with strings&lt;/em&gt;&lt;br/&gt;
&lt;em&gt;Updated 6/28/2012: Updated SetValue call to wrap up the C# string into an NSString as the API takes an NSObject now.&lt;/em&gt;&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/3tRWdtNzEqk" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2010/01/monotouch-quickie-uipasteboard-snippet/</feedburner:origLink></entry>
	
	<entry>
		<title>Chatsworth House Keeping and Update</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/cN0V4c3PGc8/" />
		<updated>2009-12-12T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/12/chatsworth-house-keeping-and-update</id>
		<category term="chatsworth" />
		<category term="chatroom" />
		<category term="chatbot" />
		<category term="documentation" />
		<category term="google" />
		<category term="gtalk" />
		<category term="iphone" />
		<category term="development" />
		<category term="projects" />
		<content type="html">&lt;p&gt;I just moved &lt;a href="http://blog.kevfoo.com/index.php/2009/01/chatsworth-a-google-talk-group-chat-bot/"&gt;Chatsworth&lt;/a&gt; from &lt;a href="http://code.google.com/p/chatsworth/"&gt;Google code&lt;/a&gt; over to its new home on &lt;a href="http://github.com/kevinmcmahon/chatsworth"&gt;github&lt;/a&gt;. I've got a couple more features in mind and figured now was as good a time as any to make the switch. I already host my &lt;a href="http://blog.kevfoo.com/index.php/2009/11/fun-with-monotouch-and-multi-level-table-views-without-interface-builder/"&gt;iPhone&lt;/a&gt; &lt;a href="http://blog.kevfoo.com/index.php/2009/11/monotouch-uialertview-uitextfield-crazy-delicious/"&gt;samples&lt;/a&gt; and some personal projects on github and, given the smoother branching and merging experience of git, I think it will be more conducive to spiking some features and trying some ideas out.&lt;/p&gt;

&lt;p&gt;As for the chatbot, I've recently added a link logging feature. Any URL sent to the chatroom now gets logged to the sqlite database. Users can query the database right from the chat window by entering &lt;em&gt;&lt;strong&gt;/links [number previous of to links return]&lt;/strong&gt;&lt;/em&gt; and the links, timestamp and the person who sent it will be sent in an individual IM to the requestor.&lt;/p&gt;

&lt;p&gt;Going forward, the two areas that I think need the most improvement are installation and documentation. The majority of the questions and feedback that I have received are setup and configuration related. Improving the installation and documentation stories at this point make the most sense and would be worth the effort. &lt;/p&gt;

&lt;p&gt;On the technical side of things, I am considering making a Chatsworth plugin for Windows Home Server. Currently I am running the service from my home server and, given the always on nature that suits the chatbot and the low/no maintenance needed to running once it is setup, the pairing seems natural and could help provide a little better setup and configuration experience.&lt;/p&gt;

&lt;p&gt;I hope to work on this more over the holidays and please feel free to reach out with a question or feedback. Enjoy.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/cN0V4c3PGc8" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/12/chatsworth-house-keeping-and-update/</feedburner:origLink></entry>
	
	<entry>
		<title>Monotouch: UIAlertView + UITextField = Crazy Delicious</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/pWuHIWpzFGA/" />
		<updated>2009-11-28T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/11/monotouch-uialertview-uitextfield-crazy-delicious</id>
		<category term="apple" />
		<category term="ui" />
		<category term="cocoa" />
		<category term="itunes" />
		<category term="iphone" />
		<category term="monotouch" />
		<category term="ios" />
		<category term="development" />
		<category term="uitextfield" />
		<category term="uialertview" />
		<content type="html">&lt;p&gt;If you have ever tried to buy or install anything from the App Store or iTunes on your iPhone, then you certainly have been prompted for your password by a screen that looks like this:&lt;/p&gt;

&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2009/11/itunes_pw_iphone.jpg"&gt;&lt;img src="http://cache.kevfoo.com/2009/11/itunes_pw_iphone_thumb.jpg" title="itunes_pw_iphone" alt="itunes_pw_iphone" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The control used by Apple to prompt you for your password isn't available out-of-the-box in Cocoa Touch, but fortunately it is pretty easy to roll your own. I've put together a &lt;a href="http://github.com/kevinmcmahon/CustomUITextFieldAlertView"&gt;sample project&lt;/a&gt; that shows a couple different techniques that are available for creating and customizing the control, and I'll go over a few of them here.&lt;/p&gt;

&lt;p&gt;The stock &lt;a href="http://www.go-mono.com/docs/index.aspx?link=T%3AMonoTouch.UIKit.UIAlertView%2FP"&gt;UIAlertView&lt;/a&gt; control consists of a title label, message label, and typically one or more buttons. It is important to note that in Monotouch, a default button setup isn't configured, and buttons have to be added explicitly. If a UIAlertView is configured without any buttons, then dismissing the control will have to be done programmatically because the user will have no way to dismiss the control. In both of my examples I've configured the control to have two buttons (Cancel and Ok), but I could have gotten by with just one. If only one button is used, it is important to also note that the button is considered the Cancel button by the control, and the &lt;a href="http://www.go-mono.com/docs/monodoc.ashx?link=P%3aMonoTouch.UIKit.UIAlertView.CancelButtonIndex"&gt;CancelButtonIndex&lt;/a&gt; property will refer to that button.&lt;/p&gt;

&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2009/11/Basic_UIAlertView.png"&gt;&lt;img src="http://cache.kevfoo.com/2009/11/Basic_UIAlertView_thumb.png" title="Basic_UIAlertView" alt="Basic_UIAlertView" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The easiest way to go about composing a UIAlertView with a &lt;a href="http://www.go-mono.com/docs/monodoc.ashx?link=T%3aMonoTouch.UIKit.UITextField"&gt;UITextField&lt;/a&gt; is to create an instance of a UITextField and add it as a sub-view. Since you're adding a layer on top of UIAlertView's view, the key will be fitting this new control into the UI. There are two ways of going about this. The first and maybe most obvious way to solve this problem is to make some room between the message label and buttons for the text field ala the iTunes password prompt. Since the UIAlertView control has already been laid out, moving those controls around within the frame is not as straight forward a task as it may seem. Before we tackle that we will explore a simpler method that overlays the text field directly on top of the message label. You sacrifice being able to display an additional message to the user, but the end result looks professional and is very easy to implement. This will also be the basis for getting the control to have the same look and feel as the iTunes password prompt, so it is important to understand this prior to attempting to move the controls around.&lt;/p&gt;

&lt;p&gt;The key to overlaying the text field on top of the message label is setting the bounding rectangle for the UITextField. The bounding rectangle is where the text field draws the box in which a user enters text. For our purposes, the rectangle needs to be drawn in between the title label and the buttons. It is important to make sure that it covers the area where the message label is drawn. Thanks to the work of others we know that if we start drawing the text field at the x,y offset of 12,45 that the text field will hide the message label.&lt;/p&gt;

&lt;p&gt;The code to overlay the text field is as follows:
  &lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:5cf6cd71-f852-4415-a2b2-654336f59dbe" style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px"&gt;&lt;pre style="background-color:#FFFFFF;white-space:-moz-pre-wrap; white-space: -pre-wrap; white-space: -o-pre-wrap; white-space: pre-wrap; word-wrap: break-word;overflow: auto;"&gt;&lt;span style="color: #0000FF;"&gt;void&lt;/span&gt;&lt;span style="color: #000000;"&gt; PromptForName(HandlerToUse handlerType){    UITextField tf &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; UITextField (&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; System.Drawing.RectangleF (12f, 45f, 260f, 25f));    tf.BackgroundColor &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; UIColor.White;    tf.UserInteractionEnabled &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;true&lt;/span&gt;&lt;span style="color: #000000;"&gt;;    tf.AutocorrectionType &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; UITextAutocorrectionType.No;    tf.AutocapitalizationType &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; UITextAutocapitalizationType.None;    tf.ReturnKeyType &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; UIReturnKeyType.Done;    tf.SecureTextEntry &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;false&lt;/span&gt;&lt;span style="color: #000000;"&gt;;         UIAlertView myAlertView &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; UIAlertView    {        Title &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Please enter your name&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;,        Message &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;this line is hidden&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;    };        myAlertView.AddButton(&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Cancel&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;);    myAlertView.AddButton(&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;Ok&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;);    myAlertView.AddSubview(tf);    &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt; More Setup Goes Here&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;    myAlertView.Show ();}&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;
The method starts by instantiating a UITextField control with a bounding rectangle passed via its constructor. The rectangle itself is constructed with four parameters via its constructor: the first two parameters set the x and y offset from the origin point of the control, and the last two parameters set the size of the drawing area. After the initial construction of the UITextField, a few additional properties are set to customize the display. &lt;/p&gt;

&lt;p&gt;Among the properties set is the &lt;em&gt;SecureTextEntry&lt;/em&gt;. Setting this property to true will make the text field act like a password field and hide all the characters that you've entered. Once the text field has been created and initialized, we move on to creating a UIAlertView. Via object initialization, the &lt;em&gt;Title&lt;/em&gt; and &lt;em&gt;Message&lt;/em&gt; properties are set with some text. Finally, two buttons are created, and the text field is added as a sub-view to the UIAlertView. Calling the show on the UIAlertView causes the alert to pop up. Below you can see the rendered control.&lt;/p&gt;

&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2009/11/TextField_As_Subview_UIAlertView.png"&gt;&lt;img src="http://cache.kevfoo.com/2009/11/TextField_As_Subview_UIAlertView_thumb.png" title="TextField_As_Subview_UIAlertView" alt="TextField_As_Subview_UIAlertView" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;So now that we have the basic control setup, we can tweak it so that the text field and the message label can both be displayed.&lt;/p&gt;

&lt;p&gt;If you recall our custom UIAlertView control is currently composed of two UILabels, two UIButtons and a UITextField that we added. The UILabels are derived from UIView and is not a subclass of UIControl; whereas, the UIButton and the UITextField are both derived from UIControls. Since we want to position the UITextField beneath the labels, we can use this knowledge to selectively shift only the UIControls in the view down leaving the title and message labels in place.&lt;/p&gt;

&lt;p&gt;To accomplish this task the following steps need to be performed:&lt;/p&gt;

&lt;p&gt;1) The control height needs to be increased to make space for the text field and provide additional space to move the UIControls. This is done by setting the frame to a larger size. The frame will be increased by the height of the text field plus a buffer, so the control has space between it and the others.   This is what the frame looks like after being enlarged:   &lt;a href="http://cache.kevfoo.com/2009/11/FrameEnlarged_CustomUIAlertView.png"&gt;&lt;img src="http://cache.kevfoo.com/2009/11/FrameEnlarged_CustomUIAlertView_thumb.png" title="FrameEnlarged_CustomUIAlertView" alt="FrameEnlarged_CustomUIAlertView" /&gt;&lt;/a&gt;&lt;br/&gt;
2) Once the frame has been enlarged, we'll loop through the sub-views looking for UIControls and adjust only those types down by the same text field plus buffer offset   Here is what the control looks like after each UIControl is found during the iteration through the sub-views.&lt;/p&gt;

&lt;p&gt;&lt;a href="http://cache.kevfoo.com/2009/11/FirstUIControlShifted_CancelButton.png"&gt;&lt;img src="http://cache.kevfoo.com/2009/11/FirstUIControlShifted_CancelButton_thumb.png" title="FirstUIControlShifted_CancelButton" alt="FirstUIControlShifted_CancelButton" /&gt;&lt;/a&gt;&lt;a href="http://cache.kevfoo.com/2009/11/SecondUIControlShifted_OkButton.png"&gt;     &lt;img src="http://cache.kevfoo.com/2009/11/SecondUIControlShifted_OkButton_thumb.png" title="SecondUIControlShifted_OkButton" alt="SecondUIControlShifted_OkButton" /&gt;&lt;/a&gt;   &lt;a href="http://cache.kevfoo.com/2009/11/FinalUIControlShifted_TextField.png"&gt;&lt;img src="http://cache.kevfoo.com/2009/11/FinalUIControlShifted_TextField_thumb.png" title="FinalUIControlShifted_TextField" alt="FinalUIControlShifted_TextField" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Here is the code that does the control adjustment:&lt;/p&gt;

&lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:ad10f1fa-b7f3-477a-8553-a24998ed586e" style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px"&gt;&lt;pre style="background-color:#FFFFFF;white-space:-moz-pre-wrap; white-space: -pre-wrap; white-space: -o-pre-wrap; white-space: pre-wrap; word-wrap: break-word;overflow: auto;"&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; TextFieldAlertView : UIAlertView{    &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;private&lt;/span&gt;&lt;span style="color: #000000;"&gt; UITextField _tf;        &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt; ... &lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;private&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;void&lt;/span&gt;&lt;span style="color: #000000;"&gt; AdjustControlSize()    {        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;float&lt;/span&gt;&lt;span style="color: #000000;"&gt; tfExtH &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; _tf.Frame.Size.Height &lt;/span&gt;&lt;span style="color: #000000;"&gt;+&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #800080;"&gt;16.0f&lt;/span&gt;&lt;span style="color: #000000;"&gt;;                var frame &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; RectangleF(&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;.Frame.X,                                    &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;.Frame.Y &lt;/span&gt;&lt;span style="color: #000000;"&gt;-&lt;/span&gt;&lt;span style="color: #000000;"&gt; tfExtH&lt;/span&gt;&lt;span style="color: #000000;"&gt;/&lt;/span&gt;&lt;span style="color: #800080;"&gt;2&lt;/span&gt;&lt;span style="color: #000000;"&gt;,                                    &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;.Frame.Size.Width,                                    &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;.Frame.Size.Height &lt;/span&gt;&lt;span style="color: #000000;"&gt;+&lt;/span&gt;&lt;span style="color: #000000;"&gt; tfExtH);                &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;.Frame &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; frame;                &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;foreach&lt;/span&gt;&lt;span style="color: #000000;"&gt;(var view &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;in&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;.Subviews)        {            &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;if&lt;/span&gt;&lt;span style="color: #000000;"&gt;(view &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;is&lt;/span&gt;&lt;span style="color: #000000;"&gt; UIControl)            {                view.Frame &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; RectangleF(view.Frame.X,                                            view.Frame.Y &lt;/span&gt;&lt;span style="color: #000000;"&gt;+&lt;/span&gt;&lt;span style="color: #000000;"&gt; tfExtH,                                            view.Frame.Size.Width,                                            view.Frame.Size.Height);            }        }    }}&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;


&lt;p&gt;So now that the desired look and feel of the control has been established, it is time to wire up the control.  There are a couple options for handling events generated by the control: one is more in line with how Cocoa handles events, and another that is similar to how .Net works. &lt;/p&gt;

&lt;p&gt;The Cocoa way to wire up delegates involves subclassing a special delegate class associated to the control and selectively overriding the methods for the actions you want to customize. In the case of the UIAlertView control, that delegate class is a &lt;a href="http://www.go-mono.com/docs/index.aspx?link=C%3AMonoTouch.UIKit.UIAlertViewDelegate"&gt;UIAlertViewDelegate&lt;/a&gt;. The delegate class includes overridable methods like &lt;em&gt;Clicked&lt;/em&gt; where you can define the actions to take when a button on the control is clicked or where you can extend behaviors by overriding methods like &lt;em&gt;Preseneted&lt;/em&gt; which is called after the control has been displayed to the user.&lt;/p&gt;

&lt;p&gt;The .Net way to wire up events is to provide specific delegates for specific events. To make interacting with the Cocoa Touch controls easier, Monotouch provides public events for each one of the methods that can be overridden in the UIAlertViewDelegate class. Having the individual public events makes wiring up controls more intuitive for the .Net developer, but it is good to know about the Cocoa-style approach especially when looking at Objective-C examples and/or ADC docs. I have examples of wiring up the control via both methods in the example source.&lt;/p&gt;

&lt;p&gt;The last topic I'd like to cover briefly is how I encapsulated the customization of control by subclassing UIAlertView. The key to getting the control to look right is to override the LayoutSubviews method and build out the text field, add it to the UIAlertView and shift the controls around there.&lt;/p&gt;

&lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:8d5d040c-523d-4749-9da5-93a758fb8e3a" style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px"&gt;&lt;pre style="background-color:#FFFFFF;white-space:-moz-pre-wrap; white-space: -pre-wrap; white-space: -o-pre-wrap; white-space: pre-wrap; word-wrap: break-word;overflow: auto;"&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;override&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;void&lt;/span&gt;&lt;span style="color: #000000;"&gt; LayoutSubviews (){    &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt; layout the stock UIAlertView&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;    &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;base&lt;/span&gt;&lt;span style="color: #000000;"&gt;.LayoutSubviews ();        &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt; build out the text field&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;    _tf &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; ComposeTextFieldControl(_secureTextEntry);        &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt; add the text field to the UIAlertView&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;    &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;.AddSubview(_tf);        &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt; shift the UIControls to fit the text field&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;    AdjustControlSize();}&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;


&lt;p&gt;&lt;/p&gt;

&lt;p&gt;I've added some more customizations to my subclassed UIAlertView control that allows you to enable the text field security via a constructor parameter and a tweak to the control's Transform property to shift the control up so it isn't hidden by the keyboard. You can see those changes and the entire working example &lt;a href="http://github.com/kevinmcmahon/CustomUITextFieldAlertView"&gt;here on github&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Enjoy.&lt;/p&gt;

&lt;p&gt;Links to some of the resources used:
  - &lt;a href="http://iphonedevelopment.blogspot.com/2009/02/alert-view-with-prompt.html"&gt;Alert View with Prompt (iPhone Development Blog)&lt;/a&gt;
  - &lt;a href="http://junecloud.com/journal/code/displaying-a-password-or-text-entry-prompt-on-the-iphone.html"&gt;Displaying a password or text entry prompt on the iPhone (Junecode Blog)&lt;/a&gt;
  - &lt;a href="http://codesofa.com/blog/archive/2009/07/15/look-uialertview-is-dating-uitableview.html"&gt;Look UIAlertView is Dating UITableView (codesofa)&lt;/a&gt;
  - &lt;a href="http://developer.apple.com/iphone/library/documentation/UIKit/Reference/UIAlertViewDelegate_Protocol/UIAlertViewDelegate/UIAlertViewDelegate.html"&gt;iPhone Dev Center: UIAlertViewDelegate Protocol Reference (Apple, &lt;em&gt;login required&lt;/em&gt;)&lt;/a&gt;&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/pWuHIWpzFGA" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/11/monotouch-uialertview-uitextfield-crazy-delicious/</feedburner:origLink></entry>
	
	<entry>
		<title>Fun with Monotouch and Multi-Level Table Views without Interface Builder</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/vKE_sH714XY/" />
		<updated>2009-11-22T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/11/fun-with-monotouch-and-multi-level-table-views-without-interface-builder</id>
		<category term="thesaurus" />
		<category term="app development" />
		<category term="rss reader" />
		<category term="programming guide" />
		<category term="monospace" />
		<category term="development" />
		<category term="monotouch" />
		<category term="iphone" />
		<category term="cocoa touch" />
		<category term="example tutorials" />
		<category term="interface builder" />
		<category term="mac mini" />
		<category term="development" />
		<category term="iphone" />
		<category term="cocoa touch" />
		<category term="c#" />
		<category term="uitableviewcontroller" />
		<category term="uitableview" />
		<content type="html">&lt;p&gt;With the recent release of &lt;a href="http://monotouch.net/"&gt;Monotouch&lt;/a&gt;, which enabled development for the iPhone/iPod Touch platform using C# and .Net, it seemed like the perfect time to take a swing at mobile app development. The strong appeal of being able to leverage my C# and .Net experience while scratching an itch that I have had for a few apps was more than enough to entice me to order a brand new &lt;a href="http://www.amazon.com/gp/product/B002QQ8CC4?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=B002QQ8CC4"&gt;Mac mini&lt;/a&gt;&lt;img src="http://www.assoc-amazon.com/e/ir?t=kev02-20&amp;amp;l=as2&amp;amp;o=1&amp;amp;a=B002QQ8CC4" alt="" /&gt; and start learning the Cocoa framework.&lt;/p&gt;

&lt;p&gt;My pet app project requires some pretty basic multi-level tabular data visualization, so that was the first thing I attempted to tackle. I started my learning endeavor by reading the &lt;a href="http://developer.apple.com/iphone/library/featuredarticles/ViewControllerPGforiPhoneOS/Introduction/Introduction.html"&gt;view controller programming guide&lt;/a&gt; from &lt;a href="http://developer.apple.com"&gt;Apple's ADC&lt;/a&gt; and working through a few of the &lt;a href="http://monotouch.net/Tutorials"&gt;tutorials&lt;/a&gt; listed on the Monotouch site. One of the example tutorials listed was for &lt;a href="http://www.alexyork.net/blog/post/UINavigationController-with-MonoTouch-Building-a-simple-RSS-reader-Part-1.aspx"&gt;a basic RSS reader&lt;/a&gt;. Armed with his guide, I got up and running with a basic table view allowed me to drill down one level deep and return to the root via navigation button. This was a great introduction and the easy to follow steps combined with the screenshots certainly hit the mark; however, this was not quite the layout I was looking for.&lt;/p&gt;

&lt;p&gt;The data that I wanted to display calls for more than just a list-view-to-detail-view relationship that the RSS reader implemented. As a beginner trying to figure out how to wire up my custom table controllers to each other and the navigation controller all via Interface Builder resulted in a lot of thrashing and a lot of ugly code. I eventually was able to roughly approximate the behavior I wanted, but it was pretty obvious to me there had to be a better way.&lt;/p&gt;

&lt;p&gt;I set out to see if I could find more Monotouch examples to see if I could pick up some tips and stumbled across &lt;a href="http://conceptdev.blogspot.com/"&gt;Craig Dunn's blog&lt;/a&gt;. Craig not only put together apps for the Monospace and PDC conferences (and graciously provided the source) but also posted a &lt;a href="http://conceptdev.blogspot.com/2009/10/monotouch-rogets-1911-thesaurus.html"&gt;Roget's Thesaurus&lt;/a&gt; app that was just what I was looking for. It was a simple app, but it had all the elements in play that I was looking for and an &lt;a href="http://3.bp.blogspot.com/_Ba76y6K7kvs/Su66_wEzO3I/AAAAAAAABIQ/9MzCAwYQ-HQ/s1600-h/RogetPlacemat.png"&gt;incredible diagram&lt;/a&gt; that tied it all together.&lt;/p&gt;

&lt;p&gt;One of the key tips and tricks I picked up from Craig's code was how easy it was to cut out the Interface Builder from the process. I also generally tend to avoid using the designer whenever possible in Visual Studio but here it was a key factor in my understand. This isn't to say that I'd never use the Interface Builder again or that it doesn't have its uses because it does but there was &lt;em&gt;too much&lt;/em&gt; magic going on in how Monotouch links up the XIBs to their backing C# classes. It wasn't until I started explicitly creating views and view controllers instead of trying to wire them up after the fact did I start to understand how things were supposed to interact.&lt;/p&gt;

&lt;p&gt;To implement a custom &lt;strong&gt;UITableViewController&lt;/strong&gt; you need to set two properties with custom classes and override a method which is invoked by the framework when the view controller is loaded. You'll need to set the TableDelegate and DataSource properties on the controller with your own implementations of &lt;strong&gt;UITableViewDelegate &lt;/strong&gt;and &lt;strong&gt;UITableViewDataSource&lt;/strong&gt;. The implementation of the table delegate allows you to customize how the table will respond to certain events and the data source implementation provides not only the data the table uses but also how that data is to be displayed within the table. Typically the ViewDidLoad method is overriden to perform the view setup work needed during initialization of the view controller. Within the method the TableDelegate and DataSource properties can be set.&lt;/p&gt;

&lt;p&gt;Example setting the TableDelegate and DataSource via the ViewDidLoad method:&lt;/p&gt;

&lt;p&gt;  &lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:18bc747e-a016-49a3-889d-2df3afb9f710" style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px"&gt;&lt;pre style="background-color:#FFFFFF;overflow: auto;"&gt;&lt;span style="color: #0000FF;"&gt;namespace&lt;/span&gt;&lt;span style="color: #000000;"&gt; MultiLevelTableView{    [MonoTouch.Foundation.Register(&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;RootViewController&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;)]    &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;partial&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; RootViewController : UITableViewController    {        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; DataSource : UITableViewDataSource { &lt;/span&gt;&lt;span style="color: #008000;"&gt;/&lt;em&gt;&lt;/span&gt;&lt;span style="color: #008000;"&gt; Impl Here &lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/em&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt; }        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; TableDelegate : UITableViewDelegate { &lt;/span&gt;&lt;span style="color: #008000;"&gt;/&lt;em&gt;&lt;/span&gt;&lt;span style="color: #008000;"&gt; Impl Here &lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/em&gt;/&lt;/span&gt;&lt;span style="color: #000000;"&gt; }                &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;override&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;void&lt;/span&gt;&lt;span style="color: #000000;"&gt; ViewDidLoad ()        {            &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;base&lt;/span&gt;&lt;span style="color: #000000;"&gt;.ViewDidLoad ();                        TableView.Delegate &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TableDelegate (&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;);            TableView.DataSource &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; DataSource (&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;);        }    }}&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;&lt;/p&gt;

&lt;p&gt;Example setting the properties during &lt;strong&gt;UITableView&lt;/strong&gt; construction:&lt;/p&gt;

&lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:ac5c342a-bdfc-49a2-89b8-5da3f272da4f" style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px"&gt;&lt;pre style="background-color:#FFFFFF;overflow: auto;"&gt;&lt;span style="color: #0000FF;"&gt;namespace&lt;/span&gt;&lt;span style="color: #000000;"&gt; MultiLevelTableView{    [MonoTouch.Foundation.Register(&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;RootViewController&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;)]    &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;partial&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; RootViewController : UITableViewController    {        UITableView tableView;                &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; DataSource : UITableViewDataSource { &lt;/span&gt;&lt;span style="color: #008000;"&gt;/*&lt;/span&gt;&lt;span style="color: #008000;"&gt; Impl Here &lt;/span&gt;&lt;span style="color: #008000;"&gt;*/&lt;/span&gt;&lt;span style="color: #000000;"&gt; }        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; TableDelegate : UITableViewDelegate { &lt;/span&gt;&lt;span style="color: #008000;"&gt;/*&lt;/span&gt;&lt;span style="color: #008000;"&gt; Impl Here &lt;/span&gt;&lt;span style="color: #008000;"&gt;*/&lt;/span&gt;&lt;span style="color: #000000;"&gt; }                &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;override&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;void&lt;/span&gt;&lt;span style="color: #000000;"&gt; ViewDidLoad ()        {            &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;base&lt;/span&gt;&lt;span style="color: #000000;"&gt;.ViewDidLoad ();                        tableView &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; UITableView()            {                Delegate &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TableViewDelegate(&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;),                DataSource &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; TableViewDataSource(&lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;),            };                        &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;You can set more properties here like size and            &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt;location in the frame etc.&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;                        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;.View.AddSubview(tableView);        }    }}&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;


&lt;p&gt;The meat of the table view controller falls in the implementations of the DataSource and TableDelegate.&lt;/p&gt;

&lt;p&gt;A basic DataSource setup involves overriding two methods used by parent controller.  The RowsInSection method tells how many rows need to be displayed in the table and the GetCell method returns a cell view which was customized for display by setting the text and display properties.&lt;/p&gt;

&lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:c5c83938-3d1d-47b9-8e66-91d91b0673c8" style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px"&gt;&lt;pre style="background-color:#FFFFFF;white-space:-moz-pre-wrap; white-space: -pre-wrap; white-space: -o-pre-wrap; white-space: pre-wrap; word-wrap: break-word;overflow: auto;"&gt;&lt;span style="color: #0000FF;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; DataSource : UITableViewDataSource{    &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;static&lt;/span&gt;&lt;span style="color: #000000;"&gt; NSString kCellIdentifier &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; NSString (&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #800000;"&gt;MyIdentifier&lt;/span&gt;&lt;span style="color: #800000;"&gt;"&lt;/span&gt;&lt;span style="color: #000000;"&gt;);    RootViewController tvc;        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; DataSource (RootViewController tvc)    {        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;.tvc &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; tvc;    }        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;override&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;int&lt;/span&gt;&lt;span style="color: #000000;"&gt; RowsInSection (UITableView tableView, &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;int&lt;/span&gt;&lt;span style="color: #000000;"&gt; section)    {        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; tvc.RootData.Count;    }    &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;override&lt;/span&gt;&lt;span style="color: #000000;"&gt; UITableViewCell GetCell (UITableView tableView, NSIndexPath indexPath)    {        var cell &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; tableView.DequeueReusableCell (kCellIdentifier);                &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;if&lt;/span&gt;&lt;span style="color: #000000;"&gt; (cell &lt;/span&gt;&lt;span style="color: #000000;"&gt;==&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)        {            cell &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; UITableViewCell (UITableViewCellStyle.Default, kCellIdentifier);        }                cell.TextLabel.Text &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; tvc.RootData.ElementAt(indexPath.Row);        cell.Accessory &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; UITableViewCellAccessory.DetailDisclosureButton;        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;return&lt;/span&gt;&lt;span style="color: #000000;"&gt; cell;    }}&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;


&lt;p&gt;&lt;/p&gt;

&lt;p&gt;The TableDelegate is where the behavior of the table to various events is defined. It is here in which we load up the next view to display when a user clicks on a cell. A basic implementation of a table view delegate involves overriding the RowSelected method with instructions on what to do with the row now that it has been selected. If the node selected happened to be a leaf node for example we might load up the detail's view to display the nodes properties or if the node was the parent of more child nodes we would load another list view to continue to drill down into the data. In our case we want to drill down to the next layer of data which is managed by the SubGroupViewController.&lt;/p&gt;

&lt;div class="wlWriterEditableSmartContent" id="scid:57F11A72-B0E5-49c7-9094-E3A15BD5B5E6:598700d1-088c-449d-9ed0-f36c3bab6d9e" style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px"&gt;&lt;pre style="background-color:#FFFFFF;white-space:-moz-pre-wrap; white-space: -pre-wrap; white-space: -o-pre-wrap; white-space: pre-wrap; word-wrap: break-word;overflow: auto;"&gt;&lt;span style="color: #0000FF;"&gt;class&lt;/span&gt;&lt;span style="color: #000000;"&gt; TableDelegate : UITableViewDelegate{    RootViewController tvc;    SubGroupViewController sgvc;        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; TableDelegate (RootViewController tvc)    {        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;this&lt;/span&gt;&lt;span style="color: #000000;"&gt;.tvc &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; tvc;    }        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;public&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;override&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;void&lt;/span&gt;&lt;span style="color: #000000;"&gt; RowSelected (UITableView tableView, NSIndexPath indexPath)    {        &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt; get info from selected row&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;string&lt;/span&gt;&lt;span style="color: #000000;"&gt; selectedGroup &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; tvc.RootData.ElementAt(indexPath.Row);                &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt; load up new controller to display&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;        &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;if&lt;/span&gt;&lt;span style="color: #000000;"&gt;(sgvc &lt;/span&gt;&lt;span style="color: #000000;"&gt;==&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;null&lt;/span&gt;&lt;span style="color: #000000;"&gt;)            sgvc &lt;/span&gt;&lt;span style="color: #000000;"&gt;=&lt;/span&gt;&lt;span style="color: #000000;"&gt; &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;new&lt;/span&gt;&lt;span style="color: #000000;"&gt; SubGroupViewController(selectedGroup);                &lt;/span&gt;&lt;span style="color: #008000;"&gt;//&lt;/span&gt;&lt;span style="color: #008000;"&gt; push the controller on the navigation stack&lt;/span&gt;&lt;span style="color: #008000;"&gt;&lt;/span&gt;&lt;span style="color: #000000;"&gt;        tvc.NavigationController.PushViewController(sgvc, &lt;/span&gt;&lt;span style="color: #0000FF;"&gt;true&lt;/span&gt;&lt;span style="color: #000000;"&gt;);    }}&lt;/span&gt;&lt;/pre&gt;&lt;!-- Code inserted with Steve Dunn's Windows Live Writer Code Formatter Plugin.  http://dunnhq.com --&gt;&lt;/div&gt;


&lt;p&gt;&lt;/p&gt;

&lt;p&gt;The hang up for me with using Interface Builder to try and get the multi-level table views wired together was mostly due to not being familiar with the objects I was dealing with and not understanding what properties are needed to be initialized so the framework can display them correctly. Approaching the problem via the Interface Builder created a lot of noise that made seeing what was really needed to wire these table view controllers with the navigation controller difficult. In this case the the pre-packaged templates and generic layouts provided by Monotouch and Interface Builder were more of a hindrance than help but that is to be expected while learning a new technology.&lt;/p&gt;

&lt;p&gt;I've packaged up my &lt;a href="http://github.com/kevinmcmahon/MultiLevelTableView"&gt;implementation of a multi-level table view&lt;/a&gt; app and put it on github.  If anyone is looking for straight-forward, simple example of nesting table views hopefully this will help.&lt;/p&gt;

&lt;p&gt;I also recommend checking out the following links which helped me immensely:
  - &lt;a href="http://www.alexyork.net/blog/category/MonoTouch.aspx"&gt;Alex York's Monotouch posts including the RSS reader&lt;/a&gt;&amp;#160;
  - &lt;a href="http://sabonrai.wordpress.com/2009/08/28/monotouch-sample-code-uitableview/"&gt;Sabon Rai's Sample Code for UITableView&lt;/a&gt;
  - &lt;a href="http://conceptdev.blogspot.com/"&gt;Craig Dunn's Blog&lt;/a&gt;&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/vKE_sH714XY" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/11/fun-with-monotouch-and-multi-level-table-views-without-interface-builder/</feedburner:origLink></entry>
	
	<entry>
		<title>Tree Surgeon: Review and a couple tips</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/_w6HucXCTnI/" />
		<updated>2009-03-07T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/03/tree-surgeon-review-and-a-couple-tips</id>
		<category term="core library" />
		<category term="test framework" />
		<category term="documents folder" />
		<category term="twitter" />
		<category term="test project" />
		<category term="source tree" />
		<category term="zip files" />
		<category term="directory structure" />
		<category term="new projects" />
		<category term="codeplex" />
		<category term="nunit" />
		<category term="unit test" />
		<category term="source trees" />
		<category term="major tools" />
		<category term="couple tips" />
		<category term="assembly name" />
		<category term="test assembly" />
		<category term="tree surgeon" />
		<category term="project forums" />
		<category term="mbunit" />
		<category term="project" />
		<category term="development" />
		<content type="html">&lt;p&gt;This past week I was playing around with &lt;a href="https://hudson.dev.java.net/"&gt;Hudson&lt;/a&gt; and &lt;a href="http://www.jetbrains.com/teamcity/index.html"&gt;Team City&lt;/a&gt; and getting some NAnt scripts put together to use. In a happy coincidence I happened to catch a mention about &lt;a href="http://treesurgeon.codeplex.com/"&gt;Tree Surgeon&lt;/a&gt; from twitter and it had piqued my curiosity. Tree Surgeon is a project on &lt;a href="http://www.codeplex.com/"&gt;CodePlex&lt;/a&gt; that has been around for a while and helps automate the process of setting up a source tree and assembling build scripts. It was just what I was looking for.&lt;/p&gt;

&lt;p&gt;The goal of Tree Surgeon was to make setting up and laying out new projects using best practices dead simple. All the major tools and libraries that typically find their way into your .Net source trees are provided for you. In addition to laying out the directory structure for your source and libraries, a solution file gets created with three main projects to get you started. The basic project setup includes a console app, core library and unit test project. The build scripts come pre-wired to have NCover run your tests and generate reports from the results and also do things like packaging your build artifacts into zip files for deployment.&lt;/p&gt;

&lt;p&gt;The whole process, start to project generated, is very easy. Download and run the installer. Launch the program, select the version of Visual Studio (2003, 2005, and 2008) and the flavor of testing framework (NUnit or MbUnit) and then hit generate. The files and directories, built out in your Documents folder, are then created and ready to be used.&lt;/p&gt;

&lt;p&gt;There are two slight issues I ran into that I'd like to point out. Both issues had already been noted in the project forums and were easy to fix. When generating a source tree with MbUnit selected as the unit test framework, the build script generated has the unit test assembly referenced is named incorrectly. You will have to change it to match your project's unit test assembly name. The second issue has to do with running NCover and NUnit on x64 machines. I found that in order for NCover and NUnit to work on x64 machines I had to add two calls to the CorFlags utility to make executables work. This was accomplished by making the modifications to the "˜run-unit-tests' target below on lines 5-8.&lt;/p&gt;

&lt;div&gt;
    &lt;div style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;     &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;   1:&lt;/span&gt; &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;target&lt;/span&gt; &lt;span style="color: #ff0000"&gt;name&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;run-unit-tests&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;   2:&lt;/span&gt;     &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;mkdir&lt;/span&gt; &lt;span style="color: #ff0000"&gt;dir&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;${build.dir}\test-reports&amp;quot;&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;   3:&lt;/span&gt;     &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;exec&lt;/span&gt; &lt;span style="color: #ff0000"&gt;program&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;regsvr32&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;workingdir&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;tools\NCover&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;commandline&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;/s CoverLib.dll&amp;quot;&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;   4:&lt;/span&gt;     &lt;span style="color: #008000"&gt;&amp;lt;!-- Need the CorFlags Commands For x64 --&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;   5:&lt;/span&gt;     &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;exec&lt;/span&gt; &lt;span style="color: #ff0000"&gt;program&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;C:\Program Files\Microsoft SDKs\Windows\v6.0A\Bin\CorFlags&amp;quot;&lt;/span&gt; &lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;   6:&lt;/span&gt;         &lt;span style="color: #ff0000"&gt;workingdir&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;tools\NCover&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;commandline&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;NCover.Console.exe /32BIT+&amp;quot;&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;   7:&lt;/span&gt;     &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;exec&lt;/span&gt; &lt;span style="color: #ff0000"&gt;program&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;c:\Program Files\Microsoft SDKs\Windows\v6.0A\Bin\CorFlags&amp;quot;&lt;/span&gt; &lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;   8:&lt;/span&gt;         &lt;span style="color: #ff0000"&gt;workingdir&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;tools\NUnit&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;commandline&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;NUnit-Console.Exe /32BIT+&amp;quot;&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;   9:&lt;/span&gt;     &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;exec&lt;/span&gt; &lt;span style="color: #ff0000"&gt;program&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;tools\ncover\NCover.Console.exe&amp;quot;&lt;/span&gt; &lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;  10:&lt;/span&gt;         &lt;span style="color: #ff0000"&gt;workingdir&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;${build.dir}\Debug\UnitTests&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;  11:&lt;/span&gt;         &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;arg&lt;/span&gt; &lt;span style="color: #ff0000"&gt;value&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;//w &amp;amp;quot;.&amp;amp;quot;&amp;quot;&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;  12:&lt;/span&gt;         &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;arg&lt;/span&gt; &lt;span style="color: #ff0000"&gt;value&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;//x &amp;amp;quot;..\..\test-reports\Coverage.xml&amp;amp;quot;&amp;quot;&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;  13:&lt;/span&gt;         &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;arg&lt;/span&gt; &lt;span style="color: #ff0000"&gt;value&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;&amp;amp;quot;..\..\..\tools\nunit\nunit-console.exe&amp;amp;quot;&amp;quot;&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;  14:&lt;/span&gt;         &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;arg&lt;/span&gt; &lt;span style="color: #ff0000"&gt;value&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;&amp;amp;quot;MyProjectName.UnitTests.dll&amp;amp;quot; &lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;  15:&lt;/span&gt;             &amp;amp;quot;/xml:..\..\test-reports\UnitTests.xml&amp;amp;quot; &amp;amp;quot;/nologo&amp;amp;quot;&amp;quot; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;  16:&lt;/span&gt;     &lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;exec&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;    &lt;pre style="border-bottom-style: none; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: consolas, &amp;#39;Courier New&amp;#39;, courier, monospace; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #606060"&gt;  17:&lt;/span&gt; &lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;target&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;  &lt;/div&gt;&lt;/div&gt;


&lt;p&gt;Even though I am pretty late to the party with Tree Surgeon I am very happy to have stumbled across it. The whole source tree and build script setup process is the perfect thing to script out and I am really glad the project creator and contributors have taken the time to do this. It is a big help and I highly recommend you try it out the next time you are spinning up a new source tree for a project.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/_w6HucXCTnI" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/03/tree-surgeon-review-and-a-couple-tips/</feedburner:origLink></entry>
	
	<entry>
		<title>Alt.Net Seattle Recap</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/apuAZxBnYQs/" />
		<updated>2009-03-05T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/03/altnet-seattle-recap</id>
		<category term="conference" />
		<category term="developers" />
		<category term="software development" />
		<category term="open spaces" />
		<category term="linq" />
		<category term="seattle conference" />
		<category term="recap" />
		<category term="conferences" />
		<category term="alt.net" />
		<content type="html">&lt;p&gt;I spent last weekend at the Alt.Net Seattle conference and had some time to reflect on it. This was my first experience with an open spaces style conference, and I have to admit that I am a big fan of the format. While I am not convinced this format would work for every type of gathering, it fit the needs for this type of group very well.&lt;/p&gt;

&lt;p&gt;There was a lot made during a couple of sessions about being more accessible, newbie friendly and encouraging more new faces and ideas at these events. If you watch some of the video from Hanselman's &lt;a href="http://www.kyte.tv/shanselman#uri=channels/240253/361163"&gt;Why So Mean&lt;/a&gt; session, you can get the general gist of some of the problems and solutions offered. While I think introspection is generally a good thing, I am not convinced that any progress on this front will be made, and question if these issues are as bad as some may think. As a first-time Alt.Net conference attendee and having only met one other person there in real life prior to last weekend, I never felt unwelcome or shunned and everyone that I talked to was cordial and friendly and definitely open to discussion.&lt;/p&gt;

&lt;p&gt;However I didn't get on a plane to Seattle to talk about feelings. What drew me to the conference was the opportunity to talk about the software with some of the most passionate and opinionated developers in the world. By participating in the workshops and sessions, I was able to soak up and participate in some great conversations about agile and lean, LINQ, DDD, context/spec based testing, etc. These are topics that I don't always have the opportunity to discuss daily and certainly not with people who have the kind of expertise as those who were in Seattle. I've already been able to apply at work and on my side projects some of the things I've picked up, and I don't think I'm close to truly synthesizing all of the great conversations that I had.&lt;/p&gt;

&lt;p&gt;While my overall experience was positive and worth both the time and expense, I did feel like there were some minuses from the trip. Some of the sessions turned out to be essentially just presentations and spurred very little discussion or participation. I expected that there might be some of this due to the lack of experience or expertise with the tech. Sessions like Miguel de Icaza's on Mono and the iPhone fell into that category since virtually no one there had any experience with developing for the iPhone and even fewer with Mono, but even things like some of the discussions on more common topics like DDD or Agile were somewhat eyes forward discussions and lacked some of the give and take that really made some of the other sessions.&lt;/p&gt;

&lt;p&gt;Some of this may have been the result of people deferring to some of the &lt;em&gt;ahem&lt;/em&gt; stronger personalities or undisputed domain experts in the field. The presence of some of these personalities in the sessions clearly defined or dramatically shifted the discussions. It did not take me long to learn and apply the law of two feet when I found myself at the same sessions as some of these people. I knew that it was a matter of time until the session's conversation was going to degrade or grind to a halt. My last complaint about the conference is about some of the new age crap that that was brought in by the facilitator. I don't think the butterfly and bumblebee metaphor stuff or the ringing of the bell really added to the experience and was not needed. I know that the facilitators were trying to make this a very Zen-like experience, but it was not.&lt;/p&gt;

&lt;p&gt;In terms of key take-aways, I think I've identified a few. I talked with quite a few people about their experiences with agile and scrum. In hearing some other companies' practices and problems, I was comforted by the knowledge that my current company is not as dysfunctional as I thought. While I still think we can improve, I also realized that I should probably take a moment to appreciate the good things that we do and celebrate the stuff that what works well. The other take-away was that I feel like I am in a much better position to clearly articulate the goals that I had set for myself earlier this year. Prior to this weekend I had not done a good job articulating some of these goals and had yet to express them in SMART terms. Now I am going to incorporate things like contributions to open source projects and community demos and/or presentations into my measurables when tracking my progress on some of my goals.&lt;/p&gt;

&lt;p&gt;The future of these conferences I think will be in the local or region open spaces starting to be held. Already conferences are planned for Vancouver and Houston that seem to fit this bill because they are drawing in people from the region versus nationally based on a quick perusal of their attendee list. I speculate that if you reduce the concentration of some of the more well known personalities in the community, you might be able to make up for any potential loss of expertise with an increase in the amount of active participation from fresh new faces. Additionally, I think some might find the benefits of participating in open discussions with developers in their own communities more meaningful as these types of interactions may yield long-term benefits.&lt;/p&gt;

&lt;p&gt;Lastly, I'd like to thank the people of the Alt.Net Seattle group for putting this together, and you should be proud of the success the conference achieved. Job well done.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/apuAZxBnYQs" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/03/altnet-seattle-recap/</feedburner:origLink></entry>
	
	<entry>
		<title>Chatsworth: A Google talk group chat bot</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/aG_Uz2oL1SI/" />
		<updated>2009-01-26T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/01/chatsworth-a-google-talk-group-chat-bot</id>
		<category term="chat bots" />
		<category term="chatsworth" />
		<category term="unit-tests" />
		<category term="windows service" />
		<category term="jabber" />
		<category term="xmpp" />
		<category term="talk group" />
		<category term="group chat" />
		<category term="home server" />
		<category term="google" />
		<category term="google talk" />
		<category term="gtalk" />
		<category term="chat" />
		<category term="development" />
		<category term="c#" />
		<category term="projects" />
		<content type="html">&lt;p&gt;For the past year and a half, I've been using &lt;a href="http://techwalla.googlepages.com/"&gt;PartyChat&lt;/a&gt; to participate in multi-user chats with friends. PartyChat essentially provides IRC type functional via &lt;a href="http://talk.google.com"&gt;GTalk&lt;/a&gt; and has been a great way to have on going conversations throughout the day while avoiding 100+ email threads.&lt;/p&gt;

&lt;p&gt;The only pitfall PartyChat has to do with stability. PartyChat is a free service used by a large number of people, and it is run off the project creator's computer in his apartment. I do not know exactly why the service goes down intermittently, but the recipe of home server plus lots of users cannot be helping. While it stinks that PartyChat isn't always up, I understand I have no right to demand or expect 100% uptime, so I decided to do something about it. I leveraged some of the knowledge I picked up about XMPP, the protocol that Jabber and GTalk use, from another project and wrote a simple group chat bot called &lt;a href="http://code.google.com/p/chatsworth"&gt;Chatsworth&lt;/a&gt; to improve the availability of group chat that my friends and I use and depend on.&lt;/p&gt;

&lt;p&gt;Chatsworth is a windows service written in C# that provides basic chat room functionality. It does not have all the features that PartyChat has, but it does offer people the ability to setup and manage their own chat bots. Additionally, if you are concerned about having all your chat logs being available not just to Google but also to the people running the PartyChat servers, then Chatsworth is the group chat provider for you.  Chatsworth is fully functional but still immature and under development. I plan to add some additional features, take care of a few loose ends and provide more unit tests in the immediate future.&lt;/p&gt;

&lt;p&gt;Admittedly I could've just downloaded the PartyChat java source, compiled it, and ran it on my own set of servers, but where is the fun in that? I figured rolling my own chat bot would give me the opportunity to do more than address some of the availability issues I was having. Starting up Chatsworth provides me a non-trivial project that I can use to explore different software development concepts and techniques as well as get some code and design samples out on the web. So if you're in the market for group chat in GTalk, give &lt;a href="http://code.google.com/p/chatsworth"&gt;Chatsworth&lt;/a&gt; a try. I am looking forward to building this project out further and would love to hear any feedback.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/aG_Uz2oL1SI" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/01/chatsworth-a-google-talk-group-chat-bot/</feedburner:origLink></entry>
	
	<entry>
		<title>Just Say No To The Big Redesign</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/PA0x-AE3zVk/" />
		<updated>2009-01-11T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/01/just-say-no-to-the-big-redesign</id>
		<content type="html">&lt;p&gt;--- wordpress_id: 78
layout: post
title: Just Say No (to the Big Redesign)
tags:
- development
- refactoring
- programming&lt;/p&gt;

&lt;h2&gt;wordpress_url: http://blog.kevfoo.com/index.php/2009/01/just-say-no-to-the-big-redesign/&lt;/h2&gt;

&lt;p&gt;In a &lt;a href="http://blog.objectmentor.com/articles/2009/01/09/the-big-redesign-in-the-sky"&gt;post&lt;/a&gt; Robert Martin made last Friday, he described a pretty common scenario that companies and teams go through in an effort to bring peace and harmony to their codebase and restore order over all their components, known as the big redesign. Having just gone through this at work and having been on the "Tiger Team" that ported/rewrote our legacy application shell that was a muddled mix of C++/MFC and C#/WinForms, this post really resonated with me.&lt;/p&gt;

&lt;p&gt;The moral of Uncle Bob's story is that the only way to clean up messes in your codebase is to do via incremental changes iteration by iteration and release by release. If I would have read this post six months ago, I might have argued that this is an overly simplistic take and that exceptional cases exist that make big redesigns necessary. Having just gone through a big redesign; however, I am confident that fixing your messes iteration by iteration is the only way to fix your codebase issues for the long term especially if your team is trying to develop with agile processes.&lt;/p&gt;

&lt;p&gt;My redesign change of heart did not come because of a spectacular failure or the system ending up in a worse shape than before.  I like to think our sob story about how terrible our legacy codebase was made a pretty compelling case for a redesign (doesn't everyone?) but I'll spare you the back story. When it comes down to it, even the best reasons and intentions don't justify a full blown redesign. &lt;/p&gt;

&lt;p&gt;Here is why in big bold letters:&lt;/p&gt;

&lt;h2&gt;You are not addressing the root causes&lt;/h2&gt;

&lt;p&gt;A codebase does not fall into disrepair over night. Having the Tiger Team do all the heavy lifting and making all the design decisions might solve the problem &lt;em&gt;righthissecond&lt;/em&gt; but none of the problems that got you in this bind will have been addressed. Also, if the redesign is radical enough, you could actually be reducing your teams ability to manage and maintain your codebase even further. Choosing to solve your team's problems by delegating cleanup to a Tiger Team is the software management equivalent of giving a man a fish instead of teaching him how to fish.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/PA0x-AE3zVk" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/01/just-say-no-to-the-big-redesign/</feedburner:origLink></entry>
	
	<entry>
		<title>Crunching some NFL Stats with F#</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/NHpZfoU9W7A/" />
		<updated>2009-01-10T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/01/crunching-some-nfl-stats-with-f</id>
		<category term="football stats" />
		<category term="qb rating" />
		<category term="nfl stats" />
		<category term="linq" />
		<category term="functional programming" />
		<category term="qb stats" />
		<category term="stats" />
		<category term="programming" />
		<category term="f#" />
		<content type="html">&lt;p&gt;To explore functional programming, I've decided to return to a familiar problem domain, football stats. I used this domain a couple years ago when I was in the process of making the transition from the Unix-based OS/Java world to the Microsoft/C# world. I am the type of person that learns better by doing than studying, so I'm going to try and jump in and cobble something together to start the learning process. I've watched the PDC presentation by &lt;a href="http://blogs.msdn.com/lucabol/"&gt;Luca Bolognese&lt;/a&gt;, and I've read through the first couple chapters of &lt;a href="http://blogs.msdn.com/dsyme/"&gt;Don Syme's&lt;/a&gt; &lt;em&gt;Expert F#&lt;/em&gt;, so consider me armed with an F# Interactive window and dangerous.&lt;/p&gt;

&lt;p&gt;The first stat that I plan to look at is the &lt;a href="http://dberri.wordpress.com/2007/09/09/a-new-qb-score/"&gt;QB Score Stat&lt;/a&gt; as outlined by Berri, et al. in &lt;a href="http://www.amazon.com/gp/product/0804752877?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=0804752877"&gt;&lt;em&gt;Wages of Wins&lt;/em&gt;&lt;/a&gt;.  The stat is much easier to calculate than the traditional QB Rating used by the NFL, and if you read the link and/or book, you'll see that it correlates much better to wins and points than QB rating. For our purposes, I'll just outline the formula here but I do recommend checking out the links for more info.&lt;/p&gt;

&lt;p&gt;QB Score = Total Yards - 3 * Plays - 30 * Turnovers&lt;/p&gt;

&lt;p&gt;I got the &lt;a href="http://sports.yahoo.com/nfl/stats/byposition?pos=QB&amp;amp;conference=NFL&amp;amp;year=season_2008&amp;amp;timeframe=All&amp;amp;sort=626&amp;amp;old_category=QB"&gt;2008 QB stats&lt;/a&gt; from Yahoo, dumped them into Excel and then saved them off into CSV.  This can be done programmatically fairly easily with &lt;a href="http://www.codeplex.com/htmlagilitypack"&gt;HtmlAgilityPack&lt;/a&gt; and Linq to Xml but I'll save that for another post.  I've provided a copy of the stats in CSV &lt;a href="http://www.kevfoo.com/files/QB_Stats_2008.csv"&gt;here&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;So to get started here is what we have to do in order to calculate the raw QB score and the QB score per play for all the NFL QB's:&lt;/p&gt;

&lt;pre&gt;&lt;code&gt; 1. Read in the CSV file 
2. Grab the relevant stats for our calculation 
3. Calculate the QB score per play for each QB 
4. Return the QB name and the score. 
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;I'll tackle this step by step and we can verify our results via the F# Interactive window.&lt;/p&gt;

&lt;p&gt;To read in the file we can leverage the .Net System.IO library. The call pattern to read a file into memory is identical to what you would see in C# or VB and is pretty straight forward.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt; &amp;amp;lt;br /&amp;amp;gt;#light    &amp;amp;lt;br /&amp;amp;gt;open System.IO    &amp;amp;lt;br /&amp;amp;gt;let filePath = &amp;amp;amp;quot;D:\code\data\QB_Stats_2008.csv&amp;amp;amp;quot;    &amp;amp;lt;br /&amp;amp;gt;let stream = new FileStream(filePath, FileMode.Open)    &amp;amp;lt;br /&amp;amp;gt;let reader = new StreamReader(stream)    &amp;amp;lt;br /&amp;amp;gt;let csv = reader.ReadToEnd()    &amp;amp;lt;br /&amp;amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Here is the output of the F# interaction window.   &lt;em&gt;val filePath : string&lt;/em&gt;    val stream : System.IO.FileStream    val reader : System.IO.StreamReader    val csv : string        As we can see from the output, 'csv' is string that holds the contents of the QB stats file. Since we know that the file is is a CSV file, we can break it down into its individual elements like so:&lt;/p&gt;

&lt;pre&gt;&lt;code&gt; &amp;amp;lt;br /&amp;amp;gt;let stats =    &amp;amp;lt;br /&amp;amp;gt;csv.Split([|'\n'|])    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.skip 1    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map(fun line -&amp;amp;amp;gt; line.Split([|','|]))    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map(fun values -&amp;amp;amp;gt;    &amp;amp;lt;br /&amp;amp;gt;string values.[0], // qb name    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[5]), // att    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[7]), // pass yds    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[11]), // int    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[12]), // rushes    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[13]), // rush yds    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[17]), // sacks    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[20])) // fumbles lost    &amp;amp;lt;br /&amp;amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Since 'csv' is a string, we can use the Split method to chunk the string up into individual lines using the '\n' character as our split token.  Once split into individual lines, the pipeline operator on line 3 further processes each line.  Sequences in F# can be thought of as IEnumerables from C# and come with some nice baked-in methods to help with processing. Our QB stats CSV file has as its first line a key to the data. We'll need to skip that first line before we get to process the real data, and to do so we'll use one of those nice baked-in methods (Seq.skip) to do so.&lt;/p&gt;

&lt;p&gt;Line 4 further deconstructs the csv file into the individual comma delimited values tokenizing each line. After the lines have been tokenized the individual values can be read. Here I've created a tuple to hold each lines values. The tokenized values have been collected in a tuple that holds 8 values.  The mapping of the values is specified by the comments.&lt;/p&gt;

&lt;p&gt;Here is the output of the F# interaction window after step 2:&lt;/p&gt;

&lt;p&gt;_val stats : seq _&lt;/p&gt;

&lt;p&gt;After step two we have a sequence of tuples that have only the stats and information that we care about. The next step now becomes calculating the QB score. The calculation of the score requires three sub-steps, so let us revise the outline we laid out earlier to include them.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt; 1. Read in the CSV file 
2. Grab the relevant stats for our calculation 
3. Calculate the QB score per play for each QB             
&lt;/code&gt;&lt;/pre&gt;

&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;&lt;em&gt;Create the formula function &lt;/em&gt;&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;&lt;em&gt;Compute the components of the formula &lt;/em&gt;&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;&lt;em&gt;Create the desired output&lt;/em&gt;&lt;/strong&gt;

&lt;ol&gt;
&lt;li&gt;Return the QB name and the score&lt;/li&gt;
&lt;/ol&gt;
&lt;/li&gt;
&lt;/ol&gt;


&lt;p&gt;Let's tackle the first sub-step and codify the formula now and see what we'll need to provide from the data we just acquired.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt; &amp;amp;lt;br /&amp;amp;gt;let qbcalc (plays,yards,turnovers) = yards - 3 * plays - 30 * turnovers    &amp;amp;lt;br /&amp;amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;This line of code creates a function called qbcalc that takes in a tuple composed of the plays, yards, and turnovers components of the formula.&lt;/p&gt;

&lt;p&gt;If we run the qbcalc function through the interactive window we get:&lt;/p&gt;

&lt;p&gt;&lt;em&gt;val qbcalc : int * int * int -&gt; int&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The end result of this is the raw QB score. The arithmetic operations in F# are similar to most languages, so the formula is a straight forward expression without any surprises. Since we know plays, yards and turnovers are all integer values, we could further constrain the types of values that the tuple is composed of, but F#'s type inference already does this for us, so it is not needed. When the compiler analyzed this code, it was able to ascertain from the operations and the integers used that the plays, yards and turnover values were of type int and automatically created the int constraints.&lt;/p&gt;

&lt;p&gt;The next step is to compute the individual values of plays, yards, and turnovers. Before we start, I just want to note that I am sure there is a slicker, more concise way to do this, but this is my first go at this, so pardon the mess.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt; &amp;amp;lt;br /&amp;amp;gt;let names = stats |&amp;amp;amp;gt; Seq.map(fun(name,_,_,_,_,_,_,_) -&amp;amp;amp;gt; name)    &amp;amp;lt;br /&amp;amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Here we start to perform operations on the stats sequence we captured from the CSV file. The basic structure of what I am doing here is grabbing the specific values of the components I am looking to either aggregate (names) or calculate (plays, yards, and turnovers) from the sequence and mapping them to a new sequence. Here is an example of how to create the plays sequence.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt; &amp;amp;lt;br /&amp;amp;gt;let plays = stats |&amp;amp;amp;gt; Seq.map(fun(_,att,_,_,rush,_,sacks,_) -&amp;amp;amp;gt; att+rush+sacks)    &amp;amp;lt;br /&amp;amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Here the stats sequence is pushed through the pipeline operator ( |&gt; ) which allows you to chain functions in a sequence. This is happens because, as pointed out in &lt;a href="http://www.amazon.com/gp/product/1590598504?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=1590598504"&gt;Expert F#&lt;/a&gt;, the pipeline operator is just function application in reverse. This can be expressed like so:&lt;/p&gt;

&lt;pre&gt;&lt;code&gt; &amp;amp;lt;br /&amp;amp;gt;let (|&amp;amp;amp;gt;) x f = f x     &amp;amp;lt;br /&amp;amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;So in our case when we have the following:&lt;/p&gt;

&lt;p&gt;   &amp;lt;br /&amp;gt;stats |&amp;amp;gt; Seq.map (fun(&lt;em&gt;,att,&lt;/em&gt;,&lt;em&gt;,rush,&lt;/em&gt;,sacks,_) -&amp;amp;gt; att+rush+sacks)    &amp;lt;br /&amp;gt;&lt;/p&gt;

&lt;p&gt;Chaining the stats sequence with the the Seq.map function will apply the function we've defined in the parenthesis to each element in the stats sequence and return a new sequence with the results of the function.  The function we have defined has a signature that matches the 8 value tuples that compose the stats sequence. Since only a few values are needed to be computed for the various values, "˜_' can be assigned to the values in the parameter definition and more meaningful names can be given to the values we care about. On the right hand side of the -&gt; (a symbol that represents a function), we do the simple adding of the values. Again the results of this function are collected in a new sequence that is returned from the Seq.map call.&lt;/p&gt;

&lt;p&gt;After all the individual components of the QB score formula have been computed, we're left with a bunch of individual sequence values that need to be reconstructed into something that we can pass to the the qbcalc function. The calculation function is defined as taking a tuple composed of a play, yard, and turnover values, so we need to utilize another method that Seq provides called zip.&lt;/p&gt;

&lt;p&gt;Here is the code that crunches the individual components.&lt;/p&gt;

&lt;p&gt;&amp;lt;br /&amp;gt;let getStats =    &amp;lt;br /&amp;gt;let stats = loadQBStats    &amp;lt;br /&amp;gt;let names = stats |&amp;amp;gt; Seq.map(fun(name,&lt;em&gt;,&lt;/em&gt;,&lt;em&gt;,&lt;/em&gt;,&lt;em&gt;,&lt;/em&gt;,&lt;em&gt;) -&amp;amp;gt; name)    &amp;lt;br /&amp;gt;let plays = stats |&amp;amp;gt; Seq.map(fun(&lt;/em&gt;,att,&lt;em&gt;,&lt;/em&gt;,rush,&lt;em&gt;,sacks,&lt;/em&gt;) -&amp;amp;gt; att+rush+sacks)    &amp;lt;br /&amp;gt;let yards = stats |&amp;amp;gt; Seq.map(fun(&lt;em&gt;,&lt;/em&gt;,passyd,&lt;em&gt;,&lt;/em&gt;,rushyd,&lt;em&gt;,&lt;/em&gt;) -&amp;amp;gt; passyd + rushyd)    &amp;lt;br /&amp;gt;let turnovers = stats |&amp;amp;gt; Seq.map( fun(&lt;em&gt;,&lt;/em&gt;,&lt;em&gt;,int,&lt;/em&gt;,&lt;em&gt;,&lt;/em&gt;,fum) -&amp;amp;gt; int+fum)    &amp;lt;br /&amp;gt;Seq.zip3 plays yards turnovers |&amp;amp;gt; Seq.zip names    &amp;lt;br /&amp;gt;&lt;/p&gt;

&lt;p&gt;The final step to complete is to apply the qbcalc function to each play, yard and turnover tuple, and zipping up the resulting sequence with the names sequence rounds out steps and completes our task. The values were balled up into tuples in previous steps, so a lot of what is left to do is unpacking what we need to do the actual calculation and then reassemble to the output. The unpacking of the tuples are done with the fst and snd functions that are applied to the sequences. These methods return the fst, and the snd functions return the first and second elements of the tuples respectively. The last line of the doCalc function divides the raw QB score over the plays completing the calculation and then back pipes that sequence to be zipped up with the names. The zipped sequence gets returned, and at last we've calculated the QB score per play for the 2008 season. The last thing to note with the calculation is that in order to get better precision from the final result, the int values being divided need to be converted to a decimal. If the integers aren't converted, then the results of the division operation will be rounded down, and we'll lose precision on the calculation.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;  &amp;amp;lt;br /&amp;amp;gt;let doCalc =     &amp;amp;lt;br /&amp;amp;gt;let stats =    &amp;amp;lt;br /&amp;amp;gt;getStats    &amp;amp;lt;br /&amp;amp;gt;let names =    &amp;amp;lt;br /&amp;amp;gt;stats |&amp;amp;amp;gt; Seq.map fst    &amp;amp;lt;br /&amp;amp;gt;let rawScore =    &amp;amp;lt;br /&amp;amp;gt;stats    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map snd    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map qbcalc    &amp;amp;lt;br /&amp;amp;gt;let plays =     &amp;amp;lt;br /&amp;amp;gt;stats    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map snd    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map (fun (plays,_,_) -&amp;amp;amp;gt; plays)    &amp;amp;lt;br /&amp;amp;gt;let components =    &amp;amp;lt;br /&amp;amp;gt;Seq.zip rawScore plays     &amp;amp;lt;br /&amp;amp;gt;Seq.zip names &amp;amp;amp;lt;| Seq.map(fun(x:int, y:int) -&amp;amp;amp;gt; System.Convert.ToDecimal(x)/ System.Convert.ToDecimal(y)) components    &amp;amp;lt;br /&amp;amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Below is the complete source listing of my first crack at doing something useful with F#. There are a couple things (the packing and repacking of the tuples, the CSV parsing) that scream "optimize me". In my next F# post, I'll refactor this code to slim it down and package it up so I can display these results graphically via C#.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt; &amp;amp;lt;br /&amp;amp;gt;#light    &amp;amp;lt;br /&amp;amp;gt;open System.IO&amp;amp;lt;/p&amp;amp;gt;  &amp;amp;lt;p&amp;amp;gt;let loadQBStats =   &amp;amp;lt;br /&amp;amp;gt;let filePath = &amp;amp;amp;quot;D:\code\ProFootballDB\Data\QB_Stats_2008.csv&amp;amp;amp;quot;    &amp;amp;lt;br /&amp;amp;gt;let stream = new FileStream(filePath, FileMode.Open)    &amp;amp;lt;br /&amp;amp;gt;let reader = new StreamReader(stream)    &amp;amp;lt;br /&amp;amp;gt;let csv = reader.ReadToEnd()&amp;amp;lt;/p&amp;amp;gt;  &amp;amp;lt;p&amp;amp;gt;let stats =   &amp;amp;lt;br /&amp;amp;gt;csv.Split([|'\n'|])    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.skip 1    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map(fun line -&amp;amp;amp;gt; line.Split([|','|]))    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map(fun values -&amp;amp;amp;gt;    &amp;amp;lt;br /&amp;amp;gt;string values.[0], // qb name    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[5]), // att    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[7]), // pass yds    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[11]), // int    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[12]), // rushes    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[13]), // rush yds    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[17]), // sacks    &amp;amp;lt;br /&amp;amp;gt;System.Int32.Parse(values.[20])) // fumbles lost    &amp;amp;lt;br /&amp;amp;gt;stats&amp;amp;lt;/p&amp;amp;gt;  &amp;amp;lt;p&amp;amp;gt;let qbcalc (plays,yards,turnovers) = yards - 3 * plays - 30 * turnovers&amp;amp;lt;/p&amp;amp;gt;  &amp;amp;lt;p&amp;amp;gt;let getStats =   &amp;amp;lt;br /&amp;amp;gt;let stats = loadQBStats    &amp;amp;lt;br /&amp;amp;gt;let names = stats |&amp;amp;amp;gt; Seq.map(fun(name,_,_,_,_,_,_,_) -&amp;amp;amp;gt; name)    &amp;amp;lt;br /&amp;amp;gt;let plays = stats |&amp;amp;amp;gt; Seq.map(fun(_,att,_,_,rush,_,sacks,_) -&amp;amp;amp;gt; att+rush+sacks)    &amp;amp;lt;br /&amp;amp;gt;let yards = stats |&amp;amp;amp;gt; Seq.map(fun(_,_,passyd,_,_,rushyd,_,_) -&amp;amp;amp;gt; passyd + rushyd)    &amp;amp;lt;br /&amp;amp;gt;let turnovers = stats |&amp;amp;amp;gt; Seq.map( fun(_,_,_,int,_,_,_,fum) -&amp;amp;amp;gt; int+fum)    &amp;amp;lt;br /&amp;amp;gt;Seq.zip3 plays yards turnovers |&amp;amp;amp;gt; Seq.zip names&amp;amp;lt;/p&amp;amp;gt;  &amp;amp;lt;p&amp;amp;gt;let doCalc =    &amp;amp;lt;br /&amp;amp;gt;let stats =    &amp;amp;lt;br /&amp;amp;gt;getStats    &amp;amp;lt;br /&amp;amp;gt;let names =    &amp;amp;lt;br /&amp;amp;gt;stats |&amp;amp;amp;gt; Seq.map fst    &amp;amp;lt;br /&amp;amp;gt;let rawScore =    &amp;amp;lt;br /&amp;amp;gt;stats    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map snd    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map qbcalc    &amp;amp;lt;br /&amp;amp;gt;let plays =     &amp;amp;lt;br /&amp;amp;gt;stats    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map snd    &amp;amp;lt;br /&amp;amp;gt;|&amp;amp;amp;gt; Seq.map (fun (plays,_,_) -&amp;amp;amp;gt; plays)    &amp;amp;lt;br /&amp;amp;gt;let components =    &amp;amp;lt;br /&amp;amp;gt;Seq.zip rawScore plays     &amp;amp;lt;br /&amp;amp;gt;Seq.zip names &amp;amp;amp;lt;| Seq.map(fun(x:int, y:int) -&amp;amp;amp;gt; System.Convert.ToDecimal(x)/ System.Convert.ToDecimal(y)) components    &amp;amp;lt;br /&amp;amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Useful links:&lt;/p&gt;

&lt;pre&gt;&lt;code&gt; - [Expert F# (Expert's Voice in .Net)](http://www.amazon.com/gp/product/1590598504?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=1590598504) 
- [Microsoft F# Developer Center](http://msdn.microsoft.com/en-us/fsharp/default.aspx "http://msdn.microsoft.com/en-us/fsharp/default.aspx") 
- [PDC Video : Introduction to Microsoft F#](http://channel9.msdn.com/pdc2008/TL11/) 
- [QB Score Stat](http://dberri.wordpress.com/2007/09/09/a-new-qb-score/) from [Wages of Wins](http://www.amazon.com/gp/product/0804752877?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=0804752877) 
&lt;/code&gt;&lt;/pre&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/NHpZfoU9W7A" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/01/crunching-some-nfl-stats-with-f/</feedburner:origLink></entry>
	
	<entry>
		<title>Exploring functional programming</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/BZ__wgKeoWY/" />
		<updated>2009-01-04T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/01/exploring-functional-programming</id>
		<category term="haskell" />
		<category term="statistics" />
		<category term="programming languages" />
		<category term="pragmatic programmer" />
		<category term="functional languages" />
		<category term="functional programming" />
		<category term="ocaml" />
		<category term="sports" />
		<category term="programming" />
		<category term="f#" />
		<content type="html">&lt;p&gt;I am trying to heed the &lt;a href="http://www.amazon.com/gp/product/020161622X?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=020161622X"&gt;Pragmatic Programmer's&lt;/a&gt; advice to learn a new language each year and this year I figured it would not be a bad idea to look at functional languages.  There is a lot of buzz and blog posts about functional programming going on right now so there should be plenty of fresh material and this won't be my first exposure to functional programming.  I'll have to dust off some of my notes from the programming languages class I took during some of my masters work.&lt;/p&gt;

&lt;p&gt;I am planning to follow along with the &lt;a href="http://www.amazon.com/gp/product/0596514980?ie=UTF8&amp;amp;tag=kev02-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=0596514980"&gt;Real World Haskell&lt;/a&gt; book club (which &lt;a href="http://codebetter.com/blogs/matthew.podwysocki/archive/2009/01/04/ann-the-real-world-haskell-book-club-starts-1-5-2009.aspx"&gt;starts tomorrow&lt;/a&gt; night) and also mess around with F# so I thankfully won't have to rely on my one semester of &lt;a href="http://www.ocaml-tutorial.org/"&gt;OCaml&lt;/a&gt; to help me get going.  As a fan of sports and statistics I'll probably try and use that as my problem domain while exploring these languages.  I am really looking forward to trying to wrap my mind around functional programming as it is so different than thinking about objects and should be a great &lt;a href="http://www.neurobics.com/"&gt;"neurobic" activity&lt;/a&gt; for the ol' brain.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/BZ__wgKeoWY" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/01/exploring-functional-programming/</feedburner:origLink></entry>
	
	<entry>
		<title>Best thing I have read all day</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/l3y-bIDpxiM/" />
		<updated>2009-01-04T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/01/best-thing-ive-read-all-day</id>
		<category term="programming" />
		<category term="quotes" />
		<content type="html">&lt;p&gt;"Most programmers think it is a sin to write code w/o comments, but it is a greater sin to write code that cannot be understood without them" &lt;a href="http://twitter.com/pjb3/status/1095852496"&gt;Paul Berry via Twitter&lt;/a&gt;&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/l3y-bIDpxiM" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/01/best-thing-ive-read-all-day/</feedburner:origLink></entry>
	
	<entry>
		<title>F# Support for the SyntaxHighlighter WordPress Plug-in</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/XgIZ51_WLcI/" />
		<updated>2009-01-02T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/01/f-support-for-the-syntaxhighlighter-wordpress-plug-in</id>
		<category term="f-sharp" />
		<category term="fsharp" />
		<category term="f#" />
		<category term="syntax highlighter" />
		<category term="plugin" />
		<category term="wordpress" />
		<content type="html">&lt;p&gt;I added the F# keywords to syntaxhighlighter.php and added the &lt;a href="http://webdevdotnet.blogspot.com/2008/11/new-f-syntaxhighlighter-brush.html"&gt;F# brush&lt;/a&gt; that Elijah Manor put together to the &lt;a href="http://wordpress.org/extend/plugins/syntaxhighlighter/"&gt;SyntaxHighlighter WordPress plug-in&lt;/a&gt;.  I am not sure if anyone is still maintaining that project but you can download the zip &lt;a href="http://www.kevfoo.com/files/syntaxhighlighter_with_fsharp.zip"&gt;here&lt;/a&gt; and install it the same way as the original.&lt;/p&gt;

&lt;p&gt;To highlight F# code you can now do [sourcecode language="'f#'"]code here[/sourcecode]. You can also swap out "˜f#' for "˜f-sharp' or "˜fsharp'.&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/XgIZ51_WLcI" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/01/f-support-for-the-syntaxhighlighter-wordpress-plug-in/</feedburner:origLink></entry>
	
	<entry>
		<title>Mini9 &amp; Vista Quick Review</title>
		<link href="http://feedproxy.google.com/~r/kevfoo/~3/wVMYd5tdMYM/" />
		<updated>2009-01-01T00:00:00-06:00</updated>
		<id>http://www.kevfoo.com/2009/01/mini9-vista-quick-review</id>
		<category term="ssd" />
		<category term="netbook" />
		<category term="ethernet driver" />
		<category term="mini9" />
		<category term="tech" />
		<category term="flash drive" />
		<category term="flash disk" />
		<category term="windows" />
		<category term="review" />
		<content type="html">&lt;p&gt;I have been playing around with my Dell Mini9 (1Gb RAM, 32GB SSD) netbook that I picked up recently over the holidays and finally got around to swapping the Ubuntu installation that came from the factory with a slimmed down version of Vista Ultimate.  For a machine that has the type of resource constraints and intended use (email/web/light office app work) a typical full Vista install wouldn't be practical but thanks to the &lt;a href="http://www.vlite.net/"&gt;vLite&lt;/a&gt; configuration tool I was able to shrink my installation footprint down to roughly 3.5Gb.  If you have the right tools (a couple gig flash drive, access to a copy of Vista, and some patience) then the conversion isn't that painful or time consuming.  The one recommendation that I would like to emphasize is make sure that you have all the drivers downloaded ahead of time especially the network drivers since neither the wireless or Ethernet drivers got installed by default..  You can dump them on the flash disk as they don't take up that much space and it will expedite the process of getting your system fully operational.&lt;/p&gt;

&lt;p&gt;Here are some of the links that I relied on heavily to get me through the conversion:&lt;br/&gt;
 - &lt;a href="http://rickatnight11.com/?p=71"&gt;Rick at Night's Install Vista on Dell Mini 9 (USB) Guide&lt;/a&gt;
 - &lt;a href="http://www.codecguide.com/download_mega.htm"&gt;K-Lite Mega Codec Pack&lt;/a&gt;
 - &lt;a href="http://support.dell.com/support/downloads/driverslist.aspx?c=us&amp;amp;l=en&amp;amp;s=gen&amp;amp;os=WLH&amp;amp;osl=en&amp;amp;catid=&amp;amp;impid=&amp;amp;SystemID=INSPIRON910"&gt;Dell's Inspiron Mini 9 (910) Driver Downloads&lt;/a&gt; (You can use the Windows XP drivers)&lt;/p&gt;

&lt;p&gt;For a resource constrained machine it certainly does not seem sluggish.  The Vista experience, while not in the same league as my tricked out M1530, is not terrible and the solid state drive really makes a world of difference in these netbooks as they are silent, low power, and fast as hell.&lt;/p&gt;

&lt;p&gt;In my eyes the one serious drawback of these Mini9's is the size and layout of the keyboard and touchpad. The keyboard on a 9" laptop obviously has to be compressed and tradeoffs conceded but for someone like me who has stubby fat fingers this becomes more of a problem than I'd thought. The other major issue I have is with the touchpad. The touch sensitive surface that comprises the touchpad runs all the way to the space bar without any buffer or separation. I continuously hit the touchpad surface causing the cursor or focus to jump to where the pointer is.  The keyboard issue by itself isn't a terrible problem, I'm sure I'll acclimate, but when you compound that with the lack of a buffer between the space bar the whole keyboard/mouse experience becomes extremely frustrating. I bought a bluetooth notebook mouse and can turn off the touchpad so I am not impacted by inadvertent contact but that defeats the purpose of this device for me since I'd much rather have my 15" laptop if I am going to have to be sitting at a table/desk/tray to use the external mouse for any length of time.&lt;/p&gt;

&lt;p&gt;Overall the Mini9 isn't bad for couch surfing and travel but this isn't a machine that I could use for extended periods of time in the situations where a netbook would be convenient. While I like the concept and the price point that this class of portable addresses I can't strongly endorse the mini9 due to the layout and design of the keyboard and touchpad.  s&lt;/p&gt;
&lt;img src="http://feeds.feedburner.com/~r/kevfoo/~4/wVMYd5tdMYM" height="1" width="1"/&gt;</content>
	<feedburner:origLink>http://www.kevfoo.com/2009/01/mini9-vista-quick-review/</feedburner:origLink></entry>
	
</feed>
