/***************************************************************************
 *   Copyright (C) 2004 by Predrag Viceic                                  *
 *   viceic@net2000.ch                                             *
 *                                                                         *
 *   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.             *
 ***************************************************************************/
#include "sf2manager.h"

SF2Manager::SF2Manager(QObject *parent, const char *name)
 : QObject(parent, name)
{
}


SF2Manager::~SF2Manager()
{
}

void SF2Manager::writeSF2File(QString path_and_filename ,QStringList* filenames,QValueList <beatline_data> bld){
    QString filename=QFileInfo(path_and_filename).fileName();
    QString dirpath=QFileInfo(path_and_filename).dirPath();
    
    char nb_keygroups=filenames->size();
    qHeapSort(bld);
    
    IpatchFile *file;
    IpatchSF2File *sffile;
    IpatchSF2Sample *sample;
    IpatchSF2Inst *inst;
    IpatchSF2Preset *preset;
    GError *err = NULL;
    
    /* initialize libInstPatch */
    ipatch_init ();
    IpatchSF2* sf2 = ipatch_sf2_new ();	/* ++ ref new SoundFont object */
    /*create new SoundFont instrument (++ ref) */
    inst = ipatch_sf2_inst_new ();
    /* set instrument name */
    ipatch_sf2_inst_set_name(inst, filename.ascii());
    /* append instrument to SoundFont (ensure that its name is unique) */
    ipatch_container_add_unique (IPATCH_CONTAINER (sf2),IPATCH_ITEM (inst));
    /* create new SoundFont preset (++ ref) */
    preset = ipatch_sf2_preset_new ();
    /* set preset name */
    ipatch_sf2_preset_set_name(preset,filename.ascii());
    /* append preset to SoundFont (ensure name/bank/preset # are unique) */
    ipatch_container_add_unique (IPATCH_CONTAINER (sf2),IPATCH_ITEM (preset));
    /* create new preset zone and link instrument to it */
    ipatch_sf2_preset_new_zone (preset, inst);

    
    
    for (int i=0;i<nb_keygroups;i++){
        QString temp_filename=filenames->operator[](i);
        temp_filename.prepend(dirpath+"/");
        int midiNote=bld[i].midiNote;
        if (midiNote==-1){
            cout<<"file: "<<temp_filename<<" midi: "<<midiNote<<"\n";
            continue;
        }
        /* identify and open file (++ new object reference) */
        file = ipatch_file_identify_open (temp_filename.ascii(), "r", &err);
        if (!file){
	  fprintf (stderr, "Failed to identify file '%s': %s\n", temp_filename.ascii(),
		   ipatch_gerror_message (err));
	  g_clear_error (&err);
	  continue;
	}

	/* attempt to convert sample file to SoundFont sample object
	 * ++ ref */
	sample = (IpatchSF2Sample *)ipatch_convert_object_to_type (G_OBJECT (file), IPATCH_TYPE_SF2_SAMPLE, &err);

	if (!sample)
	{
	  fprintf (stderr, "Failed to convert file '%s' to SoundFont sample: %s\n",
		   temp_filename.ascii(), ipatch_gerror_message (err));

          g_clear_error (&err);
	  g_object_unref (file); /* remove file reference */

	  continue;
	}

        /* append sample to SoundFont (ensure that its name is unique) */
        ipatch_container_add_unique (IPATCH_CONTAINER (sf2),
                                    IPATCH_ITEM (sample));
    
        g_object_set (sample, "root-note", midiNote, NULL); /* set the sample's root-note */
        
        /* create new instrument zone and link sample to it */      
        //ipatch_sf2_inst_new_zone(inst,sample);
        
        IpatchSF2IZone *izone= ipatch_sf2_izone_new ();
        ipatch_sf2_zone_set_link_item (IPATCH_SF2_ZONE (izone), IPATCH_ITEM (sample));
        //ipatch_sf2_gen_item_set_note_range(IPATCH_ITEM (izone),midiNote,midiNote);
        //ipatch_sf2_gen_item_set_velocity_range(IPATCH_ITEM (izone),0,127);
        ipatch_container_append (IPATCH_CONTAINER (inst), IPATCH_ITEM (izone));
        g_object_unref (izone);
        
        /*
        IpatchSF2IZone* zone=ipatch_sf2_izone_new();
        ipatch_sf2_zone_set_link_item (IPATCH_SF2_ZONE (zone), IPATCH_ITEM (sample));
        */
        IpatchRange* range=ipatch_range_new (midiNote, midiNote);
        g_object_set(izone,"key-range", range, NULL);
        ipatch_range_free(range);
        g_object_unref(izone);
        /**/
        
        g_object_unref (sample); /* -- unref SoundFont sample */
        g_object_unref (file);	/* -- unref file */
    }
    g_object_unref (inst);	/* -- unref SoundFont instrument */
    g_object_unref (preset);
    
    /* create SoundFont file object, set its name and open for writing */
    sffile = ipatch_sf2_file_new ();
    
    if (!ipatch_file_open (IPATCH_FILE (sffile), QString(dirpath+"/"+filename+".sf2").ascii(), "w", &err)){
        fprintf (stderr, "Failed to open output file for writing: %s\n",
                ipatch_gerror_message (err));
    
        g_object_unref (sffile);	/* -- unref SoundFont file */
        g_object_unref (sf2);	/* -- unref SoundFont object */
    
        return;
    }

    /* convert SoundFont object to SoundFont file (write it) */
    /*
    if (!ipatch_convert_objects (G_OBJECT (sf2), G_OBJECT (sffile), &err))
        {
        fprintf (stderr, "Failed to save SoundFont to file: %s\n",
                ipatch_gerror_message (err));
        g_clear_error (&err);
        }
     */
    
    IpatchSF2Writer* writer=ipatch_sf2_writer_new(sffile,sf2);
    if (!ipatch_sf2_writer_save(writer,&err))
        {
        fprintf (stderr, "Failed to save SoundFont to file: %s\n",
                ipatch_gerror_message (err));
        g_clear_error (&err);
    }
    
    
    g_object_unref (sffile);	/* -- unref SoundFont file */
    g_object_unref (sf2);		/* -- unref SoundFont object */
    
    //return (0);			/* we done, yeah! :) */

}
