package rose.project.passmember.gui;

import rose.project.passmember.util.entry.Entry;
import rose.project.passmember.util.entry.FolderEntry;

import javax.swing.*;
import javax.swing.tree.DefaultMutableTreeNode;
import javax.swing.tree.DefaultTreeModel;
import javax.swing.tree.TreePath;
import java.util.NoSuchElementException;

/**
 * Created by Lord Rose on 07/04/2017.
 */
public class JTreeWrapper {
    private JTree GUITree;
    private DefaultMutableTreeNode passwordsTree;
    private DefaultMutableTreeNode currentSelectedNode;
    private DefaultTreeModel treeModel;

    public JTreeWrapper() {
        this.passwordsTree = new DefaultMutableTreeNode(new FolderEntry());
        this.currentSelectedNode = this.passwordsTree;
        this.GUITree = new JTree();
        this.treeModel = (DefaultTreeModel) this.getGUITree().getModel();
    }

    public JTreeWrapper(DefaultMutableTreeNode root) {
        this.passwordsTree = (DefaultMutableTreeNode)root.getRoot(); // just to be sure
        this.currentSelectedNode = this.passwordsTree;
        this.GUITree = new JTree(this.passwordsTree);
        this.treeModel = (DefaultTreeModel) this.getGUITree().getModel();
    }

    public JTree getGUITree() {
        return this.GUITree;
    }

    public DefaultMutableTreeNode getPasswordsTree() {
        return this.passwordsTree;
    }

    public void addEntry(Entry entry) {
        DefaultMutableTreeNode childNode = new DefaultMutableTreeNode(entry);

        if(!this.currentSelectedNode.isRoot()) { // we always append a new node as child of its parent node
            this.currentSelectedNode = (DefaultMutableTreeNode) this.currentSelectedNode.getParent();
        }

        this.treeModel.insertNodeInto(childNode, this.currentSelectedNode, this.currentSelectedNode.getChildCount());
        this.GUITree.scrollPathToVisible(new TreePath(childNode.getPath()));
    }

    public Entry removeEntry() throws NoSuchElementException {
        if(this.hasSelection()) {
            Entry removedEntry = (Entry)this.currentSelectedNode.getUserObject();
            this.treeModel.removeNodeFromParent(this.currentSelectedNode);
            this.currentSelectedNode = this.passwordsTree; // we select the root node
            // TODO : check if the GUI must be updated after removing an element from its model

            return removedEntry;
        }
        else {
            throw new NoSuchElementException("Impossible to delete an entry from an empty selection");
        }
    }

    public void updateEntry(Entry entry) {
        // TODO : Implement passmember.gui.JTreeWrapper.updateEntry()
    }

    public Entry getEntry() throws NoSuchElementException {
        if(this.hasSelection()) {
            return (Entry)this.currentSelectedNode.getUserObject();
        }
        else {
            throw new NoSuchElementException("Impossible to retrieve an entry from an empty selection");
        }
    }

    public void setCurrentSelectedNode(DefaultMutableTreeNode newSelectedNode) {
        this.currentSelectedNode = newSelectedNode;
    }

    public boolean hasSelection() {
        return !this.GUITree.isSelectionEmpty();
    }
}

@@ -186,106 +186,28 @@
 ree.
-DefaultMutableTreeNode;%0Aimport javax.swing.tree.DefaultTreeModel;%0Aimport javax.swing.tree.TreePath
+*;%0Aimport java.awt.*
 ;%0Aim
@@ -755,32 +755,101 @@
 ee().getModel();
+%0A%0A        this.GUITree.setCellRenderer(new CustomTreeCellRenderer());
 %0A    %7D%0A%0A    publ
@@ -1165,16 +1165,85 @@
 Model();
+%0A%0A        this.GUITree.setCellRenderer(new CustomTreeCellRenderer());
 %0A    %7D%0A%0A
@@ -3223,11 +3223,874 @@
 );%0A    %7D
+%0A%0A    private static class CustomTreeCellRenderer extends DefaultTreeCellRenderer %7B%0A        @Override%0A        public Component getTreeCellRendererComponent(JTree tree, Object value, boolean selected, boolean expanded, boolean leaf, int row, boolean hasFocus) %7B%0A            super.getTreeCellRendererComponent(tree, value, selected, expanded, leaf, row, hasFocus);%0A%0A            Icon icon;%0A            DefaultMutableTreeNode currentNode = (DefaultMutableTreeNode)value;%0A            if(currentNode.getUserObject() instanceof FolderEntry) %7B // we do not use leaf variable because a folder may be empty if it contains no password%0A                icon = UIManager.getIcon(%22Tree.openIcon%22);%0A            %7D%0A            else %7B%0A                icon = UIManager.getIcon(%22Tree.leafIcon%22);%0A            %7D%0A%0A            this.setIcon(icon);%0A%0A            return this;%0A        %7D%0A    %7D
 %0A%7D%0A

Implement a custom TreeCellRenderer to display icon according to the kind of entry embedded in a tree node