<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:sy="http://purl.org/rss/1.0/modules/syndication/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0">

<channel>
	<title>Mea Cup O' Jo</title>
	
	<link>http://dev.bostone.us</link>
	<description>Jump Right Ahead In My Web</description>
	<lastBuildDate>Mon, 12 Dec 2011 18:30:30 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.8.4</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/MeaCupOJo" /><feedburner:info uri="meacupojo" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><item>
		<title>View core Android Java sources in Eclipse (final solution)</title>
		<link>http://feedproxy.google.com/~r/MeaCupOJo/~3/rXtE2PY7fQA/</link>
		<comments>http://dev.bostone.us/2011/12/13/android-core-sources-eclips/#comments</comments>
		<pubDate>Mon, 12 Dec 2011 18:26:55 +0000</pubDate>
		<dc:creator>bo</dc:creator>
				<category><![CDATA[Android]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://dev.bostone.us/?p=399</guid>
		<description />
			<content:encoded><![CDATA[<p>I don&#8217;t know why this is not really showing in Google search results but if you want to step through the core Android Java code in your Eclipse project, finally there&#8217;s a legit and very convenient solution that is a part of <a href="http://code.google.com/p/adt-addons/">ADT-Addons</a> project. Steps are pretty self-explanatory but just in case,  here&#8217;s what you need to do:</p>
<ol>
<li>In your Eclipse click Help-&gt;Install New Software</li>
<li>Click &#8220;Add&#8221; button and put this URL into resulting Pop-up (name it whatever you want): <a href="http://adt-addons.googlecode.com/svn/trunk/source/com.android.ide.eclipse.source.update/">http://adt-addons.googlecode.com/svn/trunk/source/com.android.ide.eclipse.source.update/</a></li>
<li>Click &#8220;OK&#8221; and mark &#8220;Android Sources&#8221; checkbox</li>
<li>Click &#8220;Next&#8221; and any &#8220;OK&#8221;, &#8220;Agree&#8221;, &#8220;Next&#8221; or &#8220;Finish&#8221; buttons afterwards</li>
<li>Restart Eclipse after the installation and now you can step right into Android code from your debugger and see the source code for Android Java files right in the Eclipse editor</li>
</ol>

<p><a href="http://feedads.g.doubleclick.net/~a/fUuh-8MwUjRWqvnj9uRuWBTaqiw/0/da"><img src="http://feedads.g.doubleclick.net/~a/fUuh-8MwUjRWqvnj9uRuWBTaqiw/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/fUuh-8MwUjRWqvnj9uRuWBTaqiw/1/da"><img src="http://feedads.g.doubleclick.net/~a/fUuh-8MwUjRWqvnj9uRuWBTaqiw/1/di" border="0" ismap="true"></img></a></p><img src="http://feeds.feedburner.com/~r/MeaCupOJo/~4/rXtE2PY7fQA" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://dev.bostone.us/2011/12/13/android-core-sources-eclips/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://dev.bostone.us/2011/12/13/android-core-sources-eclips/</feedburner:origLink></item>
		<item>
		<title>Free some space on your Android phone</title>
		<link>http://feedproxy.google.com/~r/MeaCupOJo/~3/ekPxzD0z5wY/</link>
		<comments>http://dev.bostone.us/2011/12/10/free-some-space-on-your-android-phone/#comments</comments>
		<pubDate>Fri, 09 Dec 2011 23:11:41 +0000</pubDate>
		<dc:creator>bo</dc:creator>
				<category><![CDATA[Android]]></category>
		<category><![CDATA[non-programming]]></category>

		<guid isPermaLink="false">http://dev.bostone.us/?p=392</guid>
		<description><![CDATA[If you have had your Android phone for a while it is very possible that just like me you are suffering from its unbelievably small and ever shrinking memory. You probably have no space to install any new apps and don&#8217;t want to give up any of ones you have. So here are few tips [...]]]></description>
			<content:encoded><![CDATA[<p>If you have had your Android phone for a while it is very possible that just like me you are suffering from its unbelievably small and ever shrinking memory. You probably have no space to install any new apps and don&#8217;t want to give up any of ones you have. So here are few tips that hopefully will help you to free few megs of the precious internal mem! As a note &#8211; this will not go into weird and difficult solutions such as cache management apps and rooting your phone, for that you can go to <a href="http://forum.xda-developers.com/filter.php?cat=Android">XDA forums</a></p>
<p><em>For the lawyers out there: use these tips at your own risk. I do and I&#8217;m yet to brick my phone or to lose any valuable information but that is not to say that you may not.</em></p>
<p><strong>General requirement</strong></p>
<p>Before doing anything described below make sure that your phone settings and information is backed up. Go to <strong><em>Phone-&gt;Settings-&gt;Privacy</em></strong> and make sure that &#8220;Back up my data&#8221; and &#8220;Automatic restore&#8221; options are checked. Otherwise you are at risk to lose valuable data on your phone permanently</p>
<p><strong>G+ &amp;Co</strong></p>
<p><a rel="attachment wp-att-393" href="http://dev.bostone.us/2011/12/10/free-some-space-on-your-android-phone/gplus/"><img class="alignright size-medium wp-image-393" title="gplus" src="http://dev.bostone.us/wp-content/uploads/2011/12/gplus-180x300.png" alt="gplus" width="180" height="300" /></a> This &#8220;new kid on the block&#8221; uses internal memory very liberally (slap, slap, slap). I found out that periodically it helps to go <strong><em>phone-&gt;settings-&gt;Applications-&gt;Manage Applications</em></strong>, locate G+ app and click on &#8220;Clear data&#8221; button. Yes, it will give you a stiff warning saying that your phone will melt and the boogie man will comeandgetcha but I found that it really has no adverse effect except I&#8217;d have to log back in.</p>
<p>Other apps in this category (save to Clear data) are Browser and Market and you may find more but be careful. <strong>All the apps I mentioned are backed by Google servers</strong>, when you delete data it is replaced by a new set. On the exclusively phone-based apps you will lose all your settings and modifications</p>
<p><strong>Get rid of unwanted apps (kind of)</strong></p>
<p>No I&#8217;m not telling you to delete that &#8220;Busty blonds&#8221; app that you not using (are you?).  As I said &#8211; if you&#8217;re like me you are not giving anything up. But there is number of unused &#8220;default&#8221; apps that come with your phone. Unfortunately you cannot delete these apps easily but if you were updating these (especially automatically) and want to regain some space do the following:</p>
<p>Locate the app in the same settings area as above. Do &#8220;Clear cache&#8221;, &#8220;Clear Data&#8221; and then click on &#8220;Uninstall updates&#8221;. As a very minimum the app will shrink to half of its size. Latest app on my NexusOne to go this way was Facebook (I&#8217;m a bit proud of it)</p>
<p><strong>Scary stuff or nuke your contacts</strong></p>
<p>I know this is a dangerous proposition but let me give you some background. When you got your new phone it was initially populated with your Google contact list. Any modifications or additions from your phone are also synchronized back to Google servers. So about 1 year and change ago it become fashionable for 3rd party apps to synchronize their contacts to your phone also. Fortunately, Android does not combine accounts internally but keeps them separate and only unites these on your screen. If you&#8217;ve been syncing and trying things like Facebook, Twitter, Linkedin and our own Droidin you probably have tons of strange contacts that make no sense and by the way steal your precious memory.</p>
<p>I also found out that even when removed or disabled from <strong><em>settings-&gt;Accounts &amp; sync</em></strong> just adding and removing and syncing leaves a lot of residue behind.</p>
<p>So gather your courage and locate the app called &#8220;Contacts Storage&#8221; and do the same &#8220;Clear data&#8221; trick. After that access your contacts and be horrified, you will see nothing there. However in a short while your missing contact information will be pooled from Google. <strong><span style="color: #ff0000;">Stiff warning:</span></strong> you will lose your call log and &#8220;Frequently called&#8221; section so don&#8217;t say I didn&#8217;t warn you. I gained about 10Mb with this trick so if you are very desperate you may consider this.</p>
<p><strong>Start anew</strong></p>
<p>This one is really dumb: say by-by to all the customization, pull out SD card and do factory reset. How? <strong><em>Phone-&gt;Settings-&gt;Privacy-&gt;Factory data reset</em></strong>. This will pretty much wipe out everything on your phone to a clean slate.</p>
<p>Then you can recall that sweet feeling you had 2 years ago when you first logged in into you brand new super-phone</p>
<p>If you have purchased any paid applications you will be able to add these back with no charge by going to Market and locating the app. Instead of &#8220;Purshase&#8221; button you will see &#8220;Install&#8221;</p>
<p>Hope this helps and Ho, ho, ho &#8211; Merry Christmas and a Happy New Year!</p>

<p><a href="http://feedads.g.doubleclick.net/~a/9XzPum5MBN_hx2lFcL50D-zvYnY/0/da"><img src="http://feedads.g.doubleclick.net/~a/9XzPum5MBN_hx2lFcL50D-zvYnY/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/9XzPum5MBN_hx2lFcL50D-zvYnY/1/da"><img src="http://feedads.g.doubleclick.net/~a/9XzPum5MBN_hx2lFcL50D-zvYnY/1/di" border="0" ismap="true"></img></a></p><img src="http://feeds.feedburner.com/~r/MeaCupOJo/~4/ekPxzD0z5wY" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://dev.bostone.us/2011/12/10/free-some-space-on-your-android-phone/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://dev.bostone.us/2011/12/10/free-some-space-on-your-android-phone/</feedburner:origLink></item>
		<item>
		<title>Android: display orientation in phones vs tablets</title>
		<link>http://feedproxy.google.com/~r/MeaCupOJo/~3/KCLBZwKZGVM/</link>
		<comments>http://dev.bostone.us/2011/06/30/android-display-orientation-in-phones-vs-tablets/#comments</comments>
		<pubDate>Thu, 30 Jun 2011 15:57:20 +0000</pubDate>
		<dc:creator>bo</dc:creator>
				<category><![CDATA[Android]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://dev.bostone.us/?p=386</guid>
		<description><![CDATA[If you have 2 layouts (portrait and landscape) and the order seems to be reversed on the tablet then switch to using getRotation instead of deprecated getOrientation. Something like this

    private void setLayout() {
        // Get display for detecting the phone orientation
    [...]]]></description>
			<content:encoded><![CDATA[<p>If you have 2 layouts (portrait and landscape) and the order seems to be reversed on the tablet then switch to using <strong>getRotation </strong>instead of deprecated <strong>getOrientation</strong>. Something like this</p>
<pre class="brush: java; title: ; notranslate">
    private void setLayout() {
        // Get display for detecting the phone orientation
        final Display display = ((WindowManager) getSystemService(
            WINDOW_SERVICE)).getDefaultDisplay();
        if (display.getRotation() == Surface.ROTATION_0 ||
            display.getRotation() == Surface.ROTATION_180) {
            setContentView(R.layout.home);
        } else {
            setContentView(R.layout.home_l);
        }
    }
</pre>
<p>P.S.<br />
Actually, ignore code above it will not work. All you really need to do is to detect what is larger &#8211; height or width and adjust layout accordingly</p>
<pre class="brush: java; title: ; notranslate">
    private void setLayout() {
        // Get display for detecting the phone orientation
        final Display display = ((WindowManager)
             getSystemService(WINDOW_SERVICE)).getDefaultDisplay();
        final boolean isTall = display.getHeight() &gt; display.getWidth();
        setContentView(isTall ? R.layout.home : R.layout.home_l);
    }
</pre>

<p><a href="http://feedads.g.doubleclick.net/~a/EzQG-es3tmMGrHxOkStjBpXOYrA/0/da"><img src="http://feedads.g.doubleclick.net/~a/EzQG-es3tmMGrHxOkStjBpXOYrA/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/EzQG-es3tmMGrHxOkStjBpXOYrA/1/da"><img src="http://feedads.g.doubleclick.net/~a/EzQG-es3tmMGrHxOkStjBpXOYrA/1/di" border="0" ismap="true"></img></a></p><img src="http://feeds.feedburner.com/~r/MeaCupOJo/~4/KCLBZwKZGVM" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://dev.bostone.us/2011/06/30/android-display-orientation-in-phones-vs-tablets/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://dev.bostone.us/2011/06/30/android-display-orientation-in-phones-vs-tablets/</feedburner:origLink></item>
		<item>
		<title>Replace black (grey) with color (colorize) in Photoshop</title>
		<link>http://feedproxy.google.com/~r/MeaCupOJo/~3/y3R8vUUGz2M/</link>
		<comments>http://dev.bostone.us/2011/06/19/replace-black-grey-with-color-in-photoshop/#comments</comments>
		<pubDate>Sat, 18 Jun 2011 23:33:22 +0000</pubDate>
		<dc:creator>bo</dc:creator>
				<category><![CDATA[Web stuff]]></category>
		<category><![CDATA[non-programming]]></category>

		<guid isPermaLink="false">http://dev.bostone.us/?p=380</guid>
		<description><![CDATA[I just spent some time making black (grey scaled) icon into a blue one and here&#8217;s by far the easiest way to do it in the Photoshop:

 Open the original image and change mode to RGB (Image-&#62;Mode-&#62;RGB)
Image-&#62;Adjustments-&#62;Hue/Saturation
Click on &#8220;Colorize&#8221; checkbox
At this point the image will still be black and white (grey)
Make sure that &#8220;preview&#8221; box [...]]]></description>
			<content:encoded><![CDATA[<p>I just spent some time making black (grey scaled) icon into a blue one and here&#8217;s by far the easiest way to do it in the Photoshop:</p>
<ul>
<li> Open the original image and change mode to RGB (Image-&gt;Mode-&gt;RGB)</li>
<li>Image-&gt;Adjustments-&gt;Hue/Saturation</li>
<li>Click on &#8220;Colorize&#8221; checkbox</li>
<li>At this point the image will still be black and white (grey)</li>
<li>Make sure that &#8220;preview&#8221; box is checked</li>
<li>Start by increasing &#8220;Lightness&#8221; you will immediately see color changing from b/w to blue</li>
<li>Play with other 2 dials (hue &amp; saturation) to get you to the desired color</li>
</ul>

<p><a href="http://feedads.g.doubleclick.net/~a/z3_TLXDO6entR_QGOrVCQWvR2mk/0/da"><img src="http://feedads.g.doubleclick.net/~a/z3_TLXDO6entR_QGOrVCQWvR2mk/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/z3_TLXDO6entR_QGOrVCQWvR2mk/1/da"><img src="http://feedads.g.doubleclick.net/~a/z3_TLXDO6entR_QGOrVCQWvR2mk/1/di" border="0" ismap="true"></img></a></p><img src="http://feeds.feedburner.com/~r/MeaCupOJo/~4/y3R8vUUGz2M" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://dev.bostone.us/2011/06/19/replace-black-grey-with-color-in-photoshop/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://dev.bostone.us/2011/06/19/replace-black-grey-with-color-in-photoshop/</feedburner:origLink></item>
		<item>
		<title>Use Yaml with Spring to load properties</title>
		<link>http://feedproxy.google.com/~r/MeaCupOJo/~3/uSGdavEM3Ts/</link>
		<comments>http://dev.bostone.us/2011/02/03/use-yaml-with-spring-to-load-properties/#comments</comments>
		<pubDate>Wed, 02 Feb 2011 22:39:50 +0000</pubDate>
		<dc:creator>bo</dc:creator>
				<category><![CDATA[Java]]></category>

		<guid isPermaLink="false">http://dev.bostone.us/?p=378</guid>
		<description><![CDATA[I was surprised to find that Spring framework doesn&#8217;t have Yaml-based PropertyPlaceholderConfigurer to load nested properties from Yaml property file. After some investigation turned out that instead of writing YamlPropertyPlaceholderConfigurer it is sufficient to write Yaml implementation of PropertiesPersister.
Here&#8217; show your applicationContext.xml (snippet) will look

    &#60;bean id=&#34;propertyConfigurer&#34; class=&#34;org.springframework.beans.factory.config.PropertyPlaceholderConfigurer&#34;&#62;
     [...]]]></description>
			<content:encoded><![CDATA[<p>I was surprised to find that Spring framework doesn&#8217;t have Yaml-based PropertyPlaceholderConfigurer to load nested properties from Yaml property file. After some investigation turned out that instead of writing YamlPropertyPlaceholderConfigurer it is sufficient to write Yaml implementation of PropertiesPersister.</p>
<p>Here&#8217; show your applicationContext.xml (snippet) will look</p>
<pre class="brush: xml; title: ; notranslate">
    &lt;bean id=&quot;propertyConfigurer&quot; class=&quot;org.springframework.beans.factory.config.PropertyPlaceholderConfigurer&quot;&gt;
        &lt;property name=&quot;locations&quot;&gt;
            &lt;value&gt;file:///C:/foo/properties.yaml&lt;/value&gt;
        &lt;/property&gt;
        &lt;property name=&quot;propertiesPersister&quot; ref=&quot;persister&quot;&gt;&lt;/property&gt;
    &lt;/bean&gt;
    &lt;bean id=&quot;persister&quot; class=&quot;com.foo.utils.YamlPropertiesPersister&quot;&gt;&lt;/bean&gt;
</pre>
<p>And here&#8217;s bare-bone PropertiesPersister implementation using SnakeYaml as parser</p>
<pre class="brush: java; title: ; notranslate">
public class YamlPropertiesPersister implements PropertiesPersister {
    @Override
    public void load(Properties props, InputStream is) throws IOException {
        load(props, new InputStreamReader(is));
    }

    /**
     * We want to traverse map representing Yaml object and each time we will find String:String value pair we want to
     * save it as Property. As we are going deeper into map we generate a compound key as path-like String
     *
     * @param props
     * @param reader
     * @throws IOException
     * @see org.springframework.util.PropertiesPersister#load(java.util.Properties, java.io.Reader)
     */
    @Override
    public void load(Properties props, Reader reader) throws IOException {
        Yaml yaml = CollectorUtils.instanceOfYaml();
        Map&lt;String, Object&gt; map = (Map&lt;String, Object&gt;) yaml.load(reader);
        // now we can populate supplied props
        assignProperties(props, map, null);
    }

    /**
     * @param props
     * @param map
     */
    public void assignProperties(Properties props, Map&lt;String, Object&gt; map, String path) {
        for (Entry&lt;String, Object&gt; entry : map.entrySet()) {
            String key = entry.getKey();
            if (StringUtils.isNotEmpty(path))
                key = path + &quot;.&quot; + key;
            Object val = entry.getValue();
            if (val instanceof String) {
                // see if we need to create a compound key
                props.put(key, val);
            } else if (val instanceof Map) {
                assignProperties(props, (Map&lt;String, Object&gt;) val, key);
            }
        }
    }

    @Override
    public void store(Properties props, OutputStream os, String header) throws IOException {
        throw new NotImplementedException(&quot;Current implementation is a read-only&quot;);
    }

    @Override
    public void store(Properties props, Writer writer, String header) throws IOException {
        throw new NotImplementedException(&quot;Current implementation is a read-only&quot;);
    }

    @Override
    public void loadFromXml(Properties props, InputStream is) throws IOException {
        throw new NotImplementedException(&quot;Use DefaultPropertiesPersister if you want to read/write XML&quot;);
    }

    @Override
    public void storeToXml(Properties props, OutputStream os, String header) throws IOException {
        throw new NotImplementedException(&quot;Use DefaultPropertiesPersister if you want to load/store to XML&quot;);
    }

    @Override
    public void storeToXml(Properties props, OutputStream os, String header, String encoding) throws IOException {
        throw new NotImplementedException(&quot;Use DefaultPropertiesPersister if you want to read/write XML&quot;);
    }
}
</pre>
<p>And as an added bonus, here&#8217;s how you create Yaml instance with SnakeYaml</p>
<pre class="brush: java; title: ; notranslate">
    public static Yaml instanceOfYaml() {
        DumperOptions options = new DumperOptions();
        options.setDefaultFlowStyle(DumperOptions.FlowStyle.BLOCK);
        options.setDefaultScalarStyle(ScalarStyle.DOUBLE_QUOTED);
        final Yaml yaml = new Yaml(new Loader(), new Dumper(options), new Resolver() {
            /**
             * @see org.yaml.snakeyaml.resolver.Resolver#addImplicitResolvers()
             */
            @Override
            protected void addImplicitResolvers() {
                addImplicitResolver(Tag.BOOL, BOOL, &quot;yYnNtTfFoO&quot;);
                // disable resolving of floats and integers
                // addImplicitResolver(Tags.FLOAT, FLOAT, &quot;-+0123456789.&quot;);
                // addImplicitResolver(Tag.INT, INT, &quot;-+0123456789&quot;);
                addImplicitResolver(Tag.MERGE, MERGE, &quot;&lt;&quot;);
                addImplicitResolver(Tag.NULL, NULL, &quot;~nN&#92;&#48;&quot;);
                addImplicitResolver(Tag.NULL, EMPTY, null);
                addImplicitResolver(Tag.TIMESTAMP, TIMESTAMP, &quot;0123456789&quot;);
                addImplicitResolver(Tag.VALUE, VALUE, &quot;=&quot;);
            }
        });
        return yaml;
    }
</pre>

<p><a href="http://feedads.g.doubleclick.net/~a/9mDIIukd6-SYK4dV_8IJJLva7L0/0/da"><img src="http://feedads.g.doubleclick.net/~a/9mDIIukd6-SYK4dV_8IJJLva7L0/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/9mDIIukd6-SYK4dV_8IJJLva7L0/1/da"><img src="http://feedads.g.doubleclick.net/~a/9mDIIukd6-SYK4dV_8IJJLva7L0/1/di" border="0" ismap="true"></img></a></p><img src="http://feeds.feedburner.com/~r/MeaCupOJo/~4/uSGdavEM3Ts" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://dev.bostone.us/2011/02/03/use-yaml-with-spring-to-load-properties/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://dev.bostone.us/2011/02/03/use-yaml-with-spring-to-load-properties/</feedburner:origLink></item>
		<item>
		<title>Python Pygments in Java with Jython</title>
		<link>http://feedproxy.google.com/~r/MeaCupOJo/~3/70dkSSr_atQ/</link>
		<comments>http://dev.bostone.us/2010/12/01/python-pygments-in-java-with-jython/#comments</comments>
		<pubDate>Tue, 30 Nov 2010 19:10:13 +0000</pubDate>
		<dc:creator>bo</dc:creator>
				<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://dev.bostone.us/?p=369</guid>
		<description><![CDATA[I was looking for the good code-highlighting package to use in my Java (GWT) project and after much research selected Pygments. It took me a while to figure out how to make all different parts work happily together so here&#8217;s a tutorial on how to do it.
Jython setup
To run Pygments you need to add Jython.jar [...]]]></description>
			<content:encoded><![CDATA[<p>I was looking for the good code-highlighting package to use in my Java (GWT) project and after much research selected <a href="http://pygments.org/">Pygments</a>. It took me a while to figure out how to make all different parts work happily together so here&#8217;s a tutorial on how to do it.</p>
<h1>Jython setup</h1>
<p>To run Pygments you need to add Jython.jar to the list of your libraries. I&#8217;m using release 2.5.1 at the time of writing. First and foremost &#8211; using barebone distribution such as found in Maven repo or in the Jython distro is not sufficient. I tried many ways to setup and the only way that worked is to</p>
<ol>
<li>Uncompress jython.jar in some temp directory</li>
<li>Add Jython/Lib directory to the top</li>
<li>Add Pygments Python files to the top</li>
<li>Jar everything back again and add resulting archive to your project. I called it jython-full.jar</li>
<li>No matter what you are using this jar has to be on your classpath</li>
</ol>
<h1>Code</h1>
<h2>Highlighter.py</h2>
<p>Create custom highlighter.py file and place it to your resources or even Java files as long as it gets placed in the top level of your classpath. In my case I&#8217;m using Eclipse/Maven so I placed this file into src/main/python and added that folder as a source folder. Here&#8217;s complete code for highlighter.py:</p>
<pre class="brush: python; title: ; notranslate">
from reporting.python import Highlighter
from pygments import highlight
from pygments.lexers import get_lexer_by_name
from pygments.formatters import HtmlFormatter

class PyHighlighter(Highlighter):
    def __init__(self, lexername):
        self.lexer = get_lexer_by_name(lexername, stripall=True)
        self.formatter = HtmlFormatter(linenos=True, cssclass=&quot;source&quot;)
    def colorize(self, code):
        return highlight(code, self.lexer, self.formatter)
</pre>
<h2>Highlighter.java</h2>
<p>Highlighter.java is interface that your Java code will be using to communicate with Pygments.</p>
<pre class="brush: java; title: ; notranslate">
package reporting.python;

public interface Highlighter {
    String colorize(String rawText);
}
</pre>
<h2>HighlighterFactory.java</h2>
<p>HighlighterFactory is Java class that creates instances of Highlighter object. It&#8217;s given here in barebone form and can be greatly optimized by converting to a singleton and cashing particular instances of Highlighter for further reuse. But it will work as given:</p>
<pre class="brush: java; title: ; notranslate">
package reporting.python;

import org.python.core.PyObject;
import org.python.core.PyString;
import org.python.util.PythonInterpreter;

public class HighlighterFactory {
    private PyObject matrix;

    public HighlighterFactory() {
        PythonInterpreter pi = new PythonInterpreter();
        pi.exec(&quot;import sys&quot;);
        // makes Jython able to find your custom Python code
        pi.exec(&quot;sys.path.append('WEB-INF/classes')&quot;);
        pi.exec(&quot;from highlighter import PyHighlighter&quot;);
        matrix = pi.get(&quot;PyHighlighter&quot;);
    }

    public Highlighter create(String type) {
        final PyObject instance = matrix.__call__(new PyString(type));
        return (Highlighter) instance.__tojava__(Highlighter.class);
    }
}</pre>
<h1>Putting it all together</h1>
<p>After creating/placing all these parts here&#8217;s code example on how to use it</p>
<pre class="brush: java; title: ; notranslate">
    public String colorize(String text, String type) {
        HighlighterFactory factory = new HighlighterFactory();
        Highlighter highlighter = factory.create(type);
        return highlighter.colorize(text);
    }
</pre>
<h1>References</h1>
<ul>
<li><a href="http://pygments.org/">Pygments</a></li>
<li><a href="http://jythonpodcast.hostjava.net/jythonbook/en/1.0/JythonAndJavaIntegration.html#using-jython-within-java-applications">Jython Book chapter 10</a></li>
</ul>
<p>Good luck and let me know if it worked for you</p>

<p><a href="http://feedads.g.doubleclick.net/~a/OAbUmuZ9rOtGDhpBIm-4Ve78GOM/0/da"><img src="http://feedads.g.doubleclick.net/~a/OAbUmuZ9rOtGDhpBIm-4Ve78GOM/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/OAbUmuZ9rOtGDhpBIm-4Ve78GOM/1/da"><img src="http://feedads.g.doubleclick.net/~a/OAbUmuZ9rOtGDhpBIm-4Ve78GOM/1/di" border="0" ismap="true"></img></a></p><img src="http://feeds.feedburner.com/~r/MeaCupOJo/~4/70dkSSr_atQ" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://dev.bostone.us/2010/12/01/python-pygments-in-java-with-jython/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		<feedburner:origLink>http://dev.bostone.us/2010/12/01/python-pygments-in-java-with-jython/</feedburner:origLink></item>
		<item>
		<title>iOS vs Android</title>
		<link>http://feedproxy.google.com/~r/MeaCupOJo/~3/SJO3PvmBEsc/</link>
		<comments>http://dev.bostone.us/2010/10/20/ios-vs-android/#comments</comments>
		<pubDate>Tue, 19 Oct 2010 20:41:56 +0000</pubDate>
		<dc:creator>bo</dc:creator>
				<category><![CDATA[Android]]></category>
		<category><![CDATA[non-programming]]></category>

		<guid isPermaLink="false">http://dev.bostone.us/?p=367</guid>
		<description><![CDATA[Blah, blah&#8230; I&#8217;m a simple guy. I keep hearing about hackers that make iPhone run Android, I&#8217;m yet to hear about Nexus One running iOS. Why? Because no self-respecting hacker would attempt such pointless exercise
]]></description>
			<content:encoded><![CDATA[<p>Blah, blah&#8230; I&#8217;m a simple guy. I keep hearing about hackers that make iPhone run Android, I&#8217;m yet to hear about Nexus One running iOS. Why? Because no self-respecting hacker would attempt such pointless exercise</p>

<p><a href="http://feedads.g.doubleclick.net/~a/-TGFSlQH95EtP597ZeAhTq5AYRw/0/da"><img src="http://feedads.g.doubleclick.net/~a/-TGFSlQH95EtP597ZeAhTq5AYRw/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/-TGFSlQH95EtP597ZeAhTq5AYRw/1/da"><img src="http://feedads.g.doubleclick.net/~a/-TGFSlQH95EtP597ZeAhTq5AYRw/1/di" border="0" ismap="true"></img></a></p><img src="http://feeds.feedburner.com/~r/MeaCupOJo/~4/SJO3PvmBEsc" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://dev.bostone.us/2010/10/20/ios-vs-android/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://dev.bostone.us/2010/10/20/ios-vs-android/</feedburner:origLink></item>
		<item>
		<title>DroidIn 2 is back!</title>
		<link>http://feedproxy.google.com/~r/MeaCupOJo/~3/EJmHs4dl1zM/</link>
		<comments>http://dev.bostone.us/2010/10/06/droidin-2-is-back/#comments</comments>
		<pubDate>Tue, 05 Oct 2010 22:10:25 +0000</pubDate>
		<dc:creator>bo</dc:creator>
				<category><![CDATA[Web stuff]]></category>

		<guid isPermaLink="false">http://dev.bostone.us/2010/10/06/droidin-2-is-back/</guid>
		<description><![CDATA[The DroidIn &#8211; first ever LinkedIn Android client is back. In version 2 it is a complete rewrite with all new features, design and implementation. If you have Android phone (or device) please give it a try.
The details
]]></description>
			<content:encoded><![CDATA[<p>The DroidIn &#8211; first ever LinkedIn Android client is back. In version 2 it is a complete rewrite with all new features, design and implementation. If you have Android phone (or device) please give it a try.</p>
<p><a href="http://droidin.net/2010/10/04/droidin-2-is-out/">The details</a></p>

<p><a href="http://feedads.g.doubleclick.net/~a/I4nNSAf00eRr_M48OaLppH5OIJU/0/da"><img src="http://feedads.g.doubleclick.net/~a/I4nNSAf00eRr_M48OaLppH5OIJU/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/I4nNSAf00eRr_M48OaLppH5OIJU/1/da"><img src="http://feedads.g.doubleclick.net/~a/I4nNSAf00eRr_M48OaLppH5OIJU/1/di" border="0" ismap="true"></img></a></p><img src="http://feeds.feedburner.com/~r/MeaCupOJo/~4/EJmHs4dl1zM" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://dev.bostone.us/2010/10/06/droidin-2-is-back/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://dev.bostone.us/2010/10/06/droidin-2-is-back/</feedburner:origLink></item>
		<item>
		<title>HireADroid adds Beyond.com</title>
		<link>http://feedproxy.google.com/~r/MeaCupOJo/~3/gWKQ87vQfR4/</link>
		<comments>http://dev.bostone.us/2010/09/19/hireadroid-adds-beyond-com/#comments</comments>
		<pubDate>Sat, 18 Sep 2010 21:24:49 +0000</pubDate>
		<dc:creator>bo</dc:creator>
				<category><![CDATA[Android]]></category>

		<guid isPermaLink="false">http://dev.bostone.us/?p=364</guid>
		<description><![CDATA[My pet project HireADroid adds Beyond.com support in its 2.4.0 release. HireADroid as Android job search application that now supports 5 major search engines. You can give it a try by searching for it on Android market or going to http://hireadroid.com. One query will give 5 sets of results in one neat package
]]></description>
			<content:encoded><![CDATA[<p>My pet project HireADroid <a href="http://hireadroid.com/2010/09/hireadroid-2-4-0-welcomes-beyond-com/">adds Beyond.com support</a> in its 2.4.0 release. HireADroid as Android job search application that now supports 5 major search engines. You can give it a try by searching for it on Android market or going to http://hireadroid.com. One query will give 5 sets of results in one neat package</p>

<p><a href="http://feedads.g.doubleclick.net/~a/niomaEwx4HGoR56K4Dr5bQ9Ty90/0/da"><img src="http://feedads.g.doubleclick.net/~a/niomaEwx4HGoR56K4Dr5bQ9Ty90/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/niomaEwx4HGoR56K4Dr5bQ9Ty90/1/da"><img src="http://feedads.g.doubleclick.net/~a/niomaEwx4HGoR56K4Dr5bQ9Ty90/1/di" border="0" ismap="true"></img></a></p><img src="http://feeds.feedburner.com/~r/MeaCupOJo/~4/gWKQ87vQfR4" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://dev.bostone.us/2010/09/19/hireadroid-adds-beyond-com/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://dev.bostone.us/2010/09/19/hireadroid-adds-beyond-com/</feedburner:origLink></item>
		<item>
		<title>Android – prevent Dialog to be cashed in the Activity</title>
		<link>http://feedproxy.google.com/~r/MeaCupOJo/~3/SjkbuDIw3-E/</link>
		<comments>http://dev.bostone.us/2010/05/11/android-prevent-dialog-to-be-cashed-in-the-activity/#comments</comments>
		<pubDate>Tue, 11 May 2010 05:13:45 +0000</pubDate>
		<dc:creator>bo</dc:creator>
				<category><![CDATA[Android]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://dev.bostone.us/?p=339</guid>
		<description><![CDATA[If you override Activity#onCreateDialog method to create a pop-up dialog something that you have to be aware is this dialog will be cashed for any subsequent calls. For most cases it is just the right behavior but what if you want to change contents of the dialog on the next call? One possible scenario &#8211; [...]]]></description>
			<content:encoded><![CDATA[<p>If you override <strong>Activity#onCreateDialog</strong> method to create a pop-up dialog something that you have to be aware is this dialog will be cashed for any subsequent calls. For most cases it is just the right behavior but what if you want to change contents of the dialog on the next call? One possible scenario &#8211; say you have few tabs that display similar content in the same pop-up but the info changes based on the active tab. Here&#8217;s one way to do it. When you set your onClick listener put this into onClick call:<br />
<code>dialog.dismiss();<br />
activity.removeDialog(DIALOG_ID);</code><br />
Here DIALOG_ID is the same ID you are using in the <strong>Activity#onCreateDialog</strong> call</p>

<p><a href="http://feedads.g.doubleclick.net/~a/aVdFNp_e9BLIKLco2h5YGbcYJdo/0/da"><img src="http://feedads.g.doubleclick.net/~a/aVdFNp_e9BLIKLco2h5YGbcYJdo/0/di" border="0" ismap="true"></img></a><br/>
<a href="http://feedads.g.doubleclick.net/~a/aVdFNp_e9BLIKLco2h5YGbcYJdo/1/da"><img src="http://feedads.g.doubleclick.net/~a/aVdFNp_e9BLIKLco2h5YGbcYJdo/1/di" border="0" ismap="true"></img></a></p><img src="http://feeds.feedburner.com/~r/MeaCupOJo/~4/SjkbuDIw3-E" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://dev.bostone.us/2010/05/11/android-prevent-dialog-to-be-cashed-in-the-activity/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://dev.bostone.us/2010/05/11/android-prevent-dialog-to-be-cashed-in-the-activity/</feedburner:origLink></item>
	</channel>
</rss>

