<?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:thr="http://purl.org/syndication/thread/1.0" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" xml:lang="en" xml:base="http://akosma.com/wp-atom.php"><title type="text">akosma software</title> <subtitle type="text">Leading international provider of cross-platform and multilingual software solutions, for iPhone, iPad, Mac, Windows, Linux, Android, and the web.</subtitle> <updated>2012-02-06T18:24:31Z</updated><link rel="alternate" type="text/html" href="http://akosma.com" /> <id>http://akosma.com/feed/atom/</id> <generator uri="http://wordpress.org/" version="3.3.1">WordPress</generator> <atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/atom+xml" href="http://feeds.feedburner.com/akosmasoftware" /><feedburner:info uri="akosmasoftware" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><entry> <author> <name>Adrian Kosmaczewski</name> <uri>http://kosmaczewski.net/</uri> </author><title type="html"><![CDATA[GOTO Copenhagen 2012 &#8211; Call for Speakers!]]></title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/akosmasoftware/~3/wYAf1WoDsb4/" /> <id>http://akosma.com/?p=3388</id> <updated>2012-02-06T18:24:31Z</updated> <published>2012-02-06T18:24:29Z</published> <category scheme="http://akosma.com" term="Conferences" /><category scheme="http://akosma.com" term="Call for Papers" /><category scheme="http://akosma.com" term="conference" /><category scheme="http://akosma.com" term="Denmark" /><category scheme="http://akosma.com" term="GOTO" /><category scheme="http://akosma.com" term="mobile" /> <summary type="html"><![CDATA[I am very happy to announce that I will be the host of the Mobile Technologies: Native + Web track of GOTO Copenhagen 2012! The track will feature talks by Brian LeRoux, Graham Lee and Jérôme Giraud. GOTO is a series of international software development conferences organized by Trifork in Copenhagen, Amsterdam, Århus (Denmark) and [...]]]></summary> <content type="html" xml:base="http://akosma.com/2012/02/06/goto-copenhagen-2012-call-for-speakers/"><![CDATA[<p>I am very happy to announce that I will be the host of the <a
href="http://gotocon.com/cph-2012/tracks/show_track.jsp?trackOID=541">Mobile Technologies: Native + Web</a> track of <a
href="http://gotocon.com/cph-2012/">GOTO Copenhagen 2012</a>! The track will feature talks by Brian LeRoux, Graham Lee and Jérôme Giraud.</p><p><a
href="http://gotocon.com/cph-2012/"><img
src="http://akosma.com/wp/wp-content/uploads/2012/02/GOTO_Con.png" alt="GOTO Con" border="0" width="170" height="62" class="alignleft size-full" /></a></p><p>GOTO is a series of international software development conferences organized by <a
href="http://www.trifork.com/">Trifork</a> in Copenhagen, Amsterdam, Århus (Denmark) and Prague. This year the event will happen in Copenhagen on May 21st-25th.</p><p>We are currently looking for 2 more speakers for the conference; if you are interested, just <a
href="http://akosma.com/contact/">contact us!</a> We look forward to hearing from you.<strong>Similar Posts:</strong></p><ul
class="similar-posts"><li><a
href="http://akosma.com/2011/12/12/qcon-london-2012-call-for-papers-in-the-cross-platform-mobile-track/" rel="bookmark" title="December 12, 2011">QCon London 2012: Call for Papers in the Cross-Platform Mobile Track</a></li><li><a
href="http://akosma.com/2010/10/08/qcon-london-2011-call-for-papers-in-the-mobile-track/" rel="bookmark" title="October 8, 2010">QCon London 2011: Call for Papers in the Mobile Track</a></li><li><a
href="http://akosma.com/2010/10/03/jaoo-workshop-building-your-first-iphone-application/" rel="bookmark" title="October 3, 2010">JAOO Workshop: Building your first iPhone Application</a></li><li><a
href="http://akosma.com/2010/02/10/iphone-dev-day-in-geneva-on-april-28th/" rel="bookmark" title="February 10, 2010">iPhone Dev Day in Geneva on April 28th</a></li><li><a
href="http://akosma.com/2012/01/10/swiss-app-awards-dont-forget/" rel="bookmark" title="January 10, 2012">Swiss App Awards &#8211; Don&#8217;t Forget!</a></li></ul>]]></content><link rel="replies" type="text/html" href="http://akosma.com/2012/02/06/goto-copenhagen-2012-call-for-speakers/#comments" thr:count="0" /><link rel="replies" type="application/atom+xml" href="http://akosma.com/2012/02/06/goto-copenhagen-2012-call-for-speakers/feed/atom/" thr:count="0" /> <thr:total>0</thr:total> <feedburner:origLink>http://akosma.com/2012/02/06/goto-copenhagen-2012-call-for-speakers/</feedburner:origLink></entry> <entry> <author> <name>Adrian Kosmaczewski</name> <uri>http://kosmaczewski.net/</uri> </author><title type="html"><![CDATA[Mobile Web Training in Zürich Once Again!]]></title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/akosmasoftware/~3/9GlVFmJMCbk/" /> <id>http://akosma.com/?p=3376</id> <updated>2012-02-01T17:01:35Z</updated> <published>2012-02-01T14:02:35Z</published> <category scheme="http://akosma.com" term="Education" /><category scheme="http://akosma.com" term="Mobile Web" /><category scheme="http://akosma.com" term="jQuery Mobile" /><category scheme="http://akosma.com" term="Sencha Touch" /><category scheme="http://akosma.com" term="Simplificator" /><category scheme="http://akosma.com" term="training" /><category scheme="http://akosma.com" term="web" /><category scheme="http://akosma.com" term="Zürich" /> <summary type="html"><![CDATA[Simplificator and akosma software are thrilled to announce the second edition of our successful three day training about mobile web app development using jQuery Mobile, Sencha Touch and PhoneGap in Zürich on March 14th, 15th and 16th! Today, having a mobile application online is a must. But there are multiple platforms to write for, each [...]]]></summary> <content type="html" xml:base="http://akosma.com/2012/02/01/mobile-web-training-in-zurich-once-again/"><![CDATA[<p>Simplificator and akosma software are thrilled to announce the second edition of our successful <a
href="http://mobile-training.ch/">three day training about mobile web app development using jQuery Mobile, Sencha Touch and PhoneGap</a> in Zürich on March 14th, 15th and 16th!</p><p>Today, having a mobile application online is a must. But there are multiple platforms to write for, each with their own language, idioms and pitfalls. Luckily there is a simple solution that allows to write once and deploy on all modern mobile devices: HTML5 and JavaScript.</p><h2>What others have been saying</h2><ul><li>“Die Inhalte wurden lebendig und Step-by-Step präsentiert”</li><li>“Merci, das war ein sehr lehrreicher Kurs”<span
id="more-3376"></span><a
href="http://akosma.com/wp/wp-content/uploads/2011/10/20111003-112818.jpg"><img
src="http://akosma.com/wp/wp-content/uploads/2011/10/20111003-112818.jpg" alt="20111003-112818.jpg" class="alignleft size-full" width="170" /></a></li></ul><h2>Easy, quick dev of “native” applications</h2><p>This three day intensive course takes you from being a web developer to being a mobile developer. We take you through the basics of writing HTML5 applications for mobile devices, cover the additional APIs that allow you to access the functions of the devices (like storage, geo-location, accelerometers) and put you in control of deploying an application to either iOS or Android devices.</p><h2>What</h2><ul><li>Overview over what HTML5 brings for mobile development</li><li>Overview over options for bringing web apps to a mobile device</li><li>In depth review of jQuery Mobile and Sencha Touch</li><li>JavaScript best practices</li><li>JavaScript libraries that help building applications (Backbone.js, Raphaël.js)</li><li>Bundling your app for the device with PhoneGap</li><li>Accessing your devices sensors and special features from JavaScript</li></ul><p>There will be lots of hands-on working building an application from scratch and bringing it to life on your mobile device. We will build two applications – one with jQuery Mobile, one with Sencha Touch and bring them to “life” as native applications on a mobile device.</p><h2>Prerequisites</h2><ul><li>HTML / CSS</li><li>Basic JavaScript skills</li><li>Programming experience</li><li>Laptop with either iOS SDK (Mac OSX with XCode) or Android SDK (Mac, Windows, Linux) installed and running</li><li>Mobile device (iOS, Android)</li></ul><h2>Class Size</h2><p>Learning and working is best done in a relative small group. We plan on having maximum 9 people in this class so that we can spend enough time with each of our students.</p><h2>Who</h2><h3>Jens-Christian Fischer, Simplificator GmbH</h3><p>Jens-Christian started writing software in the late 1980s and been working on Web applications since the mid 1990s. The last 6 years he has been developing, writing and teaching Ruby on Rails and other web related technologies. Jens-Christian is TechLead and responsible for training at <a
href="http://simplificator.com/">Simplificator GmbH</a>, a Zurich based web development agency.</p><h3>Adrian Kosmaczewski, akosma software</h3><p>Adrian has been writing software for the past 20 years. He started working professionally in 1996, riding the first and second waves of the web. He started writing Cocoa applications for the Mac in 2002, and has been writing iOS apps since he returned from WWDC 2008. Adrian is the founder of akosma software, with a strong focus in all things iOS.</p><h2>Course Details</h2><h3>Location</h3><p>The 3 day course is held in Zurich at the offices of Simplificator GmbH, Pfingstweidstrasse 6, 8005 Zürich.</p><h3>Price</h3><ul><li>Regular Price: CHF 2100.– (inkl. 8% VAT)</li><li>Early Bird Price: CHF 1785.– (inkl. 8% VAT) (a 15% discount). (Early bird price ends on 20.February 2012)</li><li>Multiple people from the same company? Get a 10% discount for the second person.</li><li>Members of /ch/open receive a 15% discount (not cumulative with early bird price)</li></ul><h3>Included in price</h3><ul><li>3 days of intensive hands-on training in a small group, with plenty of time to talk to the instructors</li><li>Comprehensive Documentation</li><li>Full lunch meal</li><li>“There has to be food” &#8211; plenty of snacks and drinks during the day</li></ul><h3>Sign up</h3><p>Use <a
href="https://docs.google.com/spreadsheet/viewform?formkey=dHhlLXRpWXVrWGcyNjRXV1dvSWRZaWc6MA">this form</a> to sign up! (Hurry up, in our first edition the training sold out after only 1 week!)</p><h3>More Information</h3><p>Don&#8217;t hesitate to check <a
href="http://mobile-training.ch/">http://mobile-training.ch/</a> for updates, or to <a
href="mailto:kurs@simplificator.com">contact Simplificator</a> or to <a
href="http://akosma.com/contact/">contact us</a> for more information.</p><p>Check out also the events in Facebook and LinkedIn (but remember that you have to <a
href="https://docs.google.com/spreadsheet/viewform?formkey=dHhlLXRpWXVrWGcyNjRXV1dvSWRZaWc6MA">sign up using the form in the site!</a>)</p><ul><li><a
href="https://www.facebook.com/events/273212606079153/">Facebook event</a></li><li><a
href="http://www.linkedin.com/osview/canvas?_ch_page_id=2&amp;_ch_panel_id=3&amp;_ch_app_id=30&amp;_applicationId=2000&amp;appParams=%7B%22event%22%3A916020%2C%22page%22%3A%22event%22%7D&amp;_ownerId=0&amp;completeUrlHash=mEVh">LinkedIn event</a></li><li><a
href="http://techup.ch/550/mobile-web-training-in-zurich-once-again">techup.ch</a></li></ul><p><strong>Similar Posts:</strong></p><ul
class="similar-posts"><li><a
href="http://akosma.com/2011/10/03/mobile-development-with-jquery-sencha-and-phonegap-15-17-november-2011/" rel="bookmark" title="October 3, 2011">Mobile Development with jQuery, Sencha and PhoneGap, 15 &#8211; 17 November 2011</a></li><li><a
href="http://akosma.com/2012/02/01/qcon-london-2012-cross-platform-mobile-track-announcement/" rel="bookmark" title="February 1, 2012">QCon London 2012: Cross-Platform Mobile Track Announcement!</a></li><li><a
href="http://akosma.com/2011/11/14/news-for-this-week/" rel="bookmark" title="November 14, 2011">News for this week: Training + Interview</a></li><li><a
href="http://akosma.com/2011/09/13/a-shift-in-the-market-towards-mobile-web-apps/" rel="bookmark" title="September 13, 2011">A Shift In The Market Towards Mobile Web Apps</a></li><li><a
href="http://akosma.com/2011/08/23/dropping-support-for-iphone-os-3-x/" rel="bookmark" title="August 23, 2011">Dropping support for iPhone OS 3.x</a></li></ul>]]></content><link rel="replies" type="text/html" href="http://akosma.com/2012/02/01/mobile-web-training-in-zurich-once-again/#comments" thr:count="0" /><link rel="replies" type="application/atom+xml" href="http://akosma.com/2012/02/01/mobile-web-training-in-zurich-once-again/feed/atom/" thr:count="0" /> <thr:total>0</thr:total> <feedburner:origLink>http://akosma.com/2012/02/01/mobile-web-training-in-zurich-once-again/</feedburner:origLink></entry> <entry> <author> <name>Adrian Kosmaczewski</name> <uri>http://kosmaczewski.net/</uri> </author><title type="html"><![CDATA[QCon London 2012: Cross-Platform Mobile Track Announcement!]]></title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/akosmasoftware/~3/kNwSLBJuFdw/" /> <id>http://akosma.com/?p=3370</id> <updated>2012-02-01T10:34:04Z</updated> <published>2012-02-01T10:10:26Z</published> <category scheme="http://akosma.com" term="Conferences" /><category scheme="http://akosma.com" term="Mobile Web" /><category scheme="http://akosma.com" term="London" /><category scheme="http://akosma.com" term="mobile" /><category scheme="http://akosma.com" term="QCon" /> <summary type="html"><![CDATA[The Cross-Platform Mobile Track of QCon London 2012 is ready to be announced! This year we&#8217;ll have great speakers talking about how to create mobile applications using HTML5, JavaScript and CSS3: Maximiliano Firtman, the worldwide expert on mobile web application development, will talk about Mobile, HTML5 and the cross-platform promise. Jérome Giraud, creator of the [...]]]></summary> <content type="html" xml:base="http://akosma.com/2012/02/01/qcon-london-2012-cross-platform-mobile-track-announcement/"><![CDATA[<p>The <a
href="http://qconlondon.com/london-2012/tracks/show_track.jsp?trackOID=569">Cross-Platform Mobile Track</a> of <a
href="http://qconlondon.com/">QCon London 2012</a> is ready
to be announced! This year we&#8217;ll have great speakers talking about how
to create mobile applications using HTML5, JavaScript and CSS3:</p><p><a
href="http://qconlondon.com/"><img
src="http://akosma.com/wp/wp-content/uploads/2010/10/logo_qcon.gif"
alt="logo_qcon.gif" border="0" width="170" height="53" class="alignleft
size-full" /></a></p><ul><li><a
href="http://qconlondon.com/london-2012/speaker/Maximiliano+Firtman">Maximiliano Firtman</a>, the worldwide expert on mobile web
application development, will talk about <a
href="http://qconlondon.com/london-2012/presentation/Mobile,%20HTML5%20and%20the%20cross-platform%20promise">Mobile, HTML5 and the
cross-platform promise</a>.</li><li><a
href="http://qconlondon.com/london-2012/speaker/Jerome+Giraud">Jérome Giraud</a>, creator of the <a
href="http://www.winktoolkit.org/">Wink Toolkit</a> will present his
creation in the talk <a
href="http://qconlondon.com/london-2012/presentation/Wink%20and%20the%20mobile%20web%20innovation">Wink and the mobile web innovation</a>.</li><li><a
href="http://qconlondon.com/london-2012/speaker/Andrea+Giammarchi">Andrea Giammarchi</a> from <a
href="http://www.developer.nokia.com/">Nokia</a> will talk about <a
href="http://qconlondon.com/london-2012/presentation/Location%20aware%20mobile%20web%20app%20with%20HTML5%20and%20JavaScript">Location
aware mobile web apps with HTML5 and JavaScript</a>.</li><li><a
href="http://qconlondon.com/london-2012/speaker/Tobie+Langel">Tobie Langel</a> from <a
href="https://developers.facebook.com/">Facebook</a> will give a yet undisclosed
talk about an exciting new technology! Stay tuned for updates!</li><li>Finally, <a
href="http://qconlondon.com/london-2012/speaker/Christophe+Coenraets">Christophe Coenraets</a> from <a
href="http://www.adobe.com/devnet.html">Adobe</a> will talk about
[Cross-Platform Mobile Apps with HTML, JavaScript and PhoneGap][15].</li></ul><p>All in all, an epic track with industry leaders speaking about a hot
subject! This will happen on the Fleming room of the Queen Elizabeth II
Conference Centre on Wednesday, March 7th.</p><p>We hope you see you in London in March!</p><p><a
href="http://qconlondon.com/london-2012/tracks/show_track.jsp?trackOID=569"><img
src="http://akosma.com/wp/wp-content/uploads/2012/02/programqcon2012.png"
alt="Programqcon2012" border="0" width="440" height="269"
class="alignnone size-medium" /></a></p><p>[15]:http://qconlondon.com/london-2012/presentation/Cross-Platform%20Mobile%20Apps%20with%20HTML,%20JavaScript%20and%20PhoneGap<strong>Similar Posts:</strong></p><ul
class="similar-posts"><li><a
href="http://akosma.com/2011/12/12/qcon-london-2012-call-for-papers-in-the-cross-platform-mobile-track/" rel="bookmark" title="December 12, 2011">QCon London 2012: Call for Papers in the Cross-Platform Mobile Track</a></li><li><a
href="http://akosma.com/2011/09/28/jquery-mobile-multiplatform-mobile-webapps-by-maximiliano-firtman/" rel="bookmark" title="September 28, 2011">&#8220;jQuery Mobile: multiplatform mobile webapps&#8221; &#8211; by Maximiliano Firtman!</a></li><li><a
href="http://akosma.com/2011/12/23/retrospective-2011/" rel="bookmark" title="December 23, 2011">Retrospective 2011</a></li><li><a
href="http://akosma.com/2011/06/02/introduction-to-ios-software-development-video-on-infoq/" rel="bookmark" title="June 2, 2011">&#8220;Introduction to iOS Software Development&#8221; Video on InfoQ!</a></li><li><a
href="http://akosma.com/2010/10/08/qcon-london-2011-call-for-papers-in-the-mobile-track/" rel="bookmark" title="October 8, 2010">QCon London 2011: Call for Papers in the Mobile Track</a></li></ul>]]></content><link rel="replies" type="text/html" href="http://akosma.com/2012/02/01/qcon-london-2012-cross-platform-mobile-track-announcement/#comments" thr:count="0" /><link rel="replies" type="application/atom+xml" href="http://akosma.com/2012/02/01/qcon-london-2012-cross-platform-mobile-track-announcement/feed/atom/" thr:count="0" /> <thr:total>0</thr:total> <feedburner:origLink>http://akosma.com/2012/02/01/qcon-london-2012-cross-platform-mobile-track-announcement/</feedburner:origLink></entry> <entry> <author> <name>Adrian Kosmaczewski</name> <uri>http://kosmaczewski.net/</uri> </author><title type="html"><![CDATA[Determining Delegate Object Method Call Order in Objective-C with NSProxy]]></title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/akosmasoftware/~3/wpEwCdxoNO4/" /> <id>http://akosma.com/?p=3364</id> <updated>2012-02-06T18:15:19Z</updated> <published>2012-01-31T10:50:53Z</published> <category scheme="http://akosma.com" term="Tech" /><category scheme="http://akosma.com" term="code" /><category scheme="http://akosma.com" term="Education" /><category scheme="http://akosma.com" term="iOS" /> <summary type="html"><![CDATA[This is a guest post + code, wrote together with Joe D&#8217;Andrea from LiquidJoe LLC! Many developers new to the iOS platform have trouble understanding the delegate architecture, in the sense that many other OO toolkits use properties to configure the characteristics of UI elements, instead of having a separate object doing the job. When [...]]]></summary> <content type="html" xml:base="http://akosma.com/2012/01/31/determining-delegate-object-method-call-in-objective-c-with-nsproxy/"><![CDATA[<p>This is a guest post + code, wrote together with <a
href="https://github.com/jdandrea">Joe
D&#8217;Andrea</a> from <a
href="http://www.liquidjoe.biz/">LiquidJoe
LLC</a>!</p><p>Many developers new to the iOS platform have trouble understanding the
delegate architecture, in the sense that many other OO toolkits use
properties to configure the characteristics of UI elements, instead of
having a separate object doing the job.</p><p>When using delegates, the sequence of calls for each method is
important: most Cocoa developers know that UITableView instances call
delegate and data source methods roughly in this order:</p><ul><li>numberOfSections:</li><li>numberOfRows:inSection:</li><li>cellForRowAtIndexPath:</li><li>configureCellAtIndexPath:</li></ul><p>&#8230;mixing up in the middle some calls to headers and footers and cell
sizes as well. Which prompts the following question: <strong>what is really
going on behind the scenes? Can we know exactly the order in which those
delegate methods are called?</strong></p><p>To answer that question, here&#8217;s a <a
href="https://github.com/akosma/DelegateOrder">small project in
Github</a> that uses all the
delegate and datasource methods in the same project, and that uses NSLog
to show which calls happen first, and when.</p><p><span
id="more-3364"></span></p><h2>Delegate Methods</h2><p>But first, a quick recap on delegate methods in Objective-C.</p><p>In many (if not most) object oriented toolkits, properties tend to be
used when setting up an object such as a table view, for instance in
.NET, as shown in this example from <a
href="http://support.microsoft.com/kb/307860">Microsoft</a></p><pre><code>&lt;%@ Page language="c#" %&gt;
&lt;%@ Import Namespace="System.Data" %&gt;
&lt;%@ Import Namespace="System.Data.SqlClient" %&gt;
&lt;script runat="server"&gt;
void Page_Load(Object sender, EventArgs e)
{
   SqlConnection cnn = new
       SqlConnection("server=(local);database=pubs;Integrated Security=SSPI");
   SqlDataAdapter da = new SqlDataAdapter("select * from authors", cnn);
   DataSet ds = new DataSet();
   da.Fill(ds, "authors");
   Repeater1.DataSource = ds.Tables["authors"];
   Repeater1.DataBind();
}
&lt;/script&gt;
&lt;html&gt;
&lt;body&gt;
   &lt;form id="WebForm2" method="post" runat="server"&gt;
      &lt;asp:Repeater id="Repeater1" runat="server"&gt;
         &lt;ItemTemplate&gt;
         &lt;%# DataBinder.Eval(Container.DataItem,"au_id") %&gt;&lt;br&gt;
         &lt;/ItemTemplate&gt;
      &lt;/asp:Repeater&gt;
   &lt;/form&gt;
&lt;/body&gt;
&lt;/html&gt;
</code></pre><p>In the code above (a classic ASP.NET page) the <code>Repeater1</code> instance (of
the <code>Repeater</code> class, which is a view component) is &#8220;bound&#8221; (a classic
example of &#8220;databinding&#8221;) to an instance of a <code>DataSet</code>. In this case,
we just call the <code>.DataBind()</code> method on the repeater object, and the
view component is filled with the data inside.</p><p>The advantage of this approach is that it is simpler from the point of
view of the developer; a couple of lines of code are usually enough.
However, this design tends to break the MVC model, because it creates a
direct dependency between the model and the view component. This
coupling makes it hard to modify the model of the application without
breaking the view layer.</p><p>In Objective-C this pattern is seldom used. Instead, an object will opt
to let someone else do the job for them. That other object is known as
the <strong>delegate object</strong>, and the methods to be implemented (sometimes
optionally) are referred to as a protocol. In this model, there is a
controller object that acts as intermediate between the view and the
model, effectively creating a decoupled MVC architecture.</p><p>In Objective-C, an object tells the compiler that it implements a
protocol using this syntax:</p><pre><code>@interface MyAppDelegate : NSObject &lt;UIApplicationDelegate&gt;
@end
</code></pre><p>The inclusion of <code>&lt;UIApplicationDelegate&gt;</code> signals that this class
conforms to the UIApplicationDelegate protocol. Meanwhile, in
UIApplication.h, you will see this:</p><pre><code>@protocol UIApplicationDelegate &lt;NSObject&gt;
@optional
- (void)applicationDidFinishLaunching:(UIApplication *)application;
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions __OSX_AVAILABLE_STARTING(__MAC_NA,__IPHONE_3_0);
...
@end
</code></pre><p>Thus, MyAppDelegate.m may optionally respond to <code>-applicationDidFinishLaunching:</code> and <code>-application:didFinishLaunchingWithOptions:</code>. (In this particular case,
be aware that the former method is used by apps prior to iOS 3.0, and
that the latter method should now be used instead.)</p><h2>More about Delegates</h2><p>It is up to the class in question to determine when to call a delegate
method, and in what order. This order is of particular interest when it
comes to iOS Table Views. In fact, go ahead and press Cmd-Shift-O in
Xcode right now. Search for and open UITableView.h.</p><p>Look inside. There&#8217;s a lot to take in here! In fact, that&#8217;s a good idea
- take a moment to browse this header. (Go ahead. We&#8217;ll wait.) A Cocoa
developer can write apps and never look once inside these header files.
To borrow (abuse?) a classic Apple mantra, we code different. We want to
get our hands dirty and look inside at the engine &#8230; or at least as
much of it as possible. The instance variables are out of our reach, but
there are plenty of other things to take in.</p><p>UITableView is unusual in that it declares two protocols, whereas most
classes you come across will only declare one.</p><p>The UITableViewDelegate is responsible for mediating all table cell
display and behavior. A quick look at the protocol makes this abundantly
clear. There are methods covering custom display, variable height,
headers and footers, accessories, selection, editing, reordering, and
indentation.</p><pre><code>@protocol UITableViewDelegate &lt;NSObject, UIScrollViewDelegate&gt;
</code></pre><p>UITableViewDataSource represents the data model object. While it
supplies no information about appearance &#8212; of the cells or otherwise &#8211;
this doesn&#8217;t mean it avoids cells altogether. There are methods covering
cell view creation (and, more importantly, reuse), the number of
sections and rows, titles for headers and footers, index titles along
the right-hand side, plus cell editing, insertion, deletion, and moving.</p><p>In this protocol, two methods are required:</p><pre><code>- (NSInteger)tableView:(UITableView *)table numberOfRowsInSection:(NSInteger)section;
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath;
</code></pre><p>The rest are optional. That&#8217;s right, even -numberOfSectionsInTableView:, which you almost always see implemented like so:</p><pre><code>- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
    return 1;
}
</code></pre><p>However, the header tells us that the default value is 1 if this is not
implemented! If all you have is one section, save yourself some extra
coding and leave it out. Aren&#8217;t well-documented header files great?</p><p>Now there has to be some degree of bootstrapping involved with setting
up these delegates. This is accomplished via properties:</p><pre><code>@property (nonatomic,assign) id &lt;UITableViewDataSource&gt; dataSource;
@property (nonatomic,assign) id &lt;UITableViewDelegate&gt;   delegate;
</code></pre><p>&#8230; and usually set to self:</p><pre><code>// Set the table view and data source delegates:
myTableView.delegate = self;
myTableView.dataSource = self;
</code></pre><p>If you use a UITableViewController, this is done for you automagically,
in addition to several other niceties. (We heart UITableViewController.
Use it early. Use it often!)</p><h2>Delegate Method Call Order</h2><p>Great. So we have two delegate objects that can receive almost 30 method
calls combined. Not five. Not ten. Thirty. Helpful as the delegate
design pattern is, it&#8217;s easy to get confused knowing which method will
be called at which time. Thus, it can also be instructive to know what
order these methods are called.</p><p>You can probably guess a few of them right off the bat. For instance,
-tableView:numberOfSections: is likely called before
-tableView:numberOfRows:inSection:. It&#8217;s not always so clear cut,
though.</p><p>So <em>how do we trace Objective-C messages anyway?</em> One possibility is to
set up an Xcode breakpoint and declare this as an action (borrowed from <a
href="http://stackoverflow.com/questions/1029962/nsobjcmessageloggingenabled-with-iphone-3-0">StackOverflow</a>):</p><pre><code>while 1
printf "[%s %s]", (char *)object_getClassName($r0), (char *) $r1
c
end
</code></pre><p>Hmm &#8230; maybe not.</p><p>Is it possible to trace Objective-C messages en masse? As a matter of
fact, <a
href="http://www.dribin.org/dave/blog/archives/2006/04/22/tracing_objc/">it is</a>:</p><p>On the iPhone Simulator, you can compile with the <code>NSObjCMessageLoggingEnabled</code> Foundation environment variable set to
YES, then look in <code>/tmp/msgSends-&lt;pid&gt;</code> (where <pid> is your running
app&#8217;s process id).</pid></p><p>You&#8217;ll also get a deluge of messages, accent on deluge.</p><p>What else? You could use (<a
href="http://developer.apple.com/technotes/tn2004/tn2124.html">the undocumented</a>) <code>-instrumentObjcMessageSends:</code> to toggle logging on and off.</p><p>Hmm. This isn&#8217;t looking so good. &#8220;There&#8217;s got to be a better way!&#8221;</p><p>We can certainly drop breakpoints in each of our delegate methods and
trace through them, but wouldn&#8217;t it be nice to just log the call order
of our class delegates in one swell foop, without resorting to
undocumented or cumbersome means?</p><h2>Using an NSProxy</h2><p>Of course there is. That&#8217;s why we wrote this blog post, after all, so
we&#8217;re going to show you how it&#8217;s done. Best of all, you can use this
technique for any class. Roll up your sleeves and let&#8217;s get started.</p><p>[This code is adapted from
http://blog.jayway.com/2009/03/06/proxy-based-aop-for-cocoa-touch/]</p><p>Remember, we&#8217;re operating under the notion that you know your way around
Xcode and have already built a project or two! In Xcode, create a new
&#8220;Master-Detail&#8221; iOS Application called DelegateOrder. We&#8217;re going to use
a PTV prefix for all of our classes (why? Long story <img
src='http://akosma.com/wp/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /></p><p>Thanks to the wonders of modern template technology, our root view
controller happens to be a table view. How convenient!</p><p>Time to create a new class. Right-click on the Classes group in Xcode,
and choose New File&#8230; from the popup menu. Add an Objective-C Cocoa
Touch subclass of NSObject, and name it PTVControllerProxy. Open
PTVControllerProxy.h and change it to look like this:</p><pre><code>@interface PTVControllerProxy : NSProxy
+ (id&lt;UITableViewDataSource, UITableViewDelegate&gt;)proxyWithTableViewController:(UITableViewController *)controller;
- (id)initWithTableViewController:(UITableViewController *)controller;
@end
</code></pre><p>Notice anything different?</p><p>We have not so secretly replaced the NSObject Xcode usually serves with
a dark, sparkling NSProxy object. (Footnote: This is a cultural
reference to a famous Folgers coffee commercial that ran in the US in
the &#8217;80s. Not sure if it aired worldwide though!) Like NSObject, NSProxy
is a root class, except it also <em>conforms</em> to NSObject, plus it adds a
few methods of its own. Here&#8217;s the header:</p><pre><code>#import &lt;Foundation/NSObject.h&gt;
@class NSMethodSignature, NSInvocation;
@interface NSProxy &lt;NSObject&gt; {
    Class   isa;
}
+ (id)alloc;
+ (id)allocWithZone:(NSZone *)zone;
+ (Class)class;
- (void)forwardInvocation:(NSInvocation *)invocation;
- (NSMethodSignature *)methodSignatureForSelector:(SEL)sel;
- (void)dealloc;
- (void)finalize;
- (NSString *)description;
+ (BOOL)respondsToSelector:(SEL)aSelector;
@end
</code></pre><p>NSProxy objects act as stand-ins for other objects. In our case, we&#8217;ll
use PTVControllerProxy as our table view&#8217;s dataSource and delegate. It
will also know about our actual Table View Controller (and table view)
so that it can pass messages down the line.</p><p>The next item of interest is our private instance variable, _controller,
a pointer to a UITableViewController object.</p><p>Following the Coding Guidelines for Cocoa, we always make our instance
variables private. We also add a leading underscore &#8212; just like Apple
does with their own headers &#8212; so as to distinguish them from
properties. This further enforces class interaction through properties
and methods. Meanwhile, on the implementation side, sometimes you want
to access the instance variable. Other times, you need to use the
property. Underscores make it clear which is which.</p><p>In this case, we&#8217;re not creating a property &#8230; at least not one that&#8217;s
publicly available. More on that later.</p><p>We&#8217;ve also defined one class method and one instance method:</p><pre><code>+ (id&lt;UITableViewDataSource, UITableViewDelegate&gt;)proxyWithTableViewController:(UITableViewController *)controller;
</code></pre><p>Our class method takes a UITableViewController and returns an object
that conforms to both the Table View Data Source and Delegate protocols.</p><pre><code>- (id)initWithTableViewController:(UITableViewController *)controller;
</code></pre><p>Our designated initializer method (called by the class method) does the
deed of setting our controller property.</p><p>Did we mean _controller instance variable? No, we meant property. Now
press Cmd-Option-Up-Arrow to switch to the implementation file and make
it look like this:</p><pre><code>#import "PTVControllerProxy.h"
@interface PTVControllerProxy ()
@property (nonatomic, assign) UITableViewController *controller;
- (void)logInvocation:(NSInvocation *)invocation;
@end
@implementation PTVControllerProxy
@synthesize controller = _controller;
@end
</code></pre><p>Ah-ha! So that&#8217;s where the property went.</p><p>We have included yet another interface declaration for
PTVControllerProxy, and this time we&#8217;re extending it beyond what we
originally declared in the header. The parentheses after @interface
PTVControllerProxy signify that this is a class extension. In this case,
we&#8217;ve declared a property and a method that isn&#8217;t exposed to the outside
world. It&#8217;s not private per se, but it&#8217;s not visible in the header
either. Next, in the implementation, we&#8217;ve synthesized a property named
controller, which is represented by the instance variable named
_controller.</p><p>Due to the architecture of Objective-C, you could make a few end-runs
around this and still get at the property and methods. You just have to
know how they&#8217;re defined. Be careful of doing this with Apple&#8217;s classes
though. Them&#8217;s grounds for App Store rejection!</p><p>You can even override extensions previously defined in the header,
making this technique quite handy for exposing readwrite properties as
readonly. Read more about Categories and Extensions in The Objective-C
Programming Language.</p><p>We&#8217;ll discuss <code>-logInvocation:</code> in a moment, but you probably have a
good idea of what it will do just by looking at the name.</p><p>Time to add our methods. Heads up: Some of these may &#8212; or will &#8212; be a
bit unfamiliar. All we are doing here is implementing the minimum number
of methods to handle proxying for our table view controller, and then
some.</p><p>The following should be added between @synthesize and @end in our class
implementation. First, we add our previously defined initializers, and
our lone NSObject method:</p><pre><code>#pragma mark - Initializers
+ (id&lt;UITableViewDataSource, UITableViewDelegate&gt;)proxyWithTableViewController:(UITableViewController *)controller
{
    return [[[[self class] alloc] initWithTableViewController:controller] autorelease];
}
- (id)initWithTableViewController:(UITableViewController *)controller
{
    self.controller = controller;
    return self;
}
#pragma mark - NSObject
- (void)dealloc
{
    [_controller release];
    [super dealloc];
}
</code></pre><p>Our class method takes a table view controller and sends it along to the
designated initializer, which in turn assigns it to the property
controller, and returns itself. As there is no superclass to worry
about, there is no use of <code>[super init]</code> here.</p><p>There&#8217;s one more benefit to our use of private instance variables
beginning with underscores. Our method parameters do not conflict with
like-named instance variables! Look at this line again:</p><pre><code>self.controller = controller;
</code></pre><p>This dot notation is 100% equivalent to:</p><pre><code>[self setController:controller];
</code></pre><p>Very clean, consistent, and easy to read. Contrast this with the
scenario where our instance and method variable named matched. We would
have to code methods like this:</p><pre><code>- (id)initWithTableViewController:(UITableViewController *)theController
{
    self.controller = theController;
    return self;
}
</code></pre><p>It should also be pointed out that these method names are not haphazard.
Apple does in fact provide a method (pun intended) for naming methods!
The previously mentioned Coding Guidelines for Cocoa tells all. Take the
time to name your instance variables, properties, and methods according
to the guidelines. It&#8217;s worth the effort!</p><p>The dealloc method is also standard-issue. Notice that we work with the
instance variable at this point. After dealloc, the show&#8217;s over for this
class, so we don&#8217;t even bother setting _controller to nil. In other
cases, you would likely want to clear it, using the property to take
advantage of its retain/release smarts in one step:</p><pre><code>// This setter (-setController:) releases _controller for us!
self.controller = nil;
</code></pre><p>Continuing with our NSObject methods, add the following:</p><pre><code>- (BOOL)isKindOfClass:(Class)aClass;
{
    return [self.controller isKindOfClass:aClass];
}
- (BOOL)conformsToProtocol:(Protocol *)aProtocol;
{
    return [self.controller conformsToProtocol:aProtocol];
}
- (BOOL)respondsToSelector:(SEL)aSelector;
{
    return [self.controller respondsToSelector:aSelector];
}
</code></pre><p>Be careful here. There are class methods with the same signature like
NSProxy&#8217;s +respondsToSelector:! We&#8217;re responding to NSObject&#8217;s protocol
methods instead, passing (well, proxying) the parameter over to our
table view controller. This takes care of establishing our proxy as
having the same class, protocol conformance, and selector response.
That, in turn, assures us an opportunity to tap in to the deluge of
table view delegate traffic.</p><p>Now, so we just discussed how you can avoid naming collisions between
method parameters and instance variables, and here we have aClass,
aProtocol, and aSelector! This leads us to an important maxim: &#8220;You have
to know the rules before you can break them.&#8221; Use discretion! Here,
we&#8217;re honoring the naming convention established by the authors of
NSObject.h, in particular the NSObject protocol.</p><p>As it turns out, the Protocol and Base Class declarations of <code>-conformsToProtocol:</code> are ever so slightly different:</p><pre><code>// Protocol
- (BOOL)conformsToProtocol:(Protocol *)aProtocol;
// Base Class
+ (BOOL)conformsToProtocol:(Protocol *)protocol;
</code></pre><p>Go figure. (It&#8217;s OK. We still love Cocoa. Tasty Cocoa &#8230;)</p><p>Let&#8217;s add two more, slightly longer methods, this time from NSProxy&#8217;s
protocol:</p><pre><code>#pragma mark - NSProxy
- (NSMethodSignature *)methodSignatureForSelector:(SEL)aSelector
{
    if ([self.controller respondsToSelector:aSelector])
    {
        return [self.controller methodSignatureForSelector:aSelector];
    }
    else
    {
        return [super methodSignatureForSelector:aSelector];
    }
}
</code></pre><p>Method signatures help us forward along messages we otherwise wouldn&#8217;t
respond to. Here, the message is either bound for our table view
controller or the superclass.</p><pre><code>- (void)forwardInvocation:(NSInvocation *)invocation
{
    SEL selector = [invocation selector];
    if ([self.controller respondsToSelector:selector])
    {
        [self logInvocation:invocation];
        [invocation setTarget:self.controller];
        [invocation invoke];
    }
}
</code></pre><p><code>-forwardInvocation:</code> is used by subclasses to send Objective-C
messages-as-objects (or Invocations) to other objects. For the proxy,
it&#8217;s just a matter of passing the message along to whatever object we
aim to represent. That object, of course, is the table view controller.</p><p>First, we ensure the controller responses to the selector represented by
the invocation. Then, just before we dispatch the invocation using
-invoke, we call &#8211; ta-dah &#8211; our private -loginvocation: method. With
that, we can now log every single solitary table view controller message
that comes our way, all from one place.</p><p>Oh, and look, it&#8217;s invocation and not anInvocation. (You&#8217;re not going to
let us live this one down, are you.)</p><p>At last, we come to the coup de grace of our controller proxy class. Add
this to the implementation:</p><pre><code>#pragma mark - Private
- (void)logInvocation:(NSInvocation *)invocation
{
    SEL selector = [invocation selector];
    NSString *currentMethod = NSStringFromSelector(selector);
    NSString *argument = @"";
    NSMethodSignature *methodSignature = [invocation methodSignature];
    NSInteger argCount = [methodSignature numberOfArguments];
    for (NSInteger index = 3; index &lt; argCount; ++index)
    {
        const char *argType = [methodSignature getArgumentTypeAtIndex:index];
        if (strcmp(argType, "@") == 0)
        {
            id object = nil;
            [invocation getArgument:&amp;object atIndex:index];
            if ([object isKindOfClass:[NSIndexPath class]])
            {
                NSIndexPath *indexPath = (NSIndexPath *)object;
                argument = [NSString stringWithFormat:@"{%d, %d}", indexPath.section, indexPath.row];
            }
        }
        else if (strcmp(argType, "i") == 0)
        {
            NSInteger section;
            [invocation getArgument:&amp;section atIndex:index];
            argument = [NSString stringWithFormat:@"%d", section];
        }
    }
    NSLog(@"%@%@", currentMethod, argument);
}
</code></pre><p>OK! A lot to take in here. Let&#8217;s talk through it.</p><p>Just like in <code>-forwardInvocation:</code>, we grab our selector, or in this case
our delegate message. In preparation for logging, we turn it into a
string called <code>currentMethod</code>. This gives us, for example,
@&#8221;tableView:cellForRowAtIndexPath:&#8221; &#8211; ready for logging.</p><p>Perhaps that would be enough, but we can do better. NSInvocation
contains a NSMethodSignature object with all the arguments, so let&#8217;s
grab a few of those while we&#8217;re at it.</p><p>If you were to look at the method signature&#8217;s arguments, you would soon
discover the first two arguments are always claimed by a few
behind-the-scenes players, (id)self and (SEL)_cmd. Argument indices are
zero-based, so that places us at index 2 for the start of our delegate
methods. Meanwhile, following best practices for delegate method
conventions, the table view is always passed back as the first argument,
in this case index 2. Thus we want to start at index 3, which should
explain this loop construct:</p><pre><code>for (NSInteger index = 3; index &lt; argCount; ++index)
{
    const char *argType = [methodSignature getArgumentTypeAtIndex:index];
...
</code></pre><p>Next, we look at the argument type, returned as constant C string
representing an Objective C argument type. &#8220;@&#8221; represents an object, and
&#8220;i&#8221; represents an integer. Easy enough.</p><p>If we have an object, we check to see if it&#8217;s of class NSIndexPath. If
so, good! We grab the index path&#8217;s row and section, and use that in the
log message. If we have an integer, we simply grab the integer value
instead.</p><p>What if we have no such argument, as in -numberOfSectionsInTableView? No
worries, we&#8217;ll still log the message. We just won&#8217;t have any of these
parameters to go along with it.</p><p>Finally, we log our method and our (possible) lone argument. At last,
the controller proxy is complete.</p><p>We now turn our attention to our table view controller, represented here
by PTVRootViewController. Open the header file first, and change it to
look like this:</p><pre><code>#import &lt;UIKit/UIKit.h&gt;
@interface PTVRootViewController : UITableViewController
{
@private
    id&lt;UITableViewDataSource, UITableViewDelegate&gt; _proxy;
}
@end
</code></pre><p>We&#8217;ve merely added a private instance variable for the proxy object.
Notice that there is no publicly exposed property. We will only be using
the proxy within the confines of the class.</p><p>Now switch to the implementation file and &#8230; remove everything. Nothing
wrong with the pre-fab code here. We&#8217;re just going to start over. Add
this for starters:</p><pre><code>#import "PTVRootViewController.h"
#import "PTVControllerProxy.h"
static NSInteger SECTION_COUNT = 25;
static NSInteger ROW_COUNT = 5;
</code></pre><p>We first import our class header, as well as the proxy header. Next,
because we&#8217;re testing out the proxy, we can keep the data source rather
sparse and simple, but we still want a good number of rows and sections
to work with. We define a few constants to this effect, giving us 25
table view sections, each one with five rows.</p><p>Time for another private extension:</p><pre><code>@interface PTVRootViewController ()
@property (nonatomic, retain) id&lt;UITableViewDataSource, UITableViewDelegate&gt; proxy;
@end
@implementation PTVRootViewController
@synthesize proxy = _proxy;
@end
</code></pre><p>There it is, our internal proxy property, and a bare-bones
implementation, complete with synthesized methods. Next up is our
requisite NSObject method:</p><pre><code>#pragma mark - NSObject
- (void)dealloc
{
    [_proxy release];
    [super dealloc];
}
</code></pre><p>Nothing earth-shattering there. Next up, a bunch of UIViewController
methods:</p><pre><code>#pragma mark - UIViewController
- (void)viewDidLoad
{
    [super viewDidLoad];
    self.proxy = [PTVControllerProxy proxyWithTableViewController:self];
    self.tableView.dataSource = self.proxy;
    self.tableView.delegate = self.proxy;
    self.title = @"Delegate Call Order";
    self.navigationItem.rightBarButtonItem = self.editButtonItem;
}
</code></pre><p>In -viewDidLoad, we create and connect the proxy object. We also take a
moment to set the associated navigation bar&#8217;s title and add a stock edit
button on the right side.</p><pre><code>- (void)viewDidUnload
{
}
- (void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];
}
- (void)viewDidAppear:(BOOL)animated
{
    [super viewDidAppear:animated];
}
- (void)viewWillDisappear:(BOOL)animated
{
    [super viewWillDisappear:animated];
}
- (void)viewDidDisappear:(BOOL)animated
{
    [super viewDidDisappear:animated];
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    return (interfaceOrientation == UIInterfaceOrientationPortrait);
}
</code></pre><p>We&#8217;ll disable autorotation for now, so we only respond to portrait
orientation requests.</p><pre><code>- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];
}
</code></pre><p>At last! Time to add the delegate methods. <em>All of them</em>. That&#8217;s right, <strong>we will respond to every single one</strong>. In doing so, the proxy will get
a chance to work its logging magic. Add the following for starters:</p><pre><code>#pragma mark - UITableViewDataSource
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
    return SECTION_COUNT;
}
- (NSArray *)sectionIndexTitlesForTableView:(UITableView *)tableView
{
    NSMutableArray *array = [NSMutableArray arrayWithCapacity:SECTION_COUNT];
    for (NSInteger index = 0; index &lt; SECTION_COUNT; ++index)
    {
        NSString *sectionTitle = [NSString stringWithFormat:@"%d", index];
        [array addObject:sectionTitle];
    }
    return array;
}
</code></pre><p>Our table view has <code>SECTION_COUNT</code> sections. The section index titles
(along the right side of the table view) will be represented by our
section numbers 0 through 24. This will make it easy to see the effects
of changing our vantage point.</p><p>Let&#8217;s add a few more:</p><pre><code>- (BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath
{
    return YES;
}
- (BOOL)tableView:(UITableView *)tableView canMoveRowAtIndexPath:(NSIndexPath *)indexPath
{
    return YES;
}
</code></pre><p>We allow editing and moving of all rows.</p><pre><code>- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"Cell";
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
    if (cell == nil)
    {
        cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
    }
    cell.textLabel.text = [NSString stringWithFormat:@"Section %d, row %d", indexPath.section, indexPath.row];
    return cell;
}
</code></pre><p>Here is where the cell generation and reuse takes place. Again, nothing
surprising here. We take advantage of our table view&#8217;s cell queue and
either dequeue or create a cell, setting its text label to the current
cell&#8217;s section and row.</p><pre><code>- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
    if (editingStyle == UITableViewCellEditingStyleDelete)
    {
        [tableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade];
    }
    else if (editingStyle == UITableViewCellEditingStyleInsert)
    {
    }
}
</code></pre><p>Since we&#8217;re allowing editing (and by editing we mean deletion of cells,
not insertion), we&#8217;ll respond to this method as well, deleting the row
indicated by the indexPath, fading it out as it goes.</p><pre><code>- (void)tableView:(UITableView *)tableView moveRowAtIndexPath:(NSIndexPath *)fromIndexPath toIndexPath:(NSIndexPath *)toIndexPath
{
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    return ROW_COUNT;
}
- (NSInteger)tableView:(UITableView *)tableView sectionForSectionIndexTitle:(NSString *)title atIndex:(NSInteger)index
{
    return [title intValue];
}
</code></pre><p>We respond to <code>-tableView:moveRowAtIndexPath:toIndexPath:</code> as well.
Since we aren&#8217;t manipulating any behind-the-scenes data, we don&#8217;t need
to do anything extra. We also offer up <code>ROW_COUNT</code> rows in each section.
Next, we take advantage of our section index titles (which are just
numbers represented as strings), converting them back to integers as
needed.  index is meant to be used with our index title array, which of
course we aren&#8217;t keeping track of. Then again, it&#8217;s simple enough that
we don&#8217;t have to. Each index title maps directly to a like-numbered
section in the table view, so it&#8217;s as simple as returning each title&#8217;s
integer value.</p><p>Two more data source methods and we&#8217;re more than halfway there.</p><pre><code>- (NSString *)tableView:(UITableView *)tableView titleForFooterInSection:(NSInteger)section
{
    return [NSString stringWithFormat:@"Footer for section %d", section];
}
- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section
{
    return [NSString stringWithFormat:@"Header for section %d", section];
}
</code></pre><p>Easy peasy, right? Good! Now for the table view delegate methods. These
are even easier:</p><pre><code>#pragma mark - UITableViewDelegate
- (void)tableView:(UITableView *)tableView accessoryButtonTappedForRowWithIndexPath:(NSIndexPath *)indexPath
{
}
- (void)tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath
{
}
- (void)tableView:(UITableView *)tableView didEndEditingRowAtIndexPath:(NSIndexPath *)indexPath
{
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
    [self.tableView deselectRowAtIndexPath:indexPath animated:YES];
}
- (UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath
{
    return UITableViewCellEditingStyleDelete;
}
</code></pre><p>A few more empty methods, again just to get the benefit of logging. We
will also deselect each row in response to it being selected. Next, we
assure that the editing style of each row supports deletion.</p><p>Now we&#8217;ll handle header, footer, and row sizing, plus indentation:</p><pre><code>- (CGFloat)tableView:(UITableView *)tableView heightForFooterInSection:(NSInteger)section
{
    return 20.0f;
}
- (CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section
{
    return 20.0f;
}
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{
    return 44.0f;
}
- (NSInteger)tableView:(UITableView *)tableView indentationLevelForRowAtIndexPath:(NSIndexPath *)indexPath
{
    return 0;
}
- (BOOL)tableView:(UITableView *)tableView shouldIndentWhileEditingRowAtIndexPath:(NSIndexPath *)indexPath
{
    return YES;
}
</code></pre><p>Returning YES for <code>-tableView:shouldIndentWhileEditingRowAtIndexPath:</code> allows the background of the edited row to be indented. This allows the
cell contents to shift and more gracefully accomodate the Delete button
appearing on the right-hand side.</p><pre><code>- (NSIndexPath *)tableView:(UITableView *)tableView targetIndexPathForMoveFromRowAtIndexPath:(NSIndexPath *)sourceIndexPath toProposedIndexPath:(NSIndexPath *)proposedDestinationIndexPath
{
    return proposedDestinationIndexPath;
}
</code></pre><p>We won&#8217;t do anything unusual with proposed moving of cells, so we return
the proposed destination index path.</p><pre><code>- (NSString *)tableView:(UITableView *)tableView titleForDeleteConfirmationButtonForRowAtIndexPath:(NSIndexPath *)indexPath
{
    return @"Delete";
}
- (UIView *)tableView:(UITableView *)tableView viewForFooterInSection:(NSInteger)section
{
    return nil;
}
- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section
{
    return nil;
}
</code></pre><p>The delete confirmation button will remain @&#8221;Delete&#8221;, and we won&#8217;t be
using views for the section headers or footers. Still, we need to
implement these methods if we are to see them logged!</p><p>Four more methods to go, and our implementation is finished:</p><pre><code>- (void)tableView:(UITableView *)tableView willBeginEditingRowAtIndexPath:(NSIndexPath *)indexPath
{
}
- (NSIndexPath *)tableView:(UITableView *)tableView willDeselectRowAtIndexPath:(NSIndexPath *)indexPath
{
    return indexPath;
}
- (void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath
{
}
- (NSIndexPath *)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
    return indexPath;
}
</code></pre><h2>Executing the Code</h2><p><img
src="http://akosma.com/wp/wp-content/uploads/2012/01/delegateorder1.png" alt="Delegateorder1" border="0" width="170" height="319" class="alignleft size-full" /></p><p>Congratulations! Let&#8217;s take it for a spin in the Simulator. Before
building your project, bring up the debugger console window by typing
Shift-Cmd-R or selecting Run > Console from the menu. Move the console
off to the side so that you can see what happens next. You might even
want to venture a guess as to which messages and parameters you&#8217;ll see
first. Place your bets!</p><p>Now Build and Run your project using the Debug configuration. The
Simulator will launch and the console will soon be filled with a bunch
of log messages. Do not use the Simulator just yet. Let&#8217;s focus on the
console.</p><p>Thankfully, they will only be concerning our table view controller
delegates. (Otherwise, we would be positively buried with messages. You
think <em>this</em> is a lot of messages, you should see what Objective-C deals
with in a typical app&#8217;s lifetime!)</p><p>Let&#8217;s start at the top and see what we have here. (We have removed the
timestamp and App specific info. Your log lines will be a bit lengthier
by comparison. You might want to make the console window a bit wider to
help keep the lines from wrapping.)</p><pre><code>numberOfSectionsInTableView:
numberOfSectionsInTableView:
</code></pre><p>The first thing we&#8217;re asked for is the number of sections in our table
view &#8230; and we&#8217;re asked for this information <em>twice</em>. (Your guess is as
good as ours.)</p><p>Remember, we have 24 sections in our table view.</p><pre><code>tableView:viewForHeaderInSection:24
tableView:titleForHeaderInSection:24
tableView:heightForHeaderInSection:24
tableView:heightForHeaderInSection:24
tableView:viewForFooterInSection:24
tableView:titleForFooterInSection:24
tableView:heightForFooterInSection:24
tableView:heightForFooterInSection:24
</code></pre><p>Next, we see a bunch of messages pertaining to one section, in this case
section 24. First the headers, then the footers. Here we have two more
examples of a twice-called method in <code>-tableView:heightForHeaderInSection:</code> and <code>-tableView:heightForFooterInSection:</code>.</p><p>So the order so far is as follows (eliminating duplicate invocations):</p><pre><code>numberOfSectionsInTableView:
</code></pre><p>Then, for each section, the header and footer information:</p><pre><code>tableView:viewForHeaderInSection:
tableView:titleForHeaderInSection:
tableView:heightForHeaderInSection:
tableView:viewForFooterInSection:
tableView:titleForFooterInSection:
tableView:heightForFooterInSection:
</code></pre><p>You can imagine that the title is not needed (and the relevant method
not called) if a view is returned, so it makes sense that the view is
asked for first.</p><p>Armed with our section count, the table view turns its attention to the
rows, starting with &#8230; the last one?</p><pre><code>tableView:numberOfRowsInSection:24
tableView:heightForRowAtIndexPath:{24, 0}
tableView:heightForRowAtIndexPath:{24, 1}
tableView:heightForRowAtIndexPath:{24, 2}
tableView:heightForRowAtIndexPath:{24, 3}
tableView:heightForRowAtIndexPath:{24, 4}
</code></pre><p>We have 5 rows in each section, which explains the index paths from {24,
0} through {24, 4}. The height is returned for each. So far, so good.</p><p>Now it would appear as if we&#8217;re starting at the end of the list and
working our way backward, but the next thing you see is this:</p><pre><code>tableView:viewForHeaderInSection:0
tableView:titleForHeaderInSection:0
tableView:heightForHeaderInSection:0
tableView:heightForHeaderInSection:0
tableView:viewForFooterInSection:0
tableView:titleForFooterInSection:0
tableView:heightForFooterInSection:0
tableView:heightForFooterInSection:0
tableView:numberOfRowsInSection:0
tableView:heightForRowAtIndexPath:{0, 0}
tableView:heightForRowAtIndexPath:{0, 1}
tableView:heightForRowAtIndexPath:{0, 2}
tableView:heightForRowAtIndexPath:{0, 3}
tableView:heightForRowAtIndexPath:{0, 4}
</code></pre><p>Is UITableView darting back and forth between the beginning and the end?
(Answer: No. The next section it inquires about is section 1, all the
way up to 23.) In fact, if you recompile this with only three sections,
numbered 0 through 2, you&#8217;ll get a similar outcome with the section
order: 2, 0, and 1.</p><p>So what&#8217;s happening here? Why does UITableView need to know about the
last section first? [Note: Unknown! Any insights?]</p><pre><code>sectionIndexTitlesForTableView:
</code></pre><p>Now that UITableView knows all the row heights, you shouldn&#8217;t see those
called again unless the table is reloaded. That&#8217;s a good thing too
because calculating those row heights can take some time, depending on
the situation.</p><pre><code>tableView:cellForRowAtIndexPath:{0, 0}
tableView:indentationLevelForRowAtIndexPath:{0, 0}
tableView:canEditRowAtIndexPath:{0, 0}
tableView:willDisplayCell:forRowAtIndexPath:{0, 0}
</code></pre><p>Next up are a series of four messages for each visible row, as well as
those just out of view above and below. Since we&#8217;re at the start of the
content area, we begin with index path {0, 0} and the messages are sent
all the way through index path <code>{1, 3}</code>. The familiar <code>-tableView:cellForRowAtIndexPath:</code> is called first, followed by a
request for the indentation level, and a check to see if the row is
editable.  Last comes <code>-tableView:willDisplayCell:forRowAtIndexPath:</code>.
If you&#8217;ve read the documentation, you know this is your last chance to
make final adjustments before a cell is displayed &#8230; and now we have
proof!</p><pre><code>tableView:viewForHeaderInSection:0
tableView:titleForHeaderInSection:0
tableView:viewForFooterInSection:0
tableView:titleForFooterInSection:0
</code></pre><p>Finally, we have a set of four different messages for the view (or,
failing that, the title) for the header in each visible section. You
probably know that headers are always visible, even when all of a given
section&#8217;s rows are not. This holds true for section footers as well,
only these are kept visible on the bottom of the view instead of the
top.</p><p>In the Debugger console, press return a few times to add some blank
space (or just press Clear Log in the toolbar). Now let&#8217;s try and scroll
another screenful of rows into view and see what happens. Click and drag
the bottom-most row up to the top until Section 2, row 4 is visible.
Here&#8217;s what we get. Note that we have added blank lines in between each
logical group of method invocations.</p><pre><code>tableView:viewForHeaderInSection:0
tableView:titleForHeaderInSection:0
tableView:cellForRowAtIndexPath:{1, 4}
tableView:indentationLevelForRowAtIndexPath:{1, 4}
tableView:canEditRowAtIndexPath:{1, 4}
tableView:willDisplayCell:forRowAtIndexPath:{1, 4}
tableView:viewForFooterInSection:1
tableView:titleForFooterInSection:1
tableView:viewForHeaderInSection:2
tableView:titleForHeaderInSection:2
tableView:cellForRowAtIndexPath:{2, 0}
tableView:indentationLevelForRowAtIndexPath:{2, 0}
tableView:canEditRowAtIndexPath:{2, 0}
tableView:willDisplayCell:forRowAtIndexPath:{2, 0}
tableView:viewForFooterInSection:2
tableView:titleForFooterInSection:2
tableView:cellForRowAtIndexPath:{2, 1}
tableView:indentationLevelForRowAtIndexPath:{2, 1}
tableView:canEditRowAtIndexPath:{2, 1}
tableView:willDisplayCell:forRowAtIndexPath:{2, 1}
tableView:cellForRowAtIndexPath:{2, 2}
tableView:indentationLevelForRowAtIndexPath:{2, 2}
tableView:canEditRowAtIndexPath:{2, 2}
tableView:willDisplayCell:forRowAtIndexPath:{2, 2}
tableView:cellForRowAtIndexPath:{2, 3}
tableView:indentationLevelForRowAtIndexPath:{2, 3}
tableView:canEditRowAtIndexPath:{2, 3}
tableView:willDisplayCell:forRowAtIndexPath:{2, 3}
tableView:viewForHeaderInSection:1
tableView:titleForHeaderInSection:1
tableView:cellForRowAtIndexPath:{2, 4}
tableView:indentationLevelForRowAtIndexPath:{2, 4}
tableView:canEditRowAtIndexPath:{2, 4}
tableView:willDisplayCell:forRowAtIndexPath:{2, 4}
</code></pre><p><img
src="http://akosma.com/wp/wp-content/uploads/2012/01/delegateorder2.png" alt="Delegateorder2" border="0" width="600" height="409" class="alignleft size-full" /></p><p>Of particular interest here are the header and footer related methods.
They appear to be invoked in a rather odd pattern, until you examine the
order that each header and footer appears on screen. Then it makes
perfect sense. Interestingly enough, now that we&#8217;re on the move and have
stopped at a definitive spot, we never see index path {3, 0} on the
radar, which is just out of view, past the bottom.</p><p>What about editing? Add some blank space in your debugger, then tap the
edit button.</p><pre><code>tableView:canEditRowAtIndexPath:{1, 1}
tableView:editingStyleForRowAtIndexPath:{1, 1}
tableView:shouldIndentWhileEditingRowAtIndexPath:{1, 1}
tableView:canMoveRowAtIndexPath:{1, 1}
</code></pre><p>We&#8217;ve already seen -tableView:canEditRowAtIndexPath: invoked, just
before our last chance to adjust the cell prior to display. Now it&#8217;s the
first message in the group, followed by a few additional requests. The
editing style is sought, followed by a request to indent the row while
editing, and rounded out by an inquiry to see if the row can be moved.</p><p>Here&#8217;s another observation. Notice how index path {1, 1} seems to be out
of view in our example, yet we see it being called here. This is
repeated through index path {2, 4} which is just in view, but <em>not</em> index path {3, 0} which is just out of view once again. Why?</p><p>There is a good reason for this behavior. When a header and footer are
covering up rows within their related section (that is, when the header
or footer is pegged to the top or bottom of the visible part of the
view), look for a little bit of transparency, letting the underlying
cells show through. When a header is directly above the first cell in
its section (or when a footer is directly below the last cell in its
section), there are no underlying cells to show through. In our case, we
know each section has a header and footer. Thus, there is no need for
fetching adjacent section/row data until at least the next section&#8217;s
header comes into view.</p><p>Let&#8217;s switch Section 1, rows 3 and 4. With the debugger console in view,
tap and hold index path {1, 4}, just over the three bars (signifying a
movable row). Drag it upward until it switches places with index path
{1, 3} but don&#8217;t let go just. Observe the log:</p><pre><code>tableView:targetIndexPathForMoveFromRowAtIndexPath:toProposedIndexPath:{1, 3}
</code></pre><p>Had we been logging this one more completely, it would have looked like this:</p><pre><code>tableView:targetIndexPathForMoveFromRowAtIndexPath:{1, 4}toProposedIndexPath:{1, 3}
</code></pre><p>That&#8217;s all the table view needs to do. Now let go, and the move is complete:</p><pre><code>tableView:moveRowAtIndexPath:toIndexPath:{1, 3}
</code></pre><p>Again, a more complete log would have shown:</p><pre><code>tableView:moveRowAtIndexPath:{1, 4}toIndexPath:{1, 3}
</code></pre><p>Tap Done in the navigation bar, and we see this:</p><pre><code>tableView:canEditRowAtIndexPath:{1, 1}
tableView:canEditRowAtIndexPath:{1, 2}
tableView:canEditRowAtIndexPath:{1, 3}
tableView:canEditRowAtIndexPath:{1, 4}
tableView:canEditRowAtIndexPath:{2, 0}
tableView:canEditRowAtIndexPath:{2, 1}
tableView:canEditRowAtIndexPath:{2, 2}
tableView:canEditRowAtIndexPath:{2, 3}
tableView:canEditRowAtIndexPath:{2, 4}
</code></pre><p>Terrific! Now what other mischief can we cause? Let&#8217;s delete section 2,
row 1 (index path {2, 1}). Add some whitespace to the console, then tap
edit once again, then the red circle at the left of the cell in section
2, row 1.</p><pre><code>tableView:titleForDeleteConfirmationButtonForRowAtIndexPath:{2, 1}
</code></pre><p>Makes sense. The delete button appears (properly labeled). Now tap it to
delete the row.</p><pre><code>tableView:commitEditingStyle:forRowAtIndexPath:{2, 1}
</code></pre><p>First, we commit the editing style for index path {2, 1}. Then we
effectively have a <code>reloadData</code> operation, which causes everything to be
rechecked once again &#8211; headers, footers, row heights, the works. Only
now we start at index path {0, 0} and run all the way clear through {24,
4}. So section 24 gets to go last this time!</p><p>Aaaand &#8230; the app crashes big-time.</p><pre><code> *** Assertion failure in -[UITableView _endCellAnimationsWithContext:], /SourceCache/UIKit_Sim/UIKit-1261.5/UITableView.m:920
 *** Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'Invalid update: invalid number of rows in section 2.  The number of rows contained in an existing section after the update (5) must be equal to the number of rows contained in that section before the update (5), plus or minus the number of rows inserted or deleted from that section (0 inserted, 1 deleted).'
</code></pre><p>Wha happen? Well, our faux data model still thinks there are 24 sections
of five rows each. Obviously that doesn&#8217;t match up with the table view&#8217;s
reality. In short, &#8220;table view fall down go boom.&#8221;</p><p>Well, it was fun while it lasted <img
src='http://akosma.com/wp/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> Get the <a
href="https://github.com/akosma/DelegateOrder">whole source code on
Github</a> and we hope it&#8217;ll be useful to you!</p><p><strong>Similar Posts:</strong></p><ul
class="similar-posts"><li><a
href="http://akosma.com/2010/06/03/objective-c-categories-as-stylesheets/" rel="bookmark" title="June 3, 2010">Objective-C Categories as Stylesheets</a></li><li><a
href="http://akosma.com/2011/03/28/smart-pointers-in-objective-c/" rel="bookmark" title="March 28, 2011">Smart Pointers in Objective-C++</a></li><li><a
href="http://akosma.com/2011/09/20/a-proposed-architecture-for-network-bound-ios-apps/" rel="bookmark" title="September 20, 2011">A Proposed Architecture for Network-Bound iOS Apps</a></li><li><a
href="http://akosma.com/2010/10/11/how-knowing-c-and-c-can-help-you-write-better-iphone-apps-part-1/" rel="bookmark" title="October 11, 2010">How knowing C and C++ can help you write better iPhone apps, part 1</a></li><li><a
href="http://akosma.com/2010/07/17/nib2objc-updated/" rel="bookmark" title="July 17, 2010">nib2objc updated</a></li></ul>]]></content><link rel="replies" type="text/html" href="http://akosma.com/2012/01/31/determining-delegate-object-method-call-in-objective-c-with-nsproxy/#comments" thr:count="0" /><link rel="replies" type="application/atom+xml" href="http://akosma.com/2012/01/31/determining-delegate-object-method-call-in-objective-c-with-nsproxy/feed/atom/" thr:count="0" /> <thr:total>0</thr:total> <feedburner:origLink>http://akosma.com/2012/01/31/determining-delegate-object-method-call-in-objective-c-with-nsproxy/</feedburner:origLink></entry> <entry> <author> <name>Adrian Kosmaczewski</name> <uri>http://kosmaczewski.net/</uri> </author><title type="html"><![CDATA[How we work]]></title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/akosmasoftware/~3/ud6aMfbCMc8/" /> <id>http://akosma.com/?p=3356</id> <updated>2012-01-30T15:02:38Z</updated> <published>2012-01-30T13:45:25Z</published> <category scheme="http://akosma.com" term="Business" /><category scheme="http://akosma.com" term="Opinion" /><category scheme="http://akosma.com" term="strategy" /><category scheme="http://akosma.com" term="workflow" /> <summary type="html"><![CDATA[We have been in business for quite a few years, and we have found out several things that work and other that don&#8217;t in our activities. We have had our share of successes and failures, as any other business; and we hope to have learnt something along the way. This post will outline the recipes [...]]]></summary> <content type="html" xml:base="http://akosma.com/2012/01/30/how-we-work/"><![CDATA[<p>We have been in business for quite a few years, and we have found out
several things that work and other that don&#8217;t in our activities. We have
had our share of successes and failures, as any other business; and we
hope to have learnt something along the way.</p><p>This post will outline the recipes that we have applied to obtain the
best results in the collaboration with our clients.</p><p><span
id="more-3356"></span></p><p><img
src="http://akosma.com/wp/wp-content/uploads/2011/09/you_icon.png"
alt="" border="0" width="170" height="170" class="alignleft size-full"
/></p><h2>Principles</h2><p>What are the principles that guide our work?</p><ul><li>To begin with, we do not work <strong>for</strong> our customers; we work <strong>with</strong> them. This means that we are both collaborating in our projects, in
equal terms, with as many expectations as our clients have.</li><li>Creating software is hard. If you &#8220;have a friend that can make your
application for 100 dollars in 2 days&#8221;, don&#8217;t call us.</li><li>If you are a &#8220;creative agency&#8221;, and &#8220;your first class client&#8221; wants an
application, and you try to push our rates down, &#8220;for the sake of our
future collaboration&#8221;, don&#8217;t bother calling us. We&#8217;re not interested.</li><li>Similarly, if you are an agency and you are going to shield us and
proxy (or &#8220;manage&#8221;) all communications between us and the final
customer, we are not interested. We only work in projects where we
have full access to the customer. We are not interested in other kinds
of collaboration.</li><li><a
href="http://akosma.com/2011/08/05/why-do-not-we-outsource-projects-overseas/">We do not outsource projects</a>. Period.</li><li>We do as much as we can to <a
href="http://akosma.com/2009/12/15/reducing-the-carbon-footprint/">reduce our carbon footprint</a>. And you
should, too.</li></ul><h2>How we work</h2><p>akosma software has a well defined workflow to help its clients bring
their ideas to life; if you are into buzzwords, you could say that we
use a mix of iterative and sequential approaches:</p><ul><li>We ask our clients for a single point-of-contact person, or a &#8220;Product
Owner&#8221; as some methodologies call it; this person will be our sole
communication proxy with the organization. We ask our clients to
always forward questions and remarks through this person at any times.
Doing so helps us work more efficiently and faster.</li><li>We ask our clients for a well defined Statement of Work. We believe
that the final product can only be as good as the Statement of Work
provided. This document must provide as many details as possible about
the final project. This helps us keep our costs low, it reduces
misunderstandings, and helps us deliver features faster.</li><li>For ad-hoc development projects, we usually work in &#8220;fixed time /
fixed price&#8221; mode. We will provide you a cost and a deadline for your
project, and we&#8217;ll stick to it (that&#8217;s why the Statement of Work is so
important!) We can also work in &#8220;time and materials&#8221; mode if you need
it.</li><li>We try to [manage project risks][5] from beginning to end. For that,
we require your commitment, understanding and collaboration.</li><li>We ask our clients to avoid email and phone as a communication and
coordination medium. We use our <a
href="http://projects.akosma.com">project management site</a> instead,
which features forums with threaded conversations, bug tracking and
wikis. This allows us to centralize all the information of the
project, as well as the communication with the client, in a single
repository, to avoid losing information in crowded email inboxes.</li><li>We provide feedback about our work continuously. Our clients can check
the advancement of the project at any time in our project management
site without even having to contact us.  Everything we do is logged in
the screens of the &#8220;Activity&#8221; panel, at any given time. This helps us
reduce interruptions, which are costly, and also helps us increase
customer satisfaction, because the client can always know what’s going
on.</li><li>We divide small projects (with a duration less than one month) in
one-week long iterations, while longer or more complex projects are
divided in two-weeks long iterations. At the end of each iteration,
the client is able to test the application in their own devices and
infrastructure, and we expect feedback from this. The clients’
feedback is fundamental; without it, we will assume that everything is
going according to plan and continue working in the next iteration.</li></ul><h2>Expectations</h2><p>From each client that we agree to work with, we have as many expectations
as you have.</p><ul><li>We expect you to provide us with clear explanations of what you need.
We mean it. In written form. With diagrams. Color. Details.
Everything.</li><li>We expect your feedback, quickly, because every week we are going to
use this feedback to make your product better.</li><li>We expect you to take care of your project as we do. In particular, do
not mess with the source code of what we provide to you: not only this
breaks the warranty (yes, we provide one), but even worse, it breaks
our trust in our relationship.</li><li>We expect that you pay our invoices in time. As simple as that.</li><li>We expect you to have a smile in your face, just like we want to have
one when we work with you. That&#8217;s why we do what we do.</li></ul><p>If you would like to work with us, then just <a
href="http://akosma.com/contact/project-request/">contact us!</a></p><p>[5]:http://akosma.com/2009/08/03/risk-management-in-iphone-projects/<strong>Similar Posts:</strong></p><ul
class="similar-posts"><li><a
href="http://akosma.com/2011/08/05/why-do-not-we-outsource-projects-overseas/" rel="bookmark" title="August 5, 2011">Why do not we outsource projects overseas?</a></li><li><a
href="http://akosma.com/2010/07/09/digital2-0/" rel="bookmark" title="July 9, 2010">digital2.0 iPad Application</a></li><li><a
href="http://akosma.com/2010/02/24/senbei-a-fat-free-crm-iphone-client/" rel="bookmark" title="February 24, 2010">Senbei, a Fat Free CRM iPhone Client</a></li><li><a
href="http://akosma.com/2011/01/20/new-project-request-form/" rel="bookmark" title="January 20, 2011">New Project Request Form</a></li><li><a
href="http://akosma.com/2010/10/04/integrating-ios-applications-with-backend-rest-services/" rel="bookmark" title="October 4, 2010">Integrating iOS Applications with Backend REST Services</a></li></ul>]]></content><link rel="replies" type="text/html" href="http://akosma.com/2012/01/30/how-we-work/#comments" thr:count="0" /><link rel="replies" type="application/atom+xml" href="http://akosma.com/2012/01/30/how-we-work/feed/atom/" thr:count="0" /> <thr:total>0</thr:total> <feedburner:origLink>http://akosma.com/2012/01/30/how-we-work/</feedburner:origLink></entry> <entry> <author> <name>Adrian Kosmaczewski</name> <uri>http://kosmaczewski.net/</uri> </author><title type="html"><![CDATA[Swiss App Awards &#8211; Don&#8217;t Forget!]]></title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/akosmasoftware/~3/JEQckz2NuwM/" /> <id>http://akosma.com/?p=3353</id> <updated>2012-01-10T10:37:02Z</updated> <published>2012-01-10T10:36:18Z</published> <category scheme="http://akosma.com" term="Business" /><category scheme="http://akosma.com" term="iPad" /><category scheme="http://akosma.com" term="iPhone" /><category scheme="http://akosma.com" term="Mobile Web" /><category scheme="http://akosma.com" term="application" /><category scheme="http://akosma.com" term="award" /><category scheme="http://akosma.com" term="event" /><category scheme="http://akosma.com" term="Switzerland" /> <summary type="html"><![CDATA[The deadline of the Swiss App Awards is approaching! Don&#8217;t forget to submit your application using the form before January 15th! The event will be held in Zürich, on January 27th, 2012. You can submit your application (iOS, Android, Windows Mobile, web, any kind and in any language!) or just register as an attendee on [...]]]></summary> <content type="html" xml:base="http://akosma.com/2012/01/10/swiss-app-awards-dont-forget/"><![CDATA[<p>The deadline of the <a
href="http://swissappawards.ch/">Swiss App Awards</a> is approaching! Don&#8217;t forget to <a
href="http://form.jotform.com/form/13471218230">submit your application using the form</a> before January 15th!</p><p>The event will be held in Zürich, on January 27th, 2012. You can <a
href="http://form.jotform.com/form/13471218230">submit your application</a> (iOS, Android, Windows Mobile, web, any kind and in any language!) or just <a
href="https://secure.trifork.com/swiss-app-awards-2012/registration/">register as an attendee</a> on the <a
href="http://swissappawards.ch/">website of the event</a>. You can also follow the <a
href="http://twitter.com/SwissAppAwards">official Twitter account</a> of the Swiss App Awards for more information.</p><p>We look forward to see your applications!</p><p><a
href="http://swissappawards.ch/" target="_blank"><img
src="http://akosma.com/wp/wp-content/uploads/2011/12/swissappawards_banner.png" alt="Swissappawards banner" border="0" width="620" height="113" class="alignleft size-full" /></a></p><p>[6]:http://www.trifork.com/<strong>Similar Posts:</strong></p><ul
class="similar-posts"><li><a
href="http://akosma.com/2011/12/19/swiss-app-awards-2012-submit-your-app-now/" rel="bookmark" title="December 19, 2011">Swiss App Awards 2012 &#8211; Submit your app now!</a></li><li><a
href="http://akosma.com/2011/12/23/retrospective-2011/" rel="bookmark" title="December 23, 2011">Retrospective 2011</a></li><li><a
href="http://akosma.com/2011/10/19/attending-senchacon-2011/" rel="bookmark" title="October 19, 2011">Attending SenchaCon 2011</a></li><li><a
href="http://akosma.com/2012/02/06/goto-copenhagen-2012-call-for-speakers/" rel="bookmark" title="February 6, 2012">GOTO Copenhagen 2012 &#8211; Call for Speakers!</a></li><li><a
href="http://akosma.com/2011/12/12/qcon-london-2012-call-for-papers-in-the-cross-platform-mobile-track/" rel="bookmark" title="December 12, 2011">QCon London 2012: Call for Papers in the Cross-Platform Mobile Track</a></li></ul>]]></content><link rel="replies" type="text/html" href="http://akosma.com/2012/01/10/swiss-app-awards-dont-forget/#comments" thr:count="0" /><link rel="replies" type="application/atom+xml" href="http://akosma.com/2012/01/10/swiss-app-awards-dont-forget/feed/atom/" thr:count="0" /> <thr:total>0</thr:total> <feedburner:origLink>http://akosma.com/2012/01/10/swiss-app-awards-dont-forget/</feedburner:origLink></entry> <entry> <author> <name>Adrian Kosmaczewski</name> <uri>http://kosmaczewski.net/</uri> </author><title type="html"><![CDATA[Wordle 2012]]></title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/akosmasoftware/~3/ogf1HYmM2fg/" /> <id>http://akosma.com/?p=3347</id> <updated>2012-01-09T10:54:53Z</updated> <published>2012-01-09T10:52:51Z</published> <category scheme="http://akosma.com" term="Opinion" /><category scheme="http://akosma.com" term="word cloud" /><category scheme="http://akosma.com" term="Wordle" /> <summary type="html"><![CDATA[Just like last year, here goes the Wordle cloud generated with the most important tags in this blog for 2011! Some subtle differences appear, don&#8217;t you think? Similar Posts: Wordle Senbei 1.3 hits the App Store! Attending SenchaCon 2011 QCon London 2012: Call for Papers in the Cross-Platform Mobile Track GOTO Copenhagen 2012 &#8211; Call [...]]]></summary> <content type="html" xml:base="http://akosma.com/2012/01/09/wordle-2012/"><![CDATA[<p>Just like <a
href="http://akosma.com/2011/02/08/wordle/">last year</a>, here goes the <a
href="http://www.wordle.net/">Wordle cloud</a> generated with the most important tags in this blog for 2011!</p><p><img
src="http://akosma.com/wp/wp-content/uploads/2012/01/wordle2012.png" alt="Wordle2012" border="0" width="620" height="297" class="alignleft size-full" /></p><p>Some subtle differences appear, don&#8217;t you think? <img
src='http://akosma.com/wp/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> <strong>Similar Posts:</strong></p><ul
class="similar-posts"><li><a
href="http://akosma.com/2011/02/08/wordle/" rel="bookmark" title="February 8, 2011">Wordle</a></li><li><a
href="http://akosma.com/2011/09/27/senbei-1-3-hits-the-app-store/" rel="bookmark" title="September 27, 2011">Senbei 1.3 hits the App Store!</a></li><li><a
href="http://akosma.com/2011/10/19/attending-senchacon-2011/" rel="bookmark" title="October 19, 2011">Attending SenchaCon 2011</a></li><li><a
href="http://akosma.com/2011/12/12/qcon-london-2012-call-for-papers-in-the-cross-platform-mobile-track/" rel="bookmark" title="December 12, 2011">QCon London 2012: Call for Papers in the Cross-Platform Mobile Track</a></li><li><a
href="http://akosma.com/2012/02/06/goto-copenhagen-2012-call-for-speakers/" rel="bookmark" title="February 6, 2012">GOTO Copenhagen 2012 &#8211; Call for Speakers!</a></li></ul>]]></content><link rel="replies" type="text/html" href="http://akosma.com/2012/01/09/wordle-2012/#comments" thr:count="0" /><link rel="replies" type="application/atom+xml" href="http://akosma.com/2012/01/09/wordle-2012/feed/atom/" thr:count="0" /> <thr:total>0</thr:total> <feedburner:origLink>http://akosma.com/2012/01/09/wordle-2012/</feedburner:origLink></entry> <entry> <author> <name>Adrian Kosmaczewski</name> <uri>http://kosmaczewski.net/</uri> </author><title type="html"><![CDATA[Trainings 2012: Advanced iOS, Mobile Web Apps and Node.js]]></title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/akosmasoftware/~3/T_LwSy8mXLE/" /> <id>http://akosma.com/?p=3334</id> <updated>2011-12-29T10:44:13Z</updated> <published>2011-12-29T10:08:48Z</published> <category scheme="http://akosma.com" term="Business" /><category scheme="http://akosma.com" term="Education" /><category scheme="http://akosma.com" term="iPad" /><category scheme="http://akosma.com" term="iPhone" /><category scheme="http://akosma.com" term="Mobile Web" /><category scheme="http://akosma.com" term="Geneva" /><category scheme="http://akosma.com" term="iOS" /><category scheme="http://akosma.com" term="jQuery Mobile" /><category scheme="http://akosma.com" term="Node.js" /><category scheme="http://akosma.com" term="Sencha Touch" /><category scheme="http://akosma.com" term="Switzerland" /><category scheme="http://akosma.com" term="training" /><category scheme="http://akosma.com" term="Zürich" /> <summary type="html"><![CDATA[We are thrilled to announce new training sessions in Switzerland and South Africa this year: Advanced iOS: this training is for experienced iOS developers, looking to increase their knowledge with insider tips and tricks about the following subjects: Building iOS 5.x universal applications, compatible with version 4.x of iOS. Advanced user interface design for the [...]]]></summary> <content type="html" xml:base="http://akosma.com/2011/12/29/trainings-2012-advanced-ios-mobile-web-apps-and-node-js/"><![CDATA[<p>We are thrilled to announce new training sessions in Switzerland and
South Africa this year:</p><ul><li><strong>Advanced iOS</strong>: this training is for experienced iOS developers,
looking to increase their knowledge with insider tips and tricks about
the following subjects:<ul><li>Building iOS 5.x universal applications, compatible with version
4.x of iOS.</li><li>Advanced user interface design for the iPhone and the iPad</li><li>Integrating your application with Twitter, Facebook and other
social networking sites.</li><li>Performance enhancements using Core Foundation in your
applications.</li><li>Using Instruments to find performance problems.</li><li>Major ninja-level optimizations.</li><li>2D graphics and animation: Quartz and Core Animation.</li><li>Video, audio, the iPod library, AirPlay, etc.</li></ul></li><li><strong>Mobile Web App Development</strong>: targeting web developers who want to
take their existing knowledge to the next step:<ul><li>Build mobile web applications such as to-do lists, a
location-based social networking site and other apps using <a
href="http://www.sencha.com/products/touch">Sencha
Touch</a>, <a
href="http://jquerymobile.com/">jQuery Mobile</a>.</li><li>Learn how to integrate data from remote APIs in your mobile web
apps, and how to organize your code and your architecture for the
best results.</li><li>Package those applications using <a
href="http://phonegap.com/">PhoneGap</a> and [PhoneGap
Build][9] and distribute them over the major mobile application
marketplaces.</li></ul></li><li><strong>Web Development with Node.js</strong>: this is our new training offering,
for web developers who want to learn more about [the latest and
greatest web framework of the moment][9]:<ul><li>Learn how to create common web applications such as a blog, wiki,
and management systems with backend databases, using the standard
Node.js toolkit.</li><li>Learn about other tools like <a
href="http://npmjs.org/">npm</a>, <a
href="http://expressjs.com/">Express</a>, <a
href="http://vowsjs.org/">Vows</a>, <a
href="http://www.mongodb.org/">MongoDB</a>, <a
href="http://persistencejs.org/">Persistence.js</a> and more.</li></ul></li></ul><p>All trainings are 3 days long, and they include lunch and snacks during
the day. All trainees will receive a ~100 page booklet written by Adrian
with the most important aspects of the training, in PDF, ePub and .mobi
(Kindle) formats. These trainings will take place throughout 2012 in
Geneva and Zürich.</p><p>More information about dates and locations soon! We hope to see you
soon!</p><p><strong>Update</strong>: we forgot to mention that the trainings in Geneva will be
given in French, while in Zürich they will be in English. We are also
going to offer these in South Africa!</p><p>[9]:http://nodejs.org/<strong>Similar Posts:</strong></p><ul
class="similar-posts"><li><a
href="http://akosma.com/2011/01/21/advanced-ios-4-2-training-course-zurich-february-7th-and-8th-2011-enroll-now/" rel="bookmark" title="January 21, 2011">Advanced iOS 4.2 Training Course &#8211; Zürich, February 7th and 8th 2011 &#8211; Enroll now!</a></li><li><a
href="http://akosma.com/2011/12/22/more-mobile-application-training-in-south-africa/" rel="bookmark" title="December 22, 2011">More Mobile Application Training in South Africa</a></li><li><a
href="http://akosma.com/2011/10/19/attending-senchacon-2011/" rel="bookmark" title="October 19, 2011">Attending SenchaCon 2011</a></li><li><a
href="http://akosma.com/2011/09/30/mobile-application-training-in-south-africa/" rel="bookmark" title="September 30, 2011">Mobile Application Training in South Africa</a></li><li><a
href="http://akosma.com/2012/02/01/mobile-web-training-in-zurich-once-again/" rel="bookmark" title="February 1, 2012">Mobile Web Training in Zürich Once Again!</a></li></ul>]]></content><link rel="replies" type="text/html" href="http://akosma.com/2011/12/29/trainings-2012-advanced-ios-mobile-web-apps-and-node-js/#comments" thr:count="0" /><link rel="replies" type="application/atom+xml" href="http://akosma.com/2011/12/29/trainings-2012-advanced-ios-mobile-web-apps-and-node-js/feed/atom/" thr:count="0" /> <thr:total>0</thr:total> <feedburner:origLink>http://akosma.com/2011/12/29/trainings-2012-advanced-ios-mobile-web-apps-and-node-js/</feedburner:origLink></entry> <entry> <author> <name>Adrian Kosmaczewski</name> <uri>http://kosmaczewski.net/</uri> </author><title type="html"><![CDATA[Retrospective 2011]]></title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/akosmasoftware/~3/BQeaW3AOh4s/" /> <id>http://akosma.com/?p=3326</id> <updated>2011-12-23T07:13:58Z</updated> <published>2011-12-23T07:12:51Z</published> <category scheme="http://akosma.com" term="Business" /><category scheme="http://akosma.com" term="Portfolio" /><category scheme="http://akosma.com" term="Press" /><category scheme="http://akosma.com" term="Products" /><category scheme="http://akosma.com" term="Android" /><category scheme="http://akosma.com" term="conference" /><category scheme="http://akosma.com" term="iPad" /><category scheme="http://akosma.com" term="iPhone" /><category scheme="http://akosma.com" term="technology" /><category scheme="http://akosma.com" term="training" /> <summary type="html"><![CDATA[2011 was another terrific year for akosma software, a year of growth, surprise, learning, teaching, and travel. We met fantastic new people on the road and we would like to thank all of our friends, our customers, the readers of this blog, our followers on Twitter, Facebook, Github, LinkedIn and countless other networks for their [...]]]></summary> <content type="html" xml:base="http://akosma.com/2011/12/23/retrospective-2011/"><![CDATA[<p>2011 was another terrific year for akosma software, a year of growth,
surprise, learning, teaching, and travel. We met fantastic new people on
the road and we would like to thank all of our friends, our customers,
the readers of this blog, our followers on <a
href="http://twitter.com/akosmasoftware">Twitter</a>, <a
href="https://www.facebook.com/akosmasoftware">Facebook</a>, <a
href="https://github.com/akosmasoftware">Github</a>, <a
href="http://www.linkedin.com/company/akosma-software">LinkedIn</a> and
countless other networks for their support and feedback throughout the
year! May all of you have a healthy and happy 2012.</p><p>And now let us share with you some highlights of 2012! <span
id="more-3326"></span></p><h2>Training</h2><p>akosma software has established in 2011 a solid and successful training
business, in the domains of iOS and mobile web applications:</p><p><a
href="http://www.immedia.co.za/"><img
src="http://akosma.com/wp/wp-content/uploads/2011/05/immedia-logo.png"
alt="Immedia logo" border="0" width="170" height="51" class="alignleft
size-full" /></a></p><ul><li>We started the year with a successful <a
href="http://akosma.com/2011/01/21/advanced-ios-4-2-training-course-zurich-february-7th-and-8th-2011-enroll-now/">iOS Advanced Training</a> in
February.</li><li>Then we continued with a long training, from February to June, to
teach iOS to school teachers in the Canton of Vaud, in Switzerland.</li><li>Later this year we went to <a
href="http://akosma.com/2011/09/30/mobile-application-training-in-south-africa/">teach iOS development in South Africa</a> during October, in a series of trainings co-organized with <a
href="http://www.immedia.co.za/">immedia</a>.</li><li>We organized with Simplificator GmbH the <a
href="http://akosma.com/2011/10/03/mobile-development-with-jquery-sencha-and-phonegap-15-17-november-2011/">first Swiss training on
jQuery Mobile, Sencha Touch and PhoneGap of the country</a>, which was
also a huge success in November, in Zürich.</li><li>Last but not least, we coached our friend Mathieu Tendon to get his
degree thesis, implementing an Android version of Senbei!</li></ul><p><a
href="http://akosma.com/2011/12/13/student-application-on-the-app-store-troisxrien/"><img
src="http://akosma.com/wp/wp-content/uploads/2011/12/troisxrienicon.png"
alt="Troisxrienicon" border="0" width="170" height="171"
class="alignleft size-full" /></a></p><p>The result of these efforts were an incredible suite of apps created by
some of our students, and now available on the App Store:</p><ul><li><a
href="http://akosma.com/2011/07/06/student-application-on-the-app-store-sudokulus/">Sudokulus</a> by Pieter Muller, an incredible application that allows
us to quickly solve sudoku puzzles!</li><li><a
href="http://akosma.com/2011/12/13/student-application-on-the-app-store-troisxrien/">TroisXRien</a> by Vincent Zeller, a very nice app to teach maths to
children!</li></ul><h2>Conferences</h2><p>2011 was, without any doubt, the year of the conference; not only have
we participated in lots of them as speakers, we could also be the host
of an incredible mobile track and even co-organized one in Zürich!</p><p><a
href="http://www.sigs-datacom.de/oop2011/konferenz/sessiondetails.html?tx_mwconferences_pi1%5BshowUid%5D=382&amp;tx_mwconferences_pi1%5Bpointer%5D=0&amp;tx_mwconferences_pi1%5Bmode%5D=1&amp;tx_mwconferences_pi1%5Bs%5D=0"><img
src="http://akosma.com/wp/wp-content/uploads/2011/01/oop_2011.png"
alt="oop_2011.png" border="0" width="170" height="170" class="alignleft
size-full" /></a></p><ul><li>It all started in January, when we participated at the international <a
href="http://www.sigs-datacom.de/oop2011/konferenz/sessiondetails.html?tx_mwconferences_pi1%5BshowUid%5D=382&amp;tx_mwconferences_pi1%5Bpointer%5D=0&amp;tx_mwconferences_pi1%5Bmode%5D=1&amp;tx_mwconferences_pi1%5Bs%5D=0">OOP conference</a> in Münich.</li><li>In March Adrian was the <a
href="http://qconlondon.com/london-2011/tracks/show_track.jsp?trackOID=417">host of the mobile track</a> in the
prestigious QCon Conference London! It was an incredible day, and you
can check the videos of the sessions in the mobile track directly on
the InfoQ site: <a
href="http://www.infoq.com/presentations/Making-Apps-That-Dont-Suck">Mike Lee</a>&#8216;s, <a
href="http://www.infoq.com/presentations/Mobile-App-Privacy">Graham Lee</a>&#8216;s and <a
href="http://www.infoq.com/presentations/Introduction-to-iOS-Software-Development">his own
presentation</a> are there.</li><li>In April we went to Göteborg, Sweden to talk in the <a
href="http://www.scandevconf.se/2011/conference/speakers/arian-kosmaczewski/">Scandinavian
Developer Conference 2011</a>!</li><li>In June we were invited by the <a
href="http://akosma.com/2011/06/10/foro-de-tecnologia-en-santa-cruz-de-la-sierra-bolivia-el-16-de-junio/">CAINCO in Santa Cruz</a>, Bolivia, to
talk about mobile applications!</li><li>In October, together with <a
href="http://twitter.com/jcfischer">Jens-Christian Fischer</a> from <a
href="http://simplificator.com/">Simplificator</a> we brought the biggest expert of the world of the
mobile web, <a
href="http://akosma.com/2011/09/28/jquery-mobile-multiplatform-mobile-webapps-by-maximiliano-firtman/">Maximiliano Firtman, to talk in Zürich</a>!</li><li>Later that same month we attended <a
href="http://akosma.com/2011/10/19/attending-senchacon-2011/">SenchaCon in Austin, Texas</a>, to
learn more about the incredible Sencha Touch framework.</li><li>Finally, in November we went to the Mobile Developer Summit in
Bangalore, to give <a
href="http://akosma.com/2011/08/15/speaking-at-the-mobile-developer-summit-in-bangalore/">several different talks</a> about iOS and the
mobile web.</li></ul><h2>Consulting and Development</h2><p>This year we strengthtened our collaboration with clients, providing
development and consulting services to industry leaders in Switzerland
and abroad:</p><p><a
href="http://akosma.com/2011/12/20/announcing-eerv-cal-an-iphone-android-and-web-application/"><img
src="http://akosma.com/wp/wp-content/uploads/2011/12/eerv_logo.png"
alt="Eerv logo" border="0" width="170" height="170" class="alignleft
size-full" /></a></p><ul><li>We started a long and fruitful collaboration with <a
href="http://www.immedia.co.za/">immedia</a>, a <a
href="http://akosma.com/2011/05/31/immedia-the-leader-mobile-solutions-provider-in-south-africa/">leading provider of mobile application</a> development services in
South Africa, by providing them with strategy and development
consulting services.</li><li>We extended the swissinfo iPad application into a universal iOS
application, featuring an <a
href="http://akosma.com/2011/09/28/announcing-the-swissinfo-iphone-application/">iPhone application</a> too!</li><li>The <a
href="http://www.ifrc.org/">International Federation of Red Cross and Red Crescent
Societies</a> asked us for help in the definition of the mobile
technologies for a humanitarian project, which consisted in an
extensive report.</li><li>We helped the local protestant church, the Eglise évangélique réformée
du Canton de Vaud, to create their <a
href="http://akosma.com/2011/12/20/announcing-eerv-cal-an-iphone-android-and-web-application/">brand new mobile application</a>,
built using <a
href="http://www.sencha.com/products/touch">Sencha Touch</a> and <a
href="http://phonegap.com/">PhoneGap</a>.</li><li>We worked with many other customers who have explicitly asked us to
remain anonymous, but we thank them for their trust and their
business! We are proud and happy to have worked with them.</li></ul><h2>Products</h2><p>Our apps also received some update love in 2011! We provided new
versions of all of our iOS applications on the App Store, in many cases
introducing the long-awaited iPad versions:</p><p><a
href="http://muchasnotitas.com/"><img
src="http://akosma.com/wp/wp-content/uploads/2011/09/notitas_icon.png"
alt="" border="0" width="170" height="170" class="alignleft size-full"
/></a></p><ul><li><a
href="http://bluewoki.com/">bluewoki</a> has <a
href="http://akosma.com/2011/09/15/bluewoki-2-0-hits-the-app-store/">jumped to version 2.0</a> and introduced support
for wifi networks!</li><li><a
href="http://muchasnotitas.com/">Notitas</a> has finally become a universal application! <a
href="http://akosma.com/2011/09/26/notitas-2-0-a-major-milestone/">The new
iPad</a> version was a welcome addition and has had a very nice
effect on sales so far.</li><li><a
href="http://rooifonts.com/">RooiFonts</a> has also <a
href="http://akosma.com/2011/09/22/rooifonts-1-1-in-the-app-store/">got an iPad version!</a></li><li><a
href="http://akosma.com/2011/09/27/senbei-1-3-hits-the-app-store/">Senbei was updated</a> with many bug fixes.</li><li>Finally, our flagship open source project, <a
href="https://github.com/akosma/nib2objc">nib2objc</a>, has been
updated to support new features of iOS 4.</li></ul><h2>On the Press</h2><p>This year we have increased our presence in the media, showcasing our
ideas and our opinion on the world of technology:</p><p><a
href="http://akosma.com/2011/06/19/article-in-the-sonntagszeitung-die-neuen-schweizer-macher/"><img
src="http://akosma.com/wp/wp-content/uploads/2011/06/Swiss-Made-Apps.png"
alt="Swiss Made Apps" border="0" width="170" class="alignleft size-full"
/></a></p><ul><li>Early this year, our famous nib2objc project was <a
href="http://akosma.com/2011/02/17/nib2objc-featured-on-the-changelog/">featured in the
popular open source blog &#8220;The ChangeLog&#8221;</a></li><li>The day before our talk at CAINCO, we were <a
href="http://akosma.com/2011/06/30/interview-in-the-bolivian-tv/">interviewed live on the
Bolivian TV</a></li><li>We were featured in an <a
href="http://akosma.com/2011/06/19/article-in-the-sonntagszeitung-die-neuen-schweizer-macher/">article about the local mobile application
market on the SonntagsZeitung</a>, the most important newspaper of
Switzerland!</li><li>Our talk on QCon London 2011 was <a
href="http://akosma.com/2011/06/02/introduction-to-ios-software-development-video-on-infoq/">featured on InfoQ</a>.</li><li>We&#8217;ve been <a
href="http://akosma.com/2011/11/27/interview-on-the-swiss-tv/">interviewed on the Swiss TV</a> as well, during a special
emission about smartphone applications.</li><li>And last but not least, we now have a <a
href="http://akosma.com/2011/10/17/article-in-cominmag/">regular column about mobile
applications</a> in the <a
href="http://www.cominmag.ch/">Cominmag magazine</a>!</li></ul><h2>Other news</h2><p>But that&#8217;s not all! 2011 brought lots of surprises and announcements:</p><p>[<img
src="http://akosma.com/wp/wp-content/uploads/2011/07/newdesign.png"
alt="New akosma software visual identity" border="0" width="170"
class="alignleft size-full" />][54]</p><ul><li>Early this year we moved to <a
href="http://akosma.com/2011/02/24/new-address/">new offices</a> in Oron-la-Ville.</li><li>The incredible team of <a
href="http://moserdesign.ch/">moser design</a> created for us an
[incredible new corporate image][54], including a very cool set of
logos and stationery!</li><li>We opened up a new <a
href="http://twitter.com/akosmasoftware">Twitter account</a> and a new <a
href="https://www.facebook.com/akosmasoftware">Facebook page</a> for the company!</li><li>We detected a huge change in the market, where the <a
href="http://akosma.com/2011/09/13/a-shift-in-the-market-towards-mobile-web-apps/">demand of mobile
web apps is growing</a> and opens up very exciting new opportunities!</li><li>During the year we <a
href="http://akosma.com/2011/08/23/dropping-support-for-iphone-os-3-x/">dropped support for iOS 3.x</a> in all of our
products and also for the projects we create for our clients.</li><li>Finally, we also stated our <a
href="http://akosma.com/2011/08/05/why-do-not-we-outsource-projects-overseas/">policy of refusing to offshore
projects</a>.</li></ul><h2>And What About Next Year?</h2><p>2012 is already filled up with new exciting projects coming up!</p><ul><li>In January <a
href="http://akosma.com/2011/12/19/swiss-app-awards-2012-submit-your-app-now/">we will be part of the Jury</a> of the <a
href="http://swissappawards.ch/">Swiss App
Awards</a>.</li><li>In February we will be working with <a
href="http://www.immedia.co.za/">immedia</a> providing <a
href="http://akosma.com/2011/12/22/more-mobile-application-training-in-south-africa/">new
mobile development training sessions</a> in South Africa.</li><li>We will be <a
href="http://akosma.com/2011/12/12/qcon-london-2012-call-for-papers-in-the-cross-platform-mobile-track/">hosting the Cross-Platform Mobile track</a> of QCon
London 2012.</li><li>We will participate in <a
href="http://gotocon.com/cph-2012/">GOTOcon Copenhagen 2012</a> in May.</li></ul><p>But that&#8217;s not all!</p><ul><li>Great new projects already in preparation, to be announced soon!</li><li>More trainings in Switzerland, both for iOS and the mobile web.</li><li>&#8230;and much, much more!</li></ul><p>Stay tuned as usual, and be very happy in 2012!</p><p><img
src="http://akosma.com/wp/wp-content/uploads/2009/12/arbol22.png" alt="arbol2.png" border="0" width="440" height="652" class="alignnone size-medium" /></p><p>[54]:http://akosma.com/2011/07/02/new-visual-identity/<strong>Similar Posts:</strong></p><ul
class="similar-posts"><li><a
href="http://akosma.com/2011/10/19/attending-senchacon-2011/" rel="bookmark" title="October 19, 2011">Attending SenchaCon 2011</a></li><li><a
href="http://akosma.com/2012/02/01/qcon-london-2012-cross-platform-mobile-track-announcement/" rel="bookmark" title="February 1, 2012">QCon London 2012: Cross-Platform Mobile Track Announcement!</a></li><li><a
href="http://akosma.com/2011/06/02/introduction-to-ios-software-development-video-on-infoq/" rel="bookmark" title="June 2, 2011">&#8220;Introduction to iOS Software Development&#8221; Video on InfoQ!</a></li><li><a
href="http://akosma.com/2011/12/13/student-application-on-the-app-store-troisxrien/" rel="bookmark" title="December 13, 2011">Student application on the App Store: TroisXRien</a></li><li><a
href="http://akosma.com/2010/12/29/retrospective-2010/" rel="bookmark" title="December 29, 2010">Retrospective 2010</a></li></ul>]]></content><link rel="replies" type="text/html" href="http://akosma.com/2011/12/23/retrospective-2011/#comments" thr:count="0" /><link rel="replies" type="application/atom+xml" href="http://akosma.com/2011/12/23/retrospective-2011/feed/atom/" thr:count="0" /> <thr:total>0</thr:total> <feedburner:origLink>http://akosma.com/2011/12/23/retrospective-2011/</feedburner:origLink></entry> <entry> <author> <name>Adrian Kosmaczewski</name> <uri>http://kosmaczewski.net/</uri> </author><title type="html"><![CDATA[More Mobile Application Training in South Africa]]></title><link rel="alternate" type="text/html" href="http://feedproxy.google.com/~r/akosmasoftware/~3/QK90ZP4FouE/" /> <id>http://akosma.com/?p=3319</id> <updated>2011-12-22T09:10:05Z</updated> <published>2011-12-22T08:49:59Z</published> <category scheme="http://akosma.com" term="Education" /><category scheme="http://akosma.com" term="Portfolio" /><category scheme="http://akosma.com" term="immedia" /><category scheme="http://akosma.com" term="iOS" /><category scheme="http://akosma.com" term="South Africa" /><category scheme="http://akosma.com" term="training" /> <summary type="html"><![CDATA[Just like last October I&#8217;ll be back in South Africa next February, for a whole series of mobile application trainings organized jointly by immedia and akosma software! Have you ever wanted to learn how to create a mobile app? Looked at Evernote and thought, “Hey, I can do that!” We have embarked on an exciting [...]]]></summary> <content type="html" xml:base="http://akosma.com/2011/12/22/more-mobile-application-training-in-south-africa/"><![CDATA[<p>Just <a
href="http://akosma.com/2011/09/30/mobile-application-training-in-south-africa/">like last October</a> I&#8217;ll be back in South Africa next February, for a whole series of mobile application trainings organized jointly by <a
href="http://www.immedia.co.za/">immedia</a> and akosma software!</p><p><img
src="http://akosma.com/wp/wp-content/uploads/2011/05/immedia-logo.png" alt="Immedia logo" border="0" width="170" height="51" class="alignleft size-full" /></p><p>Have you ever wanted to learn how to create a mobile app? Looked at Evernote and thought, “Hey, I can do that!” We have embarked on an exciting training initiative aimed at providing South African businesses and individuals with the skills they need to become global app creators.</p><p>Courses will be held in Cape Town, Johannesburg and Durban, and [will be provided][3] by Anice Hassim, head strategist of immedia; Kishyr Ramdial, specialist cloud and mobile app developer; and myself.</p><p>There are courses targeted at app developers, dev beginners, and executives – to ensure that you learn exactly what you need to from our programme.</p><p>Check out the complete program here: <a
href="http://www.immedia.co.za/courses/">http://www.immedia.co.za/courses/</a> and sign up sending an email to <a
href="&#109;&#x61;&#105;&#x6c;&#116;&#x6f;&#58;&#x74;&#114;&#x61;i&#110;&#x69;&#110;&#x67;&#64;&#x69;&#109;&#x6d;&#101;&#x64;&#105;&#x61;.&#99;&#x6f;&#46;&#x7a;&#97;">&#x74;&#114;&#x61;i&#110;&#x69;&#110;&#x67;&#64;&#x69;&#109;&#x6d;&#101;&#x64;&#105;&#x61;.&#99;&#x6f;&#46;&#x7a;&#97;</a>; hurry up!</p><p>[3]:http://www.immedia.co.za/courses/trainers.html<strong>Similar Posts:</strong></p><ul
class="similar-posts"><li><a
href="http://akosma.com/2011/09/30/mobile-application-training-in-south-africa/" rel="bookmark" title="September 30, 2011">Mobile Application Training in South Africa</a></li><li><a
href="http://akosma.com/2011/05/31/immedia-the-leader-mobile-solutions-provider-in-south-africa/" rel="bookmark" title="May 31, 2011">immedia: the leader mobile solutions provider in South Africa</a></li><li><a
href="http://akosma.com/2011/12/29/trainings-2012-advanced-ios-mobile-web-apps-and-node-js/" rel="bookmark" title="December 29, 2011">Trainings 2012: Advanced iOS, Mobile Web Apps and Node.js</a></li><li><a
href="http://akosma.com/2011/12/23/retrospective-2011/" rel="bookmark" title="December 23, 2011">Retrospective 2011</a></li><li><a
href="http://akosma.com/2011/09/28/jquery-mobile-multiplatform-mobile-webapps-by-maximiliano-firtman/" rel="bookmark" title="September 28, 2011">&#8220;jQuery Mobile: multiplatform mobile webapps&#8221; &#8211; by Maximiliano Firtman!</a></li></ul>]]></content><link rel="replies" type="text/html" href="http://akosma.com/2011/12/22/more-mobile-application-training-in-south-africa/#comments" thr:count="0" /><link rel="replies" type="application/atom+xml" href="http://akosma.com/2011/12/22/more-mobile-application-training-in-south-africa/feed/atom/" thr:count="0" /> <thr:total>0</thr:total> <feedburner:origLink>http://akosma.com/2011/12/22/more-mobile-application-training-in-south-africa/</feedburner:origLink></entry> </feed><!-- Dynamic page generated in 1.035 seconds. --><!-- Cached page generated by WP-Super-Cache on 2012-02-06 19:25:22 -->

