/***************************************************************/
/*                                                             */
/* prepare_raster_attribute - Prepare the raster attribute     */
/*                            value that will be inserted      */
/*                            into a raster column or used     */
/*                            to update an existing raster     */
/*                            column value.                    */
/*                                                             */
/*              arguments:                                     */  
/*                                                             */
/*              connection <SE_CONNECTION> - the connection    */
/*                                           handle.           */
/*              rasterband <SE_RASBANDINFO> - the rasterband   */
/*                                            info structure.  */
/*              client_data <CLIENT_DATA*> - Pointer to the    */
/*                                           client data       */
/*                                           structure.        */
/*              pixel_type <LONG> - The pixel bit depth.       */
/*              bsqmetadata <BSQMETADATA> - BSQ file metadata. */
/*              interpolation <SE_INTERPOLATION_TYPE> - The    */
/*                               resampling method used to     */
/*                               construct the raster pyramid. */
/*              compression <SE_COMPRESSION_TYPE> - The        */
/*                               compression method the image  */
/*                               was stored with.              */ 
/*                                                             */
/***************************************************************/

void prepare_raster_attribute ( SE_CONNECTION connection,
                                SE_RASTERATTR *raster_attrib,
				CLIENT_DATA *client_data,
				LONG pixel_type,
				BSQMETADATA bsqmetadata,
				SE_INTERPOLATION_TYPE interpolation,
				SE_COMPRESSION_TYPE compression,
				LONG mosaic_mode)
{
	SE_COLORMAP_TYPE colormap_type;
	SE_COLORMAP_DATA_TYPE colormap_data_type;
	UCHAR colormap_data[768];
	LONG rc, num_colormap_entries,
			  tile_width,
			  tile_height,
			  max_level;
	SE_ENVELOPE     raster_env;

	/* Initialize the SE_RASTERATTR structure */

	rc = SE_rasterattr_create (raster_attrib,TRUE);
	check_error (rc, NULL, NULL, "SE_rasterattr_create");

	/* Add the callback function to the SE_RASTERATTR structure. */
	/* The callback function determines how SE_stream_execute will */
	/* enter the image pixel data into the raster column. */

	rc = SE_rasterattr_set_callback ( *raster_attrib, 
					  (SE_RASTER_PROC) raster_attribute_callback,
					  (void *) client_data);
	check_error (rc, NULL, NULL, "SE_rasterattr_set_callback");

	/*  If inserting a single band 8-bit image with nearest neighbor interpolation */
	/*  prepare a colormap and mosaic mode is replace. */
	/*  Populate the color map. This color map is a 256 RGB gray scale. */

	if (bsqmetadata.numbands == 1 && interpolation == SE_INTERPOLATION_NEAREST  &&
	  (pixel_type == SE_PIXEL_TYPE_8BIT_S || pixel_type == SE_PIXEL_TYPE_8BIT_U ||
	   pixel_type == SE_PIXEL_TYPE_16BIT_S || pixel_type == SE_PIXEL_TYPE_16BIT_U)) 
        {

		prepare_colormap ( &colormap_type,
				   &colormap_data_type, 
				   &num_colormap_entries, 
				   colormap_data);

		/* Add the colormap to the SE_RASTERATTR structure. The colormap will be */ 
		/* applied to the pixels of the image. */

		rc = SE_rasterattr_set_colormap ( *raster_attrib,
						  colormap_type,
						  colormap_data_type,
						  num_colormap_entries,
						  (void *) colormap_data);
		check_error (rc, NULL, NULL, "SE_rasterattr_set_colormap");

	}

	/* Set the compression. */

	rc = SE_rasterattr_set_compression_type (*raster_attrib, compression);
	check_error (rc, NULL, NULL, "SE_rasterattr_set_compression_type");

	/* Set the image size. */

	rc = SE_rasterattr_set_image_size (*raster_attrib, 
					   bsqmetadata.pixelwidth, 
					   bsqmetadata.pixelheight, 
					   bsqmetadata.numbands);
	check_error (rc, NULL, NULL, "SE_rasterattr_set_image_size");

	/* Use a NODATA bitmask. */

	rc = SE_rasterattr_set_mask_mode (*raster_attrib, TRUE);
	check_error (rc, NULL, NULL, "SE_rasterattr_set_mask_mode");

	/* Set the mosiac mode. */

	rc = SE_rasterattr_set_mosaic_mode (*raster_attrib, mosaic_mode);
	check_error (rc, NULL, NULL, "SE_rasterattr_set_mosiac_mode");

	/* Set the pyramid info */

	if (interpolation==SE_INTERPOLATION_NONE)
		 max_level = 0;
	else
		 max_level = SE_PYRAMID_AUTO_LEVEL;

	rc = SE_rasterattr_set_pyramid_info (*raster_attrib, 
					     max_level, 
					     FALSE, 
					     interpolation);
	check_error (rc, NULL, NULL, "SE_rasterattr_set_pyramid_info");

	/* Set the pixel bit depth. */

	rc = SE_rasterattr_set_pixel_type (*raster_attrib, pixel_type);
	check_error (rc, NULL, NULL, "SE_rasterattr_set_pixel_type");
	
	tile_width = 128;
	tile_height = 128;

	/* Set the tile size */

	rc = SE_rasterattr_set_tile_size (*raster_attrib, tile_width, tile_height);
	check_error (rc, NULL, NULL, "SE_rasterattr_set_tile_size");

	/* Calculate the image envelope. Always subtract one pixel when calculating miny and maxx */
	/* because image coordinates are set a the center of the cell. You loose half a pixel on */
	/* each side of the image. Note the ycellsize returned from the bsq world file is always  */
	/* a negative value moving toward the y minimum from the y maximum. Conversely the */
	/* xcellsize is always a positive value moving from the x minimum toward the x maxiumum */ 

	raster_env.minx = bsqmetadata.xmin;
	raster_env.miny = bsqmetadata.ymax + (bsqmetadata.ycellsize * (bsqmetadata.pixelheight - 1));
	raster_env.maxx = bsqmetadata.xmin + (bsqmetadata.xcellsize * (bsqmetadata.pixelwidth - 1));
	raster_env.maxy = bsqmetadata.ymax;

	/* Set the image envelope */

	rc = SE_rasterattr_set_extent (*raster_attrib, &raster_env);
	check_error (rc, NULL, NULL, "SE_rasterattr_set_extent");

	/* Set the virtual origin for the initial insert. */

	if (mosaic_mode == SE_MOSAIC_MODE_NONE) {	
		rc = SE_rasterattr_set_image_origin (*raster_attrib, -9.65854156766455, 50.69201366247066);
		check_error (rc, NULL, NULL, "SE_rasterattr_set_extent");
	}

	return;

} /* prepare_raster_attribute */