view src/junotu/TabOptions.java @ 111:b93c6236c6cb

TabOptions: Minor progress
author Fox
date Thu, 15 Jun 2023 00:53:55 +0200
parents e4588b8a8ddc
children 9bf9fd26bb33
line wrap: on
line source

package junotu;

import java.util.Vector;

import java.awt.Component;
import javax.swing.JPanel;
import javax.swing.Box;
import javax.swing.JScrollPane;
import javax.swing.JButton;

import java.awt.BorderLayout;
import java.awt.FlowLayout;
import javax.swing.BoxLayout;

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

import junotu.Main;
import junotu.Window.TabInterface;
import junotu.OptionTree;
import junotu.Card;

public class TabOptions extends JPanel implements ActionListener, TabInterface {

	private static final String ACTION_PATH_BUTTON = "path_button";

	private static class Option extends JPanel implements ActionListener {
		TabOptions events;

		@Override
		public void actionPerformed( ActionEvent e )
		{
			if( events != null ) {
				events.actionPerformed( new ActionEvent( this, e.getID(), e.getActionCommand(), e.getWhen(), e.getModifiers() ) );
			}
		}
	}

	private static class OptionFolder extends Option {
	
		OptionTree.OptionFolder folder;
		
		public OptionFolder( TabOptions events_, OptionTree.OptionFolder folder_ )
		{
			setLayout( new BoxLayout( this, BoxLayout.X_AXIS ) );
			events = events_;
			folder = folder_;
			
			JButton button = new JButton( folder.brief );
			
			this.add(button);
			
			if( folder.hint.length() > 0 ) {
				button.setToolTipText( folder.hint );
			}
			
			button.addActionListener(this);
		}
	}
	private static class OptionCategory extends Option {}
	private static class OptionCheckbox extends Option {}
	private static class OptionSlider extends Option {}
	private static class OptionNumberCounter extends Option {}
	private static class OptionString extends Option {}
	private static class OptionAction extends Option {}

	static public final OptionTree OPTION_TREE;
	static {
		OPTION_TREE = new OptionTree();
		OPTION_TREE.root = new OptionTree.OptionFolder( Main.PROGRAM_NAME, Main.PROGRAM_NAME+" options." );
		
		OptionTree.OptionFolder f1 = OPTION_TREE.add( new OptionTree.OptionFolder( "1", "Folder one." ) );
		OptionTree.OptionFolder f2 = OPTION_TREE.add( new OptionTree.OptionFolder( "2", "Folder two." ) );
		OptionTree.OptionFolder f3 = OPTION_TREE.add( new OptionTree.OptionFolder( "3", "Folder three." ) );
		OptionTree.OptionFolder developer = OPTION_TREE.add( new OptionTree.OptionFolder(
			"Development / Internal",
			"Development-related options. Be careful, those options were not designed with safety or intutiveness in mind. "+
			"Misusing them could corrupt your card database."
		) );
		
		f1.add( new OptionTree.OptionFolder( "1.1", "Folder one one." ) );
		f1.add( new OptionTree.OptionFolder( "1.2", "Folder one two." ) );
		f1.add( new OptionTree.OptionFolder( "1.3", "Folder one three." ) );
		
		f2.add( new OptionTree.OptionFolder( "2.1", "Folder two one." ) );
		f2.add( new OptionTree.OptionFolder( "2.2", "Folder two two." ) );
		f2.add( new OptionTree.OptionFolder( "2.3", "Folder two three." ) );
		
		f3.add( new OptionTree.OptionFolder( "3.1", "Folder three one." ) );
		f3.add( new OptionTree.OptionFolder( "3.2", "Folder three two." ) );
		f3.add( new OptionTree.OptionFolder( "3.3", "Folder three three." ) );
		
		developer.add( new OptionTree.OptionCheckbox(
			Card.TAG_OPTION_PREFIX+"show_internal_tags",
			"Show 'internal' tags.",
			"Show tags prefixed with '_', which are normally hidden.",
			false
		) );
		
		developer.add( new OptionTree.OptionCategory( "Actions", "" ) );
		
		developer.add( new OptionTree.OptionAction(
			"Resave all cards",
			"Go over the whole card database, load each card and save each card. "+
			"Does not update user edit timestamp, meaning card ordering should not change on the search page. "+
			"This might be a useful thing to run after changing "+Main.PROGRAM_NAME+" version (updating or downgrading)."
		) );
		
	}

	public Card card;
	public Vector<OptionTree.OptionFolder> path = new Vector<OptionTree.OptionFolder>();

	JPanel pathBox;
	Box optionList;

	public TabOptions()
	{
		setLayout( new BorderLayout() );
		pathBox = new JPanel();
		optionList = Box.createVerticalBox();
		JScrollPane scroll = new JScrollPane(optionList);
		JButton apply = new JButton("Apply");
		
		pathBox.setLayout( new FlowLayout( FlowLayout.LEFT ) );
		
		add( pathBox, BorderLayout.NORTH );
		add( scroll, BorderLayout.CENTER );
		add( apply, BorderLayout.SOUTH );
		
		path.add( OPTION_TREE.root );
		
		scroll.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);
		
	}

	@Override
	public void onSwitchedTo()
	{
		generate();
	}

	public void generate()
	{
		optionList.removeAll();
		pathBox.removeAll();
		OptionTree.OptionFolder page = path.get( path.size()-1 );
		for( int i = 0; i < page.options.size(); i++ ) {
			OptionTree.Option<?> option = page.options.get(i);
			if( option instanceof OptionTree.OptionFolder ) {
				optionList.add( new OptionFolder( this, (OptionTree.OptionFolder)option ) );
			} else {
				System.out.print( "TabOptions, generate: Unknown option type '"+option.getClass().getName()+"', cannot create interface.\n" );
			}
		}
		optionList.add( Box.createVerticalGlue() );
		for( int i = 0; i < path.size(); i++ ) {
			JButton button = new JButton( path.get(i).brief );
			pathBox.add( button );
			button.setActionCommand( ACTION_PATH_BUTTON );
			button.addActionListener(this);
			if( path.get(i).hint.length() > 0 ) {
				button.setToolTipText( path.get(i).hint );
			}
		}
		pathBox.add( Box.createHorizontalGlue() );
		
		revalidate();
		repaint();
	}

	public void actionPerformed( ActionEvent e )
	{
		Object source = e.getSource();
		String command = e.getActionCommand();

		switch( command ) {
			case ACTION_PATH_BUTTON: {
				Component[] buttons = pathBox.getComponents();
				for( int i = 0; i < buttons.length; i++ ) {
					if( buttons[i] == source ) {
						path.setSize( i+1 );
						generate();
						return;
					}
				}
			}
		}

		if( source instanceof OptionFolder ) {
			OptionFolder clicked = (OptionFolder)source;
			path.add( clicked.folder );
			generate();
		}
	}

}