/*
 * Copyright 2011 Luke Usherwood.
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License as published by
 * the Free Software Foundation, either version 2.1 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

package net.bettyluke.tracinstant.ui;

import java.awt.Dimension;
import java.awt.Window;
import java.awt.event.HierarchyEvent;
import java.util.List;

import javax.swing.Box;
import javax.swing.BoxLayout;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JComponent;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JPasswordField;
import javax.swing.JTextField;
import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;

import net.bettyluke.tracinstant.prefs.SiteSettings;
import net.bettyluke.tracinstant.prefs.TracInstantProperties;

public class TracUrlSelectionPanel extends JPanel {

    private final JComboBox<String> url = createCombo();
    private final JTextField username = new JTextField();
    private final JPasswordField password = new JPasswordField();
    private final JComboBox<String> attachmentsDir = createCombo();
    private final JCheckBox fetchActiveTickets = new JCheckBox("Fetch only active tickets");
    private final JCheckBox instantRestart = new JCheckBox(
            "Instant restart (store downloaded data locally)");
    private final JCheckBox rememberPassword = new JCheckBox("Remember password: ");

    private static JComboBox<String> createCombo() {
        JComboBox<String> combo = new JComboBox<>();
        combo.setPreferredSize(new Dimension(400, combo.getPreferredSize().height));
        combo.setEditable(true);
        return combo;
    }

    public SiteSettings showAsDialog(Window parentWindow) {
        int opt = JOptionPane.showConfirmDialog(
            parentWindow,
            this,
            "Trac server settings",
            JOptionPane.OK_CANCEL_OPTION,
            JOptionPane.QUESTION_MESSAGE);

        if (opt != JOptionPane.OK_OPTION) {
            return null;
        }

        // Record the selected button for text time.
        TracInstantProperties.get().putInt("MasterQuery", opt);

        SiteSettings result = SiteSettings.getInstance();
        result.setUsername(username.getText().trim());
        result.setPassword(new String(password.getPassword()));
        result.setRememberPassword(rememberPassword.isSelected());
        result.setURL(getURLText());
        result.setAttachmentsDir(getAttachmentsDirText());
        result.setCacheData(instantRestart.isSelected());
        result.setFetchOnlyActiveTickets(fetchActiveTickets.isSelected());
        return result;
    }

    private void prepareForDisplay() {
        if (url.getSelectedItem() == null || "".equals(url.getSelectedItem())) {
            url.requestFocusInWindow();
        } else if (username.getText().trim().isEmpty()) {
            username.requestFocusInWindow();
        } else {
            password.requestFocusInWindow();
            password.selectAll();
        }
    }

    public TracUrlSelectionPanel(SiteSettings settings) {

        fetchActiveTickets.setSelected(settings.isFetchOnlyActiveTickets());
        instantRestart.setSelected(settings.isCacheData());

        username.setText(settings.getUsername());
        password.setText(settings.getPassword());
        rememberPassword.setSelected(settings.isRememberPassword());
        url.setSelectedItem(settings.getURL());
        attachmentsDir.setSelectedItem(settings.getAttachmentsDir());

        setLayout(new BoxLayout(this, BoxLayout.Y_AXIS));

        add(Box.createVerticalStrut(8));
        addRow("Trac url:", url);
        add(Box.createVerticalStrut(8));
        addRow("Username (if required):", username);
        add(Box.createVerticalStrut(8));
        addRow("Password:", password);
        add(rememberPassword);
        add(Box.createVerticalStrut(8));
        addRow("Additional attachments directory (optional):", attachmentsDir);
        add(Box.createVerticalStrut(16));
        add(fetchActiveTickets);
        add(Box.createVerticalStrut(8));
        add(instantRestart);
        add(Box.createVerticalStrut(16));

        addHierarchyListener(e -> {
            if ((e.getChangeFlags() & HierarchyEvent.SHOWING_CHANGED) != 0 && isShowing()) {

                // Hack: supersede JOptionPane's similar button focus placement.
                SwingUtilities.invokeLater(() -> prepareForDisplay());
            }
        });
    }

    private void addRow(String title, JComponent component) {
        JLabel label = new JLabel(title);
        label.setLabelFor(component);
        label.setHorizontalAlignment(SwingConstants.LEFT);
        label.setOpaque(true);

        // Fix alignment inconsistencies
        label.setAlignmentX(0f);
        component.setAlignmentX(0f);

        add(label);
        add(Box.createHorizontalStrut(2));
        add(component);
    }

    private String getURLText() {
        Object item = url.getSelectedItem();
        String text = (item == null) ? "" : ((String) item).trim();
        if (!text.toLowerCase().startsWith("http")) {
            return "http://" + text;
        }
        return text;
    }

    public void setURLHistory(List<String> items) {
        url.removeAllItems();
        for (String item : items) {
            url.addItem(item);
        }
    }

    private String getAttachmentsDirText() {
        Object text = attachmentsDir.getSelectedItem();
        return (text == null) ? "" : ((String) text).trim();
    }

    public void setAttachmentsDirHistory(List<String> items) {
        attachmentsDir.removeAllItems();
        for (String item : items) {
            attachmentsDir.addItem(item);
        }
    }

    public void setInstantResart(boolean b) {
        instantRestart.setSelected(b);
    }

    public void setFetchOnlyActiveTickets(boolean b) {
        fetchActiveTickets.setSelected(b);
    }
}

@@ -857,16 +857,42 @@
 il.List;
+%0Aimport java.util.Objects;
 %0A%0Aimport
@@ -1309,70 +1309,8 @@
 ngs;
-%0Aimport net.bettyluke.tracinstant.prefs.TracInstantProperties;
 %0A%0Apu
@@ -2524,126 +2524,8 @@
  %7D%0A%0A
-        // Record the selected button for text time.%0A        TracInstantProperties.get().putInt(%22MasterQuery%22, opt);%0A%0A
     
@@ -4839,16 +4839,337 @@
      %7D);
+%0A%0A        listenToClearPasswordWhenUrlChanges(settings);%0A    %7D%0A%0A    private void listenToClearPasswordWhenUrlChanges(SiteSettings settings) %7B%0A        url.addActionListener(evt -%3E %7B%0A            if (!Objects.equals(url.getSelectedItem(), settings.getURL())) %7B%0A                password.setText(%22%22);%0A            %7D%0A        %7D);
 %0A    %7D%0A%0A

Clear password when URL changes