//  $Id: SimpleViewer.java,v 1.20 2004/04/27 18:18:34 moreland Exp $
//
//  Copyright 2000-2004 The Regents of the University of California.
//  All Rights Reserved.
//
//  Permission to use, copy, modify and distribute any part of this
//  Molecular Biology Toolkit (MBT)
//  for educational, research and non-profit purposes, without fee, and without
//  a written agreement is hereby granted, provided that the above copyright
//  notice, this paragraph and the following three paragraphs appear in all
//  copies.
//
//  Those desiring to incorporate this MBT into commercial products
//  or use for commercial purposes should contact the Technology Transfer &
//  Intellectual Property Services, University of California, San Diego, 9500
//  Gilman Drive, Mail Code 0910, La Jolla, CA 92093-0910, Ph: (858) 534-5815,
//  FAX: (858) 534-7345, E-MAIL:invent@ucsd.edu.
//
//  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR
//  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES, INCLUDING
//  LOST PROFITS, ARISING OUT OF THE USE OF THIS MBT, EVEN IF THE
//  UNIVERSITY OF CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
//
//  THE MBT PROVIDED HEREIN IS ON AN "AS IS" BASIS, AND THE
//  UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT,
//  UPDATES, ENHANCEMENTS, OR MODIFICATIONS. THE UNIVERSITY OF CALIFORNIA MAKES
//  NO REPRESENTATIONS AND EXTENDS NO WARRANTIES OF ANY KIND, EITHER IMPLIED OR
//  EXPRESS, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
//  MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, OR THAT THE USE OF THE
//  MBT WILL NOT INFRINGE ANY PATENT, TRADEMARK OR OTHER RIGHTS.
//  
//  For further information, please see:  http://mbt.sdsc.edu
//  
//  History:
//  $Log: SimpleViewer.java,v $
//  Revision 1.20  2004/04/27 18:18:34  moreland
//  Added edu.sdsc.vis.viewers.Java3dCheck calls to check for Java3D installation.
//
//  Revision 1.19  2004/04/21 23:19:02  moreland
//  Added Java3dCheck code.
//
//  Revision 1.18  2004/04/08 23:55:07  moreland
//  Updated copyright to new UCSD wording.
//
//  Revision 1.17  2004/03/09 17:28:22  moreland
//  Added check to prevent call to System.exit() when running as an applet.
//
//  Revision 1.16  2004/01/30 02:07:36  moreland
//  Updated copyright and class block comments.
//
//  Revision 1.15  2004/01/30 01:59:25  moreland
//  Simplified load from pdbid code.
//
//  Revision 1.14  2003/05/01 16:06:13  moreland
//  Added support for "-p pdbid" option (really just uses the URL loader).
//
//  Revision 1.13  2003/04/24 00:36:42  moreland
//  Error condition for no dataset loaded is now handled better.
//
//  Revision 1.12  2003/02/21 23:03:09  moreland
//  Changed example URL load -u command line option to point to beta repository:
//  ftp://beta.rcsb.org/pub/pdb/uniformity/data/mmCIF.gz/all/5ebx.cif.gz
//
//  Revision 1.11  2003/02/21 22:07:42  moreland
//  Added SequenceViewer module (very basic for now).
//
//  Revision 1.10  2003/02/03 22:03:50  moreland
//  Added support for MBT Status class to output run-time messages.
//  Added "MBT" to application/frame title.
//
//  Revision 1.9  2003/01/27 20:45:18  moreland
//  Added code to example programs in order to support standardized command
//  line arguments for data-set loading from files, URLs or PDB-ID codes.
//
//  Revision 1.8  2003/01/14 00:14:25  moreland
//  The TreeViewer code has been temporarily commented out
//  in order to deploy the most basic 3D Structure viewer.
//
//  Revision 1.7  2003/01/13 23:34:32  moreland
//  Added applet parameter and application option processing code.
//  Added code to support loading data from a "file", "url", or "pdbid" property.
//  Added copyright statement.
//
//  Revision 1.0  2002/10/24 17:54:01  moreland
//  


// Core
import java.applet.*;
import java.util.*;  // Hashtable and Enumeration
import java.io.File;
import java.net.*;

// GUI
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;

// MBT
import edu.sdsc.mbt.*;
import edu.sdsc.mbt.io.*;
import edu.sdsc.mbt.viewables.*;
import edu.sdsc.mbt.viewers.*;
import edu.sdsc.mbt.util.*;


/**
 *  This class is the main SimpleViewer application class.
 *  It provides a frame with a menubar and a StructureViewer.
 *  <P>
 *  @author	John L. Moreland
 */
public class SimpleViewer
	extends Applet
{
	// GUI
	protected JFrame simpleViewerFrame = null;
	protected Container simpleViewerFrameContainer = null;
	private StatusPanel statusPanel = null;

	// Viewers
	private StructureViewer structureViewer = null;
	private TreeViewer treeViewer = null;

	// Runtime properties (options or parameters)
	private Properties properties = new Properties( );

	// Applet
	private Applet applet = null;


	/*********************************************************************/
	/***************************  ENTRY POINTS  **************************/
	/*********************************************************************/


	/*********************************************************************/
	/*                                                                   */
	/*  The main program entry point when invoked as an application.     */
	/*                                                                   */
	/*********************************************************************/
	public static void main( String[] args )
	{
		SimpleViewer simpleViewer = new SimpleViewer();
		if ( args != null )
		{
			for ( int i=0; i<args.length; i++ )
			{
				if ( args[i].equals( "-f" ) )
					simpleViewer.properties.setProperty( "file", args[++i] );
				if ( args[i].equals( "-u" ) )
					simpleViewer.properties.setProperty( "url", args[++i] );
				if ( args[i].equals( "-p" ) )
					simpleViewer.properties.setProperty( "pdbid", args[++i] );
			}
		}
		simpleViewer.initialize();
	}


	/*********************************************************************/
	/*                                                                   */
	/*  The main program entry point when invoked as an applet.          */
	/*                                                                   */
	/*********************************************************************/
	public void init()
	{
		applet = this;
		String value;
		String propertyNames[] = { "file", "url", "pdbid" };

		for ( int i=0; i<propertyNames.length; i++ )
		{
			value = applet.getParameter( propertyNames[i] );
			if ( value != null )
				properties.setProperty( propertyNames[i], value );
		}

		initialize();
	}


	/*********************************************************************/
	/**************************  INITIALIZATION  *************************/
	/*********************************************************************/


	/**
	 *  Initializes the SimpleViewer.
	 */
	public void initialize()
	{
		// Since this application uses the MBT StructureViewer,
		// make sure that Java3D is installed before continuing.
		if ( ! edu.sdsc.vis.viewers.Java3dCheck.isInstalled() )
		{
			// Display instructions for the user about installing Java3D.
			String urlString =
				edu.sdsc.vis.viewers.Java3dCheck.showInstallInfo( );
			if ( urlString != null )
			{
				try
				{
					edu.sdsc.mbt.util.BrowserLauncher.openURL( urlString );
				}
				catch( java.io.IOException e )
				{
					Status.output( Status.LEVEL_ERROR, "BrowserLauncher.openURL failed: " + e );
				}
			}
			destructor( );
			return;
		}

		// Build the frame
		simpleViewerFrame = new JFrame( "SimpleViewer" );
		simpleViewerFrameContainer = simpleViewerFrame.getContentPane();
		simpleViewerFrame.setSize( 640, 480 );
		simpleViewerFrameContainer.setLayout( new BorderLayout() );

		// Create a StatusPanel
		statusPanel = new StatusPanel( );
		simpleViewerFrameContainer.add( BorderLayout.SOUTH, statusPanel );

		// Create a StructureViewer
		structureViewer = new StructureViewer( );
		simpleViewerFrameContainer.add( BorderLayout.CENTER, structureViewer );

		// Create a SequenceViewer
		SequenceViewer sequenceViewer = new SequenceViewer( );
		simpleViewerFrameContainer.add( BorderLayout.NORTH, sequenceViewer );
/*
	// JLM NOTICE: The TreeViewer code has been temporarily commented out
	// in order to deploy the most basic 3D Structure viewer.
		// Create a TreeViewer
		treeViewer = new TreeViewer( );

		// Create a JSplitPane to hold a TreeViewer and StructureViewer
		JSplitPane splitPane = new JSplitPane( JSplitPane.HORIZONTAL_SPLIT,
			treeViewer, structureViewer );
		splitPane.setOneTouchExpandable( true );
		splitPane.setDividerLocation( 512 );
		simpleViewerFrameContainer.add( BorderLayout.CENTER, splitPane );

		// Create a menu area
		// simpleViewerFrameContainer.add( BorderLayout.NORTH, new JLabel( "Menubar" ) );

		// Create a toolbar area
		// simpleViewerFrameContainer.add( "East", new JLabel( "Toolbar" ) );
*/

		// Pack the frame
		simpleViewerFrame.pack();
		simpleViewerFrame.validate();
		simpleViewerFrame.setSize( 640, 480 );
		simpleViewerFrame.setVisible( true );

		// Make sure we clean up if the user hits the close box
		WindowAdapter closer = new WindowAdapter()
		{
			public void windowClosing( WindowEvent event )
			{
				destructor();
			}
		};
		simpleViewerFrame.addWindowListener( closer );


		//
		// See if the runtime properties specify a Structure to load.
		//

		Structure structure = null;
		String dataset = null;
		if ( properties.getProperty( "file" ) != null )
		{
			dataset = properties.getProperty( "file" );
			// System.err.println( "file = " + dataset );
			structure = StructureFactory.load( new File( dataset ) );
		}
		else if ( properties.getProperty( "url" ) != null )
		{
			dataset = properties.getProperty( "url" );
			// System.err.println( "url = " + dataset );
			try
			{
				structure = StructureFactory.load( new URL( dataset ) );
			}
			catch ( MalformedURLException e )
			{
				Status.output( Status.LEVEL_ERROR, e.toString() );
			}
		}
		else if ( properties.getProperty( "pdbid" ) != null )
		{
			dataset = properties.getProperty( "pdbid" );
			// System.err.println( "pdbid = " + dataset );
			structure = StructureFactory.load( dataset.toLowerCase() );
		}

		if ( dataset == null )
		{
			Status.output( Status.LEVEL_REMARK, "No data set specified!" );
			System.exit( 1 );
		}

		if ( structure == null )
		{
			Status.output( Status.LEVEL_REMARK, "Could not load: " + dataset );
			System.exit( 2 );
		}

		Status.output( Status.LEVEL_REMARK, "Data set loaded: " + dataset );

		// Show the Structure's UrlString in the title bar.
		simpleViewerFrame.setTitle( "MBT SimpleViewer: " + structure.getUrlString() );

		// View the Structure
		StructureDocument structureDocument = new StructureDocument( );
		structureDocument.addStructure( structure );
		structureDocument.addViewer( structureViewer );
		structureDocument.addViewer( sequenceViewer );
		// structureDocument.addViewer( treeViewer );
	}


	/*********************************************************************/
	/*                                                                   */
	/*  Quits the application.                                           */
	/*                                                                   */
	/*********************************************************************/
	private boolean destroyed = false;
	public void destructor()
	{
		if ( ! destroyed )
		{
			destroyed = true;
			// Do cleanup here...
		}
		if ( applet == null )
			System.exit( 0 );
	}
}

