back

i2gp.pl

This bit of code was originally just going to make psuedo half-tone images (which it will do with the correct paramters), but I got a bit caught-up with what I could do and it grew a little bit more. Essentially what the code does is iterate through the x-pixels and draw a vertical line that corrosponds to the brightness of the pixel. To stop it becoming a mess it only moves trough the y-pixel at a rate that the user specifies as a parameter. The user can also add a scaling factor to the line height to enhance how the waveform looks. Here's a quick example couple of images below.

As with most things, experimentation is the key.

Source image


perl i2gp.pl source.jpg 160 4 1 64 1 > output.jpg
max-line-height = 160
scaling-factor = 4
out-in-colour = 1
alpha-value = 64
alias-flag = 1


perl i2gp.pl source.jpg 100 1 0 32 1 > output.jpg
max-line-height = 100
scaling-factor = 1
out-in-colour = 0
alpha-value = 32
alias-flag = 1


perl i2gp.pl source.jpg 100 6 1 100 0 > output.jpg
max-line-height = 100
scaling-factor = 6
out-in-colour = 1
alpha-value = 100
alias-flag = 0


perl i2gp.pl source.jpg 16 40 1 96 1 > output.jpg
max-line-height =16 
scaling-factor = 40
out-in-colour = 1
alpha-value = 96
alias-flag = 1


perl i2gp.pl source.jpg 200 2 1 64 0 > output.jpg
max-line-height = 200
scaling-factor = 2
out-in-colour = 1
alpha-value = 64
alias-flag = 0


Click for 100% versions.

usage: perl i2gp.pl inputimage max-line-height scaling-factor output-in-colour alpha-value alias-flag > output.jpg

	inputimage = the graphic file to import

	max-line-height = maximum size the line can be, in pixels

	scaling-factor = applies to max-line-height, in decimal, must be >0

	out-in-colour = use the rgb values from the image rather than default to white, 1 for colour, 0 for white

	alpha-value = set the value of the alpha channel, from 0 (opaque) to 127 (transparent)

	alias-flag = flag to use a alpha-value * 1.5 to reduce opacity and draw a line either side with that value

#!/usr/bin/perl

#	i2gp.pl	-	Iterate through file and for each pixel draw a vertical line who's height is based upon the greyscale average of the rgb value
#				
#	(c) d.shaw february 2015.
#
#	abstract - 	start at the location x,y where y=max-line-height/2
#				repeat for values of x for the width of the image
#					take the rgb value and get the greyscale average ((r+g+b)/3) then scale it according to the max-line-height
#					draw a line from (x,y-(scaled grey value/2)) to (x,y+(scaled grey value/2))
#				increment y=y+max-line-height and repeat along x
#
#	note -	Thankfully the GD module doesn't care about trying to draw outside of the canvas.  This means we can abuse scaling values without
#			worrying over crashes.  Plus, we can them make cool things with the alpha transparency!
#				
use GD;

### setup a sub-routine for min() and max() becuse perl doesn't come with them

sub min ($$) { $_[$_[0] > $_[1]] }
sub max ($$) { $_[$_[0] < $_[1]] }


### setup the variables

$imagefilename = $ARGV[0];
$max_line_height = $ARGV[1];
$scaling_factor = $ARGV[2];
$out_in_colour = $ARGV[3];
$alpha = $ARGV[4];
$alias_flag = $ARGV[5];

$half_alpha = min ( ( $alpha * 1.5 ), 127);

### sanity check the inputs

if ( $max_line_height < 1 ) { $max_line_height = 1; }
if ( $scaling_factor == 0 ) { $scaling_factor = 1; }
if ( $alpha > 127 ) { $alpha = 127; }


### read in the image source file and get the paramaters

$imagedata = GD::Image->new($imagefilename);
($width , $height) = $imagedata->getBounds();


### setup the output image and colours to be used

GD::Image->trueColor(1);
#$out_im = new GD::Image( $out_width , $out_height );

$out_im = GD::Image->newTrueColor($width,$height);

$black = $out_im->colorAllocate(0,0,0);

$out_im->rectangle(0,0,$width,$height,$black);

### do the loop that does the above.

$lowest_y = $max_line_height / 2;
$highest_y = $height - ($max_line_height/2);

for ( $y = $lowest_y ; $y < $highest_y; $y = $y + $max_line_height ) {
	
	for ( $x = 0; $x < $width ; $x++ ) {
		( $r ,$g , $b ) = $imagedata->rgb( $imagedata->getPixel( $x , $y ) );
		
		$greycolour = int (($r + $g + $b) / 3);
		
		$line_height = ( $greycolour % $max_line_height );
		$line_height = ( $line_height  /2 ) * $scaling_factor ;
		$line_height = int ( $line_height );
		
		
		$y1 = $y - $line_height;
		$y2 = $y + $line_height;

		#if ( $debug == 1 ) { print "greycolour = $greycolour : x = $x : y = $y : line_height = $line_height : y1 = $y1 : y2 = $y2\n"; }
		
		if ( $out_in_colour == 1 ) {
				if ( $alias_flag == 1 ) { $half_colour = $out_im->colorAllocateAlpha( $r, $g, $b, $half_alpha ); }
				$colour = $out_im->colorAllocateAlpha( $r, $g, $b, $alpha );
				}
		else {
				if ( $alias_flag == 1 ) { $half_colour = $out_im->colorAllocateAlpha( $r, $g, $b, $half_alpha ); }
				$colour = $out_im->colorAllocateAlpha( 255, 255, 255, $alpha );
				}
				
		if ( $alias_flag == 1 ) { 
			$out_im->line( $x-1, $y1, $x-1, $y2, $half_colour);
			$out_im->line( $x+1, $y1, $x+1, $y2, $half_colour); 
			}

		$out_im->line( $x, $y1, $x, $y2, $colour);
		

	}
}

binmode STDOUT;
print $out_im->jpeg(100);			#	Output 100 quality jpeg to STDOUT (use redirection to get into a file)

exit (0);

All this code is © 2006 - 2015, except for the noted pieces which are © to their authors as noted. Feel free to use anything you find here, I'm not that precious about it. Take it, improve it, make lots of cash with it, it's a gift.

back