/*
 * @(#)MonthDemo.java
 *
 * Copyright (c) 2003-2004 Stand By Soft, Ltd. All rights reserved.
 *
 * This software is the proprietary information of Stand By Soft, Ltd.  
 * Use is subject to license terms.
 */
package com.standbysoft.demo.date;
import java.awt.Color;
import java.awt.Component;
import java.awt.Font;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.Insets;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;
import java.text.DateFormatSymbols;
import java.util.Calendar;
import java.util.Collections;
import java.util.Comparator;
import java.util.Locale;
import java.util.Vector;

import javax.swing.ButtonGroup;
import javax.swing.DefaultListCellRenderer;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JColorChooser;
import javax.swing.JComboBox;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JPanel;
import javax.swing.JRadioButton;
import javax.swing.JScrollPane;
import javax.swing.SwingConstants;
import javax.swing.border.TitledBorder;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;

import com.standbysoft.component.date.DateSelectionModel;
import com.standbysoft.component.date.DefaultDateSelectionModel;
import com.standbysoft.component.date.DateSelectionModel.SelectionMode;
import com.standbysoft.component.date.swing.DateRenderer;
import com.standbysoft.component.date.swing.DefaultDateRenderer;
import com.standbysoft.component.date.swing.DefaultMonthModel;
import com.standbysoft.component.date.swing.DefaultWeekModel;
import com.standbysoft.component.date.swing.JMonth;
import com.standbysoft.component.date.swing.MonthModel;
import com.standbysoft.component.date.swing.WeekModel;

/**
 * Shows the operations that can be performed on a <code>JMonth</code> or 
 <code>JMonthView</code> component.
 */
public class MonthDemo extends JPanel {
    /**
     * JMonth component for which this demo was created. It could be JMonth or JMonthView.
     */
    private JMonth month;

    public MonthDemo() {
        month = createMonth();
        
        setLayout(new GridBagLayout());
        
        add(month, new GridBagConstraints(00110.00.0, GridBagConstraints.NORTH, GridBagConstraints.HORIZONTAL, new Insets(8505)00));
        add(createFontsPanel()new GridBagConstraints(10111.00.0, GridBagConstraints.NORTH, GridBagConstraints.BOTH, new Insets(0505)00));
        add(createColorsPanel()new GridBagConstraints(20111.00.0, GridBagConstraints.NORTH, GridBagConstraints.BOTH, new Insets(0505)00));
        add(createMonthPanel()new GridBagConstraints(21121.00.0, GridBagConstraints.NORTH, GridBagConstraints.BOTH, new Insets(0555)00));
        add(createGridPanel()new GridBagConstraints(12111.00.0, GridBagConstraints.NORTH, GridBagConstraints.BOTH, new Insets(0555)00));
        add(createDateSelectionPanel()new GridBagConstraints(11111.00.0, GridBagConstraints.NORTH, GridBagConstraints.BOTH, new Insets(0555)00));
        add(new JLabel()new GridBagConstraints(03410.02.0, GridBagConstraints.NORTH, GridBagConstraints.BOTH, new Insets(0555)00));
    }

    /**
     * Create the <code>JMonth</code> component used by this demo.
     
     @return <code>JMonth</code> component used by this demo.
     */
    private JMonth createMonth() {
        return new JMonth();
    }
    
    /**
     * Creates a panel that controls the font for the component.
     
     @return actual panel
     */
    private JComponent createFontsPanel() {
        JScrollPane fontsPane = new JScrollPane();
        fontsPane.setBorder(new TitledBorder("Font"));

        Vector fonts = new Vector();
        fonts.add(new Font("Serif", Font.PLAIN, 10));
        fonts.add(new Font("Arial", Font.PLAIN, 10));
        fonts.add(new Font("Serif", Font.PLAIN, 12));
        fonts.add(new Font("Arial", Font.ITALIC, 12));
        fonts.add(new Font("Courier", Font.PLAIN, 13));
        fonts.add(new Font("Serif", Font.PLAIN, 13));
        fonts.add(new Font("Arial", Font.PLAIN, 14));
        fonts.add(month.getFont());
        Collections.sort(fonts, new Comparator() {
            public int compare(Object o1, Object o2) {
                Font f1 = (Fonto1;
                Font f2 = (Fonto2;

                return f1.getSize() - f2.getSize();
            }
        });
        
        final JList fontsList = new JList(fonts);
        month.setFont((Font)fonts.get(fonts.size() 1));
        fontsList.setSelectedValue(month.getFont()true);
        
        fontsList.setVisibleRowCount(5);
        fontsList.addListSelectionListener(new ListSelectionListener() {
            public void valueChanged(ListSelectionEvent evt) {
                    Font font = (FontfontsList.getSelectedValue();
                    month.setFont(font);
            }
        });
        fontsList.setCellRenderer(new DefaultListCellRenderer() {
            public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
                JLabel l = (JLabelsuper.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus);
                Font font = (Fontvalue;
                l.setFont(font);
                l.setText(font.getName() " " + font.getSize());

                return l;
            }
        });
        
        fontsPane.setViewportView(fontsList);
        
        return fontsPane;
    }

    /**
     * Creates a panel that controls the colors for the component.
     
     @return actual panel
     */
    private JPanel createColorsPanel() {
        JPanel colorsPanel = new JPanel();
        colorsPanel.setBorder(new TitledBorder("Colors"));
        colorsPanel.setLayout(new GridBagLayout());

        month.setForeground(Color.black);
        month.setTitleBackground(new Color(0114255));
        month.setTitleForeground(Color.white);
        month.setTrailingForeground(Color.gray);
        month.setMonthBackground(Color.white);
        
        JLabel foregroundLabel = new JLabel("Foreground:");
        foregroundLabel.setDisplayedMnemonic('o');
        final JButton foregroundButton = new JButton(" ");
        foregroundLabel.setLabelFor(foregroundButton);
        foregroundButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                Color color = JColorChooser.showDialog(MonthDemo.this, "Choose Foreground", month.getForeground());
                if (color != null) {
                    month.setForeground(color);
                    foregroundButton.setBackground(month.getForeground());
                }
            }
        });
        foregroundButton.setBackground(month.getForeground());
        
        JLabel titleBackgroundLabel = new JLabel("Title Background:");
        final JButton titleBackgroundButton = new JButton(" ");
        titleBackgroundLabel.setDisplayedMnemonic('b');
        titleBackgroundLabel.setLabelFor(titleBackgroundButton);
        titleBackgroundButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                Color color = JColorChooser.showDialog(MonthDemo.this, "Choose Title Background", month.getTitleBackground());
                if (color != null) {
                    month.setTitleBackground(color);
                    titleBackgroundButton.setBackground(month.getTitleBackground());
                }
            }
        });
        titleBackgroundButton.setBackground(month.getTitleBackground());
        
        JLabel titleForegroundLabel = new JLabel("Title Foreground:");
        final JButton titleForegroundButton = new JButton(" ");
        titleForegroundLabel.setDisplayedMnemonic('r');
        titleForegroundLabel.setLabelFor(titleForegroundButton);
        titleForegroundButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                Color color = JColorChooser.showDialog(MonthDemo.this, "Choose Title Foreground", month.getTitleForeground());
                if (color != null) {
                    month.setTitleForeground(color);
                    titleForegroundButton.setBackground(month.getTitleForeground());
                }
            }
        });
        titleForegroundButton.setBackground(month.getTitleForeground());
        
        JLabel trailingForegroundLabel = new JLabel("Trailing Foreground:");
        final JButton trailingForegroundButton = new JButton(" ");
        trailingForegroundLabel.setDisplayedMnemonic('t');
        trailingForegroundLabel.setLabelFor(trailingForegroundButton);
        trailingForegroundButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                Color color = JColorChooser.showDialog(MonthDemo.this, "Choose Trailing Foreground", month.getTrailingForeground());
                if (color != null) {
                    month.setTrailingForeground(color);
                    trailingForegroundButton.setBackground(month.getTrailingForeground());
                }
            }
        });
        trailingForegroundButton.setBackground(month.getTrailingForeground());
        
        JLabel monthBackgroundLabel = new JLabel("Month Background:");
        final JButton monthBackgroundButton = new JButton(" ");
        monthBackgroundLabel.setDisplayedMnemonic('m');
        monthBackgroundLabel.setLabelFor(monthBackgroundButton);
        monthBackgroundButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                Color color = JColorChooser.showDialog(MonthDemo.this, "Choose Month Background", month.getMonthBackground());
                if (color != null) {
                    month.setMonthBackground(color);
                    monthBackgroundButton.setBackground(month.getMonthBackground());
                }
            }
        });
        monthBackgroundButton.setBackground(month.getMonthBackground());

        colorsPanel.add(foregroundLabel, new GridBagConstraints(00111.00.0, GridBagConstraints.NORTH, GridBagConstraints.HORIZONTAL, new Insets(0555)00));
        colorsPanel.add(foregroundButton, new GridBagConstraints(10110.00.0, GridBagConstraints.NORTH, GridBagConstraints.NONE, new Insets(0555)00));
        colorsPanel.add(titleBackgroundLabel, new GridBagConstraints(01111.00.0, GridBagConstraints.NORTH, GridBagConstraints.HORIZONTAL, new Insets(0555)00));
        colorsPanel.add(titleBackgroundButton, new GridBagConstraints(11110.00.0, GridBagConstraints.NORTH, GridBagConstraints.NONE, new Insets(0555)00));
        colorsPanel.add(titleForegroundLabel, new GridBagConstraints(02111.00.0, GridBagConstraints.NORTH, GridBagConstraints.HORIZONTAL, new Insets(0555)00));
        colorsPanel.add(titleForegroundButton, new GridBagConstraints(12110.00.0, GridBagConstraints.NORTH, GridBagConstraints.NONE, new Insets(0555)00));
        colorsPanel.add(trailingForegroundLabel, new GridBagConstraints(03111.00.0, GridBagConstraints.NORTH, GridBagConstraints.HORIZONTAL, new Insets(0555)00));
        colorsPanel.add(trailingForegroundButton, new GridBagConstraints(13110.00.0, GridBagConstraints.NORTH, GridBagConstraints.NONE, new Insets(0555)00));
        colorsPanel.add(monthBackgroundLabel, new GridBagConstraints(04111.00.0, GridBagConstraints.NORTH, GridBagConstraints.HORIZONTAL, new Insets(0555)00));
        colorsPanel.add(monthBackgroundButton, new GridBagConstraints(14110.00.0, GridBagConstraints.NORTH, GridBagConstraints.NONE, new Insets(0555)00));
        colorsPanel.add(new JLabel()new GridBagConstraints(05211.01.0, GridBagConstraints.NORTH, GridBagConstraints.BOTH, new Insets(0555)00));
        
        return colorsPanel;
    }

    /**
     * Creates a panel that controls specific month features.
     
     @return actual panel
     */
    private JPanel createMonthPanel() {
        final DateRenderer defaultDateRenderer = new DefaultDateRenderer();
        final DateRenderer weekendDateRenderer = new CustomWeekendDateRenderer();
        final DateRenderer specialDateRenderer = new CustomSpecialDateRenderer();
        final DateRenderer squareDateRenderer = new CustomDateRenderer();
        
        JPanel monthPanel = new JPanel();
        monthPanel.setLayout(new GridBagLayout());
        monthPanel.setBorder(new TitledBorder("Month"));
                
        JLabel rendererLabel = new JLabel("Date Renderer:");
        rendererLabel.setFont(rendererLabel.getFont().deriveFont(Font.BOLD));
        final JComboBox rendererComboBox = new JComboBox(new String[]{"Default""Highlight Weekend Days""Highlight Special Dates""Square Selected Dates"});
        rendererComboBox.addItemListener(new ItemListener() {
            public void itemStateChanged(ItemEvent evt) {
                int index = rendererComboBox.getSelectedIndex();
                
                if (evt.getStateChange() == ItemEvent.SELECTED) {
                    if (index == 0) {
                        month.setDateRenderer(defaultDateRenderer);
                    else if (index == 1) {
                        month.setDateRenderer(weekendDateRenderer);
                    else if (index == 2) {
                        month.setDateRenderer(specialDateRenderer);
                    else if (index == 3) {
                        month.setDateRenderer(squareDateRenderer);
                    }
                }
            }
        });
        rendererComboBox.setSelectedIndex(1);

        final JCheckBox trailingPreviousEnabled = new JCheckBox("Enable Previous Month Dates", month.isTrailingPreviousEnabled());
        trailingPreviousEnabled.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                month.setTrailingPreviousEnabled(trailingPreviousEnabled.isSelected());
            }
        });
        
        final JCheckBox trailingNextEnabled = new JCheckBox("Enable Next Month Dates", month.isTrailingNextEnabled());
        trailingNextEnabled.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                month.setTrailingNextEnabled(trailingNextEnabled.isSelected());
            }
        });

        final JCheckBox weekNumbersVisible = new JCheckBox("Show Week Numbers", month.isWeekNumbersVisible());
        weekNumbersVisible.setMnemonic('n');
        weekNumbersVisible.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                month.setWeekNumbersVisible(weekNumbersVisible.isSelected());
            }
        });
        
        final JCheckBox weekNamesVisible = new JCheckBox("Show Day Names", month.isWeekNamesVisible());
        weekNamesVisible.setMnemonic('n');
        weekNamesVisible.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                month.setWeekNamesVisible(weekNamesVisible.isSelected());
            }
        });

        final JLabel dowFirstLabel = new JLabel("Week Starts On:");
        dowFirstLabel.setDisplayedMnemonic('s');

        final JComboBox dowFirstComboBox = new JComboBox();
        dowFirstLabel.setLabelFor(dowFirstComboBox);
        dowFirstComboBox.addItem(new Integer(Calendar.SUNDAY));
        dowFirstComboBox.addItem(new Integer(Calendar.MONDAY));
        dowFirstComboBox.addItem(new Integer(Calendar.TUESDAY));
        dowFirstComboBox.addItem(new Integer(Calendar.WEDNESDAY));
        dowFirstComboBox.addItem(new Integer(Calendar.THURSDAY));
        dowFirstComboBox.addItem(new Integer(Calendar.FRIDAY));
        dowFirstComboBox.addItem(new Integer(Calendar.SATURDAY));
        dowFirstComboBox.setSelectedItem(new Integer(month.getDowFirst()));
        dowFirstComboBox.addItemListener(new ItemListener() {
            public void itemStateChanged(ItemEvent evt) {
                if (evt.getStateChange() == ItemEvent.SELECTED) {
                    Integer df = (IntegerdowFirstComboBox.getSelectedItem();
                    month.setDowFirst(df.intValue());
                }
            }
        });
        dowFirstComboBox.setRenderer(new DefaultListCellRenderer() {
            private String DAY_NAMES[] new DateFormatSymbols().getWeekdays();

            public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
                JLabel l = (JLabelsuper.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus);
                Integer day = (Integervalue;
                l.setText(DAY_NAMES[day.intValue()]);

                return l;
            }
        });
        
        final JLabel localeLabel = new JLabel("Locale:");
        localeLabel.setDisplayedMnemonic('l');
        final JComboBox localeComboBox = new JComboBox(Locale.getAvailableLocales());
        localeLabel.setLabelFor(localeComboBox);

        localeComboBox.setSelectedItem(month.getLocale());
        localeComboBox.addItemListener(new ItemListener() {
            public void itemStateChanged(ItemEvent evt) {
                if (evt.getStateChange() == ItemEvent.SELECTED) {
                    Locale locale = (LocalelocaleComboBox.getSelectedItem();
                    dowFirstComboBox.setSelectedItem(new Integer(Calendar.getInstance(locale).getFirstDayOfWeek()));
                    month.setLocale(locale);
                }
            }
        });
        localeComboBox.setRenderer(new DefaultListCellRenderer() {
            public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
                JLabel l = (JLabelsuper.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus);
                Locale locale = (Localevalue;
                l.setText(locale.getDisplayName());

                return l;
            }
        });

        final MonthModel defaultMonthModel = new DefaultMonthModel();
        final MonthModel latinMonthModel = new LatinMonthModel();
        
        final WeekModel defaultWeekModel = new DefaultWeekModel();
        final WeekModel latinWeekModel = new LatinWeekModel();
        
        final JLabel weekMonthModelLabel = new JLabel("Week & Month Models:");
        final JComboBox weekMonthModelComboBox = new JComboBox(new String[] {"Default""Latin Names"});
        weekMonthModelLabel.setLabelFor(weekMonthModelComboBox);

        month.setMonthModel(defaultMonthModel);
        month.setWeekModel(defaultWeekModel);
        weekMonthModelComboBox.addItemListener(new ItemListener() {
            public void itemStateChanged(ItemEvent evt) {
                if (evt.getStateChange() == ItemEvent.SELECTED) {
                    localeLabel.setEnabled(true);
                    localeComboBox.setEnabled(true);
                    
                    if (weekMonthModelComboBox.getSelectedIndex() == 0) {
                        month.setMonthModel(defaultMonthModel);
                        month.setWeekModel(defaultWeekModel);
                    else if (weekMonthModelComboBox.getSelectedIndex() == 1) {
                        localeLabel.setEnabled(false);
                        localeComboBox.setEnabled(false);
                        month.setMonthModel(latinMonthModel);
                        month.setWeekModel(latinWeekModel);
                    }
                }
            }
        });
        
        JLabel datesOrientationLabel = new JLabel("Orientation:");
        final JRadioButton datesOrientationHorizontalRadioButton = new JRadioButton("Horizontal");
        JRadioButton datesOrientationVerticalRadioButton = new JRadioButton("Vertical");
        
        ButtonGroup datesOrientationButtonGroup = new ButtonGroup();
        datesOrientationButtonGroup.add(datesOrientationHorizontalRadioButton);
        datesOrientationButtonGroup.add(datesOrientationVerticalRadioButton);
        
        datesOrientationHorizontalRadioButton.setSelected(month.getDatesOrientation() == SwingConstants.HORIZONTAL);
        
        datesOrientationHorizontalRadioButton.addChangeListener(new ChangeListener() {
            public void stateChanged(ChangeEvent e) {
                month.setDatesOrientation(datesOrientationHorizontalRadioButton.isSelected()?SwingConstants.HORIZONTAL:SwingConstants.VERTICAL);
            }
        });
        
        monthPanel.add(weekNamesVisible, new GridBagConstraints(00211.00.0, GridBagConstraints.CENTER, GridBagConstraints.HORIZONTAL, new Insets(0555)00));
        monthPanel.add(weekNumbersVisible, new GridBagConstraints(01211.00.0, GridBagConstraints.CENTER, GridBagConstraints.HORIZONTAL, new Insets(0555)00));
        monthPanel.add(trailingNextEnabled, new GridBagConstraints(02211.00.0, GridBagConstraints.CENTER, GridBagConstraints.HORIZONTAL, new Insets(0555)00));
        monthPanel.add(trailingPreviousEnabled, new GridBagConstraints(03211.00.0, GridBagConstraints.CENTER, GridBagConstraints.HORIZONTAL, </