package ch.psi.plot.xyz.generator;

import java.util.logging.Logger;

import ch.psi.plot.xy.generator.Noise;
import ch.psi.plot.MatrixPlotSeries;

/**
 * Converter object converting a file into PixelPlot data
 */
public class DataGenerator implements Runnable {
	
	private static Logger logger = Logger.getLogger(DataGenerator.class.getName());
	
	private final MatrixPlotSeries data;
	private XYZGeneratorFunction function;
	
	double xMin = 0;
	double xMax = 1200;//120
	int xNStep = 1200;//120
	
	double yMin = 0;
	double yMax = 1200;//120
	int yNStep = 1200;//120
	
	private Noise noiseFunctionX = null;
	private Noise noiseFunctionY = null;
	
	public DataGenerator(XYZGeneratorFunction function){
		this(function, false, true);
	}
	
	/**
	 * 
	 * @param function	Function generator to use to generate value 
	 * @param type		Type of plot (Pixel or Matrix)
	 */
	public DataGenerator(XYZGeneratorFunction function, boolean noise, boolean metaDataAvailable){
		this.function = function;
		
		data = new MatrixPlotSeries(null, xMin,xMax,xNStep,yMin,yMax,yNStep);
		
		if(noise){
			noiseFunctionX = new Noise(data.getBinWidthX());
			noiseFunctionY = new Noise(data.getBinWidthY());
		}
	}

	/**
	 * Update data
	 * @throws NumberFormatException
	 * @throws Exception
	 */
	public void generateData() {
		
			double x;
			double y;
			//Y Axis
			for(int i=0; i < yNStep; i++){
				y = yMin + (i*data.getBinWidthY());
				if(noiseFunctionY!=null){
					y=noiseFunctionY.generate(y);
				}
				
				// X Axis
				for(int t=0;t<xNStep; t++){
					x = xMin + (t*data.getBinWidthX());
					if(noiseFunctionX!=null){
						x=noiseFunctionX.generate(x);
					}
					
					logger.fine("x: "+x+" y: "+y+" z: "+function.generate(x, y));
					data.appendData(x, y, function.generate(x, y));
//					try {
//						Thread.sleep(1);
//					} catch (InterruptedException e1) {
//						e1.printStackTrace();
//					}
				}
			}
	}
	
	public MatrixPlotSeries getData() {
		return data;
	}

	@Override
	public void run() {
		try {
			generateData();
			Thread.sleep(100);
		} catch (InterruptedException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}

	}
}
