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

<channel>
	<title>Media &#8211; Johnny Morano&#039;s Tech Articles</title>
	<atom:link href="https://jmorano.moretrix.com/tag/media/feed/" rel="self" type="application/rss+xml" />
	<link>https://jmorano.moretrix.com</link>
	<description>Ramblings of an old-fashioned space cowboy</description>
	<lastBuildDate>Wed, 20 Apr 2011 13:34:07 +0000</lastBuildDate>
	<language>en-US</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=6.6.2</generator>

<image>
	<url>https://jmorano.moretrix.com/wp-content/uploads/2022/04/cropped-jmorano_emblem-32x32.png</url>
	<title>Media &#8211; Johnny Morano&#039;s Tech Articles</title>
	<link>https://jmorano.moretrix.com</link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>Geotag your photos with Perl and GPX files</title>
		<link>https://jmorano.moretrix.com/2011/04/geotag-your-photos-with-perl-and-gpx-files/</link>
					<comments>https://jmorano.moretrix.com/2011/04/geotag-your-photos-with-perl-and-gpx-files/#respond</comments>
		
		<dc:creator><![CDATA[insaniac]]></dc:creator>
		<pubDate>Wed, 20 Apr 2011 13:34:07 +0000</pubDate>
				<category><![CDATA[Blog]]></category>
		<category><![CDATA[Development]]></category>
		<category><![CDATA[Media]]></category>
		<category><![CDATA[Perl]]></category>
		<category><![CDATA[Photo]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[Android]]></category>
		<category><![CDATA[Dev]]></category>
		<category><![CDATA[EXIF]]></category>
		<category><![CDATA[Geotag]]></category>
		<category><![CDATA[GPS]]></category>
		<guid isPermaLink="false">http://jmorano.moretrix.com/?p=588</guid>

					<description><![CDATA[Geotagging photos used to be a very expensive operation, since you needed special equipment, heavy antennas and especially:&#8230;]]></description>
										<content:encoded><![CDATA[<p>Geotagging photos used to be a very expensive operation, since you needed special equipment, heavy antennas and especially: a lot muscles to carry all your extra gear.</p>
<p>Nowadays, a lot of people have iPhone or like me, an Android phone. A descent Android phone contains a GPS device. A GPS device connected to a computer (or Android phone) could record your GPS positions during a certain period. Ok &#8230; that&#8217;s cool actually!<br />
Because, when you&#8217;re shooting photos, you practically always have your mobile phone with you!</p>
<p>So, all we need now is a handy tool on your Android phone, which will record or track your GPS positions during a certian period. Behold &#8216;<a href="http://code.google.com/p/open-gpstracker/">Open GPS Tracker</a>&#8216;. Open GPS Tracker is a tool which allows you to track your GPS positions and then afterwards, when you stop the program, you can export and share this information. The export is done using the GPX format, sharing is done through email.<br />
<span id="more-588"></span><br />
Of course, any GPS device (plus software) which generates GPX files, will do just fine <img src="https://s.w.org/images/core/emoji/15.0.3/72x72/1f609.png" alt="😉" class="wp-smiley" style="height: 1em; max-height: 1em;" /></p>
<p>This GPX file is nothing more than an XML file. And XML files are easy to parse in Perl using the <a href="http://search.cpan.org/~pajas/XML-LibXML-1.70/LibXML.pod">XML::LibXML</a> module.<br />
We will also need to other CPAN modules, <a href="http://search.cpan.org/~gbarr/TimeDate-1.20/lib/Date/Parse.pm">Date::Parse</a> and <a href="http://search.cpan.org/~gbarr/TimeDate-1.20/lib/Date/Parse.pm">Image::ExifTool</a>. The first one is used to parse the date strings in the GPX XML file and the date strings in the EXIF information of the photo. The second module is used to read the EXIF information into a Perl hash.</p>
<pre class="brush:perl">
use strict; use warnings;
use XML::LibXML;
use Image::ExifTool;
use Date::Parse;

use constant MAX_TIME_THRESHOLD => 10;

my ($gpx_file) = './Track201104180901.gpx';
my ($gpx_obj)  = XML::LibXML->new() ;
my $xml        = $gpx_obj->parse_file($gpx_file);
my $root       = $xml->getDocumentElement;

my $gps_db;
foreach my $pt ( $root->getElementsByTagName('trkpt') ) {
    my($lat)  = $pt->findvalue('@lat');
    my($lon)  = $pt->findvalue('@lon');
    my($alt)  = $pt->getElementsByTagName('ele')->[0]->textContent();
    my($time) = $pt->getElementsByTagName('time')->[0]->textContent();
    my $utime = str2time($time);

    $gps_db->{$utime} = {
        'time'   => $time,
        'lat'    => $lat,
        'lon'    => $lon,
        'alt'    => $alt,
    };
}
</pre>
<p>In this first part, we read in the XML file and store relevant information &#8211; like latitude, longitude and altitude &#8211; in a hash.</p>
<p>When the hash is ready, we can start scanning some photos.</p>
<pre class="brush:perl">
my @images = (qw/jmp151.jpg jmp152.jpg jmp154.jpg/);
foreach my $img (@images) {
    my $exif = Image::ExifTool->new();
    my $info = $exif->ImageInfo($img);
    if(not defined $info->{GPSLatitude} and not defined $info->{GPSLongitude}){
        next unless $info->{DateTimeOriginal};
        my $data = get_gps_fix($info->{DateTimeOriginal});
        
        next unless defined $data and keys %{$data};

        $exif->SetNewValue('GPSLatitude',  $data->{lat});
        $exif->SetNewValue('GPSLongitude', $data->{lon});
        $exif->SetNewValue('GPSAltitude',  $data->{alt});

        if( $exif->WriteInfo($img) ){
            print "Image [$img] EXIF info has been successfully updatedn";
        }
    }
}

sub get_gps_fix {
    my($time) = @_;
    $time =~ s/ /T/;
    $time =~ s/$/Z/;
    my $utime = str2time($time);

    for(my $count=0; $count < MAX_TIME_THRESHOLD; $count++) {
        my $index = $utime - $count;
        if(exists $gps_db->{"$index"}){
            return $gps_db->{"$index"}
        }
    }
}
</pre>
<p>I&#8217;m using a constant called MAX_TIME_THRESHOLD, because it may happen that at a certian timestamp, no GPS position was recorded or available. The threshold I use goes back maximum 10 seconds before giving up. Moreover, if the logging density has been set to Fine, Open GPS Tracker should record also every second a GPS position.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://jmorano.moretrix.com/2011/04/geotag-your-photos-with-perl-and-gpx-files/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Generate thumbnails with Perl and Image Magick</title>
		<link>https://jmorano.moretrix.com/2011/04/generate-thumbnails-with-perl-and-image-magick/</link>
					<comments>https://jmorano.moretrix.com/2011/04/generate-thumbnails-with-perl-and-image-magick/#respond</comments>
		
		<dc:creator><![CDATA[insaniac]]></dc:creator>
		<pubDate>Tue, 19 Apr 2011 15:05:28 +0000</pubDate>
				<category><![CDATA[Blog]]></category>
		<category><![CDATA[Development]]></category>
		<category><![CDATA[Media]]></category>
		<category><![CDATA[Perl]]></category>
		<category><![CDATA[Photo]]></category>
		<category><![CDATA[Web]]></category>
		<category><![CDATA[CPAN]]></category>
		<guid isPermaLink="false">http://jmorano.moretrix.com/?p=581</guid>

					<description><![CDATA[Putting photos on a website has always been a pain. There were always a few steps you had&#8230;]]></description>
										<content:encoded><![CDATA[<p>Putting photos on a website has always been a pain. There were always a few steps you had to do, before they could be seen on your webpage. Of course, nowadays there are services like <a href="http://www.flickr.com/">Flickr</a>, <a href="http://picasa.google.com/">Picassa</a>, <a href="http://www.panoramio.com/">Panoramio</a>, <a href="http://www.facebook.com/">Facebook</a> &#8230; but you still have to go through quite some steps before you pictures are online.</p>
<p>One thing you don&#8217;t have to do with those online services like Flickr etc. is generating smaller sizes of your photos, also called thumbnails. But if you maintain your own website, you will have to downsize them on your own.<br />
Being a programmer, I&#8217;m the happiest when I&#8217;m the laziest. So, in case of websites and photos, I don&#8217;t want to create the zillion of thumbnails that I need on my page.<br />
Zillion? Isn&#8217;t that a little bit exajurated? Well, mostly you will need more  than one thumbnail for every picture you will upload:<br />
&#8211; one thumbnail is needed for on the thumbnail page<br />
&#8211; one smaller thumbnail is needed for a small thumbnail preview bar<br />
&#8211; one even smaller thumbnail is needed for marking the photo on a <a href="http://maps.google.com/">Google Map</a><br />
&#8211; one smaller sized photo is needed for previewing it on the website<br />
&#8211; and finally the original image is also put available for download on the site</p>
<p>We&#8217;ll need at least 4 extra images for every photo. Okay, I could generate all those thumbs at home and then upload them all together, but that is wasting bandwidth and time and we know how precious they both are.<br />
<span id="more-581"></span><br />
Being a programmer in my professional life, I have the deviation to automate everything I know or do, with a Perl script. And this situation is again perfect for such a script.</p>
<p>First of all, the following code will make heavy use of the <a href="http://search.cpan.org/~jcristy/PerlMagick-6.67/Magick.pm.in">Image::Magick</a> Perl module, which can be downloaded from either <a href="http://search.cpan.org/">CPAN</a> or your distro&#8217;s repositry.</p>
<p>The several steps of manipulating the original image, were actually inspired by the following two links:<br />
&#8211; <a href="http://www.imagemagick.org/Usage/thumbnails/#glass_bubble">http://www.imagemagick.org/Usage/thumbnails/#glass_bubble</a><br />
&#8211; <a href="http://stackoverflow.com/questions/3973392/facebook-like-resizing-of-images-using-imagemagick">http://stackoverflow.com/questions/3973392/facebook-like-resizing-of-images-using-imagemagick</a></p>
<p>The second link explains how to resize and crop, the first link explains how create neat thumbnails using rounded corners, lighting effects and more. Now, both links give examples using the command line Image Magick tools. I&#8217;ve seen a lot of code which will call these command line tools instead of using the Image::Magick module. That is of course, NOT the way.</p>
<p>On with creating our thumbnails! First, the image needs to be resized:</p>
<pre class="brush:perl">
my $img = 'image.png';
my $magick = new Image::Magick;
$magick->Read($img);
my ($width, $height) = $magick->Get('width', 'height');

$magick->Resize(geometry => int($width/2).'x'.int($height/2));
$magick->Resize(geometry => '180x');
$magick->Resize(geometry => 'x180<');
   
my($nwidth, $nheight) = $magick->Get('width', 'height');
my $xpos = int(( $nwidth - 120 ) / 2) - 60;
my $ypos = int(( $nheight - 120 ) / 2) - 60;
$magick->Crop(geometry => "120x120+$xpos+$ypos", gravity => 'Center');
</pre>
<p>The above code will generate a thumbnail which are 120px by 120px big (or small), using a cropped field out of the 180px by 180px scaled image. The position of the cropped field is somewhat in the middle of the image, where usually the object of the photo can be found.</p>
<p>Next we&#8217;ll add some effects to our downsized image. We&#8217;ll do this by cloning the resized Image Magick object, that was created in the code above:</p>
<pre class="brush:perl">
my $thumb_mask = $magick->Clone();
</pre>
<p>Once the object has been cloned, we can start by adding effects to the new object:</p>
<pre class="brush:perl">
$thumb_mask->Set('alpha' => 'Off');
$thumb_mask->Colorize( fill => 'white', opacity => '100%' );

$thumb_mask->Draw( fill => 'black',
                   primitive => 'polygon',
                   points => '0,0 0,15 15,0');
$thumb_mask->Draw( fill => 'white',
                       primitive => 'circle',
                       points => '15,15 15,0');
my $new_2 = $thumb_mask->Clone();
$new_2->Flip();
$thumb_mask->Composite( compose => 'Multiply', 'image' => $new_2 );

my $new_3 = $thumb_mask->Clone();
$new_3->Flop();
$thumb_mask->Composite( compose => 'Multiply', 'image' => $new_3 );

$thumb_mask->Set('background' => 'Gray50');
$thumb_mask->Set('alpha' => 'Shape');

$thumb_mask->Raise(raise => 'True', geometry => '4x4');
</pre>
<p>By now we should have a rounded gray icon, based on the size of the thumbnail we&#8217;ve created above.</p>
<p>Next we will create some lighting and shading effects so that the thumbnail will look more like a button.</p>
<pre class="brush:perl">
my $thumb_lighting = $thumb_mask->Clone();
$thumb_lighting->Set('bordercolor' => 'None');
$thumb_lighting->Set('border'      => '1x1');
$thumb_lighting->Set('alpha'       => 'Extract');
$thumb_lighting->Blur('geometry'       => '0x10');
$thumb_lighting->Shade(geometry => '80x40');
$thumb_lighting->Set('alpha'       => 'On');
$thumb_lighting->Set('background'  => 'Gray50');
$thumb_lighting->Set('alpha'       => 'Background');
$thumb_lighting->AutoLevel(channel => 'alpha');
$thumb_lighting->[-1]->Function(function => 'polynomial', parameters => [3.5, -5.05, 2.05, 0.3]);

my $new_4 = $thumb_lighting->Clone();
$new_4->Set(alpha => 'Extract');
$new_4->Blur(geometry => '0x2');

$thumb_lighting->Composite(compose => 'Multiply', image => $new_4);
$thumb_lighting->Chop(geometry => '1x1');
</pre>
<p>Finally, all that rests is putting all the images togehter and saving the file to disk:</p>
<pre class="brush:perl">
$magick->Set('alpha' => 'On');
$magick->Composite(compose => 'HardLight', image => $thumb_lighting);
$magick->Set('alpha' => 'Copy');
$magick->Composite(compose => 'CopyOpacity', image => $thumb_mask);
$magick->Write('thumbnail.png');
</pre>
<p>Important to know is, since creating rounded corner will add some transparency to the original image, the newly created thumbnail must be save as either a GIF or PNG image, while those are the only two image formats which support transparency in images.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://jmorano.moretrix.com/2011/04/generate-thumbnails-with-perl-and-image-magick/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
	</channel>
</rss>
