<html><head><meta name="color-scheme" content="light dark"></head><body><pre style="word-wrap: break-word; white-space: pre-wrap;">#!/usr/bin/perl

    # programming by Jochen Puchalla (c) 2007-2010
    # mail at puchalla dash online dot de
    # License: GPL V2

$steigdist=5; # minimum distance for climbing percentage calculation

use GD::Simple;
use File::Copy;

foreach $file (@ARGV)
{
	if (! open(INPUT,"&lt;$file") )
	{
		print STDERR "Can't open input file $file\n";
		next;
	}

	print STDOUT "$file:";

	$filecore=$file;
	$filecore =~ s/.gpx$//g;

	if ($file eq $filecore)
	{
		print STDERR "$file is not a gpx file\n";
		next;
	}

	# open output file:
	$outfile="$filecore-gpx3d.png";
	if (! open(OUTPUT,"&gt;$filecore-gpx3d.png") ) { print STDERR "Can't open output file $filecore-gpx3d.png\n"; $bad++; next; }

	$pi=3.141592;
	$yzoom=-1; # flip
	$zzoom=0.3; # length of height
	$zoom=6000; # picture scale
	$picmax=8000; # max. picture size in pixels

	# set values to 0 for every new file:
 	$n=-1;
	$count=0;
	$maxcount=0;
	$h_max=10;
	$maxnorth=180;
	$maxsouth=-180;
	$maxwest=-360;
	$maxeast=360;
	$sum_h=0;
	$sum_t=0;
	$kms=0;

	$number=1;
	while ($line=&lt;INPUT&gt;)
	{
 		if ($line =~ /&lt;trk&gt;/) {print " found track "; $n=-1;} # start processing
 		if ($line =~ /&lt;rte&gt;/) {print " found route "; $n=-1;} # start processing
		if ($line =~ /pt\ lat\=/)
		{
			$n++; # next point
			@values = split(/\"/, $line);
			$lat[$n]=$values[1];
			$lon[$n]=$values[3];
			if ($lat[$n] &gt; $maxsouth) {$maxsouth = $lat[$n];}
			if ($lat[$n] &lt; $maxnorth) {$maxnorth = $lat[$n];}
			if ($lon[$n] &lt; $maxeast) {$maxeast = $lon[$n];}
			if ($lon[$n] &gt; $maxwest) {$maxwest = $lon[$n];}
# 			printf STDOUT "%5.2f  %5.2f  %5.2f  %5.2f  %5.2f $n \n" , $values[1], $values[2], $values[3], $values[4], $values[5];
			$line=&lt;INPUT&gt;;
			$line =~ s/e//g;
			$line =~ s/l//g;
			$line =~ s/&lt;//g;
			$line =~ s/&gt;//g;
			$line =~ s/\///g;
			$line =~ s/\ //g;
			$h[$n]=$line;
			if ($n&gt;0) {$h[$n]=($h[$n]+$h[$n-1]*12)/13;} ######### HÃ–HENGLÃ„TTUNG ##########
			if ($h[$n] &gt; $h_max) {$h_max=$h[$n];}
			if ($h[$n] &gt; $h[$n-1]) {$sum_h=$sum_h+$h[$n]-$h[$n-1];}
#			printf STDOUT $line;
#  			printf STDOUT " h=" . $h[$n] . " lat=" . $lat[$n] . " lon=" . $lon[$n];

			# Teilstrecke:
			$deltas[$n] = 1000 * sqrt( (($lat[$n]-$lat[$n-1])*$pi*6371/180) * (($lat[$n]-$lat[$n-1])*$pi*6371/180) + (6371*cos($pi/180*$lat[$n])*$pi*($lon[$n]-$lon[$n-1])/180) * (6371*cos($pi/180*$lat[$n])*$pi*($lon[$n]-$lon[$n-1])/180) );
# 			print " $deltas[$n] $n ";
		}
		if ($line =~ /&lt;time&gt;/)	# get date info from data
		{
			$zeit=$line;
			$zeit =~ s/t//g;
			$zeit =~ s/i//g;
			$zeit =~ s/m//g;
			$zeit =~ s/e//g;
			$zeit =~ s/Z//g;
			$zeit =~ s/&lt;//g;
			$zeit =~ s/&gt;//g;
			$zeit =~ s/\///g;
			$zeit =~ s/\ //g;
			$zeit2 = $zeit; # Kopie fÃ¼r Uhrzeit
			$zeit =~ s/T.*//g;
			$zeit =~ s/[\n\r]$//g; # remove newline at end of string
			@values = split(/-/, $zeit);
 			$date="$values[2].$values[1].$values[0]";
 			$filedate="$values[0]$values[1]$values[2]";
# 			print STDOUT $filedate;

			# Uhrzeit:
			$zeit2 =~ s/^.*T//g;
			$zeit2 =~ s/[\n\r]$//g; # remove newline at end of string
			if ( $n &lt; 2 ) {$t_start = $zeit2 ;}
			$t_ziel = $zeit2 ;
			@values = split(/\:/, $line);
			$seconds[$n]=$values[0]*3600+$values[1]*60+$values[2];

# 			$time[$n]=$seconds[$n]-$seconds[0]; if ($time[$n]&lt;0){$n=-1; $h_max=0; $h_min=8848;} # start all over
			# Zeitdiff:
			$deltat[$n] = $seconds[$n] - $seconds[$n-1];
			# Geschw.(n):
			if ($n&gt;0)
			{
				$kmh[$n] = 3.6 * $deltas[$n] / $deltat[$n];
				# summiere nur Daten mit mehr als 4 km/h
				if ( $kmh[$n] &gt; 4 )
				{
					# Nettozeit:
					$sum_t = $sum_t + $deltat[$n];
					$kms = $kms + $deltas[$n]/1000;
				}
			}
# 					print " $kms $n\n";
		}
		if ($line =~ /\&lt;\/trk\&gt;/) {last;}
		if ($line =~ /\&lt;\/rte\&gt;/) {last;}
	}

	$maxcount=$n;
# 	$h_finish=int($h[$n-1]);

# 	$minsteig=0;
# 	$maxsteig=0;
	$h[0]=$h[1];
	$s[0]=$s[1];
	$olds=$s[1];
	$oldh=$h[1];

# 	printf STDOUT "h_max=%5.3f \n",$h_max ;
 	$h[1]=int($h[1]);
 	$h_max=int($h_max);

########################### print with libgd here:

	$midlat=($maxsouth+$maxnorth)/2;
	$midlon=($maxeast+$maxwest)/2;

	$mtrlon=$maxsouth-$maxnorth;
	$mtrlat=$maxwest-$maxeast;

#  	print " midlat=" . $midlat . "\n";
#  	print " midlon=" . $midlon . "\n";
#  	print " maxeast=" . $maxeast . "\n";
#  	print " maxwest=" . $maxwest . "\n";
#  	print " maxnorth=" . $maxnorth . "\n";
#  	print " maxsouth=" . $maxsouth . "\n";

	# Picture Sizes:
	$xres=$mtrlat*$zoom*1.02;
	while ($xres&gt;$picmax) {$zoom=$zoom/2; $xres=$mtrlat*$zoom*1.02;}
	$xoff=$xres/2-$midlon*$zoom;
	$yres=($mtrlon*$zoom+$h_max*$zzoom)*1.02+20; # +20 for summary on top
	while ($yres&gt;$picmax) {$zoom=$zoom/2; $yres=($mtrlon*$zoom+$h_max*$zzoom)*1.02;}
	$yoff=$yres/2-$midlat*$yzoom*$zoom+$h_max*$zzoom*0.5+5;

# 	print $xoff . "\n";
# 	print $yoff . "\n";

	$xres=$xres+90; # fÃ¼r Legende rechts

	# create a new image
	$img = GD::Simple-&gt;new($xres,$yres);
	$img-&gt;bgcolor('white');
	$img-&gt;fgcolor('blue');

	# allocate some colors
	$col1= $img-&gt;colorAllocate(0,16,48); #&lt;-11
	$col2= $img-&gt;colorAllocate(0,8,128); #-10
	$col3= $img-&gt;colorAllocate(0,0,255); #-8
	$col4= $img-&gt;colorAllocate(0,128,255); #-6
	$col5= $img-&gt;colorAllocate(0,192,224); #-4
	$col6= $img-&gt;colorAllocate(48,224,224); #-2

	$col7= $img-&gt;colorAllocate(224,224,224); #0

	$col8= $img-&gt;colorAllocate(224,224,48); #+2 gelb
	$col9= $img-&gt;colorAllocate(224,192,0); #+4 orange
	$col10= $img-&gt;colorAllocate(255,128,0); #+6
	$col11= $img-&gt;colorAllocate(255,0,0); #+8 rot
	$col12= $img-&gt;colorAllocate(128,8,0); #+10
	$col13= $img-&gt;colorAllocate(48,16,0); #&gt;+11

	$count=1;
# 	$minsteig=0;
# 	$maxsteig=0;
	$h[0]=$h[1];
	$s[0]=$s[1];
	$olds=$s[1];
	$oldh=$h[1];
	#PRINT PROFILE:
	while ($count &lt; $maxcount-1)
	{
		$count++;
 		if($deltas[$count] &lt; $steigdist ){next;}
		$steig[$count] = ($h[$count]-$h[$count-1]) / $deltas[$count] *100 ; #Steigung
# 		if($steig[$count] &lt; $minsteig){$minsteig=$steig[$count]} #maximales GefÃ¤lle
# 		if($steig[$count] &gt; $maxsteig){$maxsteig=$steig[$count]} #maximale Steigung
		$img-&gt;fgcolor($col1);$img-&gt;bgcolor($col1);
		if ($steig[$count]&gt;-11){$img-&gt;fgcolor($col2);$img-&gt;bgcolor($col2);}
		if ($steig[$count]&gt;-9){$img-&gt;fgcolor($col3);$img-&gt;bgcolor($col3);}
		if ($steig[$count]&gt;-7){$img-&gt;fgcolor($col4);$img-&gt;bgcolor($col4);}
		if ($steig[$count]&gt;-5){$img-&gt;fgcolor($col5);$img-&gt;bgcolor($col5);}
		if ($steig[$count]&gt;-3){$img-&gt;fgcolor($col6);$img-&gt;bgcolor($col6);}
		if ($steig[$count]&gt;-1){$img-&gt;fgcolor($col7);$img-&gt;bgcolor($col7);}
		if ($steig[$count]&gt;1){$img-&gt;fgcolor($col8);$img-&gt;bgcolor($col8);}
		if ($steig[$count]&gt;3){$img-&gt;fgcolor($col9);$img-&gt;bgcolor($col9);}
		if ($steig[$count]&gt;5){$img-&gt;fgcolor($col10);$img-&gt;bgcolor($col10);}
		if ($steig[$count]&gt;7){$img-&gt;fgcolor($col11);$img-&gt;bgcolor($col11);}
		if ($steig[$count]&gt;9){$img-&gt;fgcolor($col12);$img-&gt;bgcolor($col12);}
		if ($steig[$count]&gt;11){$img-&gt;fgcolor($col13);$img-&gt;bgcolor($col13);}

		my $poly = new GD::Polygon;
		$poly-&gt;addPt($xoff+($lon[$count]*$zoom),$yoff+($lat[$count]*$yzoom*$zoom));
		$poly-&gt;addPt($xoff+($lon[$count]*$zoom),$yoff+($lat[$count]*$yzoom*$zoom)-$h[$count]*$zzoom);
		$poly-&gt;addPt($xoff+($lon[$count-1]*$zoom),$yoff+($lat[$count-1]*$yzoom*$zoom)-$h[$count-1]*$zzoom);
		$poly-&gt;addPt($xoff+($lon[$count-1]*$zoom),$yoff+($lat[$count-1]*$yzoom*$zoom));
		$img-&gt;penSize(1,1);
		$img-&gt;polygon($poly);

# 		print $xoff+($lon[$count]*$zoom) . "\n" ;
# 		print $yoff+($lat[$count]*$yzoom*$zoom) . "\n\n";
	}

	#LEGENDE:
    $img-&gt;angle(0);
	my $poly2 = new GD::Polygon;
	$img-&gt;fgcolor($col1);$img-&gt;bgcolor($col1);
	$poly2-&gt;addPt($xres-20,0);
	$poly2-&gt;addPt($xres,0);
	$poly2-&gt;addPt($xres,20);
	$poly2-&gt;addPt($xres-20,20);
	$img-&gt;polygon($poly2);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-60,17 );
	$img-&gt;string('&lt; -11%');

	my $poly3 = new GD::Polygon;
	$img-&gt;fgcolor($col2);$img-&gt;bgcolor($col2);
	$poly3-&gt;addPt($xres-20,20);
	$poly3-&gt;addPt($xres,20);
	$poly3-&gt;addPt($xres,40);
	$poly3-&gt;addPt($xres-20,40);
	$img-&gt;polygon($poly3);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-84,37 );
	$img-&gt;string('-11% - -9%');

	my $poly4 = new GD::Polygon;
	$img-&gt;fgcolor($col3);$img-&gt;bgcolor($col3);
	$poly4-&gt;addPt($xres-20,40);
	$poly4-&gt;addPt($xres,40);
	$poly4-&gt;addPt($xres,60);
	$poly4-&gt;addPt($xres-20,60);
	$img-&gt;polygon($poly4);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-78,57 );
	$img-&gt;string('-9% - -7%');

	my $poly5 = new GD::Polygon;
	$img-&gt;fgcolor($col4);$img-&gt;bgcolor($col4);
	$poly5-&gt;addPt($xres-20,60);
	$poly5-&gt;addPt($xres,60);
	$poly5-&gt;addPt($xres,80);
	$poly5-&gt;addPt($xres-20,80);
	$img-&gt;polygon($poly5);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-78,77 );
	$img-&gt;string('-7% - -5%');

	my $poly6 = new GD::Polygon;
	$img-&gt;fgcolor($col5);$img-&gt;bgcolor($col5);
	$poly6-&gt;addPt($xres-20,80);
	$poly6-&gt;addPt($xres,80);
	$poly6-&gt;addPt($xres,100);
	$poly6-&gt;addPt($xres-20,100);
	$img-&gt;polygon($poly6);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-78,97 );
	$img-&gt;string('-5% - -3%');

	my $poly7 = new GD::Polygon;
	$img-&gt;fgcolor($col6);$img-&gt;bgcolor($col6);
	$poly7-&gt;addPt($xres-20,100);
	$poly7-&gt;addPt($xres,100);
	$poly7-&gt;addPt($xres,120);
	$poly7-&gt;addPt($xres-20,120);
	$img-&gt;polygon($poly7);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-78,117 );
	$img-&gt;string('-3% - -1%');

	my $poly8 = new GD::Polygon;
	$img-&gt;fgcolor($col7);$img-&gt;bgcolor($col7);
	$poly8-&gt;addPt($xres-20,120);
	$poly8-&gt;addPt($xres,120);
	$poly8-&gt;addPt($xres,140);
	$poly8-&gt;addPt($xres-20,140);
	$img-&gt;polygon($poly8);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-78,137 );
	$img-&gt;string('-1% - +1%');

	my $poly9 = new GD::Polygon;
	$img-&gt;fgcolor($col8);$img-&gt;bgcolor($col8);
	$poly9-&gt;addPt($xres-20,140);
	$poly9-&gt;addPt($xres,140);
	$poly9-&gt;addPt($xres,160);
	$poly9-&gt;addPt($xres-20,160);
	$img-&gt;polygon($poly9);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-78,157 );
	$img-&gt;string('+1% - +3%');

	my $poly10 = new GD::Polygon;
	$img-&gt;fgcolor($col9);$img-&gt;bgcolor($col9);
	$poly10-&gt;addPt($xres-20,160);
	$poly10-&gt;addPt($xres,160);
	$poly10-&gt;addPt($xres,180);
	$poly10-&gt;addPt($xres-20,180);
	$img-&gt;polygon($poly10);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-78,177 );
	$img-&gt;string('+3% - +5%');

	my $poly11 = new GD::Polygon;
	$img-&gt;fgcolor($col10);$img-&gt;bgcolor($col10);
	$poly11-&gt;addPt($xres-20,180);
	$poly11-&gt;addPt($xres,180);
	$poly11-&gt;addPt($xres,200);
	$poly11-&gt;addPt($xres-20,200);
	$img-&gt;polygon($poly11);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-78,197 );
	$img-&gt;string('+5% - +7%');

	my $poly12 = new GD::Polygon;
	$img-&gt;fgcolor($col11);$img-&gt;bgcolor($col11);
	$poly12-&gt;addPt($xres-20,200);
	$poly12-&gt;addPt($xres,200);
	$poly12-&gt;addPt($xres,220);
	$poly12-&gt;addPt($xres-20,220);
	$img-&gt;polygon($poly12);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-78,217 );
	$img-&gt;string('+7% - +9%');

	my $poly13 = new GD::Polygon;
	$img-&gt;fgcolor($col12);$img-&gt;bgcolor($col12);
	$poly13-&gt;addPt($xres-20,220);
	$poly13-&gt;addPt($xres,220);
	$poly13-&gt;addPt($xres,240);
	$poly13-&gt;addPt($xres-20,240);
	$img-&gt;polygon($poly13);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-84,237 );
	$img-&gt;string('+9% - +11%');

	my $poly14 = new GD::Polygon;
	$img-&gt;fgcolor($col13);$img-&gt;bgcolor($col13);
	$poly14-&gt;addPt($xres-20,240);
	$poly14-&gt;addPt($xres,240);
	$poly14-&gt;addPt($xres,260);
	$poly14-&gt;addPt($xres-20,260);
	$img-&gt;polygon($poly14);
	$img-&gt;fgcolor('black');
	$img-&gt;moveTo( $xres-60,257 );
	$img-&gt;string('&gt; +11%');

	# SUMMARY
	$img-&gt;moveTo( $xres/2-140,17 );
	$sum_h = sprintf ("%.0f", $sum_h);
	$kms = sprintf ("%.0f", $kms);
	$geschw = sprintf ("%.1f", $kms/$sum_t*3600);
	$img-&gt;string($date . " - " . $kms . " km" . " - " . $sum_h . " Hm" . " - " . $geschw . " km/h");

	print OUTPUT $img-&gt;png;
	close OUTPUT;
	close GOUTPUT;
	close INPUT;

	$newfile="${filedate}_3D.png";
	if (-e $newfile) { $newfile="${filedate}a_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}b_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}c_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}d_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}e_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}f_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}g_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}h_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}i_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}j_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}k_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}l_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}m_3D.png"; }
	if (-e $newfile) { $newfile="${filedate}n_3D.png"; }
	move($outfile,$newfile);

	if (-z "$newfile"){remove("$newfile")} else {print " writing $newfile\n"};

}
exit(0);
</pre></body></html>