import java.awt.*;
import java.awt.event.*;
import java.awt.image.*;
 
public class Draw2DCanvasB extends Canvas{
	private static final Color bgcolor = new Color(0,0,0);
        private Image im;
        
        public int imax;
        
	private Image im_palette;
	private MemoryImageSource mis;
	private int rgbPixels[];
	private int rgb_palette_Pixels[];
	private int new_width;
	private Color colorArray[]; 
        private Color colorArray2[];
        
        private static final int width=603;
        private static final int height=601; 
	//private static final int height=574;
        
	private static final int palette_width=20, palette_height=500;
	private static final int LeftMargin=10, RightMargin=20, TopMargin=10, BottomMargin=10;
	private static final int LeftImageIndent=1, LeftPaletteIndent=670;
        
        private int Npoints;
        
	private Oblique_State state;
	
        public Draw2DCanvasB(Oblique_State state){
		super();
		this.state = state;
                setBackground(bgcolor);
		new_width = (int)(width+1);
		rgbPixels = new int[(width+1) * (height+1)];
		rgb_palette_Pixels = new int[palette_width * palette_height];
		colorArray = new Color[256];
                colorArray2 = new Color[256];
                
                for(int i = 0; i < 127; i++) {
		    colorArray[i] = new Color(2*i,2*i,255);
		}
		
		for(int i = 127; i < 256; i++) {
		    colorArray[i] = new Color(255,255-(i-127),255-(i-127));
		}               
	}
        
	public void paint(Graphics g){
	                
          //-----------------------------------------
            updatePixels(g);
          //-----------------------------------------
        }   
	
	private void updatePixels(Graphics g){
	    int i=0, j=0, map=0, istar = 0, jstar = 0;
	    double x, y, min, max;
            
            int iangle = 0;
            int jangle = 0;
            
	    double myarray[][] = new double[width+1][height+1];
            int myslit[][] = new int[width+1][height+1];
            
            min = -300.0;
            max = 300.0;
            int mid = height/2;
            int mid2 = width/2;
            double totang = state.totalR_angle*Math.PI/180.0;
            
            if(state.Incident || state.Total){
                for(i = 0; i < width+1; i++){
                    for(j = 0; j < height+1; j++){
                        
                        //myarray[i][j] = state.myarray[i][j];
                        myarray[i][j] = state.myarray[j][i]; 
                        myslit[i][j] = 0;

                        if(j == mid){myslit[i][j] = 1;}
                        if(i == mid2){myslit[i][j] = 1;}
                        
                        if(myarray[i][j] > max){myarray[i][j]=max;}
                        if(myarray[i][j] < min){myarray[i][j]=min;}

                        /*
                        // These create a line "parallel" to incident wave front
                        if(state.theta1 < Math.PI*0.25){
                            jangle = mid - j;
                            iangle = mid2 - (int)((double)jangle*Math.sin(state.theta1)/Math.cos(state.theta1));

                            if(iangle < 0 || j > mid){ }
                            else{
                                myslit[iangle][j] = 2;
                            }
                        }

                        if(state.theta1 >= Math.PI*0.25){
                            iangle = mid2 -i;
                            jangle = mid - (int)((double)iangle*Math.cos(state.theta1)/Math.sin(state.theta1));

                            if(jangle < 0 || i > mid2){ }
                            else{
                                myslit[i][jangle] = 2;
                            }
                        }
                        */
                        
                        // Create line perpendicular to incident wavefront
                        
                        if(state.theta1 >= Math.PI*0.25){
                            jangle = j - mid;
                            iangle = mid2 - (int)((double)jangle*Math.cos(state.theta1)/Math.sin(state.theta1));

                            if(iangle < 0 || iangle > width || j < mid ){ }
                            else{
                                myslit[iangle][j] = 2;
                            }
                        }
                        
                        
                        if(state.theta1 < Math.PI*0.25){
                            iangle = mid2 -i;
                            jangle = mid + (int)((double)iangle*Math.sin(state.theta1)/Math.cos(state.theta1));
                                
                            if(jangle < 0 || jangle > height || i > mid2){ }
                            else{
                                myslit[i][jangle] = 2;
                            }
                        }
                        //------------------------------------------------------
                        
                        /*
                        // These create lines parallel to tansmitted wavefront
                        if(state.theta2 < Math.PI*0.25){
                            jangle = mid - j;
                            
                            iangle = mid2 - (int)((double)jangle*Math.sin(state.theta2)/Math.cos(state.theta2));
                            if(iangle > width || j <= mid){ }
                            else{
                                myslit[iangle][j] = 2;
                            }

                        }

                        if(state.theta2 >= Math.PI*0.25 || state.theta1 >= totang){
                            iangle = mid2 -i;
                            
                            if(state.theta1 >= totang){
                                jangle = mid;
                            }
                            else{
                                jangle = mid - (int)((double)iangle*Math.cos(state.theta2)/Math.sin(state.theta2));
                            }
                            
                            if(jangle > height || i <= mid2){ }
                            else{
                                myslit[i][jangle] = 2;
                            }
                        }
                         */
                        
                        // Create lines perpendicular to transmitted wavefront
                        if(state.theta2 >= Math.PI*0.25 || state.theta1 >= totang){
                            jangle = mid - j;
                            if(state.theta1 >= totang){
                                iangle = mid2;
                            }
                            else{
                                iangle = mid2 + (int)((double)jangle*Math.cos(state.theta2)/Math.sin(state.theta2));
                            }
                            
                            if(iangle < 0 || iangle > width || j > mid ){ }
                            else{
                                myslit[iangle][j] = 2;
                            }
                        }
                        
                        
                        if(state.theta2 < Math.PI*0.25){
                            iangle = i -mid2;
                            jangle = mid - (int)((double)iangle*Math.sin(state.theta2)/Math.cos(state.theta2));
                                
                            if(jangle < 0 || jangle > height || i < mid2){ }
                            else{
                                myslit[i][jangle] = 2;
                            }
                        }
               
                    }
                }
            }
            
            if(state.Reflected){
                for(i = 0; i < width+1; i++){
                    for(j = 0; j < height+1; j++){
                        
                        //myarray[i][j] = state.myarray[j][i];
                        myarray[i][j] = state.myarray[j][i];//change 3
                        myslit[i][j] = 0;

                        if(j == mid){myslit[i][j] = 1;}
                        if(i == mid2){myslit[i][j] = 1;}

                        if(myarray[i][j] > max){myarray[i][j]=max;}
                        if(myarray[i][j] < min){myarray[i][j]=min;}

                        // Create lines perpendicular to reflected wavefront
                        if(state.theta1 >= Math.PI*0.25){
                            jangle = mid-j;
                            iangle = mid2 - (int)((double)jangle*Math.cos(state.theta1)/Math.sin(state.theta1));

                            if(iangle < 0 || iangle > width || j > mid){ }
                            else{
                                myslit[iangle][j] = 2;
                            }
                        }
                        
                        if(state.theta1 < Math.PI*0.25){
                            iangle = mid2 -i;
                            jangle = mid - (int)((double)iangle*Math.sin(state.theta1)/Math.cos(state.theta1));
                                
                            if((jangle) < 0 || (jangle) > height || i > mid2){ }
                            else{
                                myslit[i][jangle] = 2;
                            }
                        }
                        
                        // Create lines perpendicular to transmitted wavefront
                        if(state.theta2 >= Math.PI*0.25 || state.theta1 >= totang){
                            jangle = mid - j;
                            if(state.theta1 >= totang){
                                iangle = mid2;
                            }
                            else{
                                iangle = mid2 + (int)((double)jangle*Math.cos(state.theta2)/Math.sin(state.theta2));
                            }
                            
                            if(iangle < 0 || iangle > width || j > mid ){ }
                            else{
                                myslit[iangle][j] = 2;
                            }
                        }
                        
                        
                        if(state.theta2 < Math.PI*0.25){
                            iangle = i -mid2;
                            jangle = mid - (int)((double)iangle*Math.sin(state.theta2)/Math.cos(state.theta2));
                                
                            if(jangle < 0 || jangle > height || i < mid2){ }
                            else{
                                myslit[i][jangle] = 2;
                            }
                        }
                        
                    }
                }
            }
            
            for(i = 0; i < width+1; i++){
                    for(j = 0; j < height+1; j++){
                        
                        if(j == height -14){myslit[i][j] = 1;}
                        if(j == 12){myslit[i][j] = 1;}
                        
                    }
            }
            for(i = 0; i < width+1; i++){
		for(j = 0; j < height+1; j++){ // actual values
		  if(myslit[i][j] == 0){
                        map = (int)MaestroA.mapper(myarray[i][j],255.0,0.0,max,min);
                        //map = (int)MaestroA.mapper(myarray[i][j],511.0,0.0,max,min);
                        rgbPixels[j*new_width+i] = colorArray[map].getRGB();
                  }
                 
                  else if(myslit[i][j] == 1){ // black
                        map = 255;
                        rgbPixels[j*new_width+i] = new Color(0,0,0).getRGB();
                  }
                  
                  
                  else if(myslit[i][j] == 2){ // green
                        map = 255;
                        rgbPixels[j*new_width+i] = new Color(0,255,0).getRGB();
                  }
                  
                  
                  //rgbPixels[(height/2)*new_width+(width/2)] = new Color(255,255,255).getRGB();

                    //rgbPixels[j*new_width+i] = colorArray[map].getRGB();  
		}
	    }
            
            
            
            myarray = null;
	    mis = new MemoryImageSource(new_width,height,rgbPixels,0,new_width);
	    mis.setAnimated(true);
	    mis.setFullBufferUpdates(false);
            im = createImage(mis);
            g.drawImage(im,LeftImageIndent,(getSize().height-height)/2,this);
	}
	
	private void drawImage(Graphics g){
	   g.drawImage(im,LeftImageIndent,(getSize().height-height)/2,this);
	}
	
	private void drawPalette(Graphics g){
	    int i, j, map, imax;
	    FontMetrics fm = g.getFontMetrics();
	    imax = state.palettereference;
                /*
                for(int ii = 0; ii < imax; ii++) {
		    colorArray2[ii] = new Color((2550000/imax*ii)/10000,(2550000/imax*ii)/10000,255);
		}
		
		for(int ii = imax; ii < 256; ii++) {
		    colorArray2[ii] = new Color(255,255-(ii-imax),255-(ii-imax));
		}
                */
            
                for(int ii = 0; ii < 256; ii++) {
		   colorArray2[ii] = new Color(0,0,255);
		}
                
                for(int ii = 256; ii < 512; ii++) {
		   colorArray2[ii] = new Color(ii-256,ii-256,255);
		}
		
		for(int ii = 512; ii < 768; ii++) {
		    colorArray2[ii] = new Color(255,255-(ii-512),255-(ii-512));
		}
                
                for(int ii = 768; ii < 1024; ii++) {
		   colorArray2[ii] = new Color(255,0,0);
		}
            
                //colorArray2[126] = new Color(200,200,200);
                //colorArray2[128] = new Color(200,200,200);
                
                /*
                colorArray2[7] = new Color(0,0,255);
                colorArray2[23] = new Color(0,0,255);
                colorArray2[39] = new Color(0,0,255);
                colorArray2[55] = new Color(0,0,255);
                colorArray2[71] = new Color(0,0,255);
                colorArray2[87] = new Color(0,0,255);
                colorArray2[103] = new Color(0,0,255);
                colorArray2[119] = new Color(0,0,255);
                colorArray2[135] = new Color(255,0,0);
                colorArray2[151] = new Color(255,0,0);
                colorArray2[167] = new Color(255,0,0);
                colorArray2[183] = new Color(255,0,0);
                colorArray2[199] = new Color(255,0,0);
                colorArray2[215] = new Color(255,0,0);
                colorArray2[231] = new Color(255,0,0);
                colorArray2[247] = new Color(255,0,0);
                */
                
            for(i = 0; i < palette_width; i++){
		for(j = 0; j < palette_height; j++){
		    map = (palette_height-1-j)*1023/(palette_height-1);
                    
                    if(map < 0) { map = 0;}
		    if(map >1023) { map = 1023; }
                    rgb_palette_Pixels[j*palette_width+i] = colorArray2[map].getRGB();
		}
	    }
            //int leftshift = 15;
	    //im_palette = createImage(new MemoryImageSource(palette_width,palette_height,
		//		rgb_palette_Pixels,0,palette_width));
	    //g.drawImage(im_palette,LeftPaletteIndent-leftshift,(getSize().height-height)/2,this);
	    
	    //g.drawString("-max",LeftPaletteIndent+palette_width-27-leftshift,getSize().height-28*BottomMargin/10);
    	    //g.drawString("max",LeftPaletteIndent+palette_width-22-leftshift,getSize().height/2-height/2-5);
	    //g.drawRect(LeftPaletteIndent-1-leftshift,getSize().height/2-height/2-1,
		//	palette_width+1,1+palette_height);
	}
	
	
	public void setWidth(double ratio){
	    this.new_width=(int)(width/ratio);
	    this.rgbPixels=new int[(int)(width/ratio*height)];
	    
	}
	
	public void update(Graphics g){
		//drawPalette(g);
                updatePixels(g);
                
		mis.newPixels(0,0,new_width,height);
		drawImage(g);
	}
		
}	



/*
import java.awt.*;
import java.awt.event.*;
import java.awt.image.*;
 
public class Draw2DCanvasB extends Canvas{
	private static final Color bgcolor = new Color(0,0,0);
        private Image im;
        
        public int imax;
        
	private Image im_palette;
	private MemoryImageSource mis;
	private int rgbPixels[];
	private int rgb_palette_Pixels[];
	private int new_width;
	private Color colorArray[]; 
        private Color colorArray2[];
        
        //9,50,606,576
        
	//private static final int width=590;
	//private static final int height=564;
        private static final int width=603;
        private static final int height=601;
	//private static final int height=574;
        
	private static final int palette_width=20, palette_height=500;
	private static final int LeftMargin=10, RightMargin=20, TopMargin=10, BottomMargin=10;
	private static final int LeftImageIndent=1, LeftPaletteIndent=670;
        
        //private int Nx = 600;
        //private int Ny = 544;
        
        //private double w[][];
        
        private int Npoints;
        
	private Oblique_State state;
	
        public Draw2DCanvasB(Oblique_State state){
		super();
		this.state = state;
                setBackground(bgcolor);
		new_width = (int)(width+1);
		rgbPixels = new int[(width+1) * (height+1)];
		rgb_palette_Pixels = new int[palette_width * palette_height];
		//colorArray = new Color[512];
                //colorArray2 = new Color[512];
                colorArray = new Color[256];
                colorArray2 = new Color[256];
                
		
                //w = new double[Nx+1][Ny+1];
                
                //Initialize the color palette
                
                
                for(int i = 0; i < 127; i++) {
		    colorArray[i] = new Color(2*i,2*i,255);
		}
		
		for(int i = 127; i < 256; i++) {
		    colorArray[i] = new Color(255,255-(i-127),255-(i-127));
		}
                
                
	}
	
        
	public void paint(Graphics g){
	                
          //-----------------------------------------
            updatePixels(g);
          //-----------------------------------------
        }   
	
	private void updatePixels(Graphics g){
	    int i=0, j=0, map=0, istar = 0, jstar = 0;
	    double x, y, min, max;
            
            int iangle = 0;
            int jangle = 0;
            
	    double myarray[][] = new double[width+1][height+1];
            int myslit[][] = new int[width+1][height+1];
            
            min = -300.0;
            max = 300.0;
            int mid = height/2;
            int mid2 = width/2;
            double totang = state.totalR_angle*Math.PI/180.0;
            
            if(state.Incident || state.Total){
                for(i = 0; i < width+1; i++){
                    for(j = 0; j < height+1; j++){

                        myarray[i][j] = state.myarray[i][j];
                        myslit[i][j] = 0;

                        if(j == mid){myslit[i][j] = 1;}
                        if(i == mid2){myslit[i][j] = 1;}

                        if(myarray[i][j] > max){myarray[i][j]=max;}
                        if(myarray[i][j] < min){myarray[i][j]=min;}

                        if(state.theta1 < Math.PI*0.25){
                            jangle = mid - j;
                            iangle = mid2 - (int)((double)jangle*Math.sin(state.theta1)/Math.cos(state.theta1));

                            if(iangle < 0 || j > mid){ }
                            else{
                                myslit[iangle][j] = 2;
                            }
                        }

                        if(state.theta1 >= Math.PI*0.25){
                            iangle = mid2 -i;
                            jangle = mid - (int)((double)iangle*Math.cos(state.theta1)/Math.sin(state.theta1));

                            if(jangle < 0 || i > mid2){ }
                            else{
                                myslit[i][jangle] = 2;
                            }
                        }
                        
                        if(state.theta2 < Math.PI*0.25){
                            jangle = mid - j;
                            
                            iangle = mid2 - (int)((double)jangle*Math.sin(state.theta2)/Math.cos(state.theta2));
                            if(iangle > width || j <= mid){ }
                            else{
                                myslit[iangle][j] = 2;
                            }

                        }

                        if(state.theta2 >= Math.PI*0.25 || state.theta1 >= totang){
                            iangle = mid2 -i;
                            
                            if(state.theta1 >= totang){
                                jangle = mid;
                            }
                            else{
                                jangle = mid - (int)((double)iangle*Math.cos(state.theta2)/Math.sin(state.theta2));
                            }
                            
                            if(jangle > height || i <= mid2){ }
                            else{
                                myslit[i][jangle] = 2;
                            }
                        }

                    }
                }
            }
            
            if(state.Reflected){
                for(i = 0; i < width+1; i++){
                    for(j = 0; j < height+1; j++){

                        myarray[i][j] = state.myarray[i][j];
                        myslit[i][j] = 0;

                        if(j == mid){myslit[i][j] = 1;}
                        if(i == mid2){myslit[i][j] = 1;}

                        if(myarray[i][j] > max){myarray[i][j]=max;}
                        if(myarray[i][j] < min){myarray[i][j]=min;}

                        if(state.theta1 < Math.PI*0.25){
                            jangle = mid - j;
                            iangle = mid2 - (int)((double)jangle*Math.sin(state.theta1)/Math.cos(state.theta1));

                            if(iangle < 0 || j > mid){ }
                            else{
                                myslit[width - iangle][j] = 2;
                            }
                        }

                        if(state.theta1 >= Math.PI*0.25){
                            iangle = mid2 -i;
                            jangle = mid - (int)((double)iangle*Math.cos(state.theta1)/Math.sin(state.theta1));
                            
                            if(jangle > height || i <= mid2){ }
                            else{
                                myslit[i][height - jangle] = 2;   
                            }
                        }
                        
                        if(state.theta2 < Math.PI*0.25){
                            jangle = mid - j;
                            
                            iangle = mid2 - (int)((double)jangle*Math.sin(state.theta2)/Math.cos(state.theta2));
                            if(iangle > width || j <= mid){ }
                            else{
                                myslit[iangle][j] = 2;
                            }

                        }

                        if(state.theta2 >= Math.PI*0.25 || state.theta1 >= totang){
                            iangle = mid2 -i;
                            
                            if(state.theta1 >= totang){
                                jangle = mid;
                            }
                            else{
                                jangle = mid - (int)((double)iangle*Math.cos(state.theta2)/Math.sin(state.theta2));
                            }
                            
                            if(jangle > height || i <= mid2){ }
                            else{
                                myslit[i][jangle] = 2;
                            }
                        }

                    }
                }
            }
            
            for(i = 0; i < width+1; i++){
		for(j = 0; j < height+1; j++){ // actual values
		  if(myslit[i][j] == 0){
                        map = (int)MaestroA.mapper(myarray[i][j],255.0,0.0,max,min);
                        //map = (int)MaestroA.mapper(myarray[i][j],511.0,0.0,max,min);
                        rgbPixels[j*new_width+i] = colorArray[map].getRGB();
                  }
                 
                  else if(myslit[i][j] == 1){ // black
                        map = 255;
                        rgbPixels[j*new_width+i] = new Color(0,0,0).getRGB();
                  }
                  
                  
                  else if(myslit[i][j] == 2){ // green
                        map = 255;
                        rgbPixels[j*new_width+i] = new Color(0,255,0).getRGB();
                  }
                  
                  
                  //rgbPixels[(height/2)*new_width+(width/2)] = new Color(255,255,255).getRGB();

                    //rgbPixels[j*new_width+i] = colorArray[map].getRGB();  
		}
	    }
            
            
            
            myarray = null;
	    mis = new MemoryImageSource(new_width,height,rgbPixels,0,new_width);
	    mis.setAnimated(true);
	    mis.setFullBufferUpdates(false);
            im = createImage(mis);
            g.drawImage(im,LeftImageIndent,(getSize().height-height)/2,this);
	}
	
	private void drawImage(Graphics g){
	   g.drawImage(im,LeftImageIndent,(getSize().height-height)/2,this);
	}
	
	private void drawPalette(Graphics g){
	    int i, j, map, imax;
	    FontMetrics fm = g.getFontMetrics();
	    imax = state.palettereference;
                
                for(int ii = 0; ii < 256; ii++) {
		   colorArray2[ii] = new Color(0,0,255);
		}
                
                for(int ii = 256; ii < 512; ii++) {
		   colorArray2[ii] = new Color(ii-256,ii-256,255);
		}
		
		for(int ii = 512; ii < 768; ii++) {
		    colorArray2[ii] = new Color(255,255-(ii-512),255-(ii-512));
		}
                
                for(int ii = 768; ii < 1024; ii++) {
		   colorArray2[ii] = new Color(255,0,0);
		}
            
                //colorArray2[126] = new Color(200,200,200);
                //colorArray2[128] = new Color(200,200,200);
                
                
            for(i = 0; i < palette_width; i++){
		for(j = 0; j < palette_height; j++){
		    map = (palette_height-1-j)*1023/(palette_height-1);
                    
                    if(map < 0) { map = 0;}
		    if(map >1023) { map = 1023; }
                    rgb_palette_Pixels[j*palette_width+i] = colorArray2[map].getRGB();
		}
	    }
            //int leftshift = 15;
	    //im_palette = createImage(new MemoryImageSource(palette_width,palette_height,
		//		rgb_palette_Pixels,0,palette_width));
	    //g.drawImage(im_palette,LeftPaletteIndent-leftshift,(getSize().height-height)/2,this);
	    
	    //g.drawString("-max",LeftPaletteIndent+palette_width-27-leftshift,getSize().height-28*BottomMargin/10);
    	    //g.drawString("max",LeftPaletteIndent+palette_width-22-leftshift,getSize().height/2-height/2-5);
	    //g.drawRect(LeftPaletteIndent-1-leftshift,getSize().height/2-height/2-1,
		//	palette_width+1,1+palette_height);
	}
	
	
	public void setWidth(double ratio){
	    this.new_width=(int)(width/ratio);
	    this.rgbPixels=new int[(int)(width/ratio*height)];
	    
	}
	
	public void update(Graphics g){
		//drawPalette(g);
                updatePixels(g);
                
		mis.newPixels(0,0,new_width,height);
		drawImage(g);
	}
		
}	

*/