/*
 * Date: 2004/09/05
 */
//import java.io.FileInputStream;
//import java.io.IOException;
import java.awt.*;
import java.awt.event.*;
import java.awt.image.*;

/**
 * @author H_Kuwata
 *
 */
public class Ragna extends Frame implements Runnable
{
	/**
	 * 
	 */
	private static final long serialVersionUID = -5208124768950195157L;
	static final int CANVAS_SIZE_X = Vram._vram_size_x;
	static final int CANVAS_SIZE_Y = Vram._vram_size_y;

	static final boolean IF_DO_MOUSE_POSMOVE = false;


	static	Ragna	ragna;
	static	Music	gmdrv;
	static	Work	work;
	static	Init	init;
	static	Dos		dos;
	static	Main	main_loop;
	//static	Mouse	mouse;
	boolean		quit_thread	=	false;

	static	Fight	fight;

	static	boolean	fast_sync = false;		// PAGE_UP Fast Mode
	static	long	sync_interval = -1;
	static	long	sync_exec = -1;


	static	int		space_trig = 0;		// SPACE Pause

	public static void main(String[] args) {
		new Thread( (ragna = new Ragna()) ).start();
	}

	public	Ragna()
	{
		super("Ragnarekkr"); //Ragnarφkkr
		pack();
		
		setVisible(true);
		setVisible(false);
		pack();
		setResizable(false);
		pack();
		
		Dimension d = Toolkit.getDefaultToolkit().getScreenSize();
		setLocation( (d.width - CANVAS_SIZE_X)/2, (d.height - CANVAS_SIZE_Y)/2 );
		setSize( CANVAS_SIZE_X+getInsets().left + getInsets().right,
			CANVAS_SIZE_Y+getInsets().top + getInsets().bottom );
		addWindowListener( new WindowAdapter()
		{
			public void windowClosing( WindowEvent e)
			{
				gmdrv.closeMusic();
				gmdrv = null;

				System.exit(0);
			}
		});

		enableEvents(AWTEvent.MOUSE_EVENT_MASK);
		enableEvents(AWTEvent.MOUSE_MOTION_EVENT_MASK);
		enableEvents(AWTEvent.KEY_EVENT_MASK);

		work	=	new Work();
		dos		=	new	Dos();
		init	=	new	Init();
		Vram.setupVram();

		Const.constuction.clear();
		Pole.pole.clear();
		fight = new Fight();

		setVisible(true);

		gmdrv = new Music();

        // Erace Mouse Cursor
        Cursor cursor = Toolkit.getDefaultToolkit().createCustomCursor(
                new BufferedImage(1, 1, BufferedImage.TYPE_INT_ARGB),
                new Point(), "");
        setCursor(cursor);


		main_loop	=	new	Main();
		main_loop.start();
	}

	public	void	closeRagna()
	{
		quit_thread	=	true;
	}

	/* 
	 * @see java.lang.Runnable#run()
	 */
	public void run() {
		while(true)
		{
			if ( quit_thread ) break;
			// VSync 処理
			Mouse.MOUSE_();			// Mouse Move & Draw

			if ( Work.SUBADR != null )		// Entry Address 1
			{
				Work.SUBADR.proc();
			}
			if ( Work.SUBADR2 != null )		// Entry Address 2
			{
				Work.SUBADR2.proc();
			}
			if ( Work.SUBADR3 != null )		// Entry Address 3
			{
				Work.SUBADR3.proc();
			}

			if ( gmdrv != null )
			{
				gmdrv.execMusicProc();
			}
			
			// Key Input
			if ( (~Work.MS_BTN & Z80.Bit7) != 0 )
			{
				/*
				if ( Z80.BIT( 0 ,Work.SYS_FLAG2 ) != 0 )	// Key Repeat Flag (Ret / Space)
				{
					//KEY_REPEAT
					if ( ( Work.SPACE & 0x3f ) != 0 )	// Check  Repeat Timer
					{
						--Work.SPACE;			// Counter -1
						if ( Work.SPACE == 0 )
						{
							Work.SPACE	=	0x40+8;		// Repeat Counter Reset
						}
					}
					else
					{
						Work.SPACE	=	0x40+38;		// Repeat Counter Init
					}
				}
				else
				*/
				{
					Work.SPACE = Z80._SET( 6, Work.SPACE );		// Ret / Space ON
				}
			}
			else
			{
				Work.SPACE	&= 0x0c0;	// Clear Count expect "On Flug"
			}

			//-------  Esc Key  -------
			if ( (~Work.MS_BTN & Z80.Bit5) != 0 )
			{
				Work.SPACE = Z80._SET( 7, Work.SPACE );		// Esc ON
			}

			//------  (1/60) Counter -------
			if ( Work.INTER != 0 )		// Interrupt Count  -1
			{
				--Work.INTER;
			}

			Work.INTERJ++;

			Work.TIME_COUNT++;		// Time Counter +1

			Work.COUNTER_W	+=	0x20;	// Animate Counter  (1/8)  7.5/s
			Work.COUNTER = Work.COUNTER_W >> 8;

			// ReDraw
			repaint();

			//notifyAll();
			main_loop._notify();

			if ( quit_thread ) break;

			long sync_wait = 16 - Ragna.sync_exec;		// 1/60ms
			if ( sync_wait <= 0 ) sync_wait = 1;

			// 1/60ms
			try {
				if ( fast_sync ) {
					Thread.sleep(2);
				} else {
					Thread.sleep(sync_wait);
				}
				
			} catch( Exception e) {}
		}
	}

	Image backGrp = null;
	public void paint(Graphics g)
	{
		Graphics gbg;
		if (backGrp == null)
		{
			backGrp = createImage( CANVAS_SIZE_X, CANVAS_SIZE_Y );
		}
		gbg = backGrp.getGraphics();

		Image	ip;
		gbg.drawImage( Vram.loadVram(), 0, 0, this);
		ip = Mouse.loadMouse();
		if ( ip != null )
		{
			gbg.drawImage( ip, Work.MOUS_X, Work.MOUS_Y, this);
		}

		Mon.drawMon( gbg );

		g.drawImage(backGrp,getInsets().left,getInsets().top,this);
	}
	
	public void update(Graphics g)
	{
		paint(g);
	}

	public void processMouseEvent(MouseEvent e)
	{
	//		System.out.println("Mouse ID = " + e.getID());
		if ( e.getID() == MouseEvent.MOUSE_ENTERED)
		{
		}
		if ( e.getID() == MouseEvent.MOUSE_EXITED)
		{
		}
		if ( e.getID() == MouseEvent.MOUSE_PRESSED)
		{
			//System.out.println("Mouse Button = " + e.getButton());
			Mouse.setMouseButton( e.getButton(), 1 );
		}
		if ( e.getID() == MouseEvent.MOUSE_RELEASED)
		{
			Mouse.setMouseButton( e.getButton(), 0 );
		}
	}
	public void processMouseMotionEvent(MouseEvent e)
	{
		if ( e.getID() == MouseEvent.MOUSE_MOVED || e.getID() == MouseEvent.MOUSE_DRAGGED)
		{
			int	x	=	e.getX()-getInsets().left;
			int	y	=	e.getY()-getInsets().top;
			Mouse.setMousePosition( x, y );

			//Mon.locate(30,10);
			//Mon.println("x,y = "+x+","+y+":");
		}
	}

	public void processKeyEvent(KeyEvent e)
	{
		//System.out.println("Key ID = " + e.getID());
		if ( e.getID() == KeyEvent.KEY_RELEASED )
		{
			switch ( e.getKeyCode() ) {
			  case KeyEvent.VK_SHIFT:
			  case KeyEvent.VK_F:
				Work.KEYMEM_70H	|=	0x80;		// [Shift]
				break;
			  case KeyEvent.VK_PAGE_UP:
				  fast_sync = false;
				  break;
			  case KeyEvent.VK_SPACE:
				  space_trig &= ~0xc0;
				  break;
			}
		}
		if ( e.getID() == KeyEvent.KEY_PRESSED )
		{
			switch ( e.getKeyCode() ) {
			  case KeyEvent.VK_SHIFT:
			  case KeyEvent.VK_F:
				Work.KEYMEM_70H	&=	~0x80;		// [Shift]
				break;
			  case KeyEvent.VK_PAGE_UP:
				fast_sync = true;
				break;
			  case KeyEvent.VK_SPACE:
				  space_trig |= ((space_trig>>1) ^ 0x40) & 0x40;
				  space_trig |= 0x80;
				  break;
			}
		}
		//Mon.locate(30,1);
		//Mon.println("SH="+Work.KEYMEM_70H+"CT="+Work.KEYMEM_74H+"ST="+Work.KEYMEM_60H+"XX="+Work.KEYMEM_2AH);
		//System.out.println("Key = " + (e.getModifiersEx() & KeyEvent.SHIFT_DOWN_MASK));
	}
	
}