#!/usr/bin/perl -w

# Copyright (C) 2007-2008
# Emmanuel Saracco <esaracco@users.labs.libre-entreprise.org>
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330,
# Boston, MA 02111-1307, USA.

#
# A NS Kit7 Hydrogen's drumkit builder (quickly done and crappy :-) )
#

use strict;
use File::Find;
use File::Basename;

my $version= "0.2.0";
my $quiet = 0;
my %instruments = ();

# help needed
if ($ARGV[0]) {&help (); exit (0)}

if (!$quiet){
print <<OUT;
<drumkit_info>
	<name>ns_kit7</name>
	<author>Emmanuel Saracco</author>
	<info>Natural Studio drum kit</info>
	<instrumentList>
OUT
}

# Prepare XML data
opendir (DIR, ".");
while (my $item = readdir (DIR))
{
  next if ($item =~ /^\./);
  unlink ($item) if (-l $item);
  find (\&process, "$item") if (-d "$item");
}
closedir (DIR);

# Write XML for instruments
&writeInstruments ();

if (!$quiet){
print <<OUT;
	</instrumentList>
</drumkit_info>
OUT
}

# process ()
# IN: -
# OUT: -
#
# Browe NS Kit7 files and build drumkit
#
sub process ()
{
  my $prefix = $File::Find::name;
  my @parts = split (/\//, $prefix);
  my $name = '';
  my $file = $parts[$#parts];
  my $letterPre = '';
  my $letterPost = '';
  my $index = 0;
  my $details = '';
  
  return if (! ($file =~ /^(.*)_([0-9a-z]*)\.wav$/));

  $index = $2;
  $prefix =~ s/^[^a-z]+//g;
  ($prefix, $details) = (split (/\//, $prefix))[0, 1];
  $details = ($details =~ /(\d+)/) ? sprintf (" %02i", $1) : '';

  while ($index =~ /^([a-z])/)
  {
    $letterPre = $1;
    $index =~ s/^.//;
  }

  while ($index =~ /([a-z])$/)
  {
    $letterPost = $1;
    $index =~ s/.$//;
  }

  for (my $i = 1; $i < $#parts; $i++) {$name .= $parts[$i] . ' '}
  $name .= $letterPre if ($letterPre);
  $name .= $letterPost if ($letterPost);

  $name =~ s/_/ /g;
  $name =~ s/\s+$//g;
  $name =~ s/^[^\d]+\d+\s*//g if ($details);
  $name = "$prefix$details [$name]";
  $name =~ s/(\w)(\w*)/\u$1\L$2\E/g;

  if (!exists ($instruments{"$name"}))
  {
    $instruments{"$name"} = {int ($index) => $File::Find::name}
  }
  else
  {
    $instruments{"$name"}{int ($index)} = $File::Find::name;
  }
}

# writeInstruments ()
# IN: -
# OUT: -
#
# Write instrument XML tag
#
sub writeInstruments ()
{
  my $i = 0;

  foreach my $k (sort { $a cmp $b } keys %instruments)
  {
    my $v = $instruments{$k};
    $i++;

if (!$quiet){
print <<OUT;
	<instrument>
		<id>$i</id>
		<name>$k</name>
		<isMuted>false</isMuted>
		<volume>1.000000</volume>
		<pan_L>1.000000</pan_L>
		<pan_R>1.000000</pan_R>
		<randomPitchFactor>0</randomPitchFactor>
		<gain>1</gain>
		<filterActive>false</filterActive>
		<filterCutoff>1</filterCutoff>
		<filterResonance>0</filterResonance>
		<Attack>0</Attack>
		<Decay>0</Decay>
		<Sustain>1</Sustain>
		<Release>1000</Release>
		<exclude />
OUT
}

#    my $max_i = 0;
#    foreach my $index (keys %$v) {$max_i = $index if ($index > $max_i)}
#    my $file = $v->{$max_i};
#    $file =~ s/^[\.\/]+//g;
#    my $filename = basename ($file);
#
#    symlink ($file, $filename);

   my $count = scalar (keys (%$v));
   my $rat = 1.0 / $count;
   my $last_max = 0;

    my $j = 0.0;
    foreach my $index (sort {$a <=> $b} keys (%$v))
    {
      my $file = $v->{$index};    
      my $filename = basename ($file);
      my $min = sprintf ("%0.2f", $j * $rat);
      my $new_min = ($j && $min < $last_max) ? $last_max : 0;
      my $max = sprintf("%0.2f", $min + $rat);
      $last_max = $max;
      $min = $new_min if ($new_min);

      symlink ($file, $filename);

      $j++;
      $max = 1.0 if ($j == $count);

if (!$quiet){
print <<OUT;
		<layer>
			<filename>$filename</filename>
			<min>$min</min>
			<max>$max</max>
			<gain>1</gain>
			<pitch>0</pitch>
		</layer>
OUT
}
   }
if (!$quiet){   
print <<OUT;
	</instrument>
OUT
}
  }
}

# help ()
# IN: -
# OUT: -
#
# Display help
#
sub help ()
{
  print <<OUT;

Version: $version

Usage: ./buildNSKit7.pl > drumkit.xml
A NS Kit7 Hydrogen's drumkit builder
Report bugs to Emmanuel Saracco <esaracco\@free.fr>

		*HOWTO*

!First you will need to rebuidl Hydrogen after updated MX_LAYERS value to 70!

1/ Create a directory "~/.hydrogen/data/ns_kit7/":

	\$ mkdir -p ~/.hydrogen/data/ns_kit7

2/ Copy all NS Kit7 CDROM data on your disk under this directory (main 
   directories should be instruments names):

	\$ cd ~/.hydrogen/data/ns_kit7/
	\$ rsync -av /dev/cdrom/ns_kit7/samples/ ./
	\$ ls -l
	dr-xr-xr-x 11 grinch grinch 4,0K 2007-04-27 20:31 quinto
	dr-xr-xr-x 12 grinch grinch 4,0K 2007-04-27 20:31 requinto
	dr-xr-xr-x 11 grinch grinch 4,0K 2007-04-27 20:31 tumba
	dr-xr-xr-x 11 grinch grinch 4,0K 2007-04-27 20:30 tumbadora
	dr-xr-xr-x  4 grinch grinch 4,0K 2007-04-27 20:21 percussion
	dr-xr-xr-x 11 grinch grinch 4,0K 2005-05-25 11:00 cymbals
	dr-xr-xr-x  4 grinch grinch 4,0K 2005-05-25 11:00 hihats
	drwxr-xr-x  7 grinch grinch 4,0K 2005-05-25 11:00 kicks
	drwxr-xr-x 11 grinch grinch 4,0K 2005-05-25 11:00 snares
	dr-xr-xr-x 18 grinch grinch 4,0K 2005-05-25 11:00 toms

3/ Copy this script on this location:

	\$ cp buildNSKit7.pl ~/.hydrogen/data/ns_kit7/

4/ Execute the script, with redirection to "drumkit.xml". Example:

	\$ cd ~/.hydrogen/data/ns_kit7/
	\$ ./buildNSKit7.pl > drumkit.xml

OUT
}
