/*
 * $Id: LineGraph.java,v 1.7 2007-03-11 20:40:58 larry Exp $ 
 */
package com.representqueens.spark;

/*
 * 
 * Copyright 2006 Larry Ogrodnek
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.geom.Line2D;
import java.awt.image.BufferedImage;

/**
 * Linegraph generation.
 * 
 * @author Larry Ogrodnek <larry@cheesesteak.net>
 * @version $Revision: 1.7 $ $Date: 2007-03-11 20:40:58 $
 */
public class LineGraph
{
  private static final int WIDTH = 100;
  private static final int HEIGHT = 25;
  
  private static final int SPACING = 2;
  
  public static final SizeParams DEFAULT_SIZE = new SizeParams(WIDTH, HEIGHT, SPACING);
  
  public static final Color DEFAULT_COLOR = Color.GRAY;
  
  /**
   * Create a Linegraph using defaults.
   * 
   * @param data Array of Number Objects to graph.
   * 
   * @return BufferedImage containing a Linegraph of data.
   */  
  public static BufferedImage createGraph(final Number[] data)
  {
    return createGraph(data, DEFAULT_SIZE, DEFAULT_COLOR);
  }
  
  /**
   * Create a Linegraph.
   * 
   * @param data Array of Number Objects to graph.
   * @param size SizeParams specifying graph size attributes.
   * @param color graph Color.
   * 
   * @return BufferedImage containing a Linegraph of data.
   */
  public static BufferedImage createGraph(final Number[] data, final SizeParams size, final Color color)
  {
    return createGraph(data, size, color, null);
  }
  
  /**
   * Create a Linegraph.
   * 
   * @param data Array of Number Objects to graph.
   * @param size SizeParams specifying graph size attributes.
   * @param color graph Color.
   * @param background background color, or null for transparent.
   * 
   * @return BufferedImage containing a Linegraph of data.
   */
  public static BufferedImage createGraph(final Number[] data, final SizeParams size, final Color color, final Color background)
  {
    final BufferedImage bi = new BufferedImage(size.getWidth(), size.getHeight(), BufferedImage.TYPE_INT_ARGB);
    
    if (data == null || data.length < 2)
    {
      return bi;
    }
  
    final Graphics2D g = bi.createGraphics();
    g.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
    
    if (background != null)
    {
      g.setBackground(background);
      g.clearRect(0, 0, size.getWidth(), size.getHeight());
    }

    float d = GraphUtils.getDivisor(data, size.getHeight());
    final int w = (size.getWidth() - (size.getSpacing() * (data.length -1)))/ (data.length - 1);

    float min = Float.MAX_VALUE;
    for (final Number i : data)
    {
      min = Math.min(min,i.floatValue());    
    }

    int x = 0; 
    int y = -1;
    
    if (d == 0.0)
    {
      //special case -- a horizontal straight line
      d = 1.0f;
      y = - size.getHeight()/2;
    }
    
    for (int i=0; i< data.length - 1; i++)
    {
      final int px1 = x;
      x+= (w + size.getSpacing());
      final int px2 = x;
      
      g.setPaint(color);
      g.draw(new Line2D.Double(px1, y + (size.getHeight() - ((data[i].floatValue()-min) / d)),
                               px2, y + (size.getHeight() - ((data[i+1].floatValue()-min) / d))));
    }
    
    return bi;
  }
}
