/* Port of rgb2pct.py */

/*
#******************************************************************************
#  $Id: rgb2pct.c 6219 2004-06-01 13:24:09Z warmerda $
# 
#  Name:     rgb2pct
#  Project:  GDAL Python Interface
#  Purpose:  Application for converting an RGB image to a pseudocolored image.
#  Author:   Frank Warmerdam, warmerdam@pobox.com
# 
#******************************************************************************
#  Copyright (c) 2001, Frank Warmerdam
#  Copyright (c) 2007, Even Rouault
# 
#  Permission is hereby granted, free of charge, to any person obtaining a
#  copy of this software and associated documentation files (the "Software"),
#  to deal in the Software without restriction, including without limitation
#  the rights to use, copy, modify, merge, publish, distribute, sublicense,
#  and/or sell copies of the Software, and to permit persons to whom the
#  Software is furnished to do so, subject to the following conditions:
# 
#  The above copyright notice and this permission notice shall be included
#  in all copies or substantial portions of the Software.
# 
#  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
#  OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
#  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
#  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
#  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
#  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
#  DEALINGS IN THE SOFTWARE.
#******************************************************************************
*/

#include "gdal.h"
#include "gdal_alg.h"
#include "cpl_port.h"
#include "cpl_string.h"
#include "tiffio.h"

int main(int argc, char* argv[])
{
    int i = 0;
    char* format = "GTiff";
    int nColors = 256;
    char* src_filename = NULL;
    char* dst_filename = NULL;
    char  **papszCreateOptions = NULL;

    for(i = 1; i < argc; i++)
    {
        if (strcmp(argv[i], "-of") == 0)
        {
            format = argv[i+1];
            i++;
        }
        else if (strcmp(argv[i], "-n") == 0)
        {
            nColors = atoi(argv[i+1]);
            i++;
        }
        else if( EQUAL(argv[i],"-co") && i < argc-1 )
        {
            papszCreateOptions = CSLAddString( papszCreateOptions, argv[++i] );
        }
        else if (src_filename == NULL)
        {
            src_filename = argv[i];
        }
        else if (dst_filename == NULL)
        {
            dst_filename = argv[i];
        }
        else
        {
            printf("Usage: rgb2pct [-n colors] [-of format] [-co \"NAME=VALUE\"]* source_file dest_file\n");
            return 1;
        }
    }
    
    if (dst_filename == NULL)
    {
        printf("Usage: rgb2pct [-n colors] [-of format] [-co \"NAME=VALUE\"]* source_file dest_file\n");
        return 1;
    }
    
    GDALAllRegister();
    
    GDALDatasetH ds = GDALOpen(src_filename, GA_ReadOnly);
    if (ds == NULL)
    {
        return 1;
    }
    
    if (GDALGetRasterCount(ds) < 3)
    {
        fprintf(stderr, "%s has %d bands, need 3 for inputs red, green and blue.\n",
                src_filename, GDALGetRasterCount(ds));
        return 1;
    }
    
    GDALDriverH dst_driver = GDALGetDriverByName(format);
    if (dst_driver == NULL)
    {
        fprintf(stderr, "%s driver is not registered\n", format);
        return 1;
    }
    
    GDALColorTableH color_table = GDALCreateColorTable(GPI_RGB);
    
    /* Generate histogram */
    GDALComputeMedianCutPCT( GDALGetRasterBand(ds, 1),
                            GDALGetRasterBand(ds, 2),
                            GDALGetRasterBand(ds, 3),
                            NULL,
                            nColors,
                            color_table,
                            GDALTermProgress,
                            NULL);
    
    // Create the working file.  We have to use TIFF since there are few formats
    // that allow setting the color table after creation.
    
    char* tif_filename;
    if (strcmp(format, "GTiff") == 0)
    {
        tif_filename = dst_filename;
    }
    else
    {
        tif_filename = "temp.tif";
    }
    
    GDALDriverH gtiff_driver = GDALGetDriverByName("GTiff");
    GDALDatasetH tif_ds = GDALCreate( gtiff_driver, tif_filename,
                                      GDALGetRasterXSize(ds), GDALGetRasterYSize(ds), 1, GDT_Byte,
                                      (strcmp(format, "GTiff") == 0) ? papszCreateOptions : NULL);

    // We should copy projection information and so forth at this point.
    GDALSetProjection(tif_ds, GDALGetProjectionRef(ds));
    double adfGeoTransform[6];
    GDALGetGeoTransform(ds, adfGeoTransform);
    GDALSetGeoTransform(tif_ds, adfGeoTransform);

    GDALSetRasterColorTable(GDALGetRasterBand(tif_ds, 1), color_table);
    
    // Actually transfer and dither the data.
    printf("Dither:");
    GDALDitherRGB2PCT( GDALGetRasterBand(ds, 1),
                    GDALGetRasterBand(ds, 2),
                    GDALGetRasterBand(ds, 3),
                    GDALGetRasterBand(tif_ds, 1),
                    color_table,
                    GDALTermProgress,
                    NULL);

    GDALClose(tif_ds);


    if (strcmp(format, "GTiff") != 0)
    {
        tif_ds = GDALOpen(tif_filename, GA_ReadOnly);
        printf("Copy to %s:", format);
        GDALDatasetH dst_ds = GDALCreateCopy( dst_driver, dst_filename, tif_ds, FALSE, papszCreateOptions, GDALTermProgress, NULL);
        if (dst_ds)
            GDALClose(dst_ds);
        GDALClose(tif_ds);
        GDALDeleteDataset(gtiff_driver, tif_filename);
    }
    
    GDALDestroyColorTable(color_table);

    GDALClose(ds);

    GDALDumpOpenDatasets( stderr );

    GDALDestroyDriverManager();
    
    CSLDestroy(papszCreateOptions);

    return 0;
}
